1pub mod reader;
3
4use std::io::Cursor;
5
6use ff::PrimeField;
7use serde::Deserialize;
8use serde::Serialize;
9use wasmer::Module;
10
11use crate::error::Error;
12use crate::error::Result;
13use crate::witness::calculator::WitnessCalculator;
14
15pub(crate) type Constraint<F> = (Vec<(usize, F)>, Vec<(usize, F)>, Vec<(usize, F)>);
17
18#[derive(Clone, Debug, Serialize, Deserialize)]
20pub struct R1CS<F: PrimeField> {
21 pub num_inputs: usize,
23 pub num_aux: usize,
25 pub num_variables: usize,
27 pub constraints: Vec<Constraint<F>>,
29}
30
31#[derive(Debug, Clone, PartialEq, Eq)]
33pub enum Path {
34 Local(String),
36 Remote(String),
38}
39
40pub enum Format {
42 Json,
44 Bin,
46}
47
48pub type TyWitness<F> = Vec<F>;
50
51pub(crate) async fn fetch(url: &str) -> Result<Cursor<Vec<u8>>> {
53 let resp = reqwest::get(url).await?;
54 let bytes = resp.bytes().await?;
55 Ok(Cursor::new(bytes.to_vec()))
56}
57
58pub async fn load_r1cs_remote<F: PrimeField>(url: &str, format: Format) -> Result<R1CS<F>> {
60 let data = fetch(url).await?;
61 let ret = match format {
62 Format::Json => reader::load_r1cs_from_json::<F, Cursor<Vec<u8>>>(data),
63 Format::Bin => reader::load_r1cs_from_bin::<F, Cursor<Vec<u8>>>(data),
64 };
65 Ok(ret)
66}
67
68pub fn load_r1cs_local<F: PrimeField>(
70 path: impl AsRef<std::path::Path>,
71 format: Format,
72) -> Result<R1CS<F>> {
73 let ret = match format {
74 Format::Json => reader::load_r1cs_from_json_file::<F>(path),
75 Format::Bin => reader::load_r1cs_from_bin_file::<F>(path),
76 };
77 Ok(ret)
78}
79
80pub async fn load_r1cs<F: PrimeField>(path: Path, format: Format) -> Result<R1CS<F>> {
82 let ret = match path {
83 Path::Local(p) => load_r1cs_local::<F>(p, format)?,
84 Path::Remote(url) => load_r1cs_remote::<F>(&url, format).await?,
85 };
86 Ok(ret)
87}
88
89pub async fn load_witness_remote<F: PrimeField>(url: &str, format: Format) -> Result<TyWitness<F>> {
91 let data = fetch(url).await?;
92 let ret = match format {
93 Format::Json => reader::load_witness_from_bin_reader::<F, Cursor<Vec<u8>>>(data)
94 .map_err(|e| Error::WitnessFailedOnLoad(e.to_string()))?,
95 Format::Bin => reader::load_witness_from_json::<F, Cursor<Vec<u8>>>(data),
96 };
97 Ok(ret)
98}
99
100pub fn load_witness_local<F: PrimeField>(
102 path: impl AsRef<std::path::Path>,
103 format: Format,
104) -> Result<TyWitness<F>> {
105 let ret = match format {
106 Format::Json => reader::load_witness_from_bin_file::<F>(path),
107 Format::Bin => reader::load_witness_from_json_file::<F>(path),
108 };
109 Ok(ret)
110}
111
112pub async fn load_witness<F: PrimeField>(path: Path, format: Format) -> Result<TyWitness<F>> {
114 match path {
115 Path::Local(p) => load_witness_local::<F>(p, format),
116 Path::Remote(url) => load_witness_remote::<F>(&url, format).await,
117 }
118}
119
120pub fn load_circom_witness_calculator_local(
122 path: impl AsRef<std::path::Path>,
123) -> Result<WitnessCalculator> {
124 WitnessCalculator::from_file(path).map_err(|e| Error::WASMFailedToLoad(e.to_string()))
125}
126
127pub async fn load_circom_witness_calculator_remote(path: &str) -> Result<WitnessCalculator> {
129 let store = WitnessCalculator::new_store();
130 let data = fetch(path).await?;
131 let module = Module::from_binary(&store, data.get_ref().as_slice())?;
132 WitnessCalculator::from_module(module, store)
133}
134
135pub async fn load_circom_witness_calculator(path: Path) -> Result<WitnessCalculator> {
137 match path {
138 Path::Local(p) => load_circom_witness_calculator_local(p),
139 Path::Remote(url) => load_circom_witness_calculator_remote(&url).await,
140 }
141}