mirror of
https://github.com/ProvableHQ/leo.git
synced 2024-11-27 02:24:15 +03:00
cargo fmt
This commit is contained in:
parent
79bea057b3
commit
837d107a54
16
.travis.yml
16
.travis.yml
@ -51,14 +51,14 @@ matrix:
|
||||
- libiberty-dev
|
||||
script:
|
||||
- cargo test --all
|
||||
after_success: |
|
||||
wget https://github.com/SimonKagstrom/kcov/archive/master.tar.gz &&
|
||||
tar xzf master.tar.gz && cd kcov-master &&
|
||||
mkdir build && cd build && cmake .. && make && sudo make install &&
|
||||
cd ../.. && rm -rf kcov-master &&
|
||||
for file in target/debug/*-*[^\.d]; do mkdir -p "target/cov/$(basename $file)"; kcov --exclude-pattern=/.cargo,/usr/lib --verify "target/cov/$(basename $file)" "$file"; done &&
|
||||
bash <(curl -s https://codecov.io/bash) &&
|
||||
echo "Uploaded code coverage"
|
||||
after_success:
|
||||
- wget https://github.com/SimonKagstrom/kcov/archive/master.tar.gz
|
||||
- tar xzf master.tar.gz && cd kcov-master
|
||||
- mkdir build && cd build && cmake .. && make && sudo make install
|
||||
- cd ../.. && rm -rf kcov-master
|
||||
- for file in target/debug/*-*[^\.d]; do mkdir -p "target/cov/$(basename $file)"; kcov --exclude-pattern=/.cargo,/usr/lib --verify "target/cov/$(basename $file)" "$file"; done
|
||||
- bash <(curl -s https://codecov.io/bash)
|
||||
- echo "Uploaded code coverage"
|
||||
- rust: nightly-2020-03-18
|
||||
install:
|
||||
- rustup component add rustfmt
|
||||
|
@ -1,4 +1,7 @@
|
||||
use crate::{access::{ArrayAccess, MemberAccess}, ast::Rule};
|
||||
use crate::{
|
||||
access::{ArrayAccess, MemberAccess},
|
||||
ast::Rule,
|
||||
};
|
||||
|
||||
use pest_ast::FromPest;
|
||||
use std::fmt;
|
||||
|
@ -2,18 +2,15 @@
|
||||
use crate::{
|
||||
common::Identifier,
|
||||
expressions::{
|
||||
ArrayInlineExpression,
|
||||
ArrayInitializerExpression,
|
||||
ArrayInlineExpression,
|
||||
CircuitInlineExpression,
|
||||
Expression,
|
||||
TernaryExpression,
|
||||
NotExpression,
|
||||
PostfixExpression
|
||||
},
|
||||
operations::{
|
||||
BinaryOperation,
|
||||
NotOperation,
|
||||
PostfixExpression,
|
||||
TernaryExpression,
|
||||
},
|
||||
operations::{BinaryOperation, NotOperation},
|
||||
values::Value,
|
||||
};
|
||||
|
||||
@ -22,7 +19,8 @@ use pest::{
|
||||
error::Error,
|
||||
iterators::{Pair, Pairs},
|
||||
prec_climber::{Assoc, Operator, PrecClimber},
|
||||
Parser, Span,
|
||||
Parser,
|
||||
Span,
|
||||
};
|
||||
|
||||
#[derive(Parser)]
|
||||
@ -47,16 +45,13 @@ fn precedence_climber() -> PrecClimber<Rule> {
|
||||
PrecClimber::new(vec![
|
||||
Operator::new(Rule::operation_or, Assoc::Left),
|
||||
Operator::new(Rule::operation_and, Assoc::Left),
|
||||
Operator::new(Rule::operation_eq, Assoc::Left)
|
||||
| Operator::new(Rule::operation_ne, Assoc::Left),
|
||||
Operator::new(Rule::operation_eq, Assoc::Left) | Operator::new(Rule::operation_ne, Assoc::Left),
|
||||
Operator::new(Rule::operation_ge, Assoc::Left)
|
||||
| Operator::new(Rule::operation_gt, Assoc::Left)
|
||||
| Operator::new(Rule::operation_le, Assoc::Left)
|
||||
| Operator::new(Rule::operation_lt, Assoc::Left),
|
||||
Operator::new(Rule::operation_add, Assoc::Left)
|
||||
| Operator::new(Rule::operation_sub, Assoc::Left),
|
||||
Operator::new(Rule::operation_mul, Assoc::Left)
|
||||
| Operator::new(Rule::operation_div, Assoc::Left),
|
||||
Operator::new(Rule::operation_add, Assoc::Left) | Operator::new(Rule::operation_sub, Assoc::Left),
|
||||
Operator::new(Rule::operation_mul, Assoc::Left) | Operator::new(Rule::operation_div, Assoc::Left),
|
||||
Operator::new(Rule::operation_pow, Assoc::Left),
|
||||
])
|
||||
}
|
||||
@ -69,55 +64,55 @@ fn parse_term(pair: Pair<Rule>) -> Box<Expression> {
|
||||
match next.as_rule() {
|
||||
Rule::expression => Expression::from_pest(&mut pair.into_inner()).unwrap(), // Parenthesis case
|
||||
Rule::expression_array_inline => {
|
||||
Expression::ArrayInline(
|
||||
ArrayInlineExpression::from_pest(&mut pair.into_inner()).unwrap()
|
||||
)
|
||||
},
|
||||
Expression::ArrayInline(ArrayInlineExpression::from_pest(&mut pair.into_inner()).unwrap())
|
||||
}
|
||||
Rule::expression_array_initializer => {
|
||||
Expression::ArrayInitializer(
|
||||
ArrayInitializerExpression::from_pest(&mut pair.into_inner()).unwrap()
|
||||
)
|
||||
},
|
||||
Expression::ArrayInitializer(ArrayInitializerExpression::from_pest(&mut pair.into_inner()).unwrap())
|
||||
}
|
||||
Rule::expression_circuit_inline => {
|
||||
Expression::CircuitInline(
|
||||
CircuitInlineExpression::from_pest(&mut pair.into_inner()).unwrap(),
|
||||
)
|
||||
},
|
||||
Expression::CircuitInline(CircuitInlineExpression::from_pest(&mut pair.into_inner()).unwrap())
|
||||
}
|
||||
Rule::expression_conditional => {
|
||||
Expression::Ternary(
|
||||
TernaryExpression::from_pest(&mut pair.into_inner()).unwrap(),
|
||||
)
|
||||
},
|
||||
Expression::Ternary(TernaryExpression::from_pest(&mut pair.into_inner()).unwrap())
|
||||
}
|
||||
Rule::expression_not => {
|
||||
let span = next.as_span();
|
||||
let mut inner = next.into_inner();
|
||||
let operation = match inner.next().unwrap().as_rule() {
|
||||
Rule::operation_not => NotOperation::from_pest(&mut pair.into_inner().next().unwrap().into_inner()).unwrap(),
|
||||
rule => unreachable!("`expression_not` should yield `operation_pre_not`, found {:#?}", rule)
|
||||
Rule::operation_not => {
|
||||
NotOperation::from_pest(&mut pair.into_inner().next().unwrap().into_inner()).unwrap()
|
||||
}
|
||||
rule => unreachable!("`expression_not` should yield `operation_pre_not`, found {:#?}", rule),
|
||||
};
|
||||
let expression = parse_term(inner.next().unwrap());
|
||||
Expression::Not(NotExpression { operation, expression, span })
|
||||
},
|
||||
Expression::Not(NotExpression {
|
||||
operation,
|
||||
expression,
|
||||
span,
|
||||
})
|
||||
}
|
||||
Rule::expression_postfix => {
|
||||
Expression::Postfix(
|
||||
PostfixExpression::from_pest(&mut pair.into_inner()).unwrap(),
|
||||
)
|
||||
Expression::Postfix(PostfixExpression::from_pest(&mut pair.into_inner()).unwrap())
|
||||
}
|
||||
Rule::expression_primitive => {
|
||||
let next = next.into_inner().next().unwrap();
|
||||
match next.as_rule() {
|
||||
Rule::value => {
|
||||
Expression::Value(
|
||||
Value::from_pest(&mut pair.into_inner().next().unwrap().into_inner()).unwrap()
|
||||
)
|
||||
},
|
||||
Rule::value => Expression::Value(
|
||||
Value::from_pest(&mut pair.into_inner().next().unwrap().into_inner()).unwrap(),
|
||||
),
|
||||
Rule::identifier => Expression::Identifier(
|
||||
Identifier::from_pest(&mut pair.into_inner().next().unwrap().into_inner()).unwrap(),
|
||||
),
|
||||
rule => unreachable!("`expression_primitive` should contain one of [`value`, `identifier`], found {:#?}", rule)
|
||||
rule => unreachable!(
|
||||
"`expression_primitive` should contain one of [`value`, `identifier`], found {:#?}",
|
||||
rule
|
||||
),
|
||||
}
|
||||
},
|
||||
rule => unreachable!("`term` should contain one of ['value', 'identifier', 'expression', 'expression_not', 'expression_increment', 'expression_decrement'], found {:#?}", rule)
|
||||
}
|
||||
rule => unreachable!(
|
||||
"`term` should contain one of ['value', 'identifier', 'expression', 'expression_not', 'expression_increment', 'expression_decrement'], found {:#?}",
|
||||
rule
|
||||
),
|
||||
}
|
||||
}
|
||||
rule => unreachable!(
|
||||
@ -155,8 +150,8 @@ fn binary_expression<'ast>(
|
||||
}
|
||||
|
||||
impl<'ast> FromPest<'ast> for Expression<'ast> {
|
||||
type Rule = Rule;
|
||||
type FatalError = Void;
|
||||
type Rule = Rule;
|
||||
|
||||
fn from_pest(pest: &mut Pairs<'ast, Rule>) -> Result<Self, ConversionError<Void>> {
|
||||
let mut clone = pest.clone();
|
||||
|
@ -1,4 +1,7 @@
|
||||
use crate::{ast::Rule, circuits::{CircuitFunction, CircuitFieldDefinition}};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
circuits::{CircuitFieldDefinition, CircuitFunction},
|
||||
};
|
||||
|
||||
use pest_ast::FromPest;
|
||||
|
||||
|
@ -17,16 +17,8 @@ impl<'ast> fmt::Display for RangeOrExpression<'ast> {
|
||||
RangeOrExpression::Range(ref range) => write!(
|
||||
f,
|
||||
"{}..{}",
|
||||
range
|
||||
.from
|
||||
.as_ref()
|
||||
.map(|e| e.0.to_string())
|
||||
.unwrap_or("".to_string()),
|
||||
range
|
||||
.to
|
||||
.as_ref()
|
||||
.map(|e| e.0.to_string())
|
||||
.unwrap_or("".to_string())
|
||||
range.from.as_ref().map(|e| e.0.to_string()).unwrap_or("".to_string()),
|
||||
range.to.as_ref().map(|e| e.0.to_string()).unwrap_or("".to_string())
|
||||
),
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,8 @@
|
||||
use crate::{ast::Rule, common::{Identifier, Mutable}, types::Type};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
common::{Identifier, Mutable},
|
||||
types::Type,
|
||||
};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::{ast::Rule, circuits::CircuitField, common::Identifier,};
|
||||
use crate::{ast::Rule, circuits::CircuitField, common::Identifier};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::{common::Identifier, expressions::*, operations::BinaryOperation, values::Value,};
|
||||
use crate::{common::Identifier, expressions::*, operations::BinaryOperation, values::Value};
|
||||
|
||||
use pest::Span;
|
||||
use std::fmt;
|
||||
@ -66,9 +66,7 @@ impl<'ast> fmt::Display for Expression<'ast> {
|
||||
Expression::Value(ref expression) => write!(f, "{}", expression),
|
||||
Expression::Identifier(ref expression) => write!(f, "{}", expression),
|
||||
Expression::Not(ref expression) => write!(f, "!{}", expression.expression),
|
||||
Expression::Binary(ref expression) => {
|
||||
write!(f, "{} == {}", expression.left, expression.right)
|
||||
}
|
||||
Expression::Binary(ref expression) => write!(f, "{} == {}", expression.left, expression.right),
|
||||
Expression::Ternary(ref expression) => write!(
|
||||
f,
|
||||
"if {} ? {} : {}",
|
||||
@ -86,14 +84,10 @@ impl<'ast> fmt::Display for Expression<'ast> {
|
||||
Expression::ArrayInitializer(ref expression) => {
|
||||
write!(f, "[{} ; {}]", expression.expression, expression.count)
|
||||
}
|
||||
Expression::CircuitInline(ref expression) => write!(
|
||||
f,
|
||||
"inline circuit display not impl {}",
|
||||
expression.identifier
|
||||
),
|
||||
Expression::Postfix(ref expression) => {
|
||||
write!(f, "Postfix display not impl {}", expression.identifier)
|
||||
}
|
||||
Expression::CircuitInline(ref expression) => {
|
||||
write!(f, "inline circuit display not impl {}", expression.identifier)
|
||||
}
|
||||
Expression::Postfix(ref expression) => write!(f, "Postfix display not impl {}", expression.identifier),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,10 @@
|
||||
use crate::{ast::Rule, common::EOI, functions::{Function, TestFunction}, imports::Import, circuits::Circuit};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
circuits::Circuit,
|
||||
common::EOI,
|
||||
functions::{Function, TestFunction},
|
||||
imports::Import,
|
||||
};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,8 @@
|
||||
use crate::{ast::Rule, common::{Identifier, Visibility, Mutable}, types::Type};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
common::{Identifier, Mutable, Visibility},
|
||||
types::Type,
|
||||
};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,8 @@
|
||||
use crate::{ast::Rule, common::LineEnd, imports::{ImportSource, ImportSymbol}};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
common::LineEnd,
|
||||
imports::{ImportSource, ImportSymbol},
|
||||
};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::ast::{Rule, span_into_string};
|
||||
use crate::ast::{span_into_string, Rule};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -18,11 +18,11 @@ pub mod functions;
|
||||
pub mod imports;
|
||||
pub mod operations;
|
||||
pub mod statements;
|
||||
pub mod values;
|
||||
pub mod types;
|
||||
pub mod values;
|
||||
|
||||
use from_pest::FromPest;
|
||||
use std::{path::PathBuf, fs};
|
||||
use std::{fs, path::PathBuf};
|
||||
|
||||
pub struct LeoParser;
|
||||
|
||||
@ -35,9 +35,8 @@ impl LeoParser {
|
||||
/// Parses the input file and constructs a syntax tree.
|
||||
pub fn parse_file<'a>(file_path: &'a PathBuf, input_file: &'a str) -> Result<files::File<'a>, ParserError> {
|
||||
// Parse the file using leo.pest
|
||||
let mut file = ast::parse(input_file).map_err(|error| {
|
||||
ParserError::from(error.with_path(file_path.to_str().unwrap()))
|
||||
})?;
|
||||
let mut file =
|
||||
ast::parse(input_file).map_err(|error| ParserError::from(error.with_path(file_path.to_str().unwrap())))?;
|
||||
|
||||
// Build the abstract syntax tree
|
||||
let syntax_tree = files::File::from_pest(&mut file).map_err(|_| ParserError::SyntaxTreeError)?;
|
||||
|
@ -13,9 +13,7 @@ pub enum AssertStatement<'ast> {
|
||||
impl<'ast> fmt::Display for AssertStatement<'ast> {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
AssertStatement::AssertEq(ref assert) => {
|
||||
write!(f, "assert_eq({}, {});", assert.left, assert.right)
|
||||
}
|
||||
AssertStatement::AssertEq(ref assert) => write!(f, "assert_eq({}, {});", assert.left, assert.right),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,9 @@
|
||||
use crate::{ast::Rule, common::{Assignee, LineEnd}, expressions::Expression, operations::AssignOperation};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
common::{Assignee, LineEnd},
|
||||
expressions::Expression,
|
||||
operations::AssignOperation,
|
||||
};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,7 @@
|
||||
use crate::{ast::Rule, statements::{ConditionalStatement, Statement}};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
statements::{ConditionalStatement, Statement},
|
||||
};
|
||||
|
||||
use pest_ast::FromPest;
|
||||
use std::fmt;
|
||||
@ -14,9 +17,7 @@ impl<'ast> fmt::Display for ConditionalNestedOrEndStatement<'ast> {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
ConditionalNestedOrEndStatement::Nested(ref nested) => write!(f, "else {}", nested),
|
||||
ConditionalNestedOrEndStatement::End(ref statements) => {
|
||||
write!(f, "else {{\n \t{:#?}\n }}", statements)
|
||||
}
|
||||
ConditionalNestedOrEndStatement::End(ref statements) => write!(f, "else {{\n \t{:#?}\n }}", statements),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,8 @@
|
||||
use crate::{ast::Rule, expressions::Expression, statements::{ConditionalNestedOrEndStatement, Statement}};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
expressions::Expression,
|
||||
statements::{ConditionalNestedOrEndStatement, Statement},
|
||||
};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,8 @@
|
||||
use crate::{ast::Rule, common::{LineEnd, Variable}, expressions::Expression};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
common::{LineEnd, Variable},
|
||||
expressions::Expression,
|
||||
};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::{ast::Rule, expressions::{Expression}, statements::Statement, common::Identifier};
|
||||
use crate::{ast::Rule, common::Identifier, expressions::Expression, statements::Statement};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,8 @@
|
||||
use crate::{ast::Rule, common::{Identifier, LineEnd, Variable}, expressions::{Expression}};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
common::{Identifier, LineEnd, Variable},
|
||||
expressions::Expression,
|
||||
};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,7 @@
|
||||
use crate::{ast::Rule, types::{IntegerType, FieldType, GroupType, BooleanType}};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
types::{BooleanType, FieldType, GroupType, IntegerType},
|
||||
};
|
||||
|
||||
use pest_ast::FromPest;
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::ast::{Rule, span_into_string};
|
||||
use crate::ast::{span_into_string, Rule};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::{ast::Rule, types::FieldType, values::NumberValue,};
|
||||
use crate::{ast::Rule, types::FieldType, values::NumberValue};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::{ast::Rule, types::GroupType, values::NumberValue,};
|
||||
use crate::{ast::Rule, types::GroupType, values::NumberValue};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::ast::{Rule, span_into_string};
|
||||
use crate::ast::{span_into_string, Rule};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -1,4 +1,7 @@
|
||||
use crate::{ast::Rule, values::{BooleanValue, IntegerValue, FieldValue, GroupValue, NumberImplicitValue}};
|
||||
use crate::{
|
||||
ast::Rule,
|
||||
values::{BooleanValue, FieldValue, GroupValue, IntegerValue, NumberImplicitValue},
|
||||
};
|
||||
|
||||
use pest::Span;
|
||||
use pest_ast::FromPest;
|
||||
|
@ -68,10 +68,7 @@ impl<F: Field + PrimeField, G: GroupType<F>> Compiler<F, G> {
|
||||
generate_constraints(cs, self.program, self.program_inputs)
|
||||
}
|
||||
|
||||
pub fn compile_test_constraints(
|
||||
self,
|
||||
cs: &mut TestConstraintSystem<F>,
|
||||
) -> Result<(), CompilerError> {
|
||||
pub fn compile_test_constraints(self, cs: &mut TestConstraintSystem<F>) -> Result<(), CompilerError> {
|
||||
generate_test_constraints::<F, G>(cs, self.program)
|
||||
}
|
||||
|
||||
@ -94,12 +91,8 @@ impl<F: Field + PrimeField, G: GroupType<F>> Compiler<F, G> {
|
||||
}
|
||||
|
||||
impl<F: Field + PrimeField, G: GroupType<F>> ConstraintSynthesizer<F> for Compiler<F, G> {
|
||||
fn generate_constraints<CS: ConstraintSystem<F>>(
|
||||
self,
|
||||
cs: &mut CS,
|
||||
) -> Result<(), SynthesisError> {
|
||||
let _result =
|
||||
generate_constraints::<_, G, _>(cs, self.program, self.program_inputs).unwrap();
|
||||
fn generate_constraints<CS: ConstraintSystem<F>>(self, cs: &mut CS) -> Result<(), SynthesisError> {
|
||||
let _result = generate_constraints::<_, G, _>(cs, self.program, self.program_inputs).unwrap();
|
||||
|
||||
// Write results to file or something
|
||||
|
||||
|
@ -38,13 +38,9 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
|
||||
// Check visibility of input
|
||||
let number = if private {
|
||||
Boolean::alloc(cs.ns(|| name), || {
|
||||
bool_value.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?
|
||||
Boolean::alloc(cs.ns(|| name), || bool_value.ok_or(SynthesisError::AssignmentMissing))?
|
||||
} else {
|
||||
Boolean::alloc_input(cs.ns(|| name), || {
|
||||
bool_value.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?
|
||||
Boolean::alloc_input(cs.ns(|| name), || bool_value.ok_or(SynthesisError::AssignmentMissing))?
|
||||
};
|
||||
|
||||
Ok(ConstrainedValue::Boolean(number))
|
||||
@ -54,9 +50,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
ConstrainedValue::Boolean(bool)
|
||||
}
|
||||
|
||||
pub(crate) fn evaluate_not(
|
||||
value: ConstrainedValue<F, G>,
|
||||
) -> Result<ConstrainedValue<F, G>, BooleanError> {
|
||||
pub(crate) fn evaluate_not(value: ConstrainedValue<F, G>) -> Result<ConstrainedValue<F, G>, BooleanError> {
|
||||
match value {
|
||||
ConstrainedValue::Boolean(boolean) => Ok(ConstrainedValue::Boolean(boolean.not())),
|
||||
value => Err(BooleanError::CannotEvaluate(format!("!{}", value))),
|
||||
@ -70,9 +64,9 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
right: ConstrainedValue<F, G>,
|
||||
) -> Result<ConstrainedValue<F, G>, BooleanError> {
|
||||
match (left, right) {
|
||||
(ConstrainedValue::Boolean(left_bool), ConstrainedValue::Boolean(right_bool)) => Ok(
|
||||
ConstrainedValue::Boolean(Boolean::or(cs, &left_bool, &right_bool)?),
|
||||
),
|
||||
(ConstrainedValue::Boolean(left_bool), ConstrainedValue::Boolean(right_bool)) => {
|
||||
Ok(ConstrainedValue::Boolean(Boolean::or(cs, &left_bool, &right_bool)?))
|
||||
}
|
||||
(left_value, right_value) => Err(BooleanError::CannotEnforce(format!(
|
||||
"{} || {}",
|
||||
left_value, right_value
|
||||
@ -87,9 +81,9 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
right: ConstrainedValue<F, G>,
|
||||
) -> Result<ConstrainedValue<F, G>, BooleanError> {
|
||||
match (left, right) {
|
||||
(ConstrainedValue::Boolean(left_bool), ConstrainedValue::Boolean(right_bool)) => Ok(
|
||||
ConstrainedValue::Boolean(Boolean::and(cs, &left_bool, &right_bool)?),
|
||||
),
|
||||
(ConstrainedValue::Boolean(left_bool), ConstrainedValue::Boolean(right_bool)) => {
|
||||
Ok(ConstrainedValue::Boolean(Boolean::and(cs, &left_bool, &right_bool)?))
|
||||
}
|
||||
(left_value, right_value) => Err(BooleanError::CannotEnforce(format!(
|
||||
"{} && {}",
|
||||
left_value, right_value
|
||||
|
@ -4,10 +4,20 @@ use crate::{
|
||||
constraints::{ConstrainedCircuitMember, ConstrainedProgram, ConstrainedValue},
|
||||
errors::ExpressionError,
|
||||
new_scope,
|
||||
FieldType, GroupType,
|
||||
FieldType,
|
||||
GroupType,
|
||||
};
|
||||
use leo_types::{
|
||||
CircuitFieldDefinition,
|
||||
CircuitMember,
|
||||
Expression,
|
||||
Identifier,
|
||||
Integer,
|
||||
IntegerType,
|
||||
RangeOrExpression,
|
||||
SpreadOrExpression,
|
||||
Type,
|
||||
};
|
||||
use leo_types::{CircuitFieldDefinition,CircuitMember, Expression, RangeOrExpression,
|
||||
SpreadOrExpression, Identifier, Integer, IntegerType, Type};
|
||||
|
||||
use snarkos_models::{
|
||||
curves::{Field, PrimeField},
|
||||
@ -37,9 +47,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
// Check global scope (function and circuit names)
|
||||
value.clone()
|
||||
} else {
|
||||
return Err(ExpressionError::UndefinedIdentifier(
|
||||
unresolved_identifier.to_string(),
|
||||
));
|
||||
return Err(ExpressionError::UndefinedIdentifier(unresolved_identifier.to_string()));
|
||||
};
|
||||
|
||||
result_value.resolve_type(expected_types)?;
|
||||
@ -72,10 +80,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
let val_2 = ConstrainedValue::from_other(string, &val_1)?;
|
||||
self.enforce_add_expression(cs, val_1, val_2)
|
||||
}
|
||||
(val_1, val_2) => Err(ExpressionError::IncompatibleTypes(format!(
|
||||
"{} + {}",
|
||||
val_1, val_2,
|
||||
))),
|
||||
(val_1, val_2) => Err(ExpressionError::IncompatibleTypes(format!("{} + {}", val_1, val_2,))),
|
||||
}
|
||||
}
|
||||
|
||||
@ -103,10 +108,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
let val_2 = ConstrainedValue::from_other(string, &val_1)?;
|
||||
self.enforce_sub_expression(cs, val_1, val_2)
|
||||
}
|
||||
(val_1, val_2) => Err(ExpressionError::IncompatibleTypes(format!(
|
||||
"{} - {}",
|
||||
val_1, val_2,
|
||||
))),
|
||||
(val_1, val_2) => Err(ExpressionError::IncompatibleTypes(format!("{} - {}", val_1, val_2,))),
|
||||
}
|
||||
}
|
||||
|
||||
@ -131,12 +133,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
let val_2 = ConstrainedValue::from_other(string, &val_1)?;
|
||||
self.enforce_mul_expression(cs, val_1, val_2)
|
||||
}
|
||||
(val_1, val_2) => {
|
||||
return Err(ExpressionError::IncompatibleTypes(format!(
|
||||
"{} * {}",
|
||||
val_1, val_2,
|
||||
)))
|
||||
}
|
||||
(val_1, val_2) => return Err(ExpressionError::IncompatibleTypes(format!("{} * {}", val_1, val_2,))),
|
||||
}
|
||||
}
|
||||
|
||||
@ -161,14 +158,10 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
let val_2 = ConstrainedValue::from_other(string, &val_1)?;
|
||||
self.enforce_div_expression(cs, val_1, val_2)
|
||||
}
|
||||
(val_1, val_2) => {
|
||||
return Err(ExpressionError::IncompatibleTypes(format!(
|
||||
"{} / {}",
|
||||
val_1, val_2,
|
||||
)))
|
||||
}
|
||||
(val_1, val_2) => return Err(ExpressionError::IncompatibleTypes(format!("{} / {}", val_1, val_2,))),
|
||||
}
|
||||
}
|
||||
|
||||
fn enforce_pow_expression(
|
||||
&mut self,
|
||||
cs: &mut CS,
|
||||
@ -187,10 +180,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
let val_2 = ConstrainedValue::from_other(string, &val_1)?;
|
||||
self.enforce_pow_expression(cs, val_1, val_2)
|
||||
}
|
||||
(val_1, val_2) => Err(ExpressionError::IncompatibleTypes(format!(
|
||||
"{} * {}",
|
||||
val_1, val_2,
|
||||
))),
|
||||
(val_1, val_2) => Err(ExpressionError::IncompatibleTypes(format!("{} * {}", val_1, val_2,))),
|
||||
}
|
||||
}
|
||||
|
||||
@ -204,9 +194,9 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
(ConstrainedValue::Boolean(bool_1), ConstrainedValue::Boolean(bool_2)) => {
|
||||
Ok(Self::boolean_eq(bool_1, bool_2))
|
||||
}
|
||||
(ConstrainedValue::Integer(num_1), ConstrainedValue::Integer(num_2)) => Ok(
|
||||
ConstrainedValue::Boolean(Boolean::Constant(num_1.eq(&num_2))),
|
||||
),
|
||||
(ConstrainedValue::Integer(num_1), ConstrainedValue::Integer(num_2)) => {
|
||||
Ok(ConstrainedValue::Boolean(Boolean::Constant(num_1.eq(&num_2))))
|
||||
}
|
||||
(ConstrainedValue::Field(fe_1), ConstrainedValue::Field(fe_2)) => {
|
||||
Ok(ConstrainedValue::Boolean(Boolean::Constant(fe_1.eq(&fe_2))))
|
||||
}
|
||||
@ -221,10 +211,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
let val_2 = ConstrainedValue::from_other(string, &val_1)?;
|
||||
self.evaluate_eq_expression(val_1, val_2)
|
||||
}
|
||||
(val_1, val_2) => Err(ExpressionError::IncompatibleTypes(format!(
|
||||
"{} == {}",
|
||||
val_1, val_2,
|
||||
))),
|
||||
(val_1, val_2) => Err(ExpressionError::IncompatibleTypes(format!("{} == {}", val_1, val_2,))),
|
||||
}
|
||||
}
|
||||
|
||||
@ -366,15 +353,9 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
value => return Err(ExpressionError::IfElseConditional(value.to_string())),
|
||||
};
|
||||
|
||||
let resolved_second = self.enforce_branch(
|
||||
cs,
|
||||
file_scope.clone(),
|
||||
function_scope.clone(),
|
||||
expected_types,
|
||||
second,
|
||||
)?;
|
||||
let resolved_third =
|
||||
self.enforce_branch(cs, file_scope, function_scope, expected_types, third)?;
|
||||
let resolved_second =
|
||||
self.enforce_branch(cs, file_scope.clone(), function_scope.clone(), expected_types, second)?;
|
||||
let resolved_third = self.enforce_branch(cs, file_scope, function_scope, expected_types, third)?;
|
||||
|
||||
match (resolved_second, resolved_third) {
|
||||
(ConstrainedValue::Boolean(bool_2), ConstrainedValue::Boolean(bool_3)) => {
|
||||
@ -382,8 +363,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
Ok(ConstrainedValue::Boolean(result))
|
||||
}
|
||||
(ConstrainedValue::Integer(integer_2), ConstrainedValue::Integer(integer_3)) => {
|
||||
let result =
|
||||
Integer::conditionally_select(cs, &resolved_first, &integer_2, &integer_3)?;
|
||||
let result = Integer::conditionally_select(cs, &resolved_first, &integer_2, &integer_3)?;
|
||||
Ok(ConstrainedValue::Integer(result))
|
||||
}
|
||||
(ConstrainedValue::Field(fe_1), ConstrainedValue::Field(fe_2)) => {
|
||||
@ -394,9 +374,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
let result = G::conditionally_select(cs, &resolved_first, &ge_1, &ge_2)?;
|
||||
Ok(ConstrainedValue::Group(result))
|
||||
}
|
||||
(_, _) => {
|
||||
unimplemented!("conditional select gadget not implemented between given types")
|
||||
}
|
||||
(_, _) => unimplemented!("conditional select gadget not implemented between given types"),
|
||||
}
|
||||
}
|
||||
|
||||
@ -473,13 +451,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
index: Expression,
|
||||
) -> Result<usize, ExpressionError> {
|
||||
let expected_types = vec![Type::IntegerType(IntegerType::U32)];
|
||||
match self.enforce_branch(
|
||||
cs,
|
||||
file_scope.clone(),
|
||||
function_scope.clone(),
|
||||
&expected_types,
|
||||
index,
|
||||
)? {
|
||||
match self.enforce_branch(cs, file_scope.clone(), function_scope.clone(), &expected_types, index)? {
|
||||
ConstrainedValue::Integer(number) => Ok(number.to_usize()),
|
||||
value => Err(ExpressionError::InvalidIndex(value.to_string())),
|
||||
}
|
||||
@ -494,13 +466,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
array: Box<Expression>,
|
||||
index: RangeOrExpression,
|
||||
) -> Result<ConstrainedValue<F, G>, ExpressionError> {
|
||||
let array = match self.enforce_branch(
|
||||
cs,
|
||||
file_scope.clone(),
|
||||
function_scope.clone(),
|
||||
expected_types,
|
||||
*array,
|
||||
)? {
|
||||
let array = match self.enforce_branch(cs, file_scope.clone(), function_scope.clone(), expected_types, *array)? {
|
||||
ConstrainedValue::Array(array) => array,
|
||||
value => return Err(ExpressionError::InvalidArrayAccess(value.to_string())),
|
||||
};
|
||||
@ -515,9 +481,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
Some(to_index) => to_index.to_usize(),
|
||||
None => array.len(), // Array slice ends at array length
|
||||
};
|
||||
Ok(ConstrainedValue::Array(
|
||||
array[from_resolved..to_resolved].to_owned(),
|
||||
))
|
||||
Ok(ConstrainedValue::Array(array[from_resolved..to_resolved].to_owned()))
|
||||
}
|
||||
RangeOrExpression::Expression(index) => {
|
||||
let index_resolved = self.enforce_index(cs, file_scope, function_scope, index)?;
|
||||
@ -540,9 +504,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
program_identifier = file_scope.clone();
|
||||
}
|
||||
|
||||
if let Some(ConstrainedValue::CircuitDefinition(circuit_definition)) =
|
||||
self.get_mut(&program_identifier)
|
||||
{
|
||||
if let Some(ConstrainedValue::CircuitDefinition(circuit_definition)) = self.get_mut(&program_identifier) {
|
||||
let circuit_identifier = circuit_definition.identifier.clone();
|
||||
let mut resolved_members = vec![];
|
||||
for member in circuit_definition.members.clone().into_iter() {
|
||||
@ -563,14 +525,9 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
field.expression,
|
||||
)?;
|
||||
|
||||
resolved_members
|
||||
.push(ConstrainedCircuitMember(identifier, field_value))
|
||||
}
|
||||
None => {
|
||||
return Err(ExpressionError::ExpectedCircuitMember(
|
||||
identifier.to_string(),
|
||||
))
|
||||
resolved_members.push(ConstrainedCircuitMember(identifier, field_value))
|
||||
}
|
||||
None => return Err(ExpressionError::ExpectedCircuitMember(identifier.to_string())),
|
||||
}
|
||||
}
|
||||
CircuitMember::CircuitFunction(_static, function) => {
|
||||
@ -579,14 +536,10 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
ConstrainedValue::Function(Some(circuit_identifier.clone()), function);
|
||||
|
||||
if _static {
|
||||
constrained_function_value =
|
||||
ConstrainedValue::Static(Box::new(constrained_function_value));
|
||||
constrained_function_value = ConstrainedValue::Static(Box::new(constrained_function_value));
|
||||
}
|
||||
|
||||
resolved_members.push(ConstrainedCircuitMember(
|
||||
identifier,
|
||||
constrained_function_value,
|
||||
));
|
||||
resolved_members.push(ConstrainedCircuitMember(identifier, constrained_function_value));
|
||||
}
|
||||
};
|
||||
}
|
||||
@ -620,10 +573,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
value => return Err(ExpressionError::InvalidCircuitAccess(value.to_string())),
|
||||
};
|
||||
|
||||
let matched_member = members
|
||||
.clone()
|
||||
.into_iter()
|
||||
.find(|member| member.0 == circuit_member);
|
||||
let matched_member = members.clone().into_iter().find(|member| member.0 == circuit_member);
|
||||
|
||||
match matched_member {
|
||||
Some(member) => {
|
||||
@ -635,12 +585,9 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
ConstrainedValue::Function(_, _) => {}
|
||||
ConstrainedValue::Static(_) => {}
|
||||
_ => {
|
||||
let circuit_scope =
|
||||
new_scope(file_scope.clone(), circuit_name.to_string());
|
||||
let function_scope =
|
||||
new_scope(circuit_scope, member.0.to_string());
|
||||
let field =
|
||||
new_scope(function_scope, stored_member.0.to_string());
|
||||
let circuit_scope = new_scope(file_scope.clone(), circuit_name.to_string());
|
||||
let function_scope = new_scope(circuit_scope, member.0.to_string());
|
||||
let field = new_scope(function_scope, stored_member.0.to_string());
|
||||
|
||||
self.store(field, stored_member.1.clone());
|
||||
}
|
||||
@ -648,7 +595,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
}
|
||||
}
|
||||
ConstrainedValue::Static(value) => {
|
||||
return Err(ExpressionError::InvalidStaticAccess(value.to_string()))
|
||||
return Err(ExpressionError::InvalidStaticAccess(value.to_string()));
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
@ -684,9 +631,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
|
||||
// Find static circuit function
|
||||
let matched_function = circuit.members.into_iter().find(|member| match member {
|
||||
CircuitMember::CircuitFunction(_static, function) => {
|
||||
function.function_name == circuit_member
|
||||
}
|
||||
CircuitMember::CircuitFunction(_static, function) => function.function_name == circuit_member,
|
||||
_ => false,
|
||||
});
|
||||
|
||||
@ -696,23 +641,18 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
if _static {
|
||||
function
|
||||
} else {
|
||||
return Err(ExpressionError::InvalidMemberAccess(
|
||||
function.function_name.to_string(),
|
||||
));
|
||||
return Err(ExpressionError::InvalidMemberAccess(function.function_name.to_string()));
|
||||
}
|
||||
}
|
||||
_ => {
|
||||
return Err(ExpressionError::UndefinedStaticAccess(
|
||||
circuit.identifier.to_string(),
|
||||
circuit_member.to_string(),
|
||||
))
|
||||
));
|
||||
}
|
||||
};
|
||||
|
||||
Ok(ConstrainedValue::Function(
|
||||
Some(circuit.identifier),
|
||||
function,
|
||||
))
|
||||
Ok(ConstrainedValue::Function(Some(circuit.identifier), function))
|
||||
}
|
||||
|
||||
fn enforce_function_call_expression(
|
||||
@ -780,8 +720,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
expected_types: &Vec<Type>,
|
||||
expression: Expression,
|
||||
) -> Result<ConstrainedValue<F, G>, ExpressionError> {
|
||||
let mut branch =
|
||||
self.enforce_expression(cs, file_scope, function_scope, expected_types, expression)?;
|
||||
let mut branch = self.enforce_expression(cs, file_scope, function_scope, expected_types, expression)?;
|
||||
|
||||
branch.get_inner_mut();
|
||||
branch.resolve_type(expected_types)?;
|
||||
@ -798,20 +737,10 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
left: Expression,
|
||||
right: Expression,
|
||||
) -> Result<(ConstrainedValue<F, G>, ConstrainedValue<F, G>), ExpressionError> {
|
||||
let resolved_left = self.enforce_branch(
|
||||
cs,
|
||||
file_scope.clone(),
|
||||
function_scope.clone(),
|
||||
expected_types,
|
||||
left,
|
||||
)?;
|
||||
let resolved_right = self.enforce_branch(
|
||||
cs,
|
||||
file_scope.clone(),
|
||||
function_scope.clone(),
|
||||
expected_types,
|
||||
right,
|
||||
)?;
|
||||
let resolved_left =
|
||||
self.enforce_branch(cs, file_scope.clone(), function_scope.clone(), expected_types, left)?;
|
||||
let resolved_right =
|
||||
self.enforce_branch(cs, file_scope.clone(), function_scope.clone(), expected_types, right)?;
|
||||
|
||||
Ok((resolved_left, resolved_right))
|
||||
}
|
||||
@ -826,19 +755,14 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
) -> Result<ConstrainedValue<F, G>, ExpressionError> {
|
||||
match expression {
|
||||
// Variables
|
||||
Expression::Identifier(unresolved_variable) => self.evaluate_identifier(
|
||||
file_scope,
|
||||
function_scope,
|
||||
expected_types,
|
||||
unresolved_variable,
|
||||
),
|
||||
Expression::Identifier(unresolved_variable) => {
|
||||
self.evaluate_identifier(file_scope, function_scope, expected_types, unresolved_variable)
|
||||
}
|
||||
|
||||
// Values
|
||||
Expression::Integer(integer) => Ok(ConstrainedValue::Integer(integer)),
|
||||
Expression::Field(field) => Ok(ConstrainedValue::Field(FieldType::constant(field)?)),
|
||||
Expression::Group(group_affine) => {
|
||||
Ok(ConstrainedValue::Group(G::constant(group_affine)?))
|
||||
}
|
||||
Expression::Group(group_affine) => Ok(ConstrainedValue::Group(G::constant(group_affine)?)),
|
||||
Expression::Boolean(bool) => Ok(Self::get_boolean_constant(bool)),
|
||||
Expression::Implicit(value) => Self::enforce_number_implicit(expected_types, value),
|
||||
|
||||
@ -1012,23 +936,14 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
Expression::Array(array) => {
|
||||
self.enforce_array_expression(cs, file_scope, function_scope, expected_types, array)
|
||||
}
|
||||
Expression::ArrayAccess(array, index) => self.enforce_array_access_expression(
|
||||
cs,
|
||||
file_scope,
|
||||
function_scope,
|
||||
expected_types,
|
||||
array,
|
||||
*index,
|
||||
),
|
||||
Expression::ArrayAccess(array, index) => {
|
||||
self.enforce_array_access_expression(cs, file_scope, function_scope, expected_types, array, *index)
|
||||
}
|
||||
|
||||
// Circuits
|
||||
Expression::Circuit(circuit_name, members) => self.enforce_circuit_expression(
|
||||
cs,
|
||||
file_scope,
|
||||
function_scope,
|
||||
circuit_name,
|
||||
members,
|
||||
),
|
||||
Expression::Circuit(circuit_name, members) => {
|
||||
self.enforce_circuit_expression(cs, file_scope, function_scope, circuit_name, members)
|
||||
}
|
||||
Expression::CircuitMemberAccess(circuit_variable, circuit_member) => self
|
||||
.enforce_circuit_access_expression(
|
||||
cs,
|
||||
|
@ -1,8 +1,6 @@
|
||||
//! Methods to enforce constraints on field elements in a resolved Leo program.
|
||||
|
||||
use crate::{
|
||||
constraints::ConstrainedValue, errors::FieldError, FieldType, GroupType,
|
||||
};
|
||||
use crate::{constraints::ConstrainedValue, errors::FieldError, FieldType, GroupType};
|
||||
use leo_types::InputValue;
|
||||
|
||||
use snarkos_errors::gadgets::SynthesisError;
|
||||
@ -31,13 +29,9 @@ pub(crate) fn field_from_input<F: Field + PrimeField, G: GroupType<F>, CS: Const
|
||||
|
||||
// Check visibility of parameter
|
||||
let field_value = if private {
|
||||
FieldType::alloc(cs.ns(|| name), || {
|
||||
field_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?
|
||||
FieldType::alloc(cs.ns(|| name), || field_option.ok_or(SynthesisError::AssignmentMissing))?
|
||||
} else {
|
||||
FieldType::alloc_input(cs.ns(|| name), || {
|
||||
field_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?
|
||||
FieldType::alloc_input(cs.ns(|| name), || field_option.ok_or(SynthesisError::AssignmentMissing))?
|
||||
};
|
||||
|
||||
Ok(ConstrainedValue::Field(field_value))
|
||||
|
@ -4,8 +4,10 @@
|
||||
use crate::{
|
||||
constraints::{new_scope, ConstrainedProgram, ConstrainedValue},
|
||||
errors::{FunctionError, ImportError},
|
||||
field_from_input, group_from_input,
|
||||
GroupType};
|
||||
field_from_input,
|
||||
group_from_input,
|
||||
GroupType,
|
||||
};
|
||||
use leo_types::{Expression, Function, Identifier, InputValue, Integer, Program, Type};
|
||||
|
||||
use snarkos_models::{
|
||||
@ -35,19 +37,10 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
// Evaluate the function input value as pass by value from the caller or
|
||||
// evaluate as an expression in the current function scope
|
||||
match input {
|
||||
Expression::Identifier(identifier) => Ok(self.evaluate_identifier(
|
||||
caller_scope,
|
||||
function_name,
|
||||
&expected_types,
|
||||
identifier,
|
||||
)?),
|
||||
expression => Ok(self.enforce_expression(
|
||||
cs,
|
||||
scope,
|
||||
function_name,
|
||||
&expected_types,
|
||||
expression,
|
||||
)?),
|
||||
Expression::Identifier(identifier) => {
|
||||
Ok(self.evaluate_identifier(caller_scope, function_name, &expected_types, identifier)?)
|
||||
}
|
||||
expression => Ok(self.enforce_expression(cs, scope, function_name, &expected_types, expression)?),
|
||||
}
|
||||
}
|
||||
|
||||
@ -65,9 +58,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
Self::check_arguments_length(function.inputs.len(), inputs.len())?;
|
||||
|
||||
// Store input values as new variables in resolved program
|
||||
for (input_model, input_expression) in
|
||||
function.inputs.clone().iter().zip(inputs.into_iter())
|
||||
{
|
||||
for (input_model, input_expression) in function.inputs.clone().iter().zip(inputs.into_iter()) {
|
||||
// First evaluate input expression
|
||||
let mut input_value = self.enforce_input(
|
||||
cs,
|
||||
@ -83,8 +74,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
}
|
||||
|
||||
// Store input as variable with {function_name}_{input_name}
|
||||
let input_program_identifier =
|
||||
new_scope(function_name.clone(), input_model.identifier.name.clone());
|
||||
let input_program_identifier = new_scope(function_name.clone(), input_model.identifier.name.clone());
|
||||
self.store(input_program_identifier, input_value);
|
||||
}
|
||||
|
||||
@ -149,18 +139,10 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
let value_name = new_scope(name.clone(), i.to_string());
|
||||
let value_type = array_type.outer_dimension(&array_dimensions);
|
||||
|
||||
array_value.push(
|
||||
self.allocate_main_function_input(
|
||||
cs, value_type, value_name, private, None,
|
||||
)?,
|
||||
);
|
||||
array_value.push(self.allocate_main_function_input(cs, value_type, value_name, private, None)?);
|
||||
}
|
||||
}
|
||||
_ => {
|
||||
return Err(FunctionError::InvalidArray(
|
||||
input_value.unwrap().to_string(),
|
||||
))
|
||||
}
|
||||
_ => return Err(FunctionError::InvalidArray(input_value.unwrap().to_string())),
|
||||
}
|
||||
|
||||
Ok(ConstrainedValue::Array(array_value))
|
||||
@ -185,9 +167,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
Type::Field => Ok(field_from_input(cs, name, private, input_value)?),
|
||||
Type::Group => Ok(group_from_input(cs, name, private, input_value)?),
|
||||
Type::Boolean => Ok(self.bool_from_input(cs, name, private, input_value)?),
|
||||
Type::Array(_type, dimensions) => {
|
||||
self.allocate_array(cs, name, private, *_type, dimensions, input_value)
|
||||
}
|
||||
Type::Array(_type, dimensions) => self.allocate_array(cs, name, private, *_type, dimensions, input_value),
|
||||
_ => unimplemented!("main function input not implemented for type"),
|
||||
}
|
||||
}
|
||||
@ -206,9 +186,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
|
||||
// Iterate over main function inputs and allocate new passed-by variable values
|
||||
let mut input_variables = vec![];
|
||||
for (input_model, input_option) in
|
||||
function.inputs.clone().into_iter().zip(inputs.into_iter())
|
||||
{
|
||||
for (input_model, input_option) in function.inputs.clone().into_iter().zip(inputs.into_iter()) {
|
||||
let input_name = new_scope(function_name.clone(), input_model.identifier.name.clone());
|
||||
let input_value = self.allocate_main_function_input(
|
||||
cs,
|
||||
@ -229,11 +207,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
self.enforce_function(cs, scope, function_name, function, input_variables)
|
||||
}
|
||||
|
||||
pub(crate) fn resolve_definitions(
|
||||
&mut self,
|
||||
cs: &mut CS,
|
||||
program: Program,
|
||||
) -> Result<(), ImportError> {
|
||||
pub(crate) fn resolve_definitions(&mut self, cs: &mut CS, program: Program) -> Result<(), ImportError> {
|
||||
let program_name = program.name.clone();
|
||||
|
||||
// evaluate and store all imports
|
||||
@ -244,29 +218,15 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
.collect::<Result<Vec<_>, ImportError>>()?;
|
||||
|
||||
// evaluate and store all circuit definitions
|
||||
program
|
||||
.circuits
|
||||
.into_iter()
|
||||
.for_each(|(identifier, circuit)| {
|
||||
let resolved_circuit_name =
|
||||
new_scope(program_name.to_string(), identifier.to_string());
|
||||
self.store(
|
||||
resolved_circuit_name,
|
||||
ConstrainedValue::CircuitDefinition(circuit),
|
||||
);
|
||||
program.circuits.into_iter().for_each(|(identifier, circuit)| {
|
||||
let resolved_circuit_name = new_scope(program_name.to_string(), identifier.to_string());
|
||||
self.store(resolved_circuit_name, ConstrainedValue::CircuitDefinition(circuit));
|
||||
});
|
||||
|
||||
// evaluate and store all function definitions
|
||||
program
|
||||
.functions
|
||||
.into_iter()
|
||||
.for_each(|(function_name, function)| {
|
||||
let resolved_function_name =
|
||||
new_scope(program_name.to_string(), function_name.to_string());
|
||||
self.store(
|
||||
resolved_function_name,
|
||||
ConstrainedValue::Function(None, function),
|
||||
);
|
||||
program.functions.into_iter().for_each(|(function_name, function)| {
|
||||
let resolved_function_name = new_scope(program_name.to_string(), function_name.to_string());
|
||||
self.store(resolved_function_name, ConstrainedValue::Function(None, function));
|
||||
});
|
||||
|
||||
Ok(())
|
||||
|
@ -27,13 +27,9 @@ pub(crate) fn group_from_input<F: Field + PrimeField, G: GroupType<F>, CS: Const
|
||||
|
||||
// Check visibility of parameter
|
||||
let group_value = if private {
|
||||
G::alloc(cs.ns(|| name), || {
|
||||
group_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?
|
||||
G::alloc(cs.ns(|| name), || group_option.ok_or(SynthesisError::AssignmentMissing))?
|
||||
} else {
|
||||
G::alloc_input(cs.ns(|| name), || {
|
||||
group_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?
|
||||
G::alloc_input(cs.ns(|| name), || group_option.ok_or(SynthesisError::AssignmentMissing))?
|
||||
};
|
||||
|
||||
Ok(ConstrainedValue::Group(group_value))
|
||||
|
@ -14,12 +14,7 @@ use snarkos_models::{
|
||||
use std::env::current_dir;
|
||||
|
||||
impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> ConstrainedProgram<F, G, CS> {
|
||||
pub fn enforce_import(
|
||||
&mut self,
|
||||
cs: &mut CS,
|
||||
scope: String,
|
||||
import: Import,
|
||||
) -> Result<(), ImportError> {
|
||||
pub fn enforce_import(&mut self, cs: &mut CS, scope: String, import: Import) -> Result<(), ImportError> {
|
||||
let path = current_dir().map_err(|error| ImportError::DirectoryError(error))?;
|
||||
|
||||
// Sanitize the package path to the imports directory
|
||||
@ -64,19 +59,17 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
.find(|(circuit_name, _circuit_def)| symbol.symbol == *circuit_name);
|
||||
|
||||
let value = match matched_circuit {
|
||||
Some((_circuit_name, circuit_def)) => {
|
||||
ConstrainedValue::CircuitDefinition(circuit_def)
|
||||
}
|
||||
Some((_circuit_name, circuit_def)) => ConstrainedValue::CircuitDefinition(circuit_def),
|
||||
None => {
|
||||
// see if the imported symbol is a function
|
||||
let matched_function = program.functions.clone().into_iter().find(
|
||||
|(function_name, _function)| symbol.symbol.name == *function_name.name,
|
||||
);
|
||||
let matched_function = program
|
||||
.functions
|
||||
.clone()
|
||||
.into_iter()
|
||||
.find(|(function_name, _function)| symbol.symbol.name == *function_name.name);
|
||||
|
||||
match matched_function {
|
||||
Some((_function_name, function)) => {
|
||||
ConstrainedValue::Function(None, function)
|
||||
}
|
||||
Some((_function_name, function)) => ConstrainedValue::Function(None, function),
|
||||
None => unimplemented!(
|
||||
"cannot find imported symbol {} in imported file {}",
|
||||
symbol,
|
||||
@ -88,8 +81,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
|
||||
// take the alias if it is present
|
||||
let resolved_name = symbol.alias.unwrap_or(symbol.symbol);
|
||||
let resolved_circuit_name =
|
||||
new_scope(program_name.to_string(), resolved_name.to_string());
|
||||
let resolved_circuit_name = new_scope(program_name.to_string(), resolved_name.to_string());
|
||||
|
||||
// store imported circuit under resolved name
|
||||
self.store(resolved_circuit_name, value);
|
||||
@ -99,9 +91,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
program
|
||||
.imports
|
||||
.into_iter()
|
||||
.map(|nested_import| {
|
||||
self.enforce_import(cs, program_name.name.clone(), nested_import)
|
||||
})
|
||||
.map(|nested_import| self.enforce_import(cs, program_name.name.clone(), nested_import))
|
||||
.collect::<Result<Vec<_>, ImportError>>()?;
|
||||
|
||||
Ok(())
|
||||
|
@ -27,10 +27,7 @@ pub use value::*;
|
||||
pub mod statement;
|
||||
pub use statement::*;
|
||||
|
||||
use crate::{
|
||||
errors::CompilerError,
|
||||
GroupType,
|
||||
};
|
||||
use crate::{errors::CompilerError, GroupType};
|
||||
use leo_types::{InputValue, Program};
|
||||
|
||||
use snarkos_models::{
|
||||
@ -55,8 +52,7 @@ pub fn generate_constraints<F: Field + PrimeField, G: GroupType<F>, CS: Constrai
|
||||
|
||||
match main.clone() {
|
||||
ConstrainedValue::Function(_circuit_identifier, function) => {
|
||||
let result =
|
||||
resolved_program.enforce_main_function(cs, program_name, function, parameters)?;
|
||||
let result = resolved_program.enforce_main_function(cs, program_name, function, parameters)?;
|
||||
log::debug!("{}", result);
|
||||
Ok(result)
|
||||
}
|
||||
|
@ -6,7 +6,18 @@ use crate::{
|
||||
new_scope,
|
||||
GroupType,
|
||||
};
|
||||
use leo_types::{Assignee, ConditionalNestedOrEndStatement, ConditionalStatement, Statement, Expression, Identifier, Integer, RangeOrExpression, Type, Variable};
|
||||
use leo_types::{
|
||||
Assignee,
|
||||
ConditionalNestedOrEndStatement,
|
||||
ConditionalStatement,
|
||||
Expression,
|
||||
Identifier,
|
||||
Integer,
|
||||
RangeOrExpression,
|
||||
Statement,
|
||||
Type,
|
||||
Variable,
|
||||
};
|
||||
|
||||
use snarkos_models::{
|
||||
curves::{Field, PrimeField},
|
||||
@ -21,16 +32,11 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
match assignee {
|
||||
Assignee::Identifier(name) => new_scope(scope, name.to_string()),
|
||||
Assignee::Array(array, _index) => self.resolve_assignee(scope, *array),
|
||||
Assignee::CircuitField(circuit_name, _member) => {
|
||||
self.resolve_assignee(scope, *circuit_name)
|
||||
}
|
||||
Assignee::CircuitField(circuit_name, _member) => self.resolve_assignee(scope, *circuit_name),
|
||||
}
|
||||
}
|
||||
|
||||
fn get_mutable_assignee(
|
||||
&mut self,
|
||||
name: String,
|
||||
) -> Result<&mut ConstrainedValue<F, G>, StatementError> {
|
||||
fn get_mutable_assignee(&mut self, name: String) -> Result<&mut ConstrainedValue<F, G>, StatementError> {
|
||||
// Check that assignee exists and is mutable
|
||||
Ok(match self.get_mut(&name) {
|
||||
Some(value) => match value {
|
||||
@ -53,8 +59,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
// Resolve index so we know if we are assigning to a single value or a range of values
|
||||
match range_or_expression {
|
||||
RangeOrExpression::Expression(index) => {
|
||||
let index =
|
||||
self.enforce_index(cs, file_scope.clone(), function_scope.clone(), index)?;
|
||||
let index = self.enforce_index(cs, file_scope.clone(), function_scope.clone(), index)?;
|
||||
|
||||
// Modify the single value of the array in place
|
||||
match self.get_mutable_assignee(name)? {
|
||||
@ -104,18 +109,14 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
ConstrainedValue::Function(_circuit_identifier, function) => {
|
||||
return Err(StatementError::ImmutableCircuitFunction(
|
||||
function.function_name.to_string(),
|
||||
))
|
||||
));
|
||||
}
|
||||
ConstrainedValue::Static(_value) => {
|
||||
return Err(StatementError::ImmutableCircuitFunction("static".into()))
|
||||
return Err(StatementError::ImmutableCircuitFunction("static".into()));
|
||||
}
|
||||
_ => object.1 = new_value.to_owned(),
|
||||
},
|
||||
None => {
|
||||
return Err(StatementError::UndefinedCircuitObject(
|
||||
object_name.to_string(),
|
||||
))
|
||||
}
|
||||
None => return Err(StatementError::UndefinedCircuitObject(object_name.to_string())),
|
||||
}
|
||||
}
|
||||
_ => return Err(StatementError::UndefinedCircuit(object_name.to_string())),
|
||||
@ -136,13 +137,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
let variable_name = self.resolve_assignee(function_scope.clone(), assignee.clone());
|
||||
|
||||
// Evaluate new value
|
||||
let new_value = self.enforce_expression(
|
||||
cs,
|
||||
file_scope.clone(),
|
||||
function_scope.clone(),
|
||||
&vec![],
|
||||
expression,
|
||||
)?;
|
||||
let new_value = self.enforce_expression(cs, file_scope.clone(), function_scope.clone(), &vec![], expression)?;
|
||||
|
||||
// Mutate the old value into the new value
|
||||
match assignee {
|
||||
@ -232,10 +227,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
function,
|
||||
)? {
|
||||
ConstrainedValue::Return(values) => values,
|
||||
value => unimplemented!(
|
||||
"multiple assignment only implemented for functions, got {}",
|
||||
value
|
||||
),
|
||||
value => unimplemented!("multiple assignment only implemented for functions, got {}", value),
|
||||
};
|
||||
|
||||
if variables.len() != return_values.len() {
|
||||
@ -332,30 +324,16 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
|
||||
// use gadget impl
|
||||
if condition.eq(&Boolean::Constant(true)) {
|
||||
self.iterate_or_early_return(
|
||||
cs,
|
||||
file_scope,
|
||||
function_scope,
|
||||
statement.statements,
|
||||
return_types,
|
||||
)
|
||||
self.iterate_or_early_return(cs, file_scope, function_scope, statement.statements, return_types)
|
||||
} else {
|
||||
match statement.next {
|
||||
Some(next) => match next {
|
||||
ConditionalNestedOrEndStatement::Nested(nested) => self.enforce_conditional_statement(
|
||||
cs,
|
||||
file_scope,
|
||||
function_scope,
|
||||
*nested,
|
||||
return_types,
|
||||
),
|
||||
ConditionalNestedOrEndStatement::End(statements) => self.iterate_or_early_return(
|
||||
cs,
|
||||
file_scope,
|
||||
function_scope,
|
||||
statements,
|
||||
return_types,
|
||||
),
|
||||
ConditionalNestedOrEndStatement::Nested(nested) => {
|
||||
self.enforce_conditional_statement(cs, file_scope, function_scope, *nested, return_types)
|
||||
}
|
||||
ConditionalNestedOrEndStatement::End(statements) => {
|
||||
self.iterate_or_early_return(cs, file_scope, function_scope, statements, return_types)
|
||||
}
|
||||
},
|
||||
None => Ok(None),
|
||||
}
|
||||
@ -410,11 +388,9 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
(ConstrainedValue::Boolean(bool_1), ConstrainedValue::Boolean(bool_2)) => {
|
||||
self.enforce_boolean_eq(cs, bool_1, bool_2)?
|
||||
}
|
||||
(ConstrainedValue::Integer(num_1), ConstrainedValue::Integer(num_2)) => {
|
||||
num_1.enforce_equal(cs, &num_2).map_err(|_| {
|
||||
StatementError::AssertionFailed(num_1.to_string(), num_2.to_string())
|
||||
})?
|
||||
}
|
||||
(ConstrainedValue::Integer(num_1), ConstrainedValue::Integer(num_2)) => num_1
|
||||
.enforce_equal(cs, &num_2)
|
||||
.map_err(|_| StatementError::AssertionFailed(num_1.to_string(), num_2.to_string()))?,
|
||||
(ConstrainedValue::Field(fe_1), ConstrainedValue::Field(fe_2)) => fe_1
|
||||
.enforce_equal(cs, &fe_2)
|
||||
.map_err(|_| StatementError::AssertionFailed(fe_1.to_string(), fe_2.to_string()))?,
|
||||
@ -426,12 +402,7 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
self.enforce_assert_eq_statement(cs, left, right)?;
|
||||
}
|
||||
}
|
||||
(val_1, val_2) => {
|
||||
return Err(StatementError::AssertEq(
|
||||
val_1.to_string(),
|
||||
val_2.to_string(),
|
||||
))
|
||||
}
|
||||
(val_1, val_2) => return Err(StatementError::AssertEq(val_1.to_string(), val_2.to_string())),
|
||||
})
|
||||
}
|
||||
|
||||
@ -446,49 +417,21 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
let mut res = None;
|
||||
match statement {
|
||||
Statement::Return(expressions) => {
|
||||
res = Some(self.enforce_return_statement(
|
||||
cs,
|
||||
file_scope,
|
||||
function_scope,
|
||||
expressions,
|
||||
return_types,
|
||||
)?);
|
||||
res = Some(self.enforce_return_statement(cs, file_scope, function_scope, expressions, return_types)?);
|
||||
}
|
||||
Statement::Definition(variable, expression) => {
|
||||
self.enforce_definition_statement(
|
||||
cs,
|
||||
file_scope,
|
||||
function_scope,
|
||||
variable,
|
||||
expression,
|
||||
)?;
|
||||
self.enforce_definition_statement(cs, file_scope, function_scope, variable, expression)?;
|
||||
}
|
||||
Statement::Assign(variable, expression) => {
|
||||
self.enforce_assign_statement(
|
||||
cs,
|
||||
file_scope,
|
||||
function_scope,
|
||||
variable,
|
||||
expression,
|
||||
)?;
|
||||
self.enforce_assign_statement(cs, file_scope, function_scope, variable, expression)?;
|
||||
}
|
||||
Statement::MultipleAssign(variables, function) => {
|
||||
self.enforce_multiple_definition_statement(
|
||||
cs,
|
||||
file_scope,
|
||||
function_scope,
|
||||
variables,
|
||||
function,
|
||||
)?;
|
||||
self.enforce_multiple_definition_statement(cs, file_scope, function_scope, variables, function)?;
|
||||
}
|
||||
Statement::Conditional(statement) => {
|
||||
if let Some(early_return) = self.enforce_conditional_statement(
|
||||
cs,
|
||||
file_scope,
|
||||
function_scope,
|
||||
statement,
|
||||
return_types,
|
||||
)? {
|
||||
if let Some(early_return) =
|
||||
self.enforce_conditional_statement(cs, file_scope, function_scope, statement, return_types)?
|
||||
{
|
||||
res = Some(early_return)
|
||||
}
|
||||
}
|
||||
@ -507,31 +450,15 @@ impl<F: Field + PrimeField, G: GroupType<F>, CS: ConstraintSystem<F>> Constraine
|
||||
}
|
||||
}
|
||||
Statement::AssertEq(left, right) => {
|
||||
let resolved_left = self.enforce_expression(
|
||||
cs,
|
||||
file_scope.clone(),
|
||||
function_scope.clone(),
|
||||
&vec![],
|
||||
left,
|
||||
)?;
|
||||
let resolved_right = self.enforce_expression(
|
||||
cs,
|
||||
file_scope.clone(),
|
||||
function_scope.clone(),
|
||||
&vec![],
|
||||
right,
|
||||
)?;
|
||||
let resolved_left =
|
||||
self.enforce_expression(cs, file_scope.clone(), function_scope.clone(), &vec![], left)?;
|
||||
let resolved_right =
|
||||
self.enforce_expression(cs, file_scope.clone(), function_scope.clone(), &vec![], right)?;
|
||||
|
||||
self.enforce_assert_eq_statement(cs, resolved_left, resolved_right)?;
|
||||
}
|
||||
Statement::Expression(expression) => {
|
||||
match self.enforce_expression(
|
||||
cs,
|
||||
file_scope,
|
||||
function_scope,
|
||||
&vec![],
|
||||
expression.clone(),
|
||||
)? {
|
||||
match self.enforce_expression(cs, file_scope, function_scope, &vec![], expression.clone())? {
|
||||
ConstrainedValue::Return(values) => {
|
||||
if !values.is_empty() {
|
||||
return Err(StatementError::Unassigned(expression.to_string()));
|
||||
|
@ -1,9 +1,6 @@
|
||||
//! The in memory stored value for a defined name in a resolved Leo program.
|
||||
|
||||
use crate::{
|
||||
errors::ValueError,
|
||||
FieldType, GroupType,
|
||||
};
|
||||
use crate::{errors::ValueError, FieldType, GroupType};
|
||||
use leo_types::{Circuit, Function, Identifier, Integer, IntegerType, Type};
|
||||
|
||||
use snarkos_models::{
|
||||
@ -16,10 +13,7 @@ use snarkos_models::{
|
||||
use std::fmt;
|
||||
|
||||
#[derive(Clone, PartialEq, Eq)]
|
||||
pub struct ConstrainedCircuitMember<F: Field + PrimeField, G: GroupType<F>>(
|
||||
pub Identifier,
|
||||
pub ConstrainedValue<F, G>,
|
||||
);
|
||||
pub struct ConstrainedCircuitMember<F: Field + PrimeField, G: GroupType<F>>(pub Identifier, pub ConstrainedValue<F, G>);
|
||||
|
||||
#[derive(Clone, PartialEq, Eq)]
|
||||
pub enum ConstrainedValue<F: Field + PrimeField, G: GroupType<F>> {
|
||||
@ -42,10 +36,7 @@ pub enum ConstrainedValue<F: Field + PrimeField, G: GroupType<F>> {
|
||||
}
|
||||
|
||||
impl<F: Field + PrimeField, G: GroupType<F>> ConstrainedValue<F, G> {
|
||||
pub(crate) fn from_other(
|
||||
value: String,
|
||||
other: &ConstrainedValue<F, G>,
|
||||
) -> Result<Self, ValueError> {
|
||||
pub(crate) fn from_other(value: String, other: &ConstrainedValue<F, G>) -> Result<Self, ValueError> {
|
||||
let other_type = other.to_type();
|
||||
|
||||
ConstrainedValue::from_type(value, &other_type)
|
||||
@ -62,9 +53,7 @@ impl<F: Field + PrimeField, G: GroupType<F>> ConstrainedValue<F, G> {
|
||||
})),
|
||||
Type::Field => Ok(ConstrainedValue::Field(FieldType::constant(value)?)),
|
||||
Type::Group => Ok(ConstrainedValue::Group(G::constant(value)?)),
|
||||
Type::Boolean => Ok(ConstrainedValue::Boolean(Boolean::Constant(
|
||||
value.parse::<bool>()?,
|
||||
))),
|
||||
Type::Boolean => Ok(ConstrainedValue::Boolean(Boolean::Constant(value.parse::<bool>()?))),
|
||||
Type::Array(ref _type, _dimensions) => ConstrainedValue::from_type(value, _type),
|
||||
_ => Ok(ConstrainedValue::Unresolved(value)),
|
||||
}
|
||||
@ -137,9 +126,7 @@ impl<F: Field + PrimeField, G: GroupType<F>> fmt::Display for ConstrainedValue<F
|
||||
ConstrainedValue::CircuitDefinition(ref _definition) => {
|
||||
unimplemented!("cannot return circuit definition in program")
|
||||
}
|
||||
ConstrainedValue::Function(ref _circuit_option, ref function) => {
|
||||
write!(f, "{}", function)
|
||||
}
|
||||
ConstrainedValue::Function(ref _circuit_option, ref function) => write!(f, "{}", function),
|
||||
ConstrainedValue::Mutable(ref value) => write!(f, "mut {}", value),
|
||||
ConstrainedValue::Static(ref value) => write!(f, "static {}", value),
|
||||
ConstrainedValue::Unresolved(ref value) => write!(f, "unresolved {}", value),
|
||||
|
@ -1,5 +1,5 @@
|
||||
use crate::errors::{FunctionError, ImportError};
|
||||
use leo_ast::{SyntaxError, ParserError};
|
||||
use leo_ast::{ParserError, SyntaxError};
|
||||
use leo_types::IntegerError;
|
||||
|
||||
use std::{io, path::PathBuf};
|
||||
|
@ -1,6 +1,4 @@
|
||||
use crate::errors::{
|
||||
BooleanError, FieldError, FunctionError, GroupError, ValueError,
|
||||
};
|
||||
use crate::errors::{BooleanError, FieldError, FunctionError, GroupError, ValueError};
|
||||
use leo_types::IntegerError;
|
||||
|
||||
use snarkos_errors::gadgets::SynthesisError;
|
||||
@ -47,10 +45,7 @@ pub enum ExpressionError {
|
||||
#[error("Spread should contain an array, got {}", _0)]
|
||||
InvalidSpread(String),
|
||||
|
||||
#[error(
|
||||
"Array {} must be declared before it is used in an inline expression",
|
||||
_0
|
||||
)]
|
||||
#[error("Array {} must be declared before it is used in an inline expression", _0)]
|
||||
UndefinedArray(String),
|
||||
|
||||
// Circuits
|
||||
@ -66,10 +61,7 @@ pub enum ExpressionError {
|
||||
#[error("Static member {} must be accessed using `::` syntax", _0)]
|
||||
InvalidStaticAccess(String),
|
||||
|
||||
#[error(
|
||||
"Circuit {} must be declared before it is used in an inline expression",
|
||||
_0
|
||||
)]
|
||||
#[error("Circuit {} must be declared before it is used in an inline expression", _0)]
|
||||
UndefinedCircuit(String),
|
||||
|
||||
#[error("Circuit {} has no member {}", _0, _1)]
|
||||
@ -85,10 +77,7 @@ pub enum ExpressionError {
|
||||
#[error("{}", _0)]
|
||||
FunctionError(#[from] Box<FunctionError>),
|
||||
|
||||
#[error(
|
||||
"Function {} must be declared before it is used in an inline expression",
|
||||
_0
|
||||
)]
|
||||
#[error("Function {} must be declared before it is used in an inline expression", _0)]
|
||||
UndefinedFunction(String),
|
||||
|
||||
// Conditionals
|
||||
|
@ -1,6 +1,4 @@
|
||||
use crate::errors::{
|
||||
BooleanError, ExpressionError, FieldError, GroupError, StatementError, ValueError,
|
||||
};
|
||||
use crate::errors::{BooleanError, ExpressionError, FieldError, GroupError, StatementError, ValueError};
|
||||
use leo_types::IntegerError;
|
||||
|
||||
#[derive(Debug, Error)]
|
||||
|
@ -43,11 +43,7 @@ pub enum StatementError {
|
||||
#[error("Cannot assign to immutable variable {}", _0)]
|
||||
ImmutableAssign(String),
|
||||
|
||||
#[error(
|
||||
"Multiple definition statement expected {} return values, got {}",
|
||||
_0,
|
||||
_1
|
||||
)]
|
||||
#[error("Multiple definition statement expected {} return values, got {}", _0, _1)]
|
||||
InvalidNumberOfDefinitions(usize, usize),
|
||||
|
||||
#[error("Function return statement expected {} return values, got {}", _0, _1)]
|
||||
|
@ -3,11 +3,10 @@
|
||||
use crate::errors::FieldError;
|
||||
|
||||
use snarkos_errors::gadgets::SynthesisError;
|
||||
use snarkos_models::gadgets::curves::FieldGadget;
|
||||
use snarkos_models::{
|
||||
curves::{Field, PrimeField},
|
||||
gadgets::{
|
||||
curves::FpGadget,
|
||||
curves::{FieldGadget, FpGadget},
|
||||
r1cs::ConstraintSystem,
|
||||
utilities::{
|
||||
alloc::AllocGadget,
|
||||
@ -15,12 +14,12 @@ use snarkos_models::{
|
||||
eq::{ConditionalEqGadget, EqGadget},
|
||||
select::CondSelectGadget,
|
||||
uint::UInt8,
|
||||
ToBitsGadget, ToBytesGadget,
|
||||
ToBitsGadget,
|
||||
ToBytesGadget,
|
||||
},
|
||||
},
|
||||
};
|
||||
use std::borrow::Borrow;
|
||||
use std::cmp::Ordering;
|
||||
use std::{borrow::Borrow, cmp::Ordering};
|
||||
|
||||
#[derive(Clone, Debug)]
|
||||
pub enum FieldType<F: Field + PrimeField> {
|
||||
@ -55,9 +54,9 @@ impl<F: Field + PrimeField> FieldType<F> {
|
||||
}
|
||||
|
||||
(FieldType::Constant(constant_value), FieldType::Allocated(allocated_value))
|
||||
| (FieldType::Allocated(allocated_value), FieldType::Constant(constant_value)) => Ok(
|
||||
FieldType::Allocated(allocated_value.add_constant(cs, constant_value)?),
|
||||
),
|
||||
| (FieldType::Allocated(allocated_value), FieldType::Constant(constant_value)) => {
|
||||
Ok(FieldType::Allocated(allocated_value.add_constant(cs, constant_value)?))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -74,9 +73,9 @@ impl<F: Field + PrimeField> FieldType<F> {
|
||||
}
|
||||
|
||||
(FieldType::Constant(constant_value), FieldType::Allocated(allocated_value))
|
||||
| (FieldType::Allocated(allocated_value), FieldType::Constant(constant_value)) => Ok(
|
||||
FieldType::Allocated(allocated_value.sub_constant(cs, constant_value)?),
|
||||
),
|
||||
| (FieldType::Allocated(allocated_value), FieldType::Constant(constant_value)) => {
|
||||
Ok(FieldType::Allocated(allocated_value.sub_constant(cs, constant_value)?))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -93,22 +92,16 @@ impl<F: Field + PrimeField> FieldType<F> {
|
||||
}
|
||||
|
||||
(FieldType::Constant(constant_value), FieldType::Allocated(allocated_value))
|
||||
| (FieldType::Allocated(allocated_value), FieldType::Constant(constant_value)) => Ok(
|
||||
FieldType::Allocated(allocated_value.mul_by_constant(cs, constant_value)?),
|
||||
),
|
||||
| (FieldType::Allocated(allocated_value), FieldType::Constant(constant_value)) => Ok(FieldType::Allocated(
|
||||
allocated_value.mul_by_constant(cs, constant_value)?,
|
||||
)),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn div<CS: ConstraintSystem<F>>(
|
||||
&self,
|
||||
mut cs: CS,
|
||||
other: &Self,
|
||||
) -> Result<Self, FieldError> {
|
||||
pub fn div<CS: ConstraintSystem<F>>(&self, mut cs: CS, other: &Self) -> Result<Self, FieldError> {
|
||||
let inverse = match other {
|
||||
FieldType::Constant(constant) => {
|
||||
let constant_inverse = constant
|
||||
.inverse()
|
||||
.ok_or(FieldError::NoInverse(constant.to_string()))?;
|
||||
let constant_inverse = constant.inverse().ok_or(FieldError::NoInverse(constant.to_string()))?;
|
||||
FieldType::Constant(constant_inverse)
|
||||
}
|
||||
FieldType::Allocated(allocated) => {
|
||||
@ -134,25 +127,16 @@ impl<F: Field + PrimeField> FieldType<F> {
|
||||
F::from_str(&field_string).map_err(|_| SynthesisError::AssignmentMissing)
|
||||
}
|
||||
|
||||
pub fn allocated<CS: ConstraintSystem<F>>(
|
||||
&self,
|
||||
mut cs: CS,
|
||||
) -> Result<FpGadget<F>, SynthesisError> {
|
||||
pub fn allocated<CS: ConstraintSystem<F>>(&self, mut cs: CS) -> Result<FpGadget<F>, SynthesisError> {
|
||||
match self {
|
||||
FieldType::Constant(constant) => {
|
||||
FpGadget::alloc(&mut cs.ns(|| format!("{:?}", constant)), || Ok(constant))
|
||||
}
|
||||
FieldType::Constant(constant) => FpGadget::alloc(&mut cs.ns(|| format!("{:?}", constant)), || Ok(constant)),
|
||||
FieldType::Allocated(allocated) => Ok(allocated.clone()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: Field + PrimeField> AllocGadget<String, F> for FieldType<F> {
|
||||
fn alloc<
|
||||
Fn: FnOnce() -> Result<T, SynthesisError>,
|
||||
T: Borrow<String>,
|
||||
CS: ConstraintSystem<F>,
|
||||
>(
|
||||
fn alloc<Fn: FnOnce() -> Result<T, SynthesisError>, T: Borrow<String>, CS: ConstraintSystem<F>>(
|
||||
cs: CS,
|
||||
value_gen: Fn,
|
||||
) -> Result<Self, SynthesisError> {
|
||||
@ -161,11 +145,7 @@ impl<F: Field + PrimeField> AllocGadget<String, F> for FieldType<F> {
|
||||
Ok(FieldType::Allocated(value))
|
||||
}
|
||||
|
||||
fn alloc_input<
|
||||
Fn: FnOnce() -> Result<T, SynthesisError>,
|
||||
T: Borrow<String>,
|
||||
CS: ConstraintSystem<F>,
|
||||
>(
|
||||
fn alloc_input<Fn: FnOnce() -> Result<T, SynthesisError>, T: Borrow<String>, CS: ConstraintSystem<F>>(
|
||||
cs: CS,
|
||||
value_gen: Fn,
|
||||
) -> Result<Self, SynthesisError> {
|
||||
@ -239,11 +219,7 @@ impl<F: Field + PrimeField> CondSelectGadget<F> for FieldType<F> {
|
||||
second: &Self,
|
||||
) -> Result<Self, SynthesisError> {
|
||||
if let Boolean::Constant(cond) = *cond {
|
||||
if cond {
|
||||
Ok(first.clone())
|
||||
} else {
|
||||
Ok(second.clone())
|
||||
}
|
||||
if cond { Ok(first.clone()) } else { Ok(second.clone()) }
|
||||
} else {
|
||||
let first_gadget = first.allocated(&mut cs)?;
|
||||
let second_gadget = second.allocated(&mut cs)?;
|
||||
@ -264,10 +240,7 @@ impl<F: Field + PrimeField> ToBitsGadget<F> for FieldType<F> {
|
||||
self_gadget.to_bits(cs)
|
||||
}
|
||||
|
||||
fn to_bits_strict<CS: ConstraintSystem<F>>(
|
||||
&self,
|
||||
mut cs: CS,
|
||||
) -> Result<Vec<Boolean>, SynthesisError> {
|
||||
fn to_bits_strict<CS: ConstraintSystem<F>>(&self, mut cs: CS) -> Result<Vec<Boolean>, SynthesisError> {
|
||||
let self_gadget = self.allocated(&mut cs)?;
|
||||
self_gadget.to_bits_strict(cs)
|
||||
}
|
||||
@ -279,10 +252,7 @@ impl<F: Field + PrimeField> ToBytesGadget<F> for FieldType<F> {
|
||||
self_gadget.to_bytes(cs)
|
||||
}
|
||||
|
||||
fn to_bytes_strict<CS: ConstraintSystem<F>>(
|
||||
&self,
|
||||
mut cs: CS,
|
||||
) -> Result<Vec<UInt8>, SynthesisError> {
|
||||
fn to_bytes_strict<CS: ConstraintSystem<F>>(&self, mut cs: CS) -> Result<Vec<UInt8>, SynthesisError> {
|
||||
let self_gadget = self.allocated(&mut cs)?;
|
||||
self_gadget.to_bytes_strict(cs)
|
||||
}
|
||||
|
@ -17,7 +17,8 @@ use snarkos_models::{
|
||||
eq::{ConditionalEqGadget, EqGadget},
|
||||
select::CondSelectGadget,
|
||||
uint::UInt8,
|
||||
ToBitsGadget, ToBytesGadget,
|
||||
ToBitsGadget,
|
||||
ToBytesGadget,
|
||||
},
|
||||
},
|
||||
};
|
||||
@ -43,23 +44,18 @@ impl GroupType<Fq> for EdwardsGroupType {
|
||||
}
|
||||
|
||||
(EdwardsGroupType::Allocated(self_value), EdwardsGroupType::Allocated(other_value)) => {
|
||||
let result = <EdwardsBlsGadget as GroupGadget<
|
||||
GroupAffine<EdwardsParameters>,
|
||||
Fq,
|
||||
>>::add(self_value, cs, other_value)?;
|
||||
let result = <EdwardsBlsGadget as GroupGadget<GroupAffine<EdwardsParameters>, Fq>>::add(
|
||||
self_value,
|
||||
cs,
|
||||
other_value,
|
||||
)?;
|
||||
Ok(EdwardsGroupType::Allocated(result))
|
||||
}
|
||||
|
||||
(
|
||||
EdwardsGroupType::Constant(constant_value),
|
||||
EdwardsGroupType::Allocated(allocated_value),
|
||||
)
|
||||
| (
|
||||
EdwardsGroupType::Allocated(allocated_value),
|
||||
EdwardsGroupType::Constant(constant_value),
|
||||
) => Ok(EdwardsGroupType::Allocated(
|
||||
allocated_value.add_constant(cs, constant_value)?,
|
||||
)),
|
||||
(EdwardsGroupType::Constant(constant_value), EdwardsGroupType::Allocated(allocated_value))
|
||||
| (EdwardsGroupType::Allocated(allocated_value), EdwardsGroupType::Constant(constant_value)) => Ok(
|
||||
EdwardsGroupType::Allocated(allocated_value.add_constant(cs, constant_value)?),
|
||||
),
|
||||
}
|
||||
}
|
||||
|
||||
@ -70,23 +66,18 @@ impl GroupType<Fq> for EdwardsGroupType {
|
||||
}
|
||||
|
||||
(EdwardsGroupType::Allocated(self_value), EdwardsGroupType::Allocated(other_value)) => {
|
||||
let result = <EdwardsBlsGadget as GroupGadget<
|
||||
GroupAffine<EdwardsParameters>,
|
||||
Fq,
|
||||
>>::sub(self_value, cs, other_value)?;
|
||||
let result = <EdwardsBlsGadget as GroupGadget<GroupAffine<EdwardsParameters>, Fq>>::sub(
|
||||
self_value,
|
||||
cs,
|
||||
other_value,
|
||||
)?;
|
||||
Ok(EdwardsGroupType::Allocated(result))
|
||||
}
|
||||
|
||||
(
|
||||
EdwardsGroupType::Constant(constant_value),
|
||||
EdwardsGroupType::Allocated(allocated_value),
|
||||
)
|
||||
| (
|
||||
EdwardsGroupType::Allocated(allocated_value),
|
||||
EdwardsGroupType::Constant(constant_value),
|
||||
) => Ok(EdwardsGroupType::Allocated(
|
||||
allocated_value.sub_constant(cs, constant_value)?,
|
||||
)),
|
||||
(EdwardsGroupType::Constant(constant_value), EdwardsGroupType::Allocated(allocated_value))
|
||||
| (EdwardsGroupType::Allocated(allocated_value), EdwardsGroupType::Constant(constant_value)) => Ok(
|
||||
EdwardsGroupType::Allocated(allocated_value.sub_constant(cs, constant_value)?),
|
||||
),
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -114,10 +105,7 @@ impl EdwardsGroupType {
|
||||
Self::edwards_affine_from_str(affine_string).map_err(|_| SynthesisError::AssignmentMissing)
|
||||
}
|
||||
|
||||
pub fn allocated<CS: ConstraintSystem<Fq>>(
|
||||
&self,
|
||||
mut cs: CS,
|
||||
) -> Result<EdwardsBlsGadget, SynthesisError> {
|
||||
pub fn allocated<CS: ConstraintSystem<Fq>>(&self, mut cs: CS) -> Result<EdwardsBlsGadget, SynthesisError> {
|
||||
match self {
|
||||
EdwardsGroupType::Constant(constant) => {
|
||||
<EdwardsBlsGadget as AllocGadget<GroupAffine<EdwardsParameters>, Fq>>::alloc(
|
||||
@ -131,35 +119,24 @@ impl EdwardsGroupType {
|
||||
}
|
||||
|
||||
impl AllocGadget<String, Fq> for EdwardsGroupType {
|
||||
fn alloc<
|
||||
Fn: FnOnce() -> Result<T, SynthesisError>,
|
||||
T: Borrow<String>,
|
||||
CS: ConstraintSystem<Fq>,
|
||||
>(
|
||||
fn alloc<Fn: FnOnce() -> Result<T, SynthesisError>, T: Borrow<String>, CS: ConstraintSystem<Fq>>(
|
||||
cs: CS,
|
||||
value_gen: Fn,
|
||||
) -> Result<Self, SynthesisError> {
|
||||
let value = <EdwardsBlsGadget as AllocGadget<GroupAffine<EdwardsParameters>, Fq>>::alloc(
|
||||
cs,
|
||||
|| Self::alloc_x_helper(value_gen),
|
||||
)?;
|
||||
let value = <EdwardsBlsGadget as AllocGadget<GroupAffine<EdwardsParameters>, Fq>>::alloc(cs, || {
|
||||
Self::alloc_x_helper(value_gen)
|
||||
})?;
|
||||
|
||||
Ok(EdwardsGroupType::Allocated(value))
|
||||
}
|
||||
|
||||
fn alloc_input<
|
||||
Fn: FnOnce() -> Result<T, SynthesisError>,
|
||||
T: Borrow<String>,
|
||||
CS: ConstraintSystem<Fq>,
|
||||
>(
|
||||
fn alloc_input<Fn: FnOnce() -> Result<T, SynthesisError>, T: Borrow<String>, CS: ConstraintSystem<Fq>>(
|
||||
cs: CS,
|
||||
value_gen: Fn,
|
||||
) -> Result<Self, SynthesisError> {
|
||||
let value =
|
||||
<EdwardsBlsGadget as AllocGadget<GroupAffine<EdwardsParameters>, Fq>>::alloc_input(
|
||||
cs,
|
||||
|| Self::alloc_x_helper(value_gen),
|
||||
)?;
|
||||
let value = <EdwardsBlsGadget as AllocGadget<GroupAffine<EdwardsParameters>, Fq>>::alloc_input(cs, || {
|
||||
Self::alloc_x_helper(value_gen)
|
||||
})?;
|
||||
|
||||
Ok(EdwardsGroupType::Allocated(value))
|
||||
}
|
||||
@ -176,18 +153,12 @@ impl PartialEq for EdwardsGroupType {
|
||||
self_value.eq(other_value)
|
||||
}
|
||||
|
||||
(
|
||||
EdwardsGroupType::Constant(constant_value),
|
||||
EdwardsGroupType::Allocated(allocated_value),
|
||||
)
|
||||
| (
|
||||
EdwardsGroupType::Allocated(allocated_value),
|
||||
EdwardsGroupType::Constant(constant_value),
|
||||
) => <EdwardsBlsGadget as GroupGadget<GroupAffine<EdwardsParameters>, Fq>>::get_value(
|
||||
allocated_value,
|
||||
)
|
||||
(EdwardsGroupType::Constant(constant_value), EdwardsGroupType::Allocated(allocated_value))
|
||||
| (EdwardsGroupType::Allocated(allocated_value), EdwardsGroupType::Constant(constant_value)) => {
|
||||
<EdwardsBlsGadget as GroupGadget<GroupAffine<EdwardsParameters>, Fq>>::get_value(allocated_value)
|
||||
.map(|allocated_value| allocated_value == *constant_value)
|
||||
.unwrap_or(false),
|
||||
.unwrap_or(false)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -214,22 +185,11 @@ impl ConditionalEqGadget<Fq> for EdwardsGroupType {
|
||||
}
|
||||
// a - a
|
||||
(EdwardsGroupType::Allocated(self_value), EdwardsGroupType::Allocated(other_value)) => {
|
||||
<EdwardsBlsGadget>::conditional_enforce_equal(
|
||||
self_value,
|
||||
cs,
|
||||
other_value,
|
||||
condition,
|
||||
)
|
||||
<EdwardsBlsGadget>::conditional_enforce_equal(self_value, cs, other_value, condition)
|
||||
}
|
||||
// c - a = a - c
|
||||
(
|
||||
EdwardsGroupType::Constant(constant_value),
|
||||
EdwardsGroupType::Allocated(allocated_value),
|
||||
)
|
||||
| (
|
||||
EdwardsGroupType::Allocated(allocated_value),
|
||||
EdwardsGroupType::Constant(constant_value),
|
||||
) => {
|
||||
(EdwardsGroupType::Constant(constant_value), EdwardsGroupType::Allocated(allocated_value))
|
||||
| (EdwardsGroupType::Allocated(allocated_value), EdwardsGroupType::Constant(constant_value)) => {
|
||||
let x = FpGadget::from(&mut cs, &constant_value.x);
|
||||
let y = FpGadget::from(&mut cs, &constant_value.y);
|
||||
let constant_gadget = EdwardsBlsGadget::new(x, y);
|
||||
@ -252,16 +212,11 @@ impl CondSelectGadget<Fq> for EdwardsGroupType {
|
||||
second: &Self,
|
||||
) -> Result<Self, SynthesisError> {
|
||||
if let Boolean::Constant(cond) = *cond {
|
||||
if cond {
|
||||
Ok(first.clone())
|
||||
} else {
|
||||
Ok(second.clone())
|
||||
}
|
||||
if cond { Ok(first.clone()) } else { Ok(second.clone()) }
|
||||
} else {
|
||||
let first_gadget = first.allocated(&mut cs)?;
|
||||
let second_gadget = second.allocated(&mut cs)?;
|
||||
let result =
|
||||
EdwardsBlsGadget::conditionally_select(cs, cond, &first_gadget, &second_gadget)?;
|
||||
let result = EdwardsBlsGadget::conditionally_select(cs, cond, &first_gadget, &second_gadget)?;
|
||||
|
||||
Ok(EdwardsGroupType::Allocated(result))
|
||||
}
|
||||
@ -273,18 +228,12 @@ impl CondSelectGadget<Fq> for EdwardsGroupType {
|
||||
}
|
||||
|
||||
impl ToBitsGadget<Fq> for EdwardsGroupType {
|
||||
fn to_bits<CS: ConstraintSystem<Fq>>(
|
||||
&self,
|
||||
mut cs: CS,
|
||||
) -> Result<Vec<Boolean>, SynthesisError> {
|
||||
fn to_bits<CS: ConstraintSystem<Fq>>(&self, mut cs: CS) -> Result<Vec<Boolean>, SynthesisError> {
|
||||
let self_gadget = self.allocated(&mut cs)?;
|
||||
self_gadget.to_bits(cs)
|
||||
}
|
||||
|
||||
fn to_bits_strict<CS: ConstraintSystem<Fq>>(
|
||||
&self,
|
||||
mut cs: CS,
|
||||
) -> Result<Vec<Boolean>, SynthesisError> {
|
||||
fn to_bits_strict<CS: ConstraintSystem<Fq>>(&self, mut cs: CS) -> Result<Vec<Boolean>, SynthesisError> {
|
||||
let self_gadget = self.allocated(&mut cs)?;
|
||||
self_gadget.to_bits_strict(cs)
|
||||
}
|
||||
@ -296,10 +245,7 @@ impl ToBytesGadget<Fq> for EdwardsGroupType {
|
||||
self_gadget.to_bytes(cs)
|
||||
}
|
||||
|
||||
fn to_bytes_strict<CS: ConstraintSystem<Fq>>(
|
||||
&self,
|
||||
mut cs: CS,
|
||||
) -> Result<Vec<UInt8>, SynthesisError> {
|
||||
fn to_bytes_strict<CS: ConstraintSystem<Fq>>(&self, mut cs: CS) -> Result<Vec<UInt8>, SynthesisError> {
|
||||
let self_gadget = self.allocated(&mut cs)?;
|
||||
self_gadget.to_bytes_strict(cs)
|
||||
}
|
||||
|
@ -10,7 +10,8 @@ use snarkos_models::{
|
||||
alloc::AllocGadget,
|
||||
eq::{ConditionalEqGadget, EqGadget},
|
||||
select::CondSelectGadget,
|
||||
ToBitsGadget, ToBytesGadget,
|
||||
ToBitsGadget,
|
||||
ToBytesGadget,
|
||||
},
|
||||
},
|
||||
};
|
||||
|
@ -13,9 +13,12 @@ const DIRECTORY_NAME: &str = "tests/array/";
|
||||
fn output_ones(program: EdwardsTestCompiler) {
|
||||
let output = get_output(program);
|
||||
assert_eq!(
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Array(
|
||||
vec![ConstrainedValue::Integer(Integer::U32(UInt32::constant(1u32))); 3]
|
||||
)])
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Array(vec![
|
||||
ConstrainedValue::Integer(
|
||||
Integer::U32(UInt32::constant(1u32))
|
||||
);
|
||||
3
|
||||
])])
|
||||
.to_string(),
|
||||
output.to_string()
|
||||
);
|
||||
@ -46,9 +49,7 @@ fn fail_array(program: EdwardsTestCompiler) {
|
||||
|
||||
fn fail_synthesis(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::IntegerError(
|
||||
IntegerError::SynthesisError(_string),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::IntegerError(IntegerError::SynthesisError(_string))) => {}
|
||||
error => panic!("Expected synthesis error, got {}", error),
|
||||
}
|
||||
}
|
||||
@ -90,12 +91,7 @@ fn test_multi() {
|
||||
#[test]
|
||||
fn test_input_array() {
|
||||
let mut program = compile_program(DIRECTORY_NAME, "input_array.leo").unwrap();
|
||||
program.set_inputs(vec![Some(InputValue::Array(vec![
|
||||
InputValue::Integer(
|
||||
1u128
|
||||
);
|
||||
3
|
||||
]))]);
|
||||
program.set_inputs(vec![Some(InputValue::Array(vec![InputValue::Integer(1u128); 3]))]);
|
||||
output_ones(program)
|
||||
}
|
||||
|
||||
|
@ -12,10 +12,7 @@ const DIRECTORY_NAME: &str = "tests/boolean/";
|
||||
pub fn output_expected_boolean(program: EdwardsTestCompiler, boolean: bool) {
|
||||
let output = get_output(program);
|
||||
assert_eq!(
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Boolean(Boolean::Constant(
|
||||
boolean
|
||||
))])
|
||||
.to_string(),
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Boolean(Boolean::Constant(boolean))]).to_string(),
|
||||
output.to_string()
|
||||
);
|
||||
}
|
||||
@ -30,40 +27,32 @@ pub fn output_false(program: EdwardsTestCompiler) {
|
||||
|
||||
fn fail_evaluate(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::ExpressionError(ExpressionError::BooleanError(
|
||||
BooleanError::CannotEvaluate(_string),
|
||||
)),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError(
|
||||
ExpressionError::BooleanError(BooleanError::CannotEvaluate(_string)),
|
||||
))) => {}
|
||||
error => panic!("Expected evaluate error, got {}", error),
|
||||
}
|
||||
}
|
||||
|
||||
fn fail_enforce(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::ExpressionError(ExpressionError::BooleanError(
|
||||
BooleanError::CannotEnforce(_string),
|
||||
)),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError(
|
||||
ExpressionError::BooleanError(BooleanError::CannotEnforce(_string)),
|
||||
))) => {}
|
||||
error => panic!("Expected evaluate error, got {}", error),
|
||||
}
|
||||
}
|
||||
|
||||
fn fail_boolean(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::BooleanError(
|
||||
BooleanError::InvalidBoolean(_string),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::BooleanError(BooleanError::InvalidBoolean(_string))) => {}
|
||||
error => panic!("Expected invalid boolean error, got {}", error),
|
||||
}
|
||||
}
|
||||
|
||||
fn fail_synthesis(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::BooleanError(
|
||||
BooleanError::SynthesisError(_string),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::BooleanError(BooleanError::SynthesisError(_string))) => {}
|
||||
error => panic!("Expected synthesis error, got {}", error),
|
||||
}
|
||||
}
|
||||
|
@ -1,13 +1,17 @@
|
||||
use crate::{
|
||||
compile_program, get_error, get_output, integers::u32::output_one, EdwardsConstrainedValue,
|
||||
compile_program,
|
||||
get_error,
|
||||
get_output,
|
||||
integers::u32::output_one,
|
||||
EdwardsConstrainedValue,
|
||||
EdwardsTestCompiler,
|
||||
};
|
||||
use leo_compiler::{
|
||||
errors::{CompilerError, ExpressionError, FunctionError, StatementError},
|
||||
ConstrainedCircuitMember, ConstrainedValue,
|
||||
ConstrainedCircuitMember,
|
||||
ConstrainedValue,
|
||||
};
|
||||
use leo_types::{Expression, Function, Identifier, Integer,
|
||||
Statement, Type,};
|
||||
use leo_types::{Expression, Function, Identifier, Integer, Statement, Type};
|
||||
|
||||
use snarkos_models::gadgets::utilities::uint::UInt32;
|
||||
|
||||
@ -31,18 +35,18 @@ fn output_circuit(program: EdwardsTestCompiler) {
|
||||
|
||||
fn fail_expected_member(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::ExpressionError(ExpressionError::ExpectedCircuitMember(_string)),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError(
|
||||
ExpressionError::ExpectedCircuitMember(_string),
|
||||
))) => {}
|
||||
error => panic!("Expected invalid circuit member error, got {}", error),
|
||||
}
|
||||
}
|
||||
|
||||
fn fail_undefined_member(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::ExpressionError(ExpressionError::UndefinedMemberAccess(_, _)),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError(
|
||||
ExpressionError::UndefinedMemberAccess(_, _),
|
||||
))) => {}
|
||||
error => panic!("Expected undefined circuit member error, got {}", error),
|
||||
}
|
||||
}
|
||||
@ -65,9 +69,9 @@ fn test_inline_fail() {
|
||||
fn test_inline_undefined() {
|
||||
let program = compile_program(DIRECTORY_NAME, "inline_undefined.leo").unwrap();
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::ExpressionError(ExpressionError::UndefinedCircuit(_)),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError(
|
||||
ExpressionError::UndefinedCircuit(_),
|
||||
))) => {}
|
||||
error => panic!("Expected undefined circuit error, got {}", error),
|
||||
}
|
||||
}
|
||||
@ -102,9 +106,9 @@ fn test_member_function_fail() {
|
||||
fn test_member_function_invalid() {
|
||||
let program = compile_program(DIRECTORY_NAME, "member_function_invalid.leo").unwrap();
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::ExpressionError(ExpressionError::InvalidStaticAccess(_)),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError(
|
||||
ExpressionError::InvalidStaticAccess(_),
|
||||
))) => {}
|
||||
error => panic!("Expected invalid function error, got {}", error),
|
||||
}
|
||||
}
|
||||
@ -119,9 +123,9 @@ fn test_member_static_function() {
|
||||
fn test_member_static_function_undefined() {
|
||||
let program = compile_program(DIRECTORY_NAME, "member_static_function_undefined.leo").unwrap();
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::ExpressionError(ExpressionError::UndefinedStaticAccess(_, _)),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError(
|
||||
ExpressionError::UndefinedStaticAccess(_, _),
|
||||
))) => {}
|
||||
error => panic!("Expected undefined static function error, got {}", error),
|
||||
}
|
||||
}
|
||||
@ -129,9 +133,9 @@ fn test_member_static_function_undefined() {
|
||||
fn test_member_static_function_invalid() {
|
||||
let program = compile_program(DIRECTORY_NAME, "member_static_function_invalid.leo").unwrap();
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::ExpressionError(ExpressionError::InvalidMemberAccess(_)),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError(
|
||||
ExpressionError::InvalidMemberAccess(_),
|
||||
))) => {}
|
||||
error => panic!("Expected invalid static function error, got {}", error),
|
||||
}
|
||||
}
|
||||
|
@ -1,17 +1,26 @@
|
||||
use crate::boolean::{output_expected_boolean, output_false, output_true};
|
||||
use crate::{compile_program, get_error, get_output, EdwardsConstrainedValue, EdwardsTestCompiler};
|
||||
use crate::{
|
||||
boolean::{output_expected_boolean, output_false, output_true},
|
||||
compile_program,
|
||||
get_error,
|
||||
get_output,
|
||||
EdwardsConstrainedValue,
|
||||
EdwardsTestCompiler,
|
||||
};
|
||||
use leo_compiler::{
|
||||
errors::{CompilerError, FieldError, FunctionError},
|
||||
ConstrainedValue, FieldType,
|
||||
ConstrainedValue,
|
||||
FieldType,
|
||||
};
|
||||
use leo_types::InputValue;
|
||||
|
||||
use snarkos_curves::edwards_bls12::Fq;
|
||||
use snarkos_gadgets::curves::edwards_bls12::FqGadget;
|
||||
use snarkos_models::curves::{Field, PrimeField};
|
||||
use snarkos_models::gadgets::{
|
||||
use snarkos_models::{
|
||||
curves::{Field, PrimeField},
|
||||
gadgets::{
|
||||
curves::field::FieldGadget,
|
||||
r1cs::{ConstraintSystem, TestConstraintSystem},
|
||||
},
|
||||
};
|
||||
use snarkos_utilities::biginteger::BigInteger256;
|
||||
|
||||
@ -20,10 +29,7 @@ const DIRECTORY_NAME: &str = "tests/field/";
|
||||
fn output_expected_constant(program: EdwardsTestCompiler, expected: Fq) {
|
||||
let output = get_output(program);
|
||||
assert_eq!(
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Field(FieldType::Constant(
|
||||
expected
|
||||
))])
|
||||
.to_string(),
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Field(FieldType::Constant(expected))]).to_string(),
|
||||
output.to_string()
|
||||
);
|
||||
}
|
||||
@ -33,9 +39,7 @@ fn output_expected_allocated(program: EdwardsTestCompiler, expected: FqGadget) {
|
||||
|
||||
match output {
|
||||
EdwardsConstrainedValue::Return(vec) => match vec.as_slice() {
|
||||
[ConstrainedValue::Field(FieldType::Allocated(fp_gadget))] => {
|
||||
assert_eq!(*fp_gadget, expected as FqGadget)
|
||||
}
|
||||
[ConstrainedValue::Field(FieldType::Allocated(fp_gadget))] => assert_eq!(*fp_gadget, expected as FqGadget),
|
||||
_ => panic!("program output unknown return value"),
|
||||
},
|
||||
_ => panic!("program output unknown return value"),
|
||||
@ -59,9 +63,7 @@ fn fail_field(program: EdwardsTestCompiler) {
|
||||
|
||||
fn fail_synthesis(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::FieldError(FieldError::SynthesisError(
|
||||
_string,
|
||||
))) => {}
|
||||
CompilerError::FunctionError(FunctionError::FieldError(FieldError::SynthesisError(_string))) => {}
|
||||
error => panic!("Expected synthesis error, got {}", error),
|
||||
}
|
||||
}
|
||||
|
@ -1,5 +1,9 @@
|
||||
use crate::{
|
||||
compile_program, get_error, get_output, integers::u32::output_one, EdwardsConstrainedValue,
|
||||
compile_program,
|
||||
get_error,
|
||||
get_output,
|
||||
integers::u32::output_one,
|
||||
EdwardsConstrainedValue,
|
||||
EdwardsTestCompiler,
|
||||
};
|
||||
use leo_compiler::{
|
||||
@ -13,10 +17,7 @@ const DIRECTORY_NAME: &str = "tests/function/";
|
||||
|
||||
pub(crate) fn output_empty(program: EdwardsTestCompiler) {
|
||||
let output = get_output(program);
|
||||
assert_eq!(
|
||||
EdwardsConstrainedValue::Return(vec![]).to_string(),
|
||||
output.to_string()
|
||||
);
|
||||
assert_eq!(EdwardsConstrainedValue::Return(vec![]).to_string(), output.to_string());
|
||||
}
|
||||
|
||||
// (true, false)
|
||||
@ -34,9 +35,9 @@ pub(crate) fn output_multiple(program: EdwardsTestCompiler) {
|
||||
|
||||
fn fail_undefined_identifier(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::ExpressionError(ExpressionError::UndefinedIdentifier(_)),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError(
|
||||
ExpressionError::UndefinedIdentifier(_),
|
||||
))) => {}
|
||||
error => panic!("Expected function undefined, got {}", error),
|
||||
}
|
||||
}
|
||||
@ -67,12 +68,11 @@ fn test_undefined() {
|
||||
fn test_global_scope_fail() {
|
||||
let program = compile_program(DIRECTORY_NAME, "scope_fail.leo").unwrap();
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::ExpressionError(ExpressionError::FunctionError(value)),
|
||||
)) => match *value {
|
||||
FunctionError::StatementError(StatementError::ExpressionError(
|
||||
ExpressionError::UndefinedIdentifier(_),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError(
|
||||
ExpressionError::FunctionError(value),
|
||||
))) => match *value {
|
||||
FunctionError::StatementError(StatementError::ExpressionError(ExpressionError::UndefinedIdentifier(_))) => {
|
||||
}
|
||||
error => panic!("Expected function undefined, got {}", error),
|
||||
},
|
||||
error => panic!("Expected function undefined, got {}", error),
|
||||
|
@ -1,6 +1,10 @@
|
||||
use crate::{
|
||||
boolean::{output_false, output_true},
|
||||
compile_program, fail_enforce, get_output, EdwardsConstrainedValue, EdwardsTestCompiler,
|
||||
compile_program,
|
||||
fail_enforce,
|
||||
get_output,
|
||||
EdwardsConstrainedValue,
|
||||
EdwardsTestCompiler,
|
||||
};
|
||||
use leo_compiler::{group::edwards_bls12::EdwardsGroupType, ConstrainedValue};
|
||||
use leo_types::InputValue;
|
||||
@ -21,9 +25,7 @@ const TEST_POINT_2: &str = "(100584211797438414962237006104297858121134211165396
|
||||
fn output_expected_constant(program: EdwardsTestCompiler, expected: EdwardsAffine) {
|
||||
let output = get_output(program);
|
||||
assert_eq!(
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Group(EdwardsGroupType::Constant(
|
||||
expected
|
||||
))])
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Group(EdwardsGroupType::Constant(expected))])
|
||||
.to_string(),
|
||||
output.to_string()
|
||||
)
|
||||
@ -68,8 +70,7 @@ fn test_input() {
|
||||
let mut cs = TestConstraintSystem::<Fq>::new();
|
||||
let constant_point = EdwardsAffine::from_str(TEST_POINT_1).unwrap();
|
||||
let allocated_point =
|
||||
<EdwardsBlsGadget as AllocGadget<EdwardsAffine, Fq>>::alloc(&mut cs, || Ok(constant_point))
|
||||
.unwrap();
|
||||
<EdwardsBlsGadget as AllocGadget<EdwardsAffine, Fq>>::alloc(&mut cs, || Ok(constant_point)).unwrap();
|
||||
|
||||
output_expected_allocated(program, allocated_point);
|
||||
}
|
||||
@ -135,8 +136,7 @@ fn test_ternary() {
|
||||
let mut cs = TestConstraintSystem::<Fq>::new();
|
||||
let point_1 = EdwardsAffine::from_str(TEST_POINT_1).unwrap();
|
||||
let expected_point_1 =
|
||||
<EdwardsBlsGadget as AllocGadget<EdwardsAffine, Fq>>::alloc(&mut cs, || Ok(point_1))
|
||||
.unwrap();
|
||||
<EdwardsBlsGadget as AllocGadget<EdwardsAffine, Fq>>::alloc(&mut cs, || Ok(point_1)).unwrap();
|
||||
output_expected_allocated(program_1, expected_point_1);
|
||||
|
||||
// false -> point_2
|
||||
@ -145,7 +145,6 @@ fn test_ternary() {
|
||||
let mut cs = TestConstraintSystem::<Fq>::new();
|
||||
let point_2 = EdwardsAffine::from_str(TEST_POINT_2).unwrap();
|
||||
let expected_point_2 =
|
||||
<EdwardsBlsGadget as AllocGadget<EdwardsAffine, Fq>>::alloc(&mut cs, || Ok(point_2))
|
||||
.unwrap();
|
||||
<EdwardsBlsGadget as AllocGadget<EdwardsAffine, Fq>>::alloc(&mut cs, || Ok(point_2)).unwrap();
|
||||
output_expected_allocated(program_2, expected_point_2);
|
||||
}
|
||||
|
@ -48,18 +48,14 @@ pub trait IntegerTester {
|
||||
|
||||
pub(crate) fn fail_integer(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::IntegerError(
|
||||
IntegerError::InvalidInteger(_string),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::IntegerError(IntegerError::InvalidInteger(_string))) => {}
|
||||
error => panic!("Expected invalid boolean error, got {}", error),
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn fail_synthesis(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::IntegerError(
|
||||
IntegerError::SynthesisError(_string),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::IntegerError(IntegerError::SynthesisError(_string))) => {}
|
||||
error => panic!("Expected synthesis error, got {}", error),
|
||||
}
|
||||
}
|
||||
|
@ -1,15 +1,19 @@
|
||||
use crate::{
|
||||
boolean::{output_expected_boolean, output_false, output_true},
|
||||
compile_program, get_output,
|
||||
compile_program,
|
||||
get_output,
|
||||
integers::{fail_integer, fail_synthesis, IntegerTester},
|
||||
EdwardsConstrainedValue, EdwardsTestCompiler,
|
||||
EdwardsConstrainedValue,
|
||||
EdwardsTestCompiler,
|
||||
};
|
||||
use leo_compiler::ConstrainedValue;
|
||||
use leo_types::{Integer, InputValue};
|
||||
use leo_types::{InputValue, Integer};
|
||||
|
||||
use snarkos_curves::edwards_bls12::Fq;
|
||||
use snarkos_models::gadgets::r1cs::TestConstraintSystem;
|
||||
use snarkos_models::gadgets::utilities::{alloc::AllocGadget, uint::UInt128};
|
||||
use snarkos_models::gadgets::{
|
||||
r1cs::TestConstraintSystem,
|
||||
utilities::{alloc::AllocGadget, uint::UInt128},
|
||||
};
|
||||
|
||||
const DIRECTORY_NAME: &str = "tests/integers/u128/";
|
||||
|
||||
|
@ -1,15 +1,19 @@
|
||||
use crate::{
|
||||
boolean::{output_expected_boolean, output_false, output_true},
|
||||
compile_program, get_output,
|
||||
compile_program,
|
||||
get_output,
|
||||
integers::{fail_integer, fail_synthesis, IntegerTester},
|
||||
EdwardsConstrainedValue, EdwardsTestCompiler,
|
||||
EdwardsConstrainedValue,
|
||||
EdwardsTestCompiler,
|
||||
};
|
||||
use leo_compiler::ConstrainedValue;
|
||||
use leo_types::{Integer, InputValue};
|
||||
use leo_types::{InputValue, Integer};
|
||||
|
||||
use snarkos_curves::edwards_bls12::Fq;
|
||||
use snarkos_models::gadgets::r1cs::TestConstraintSystem;
|
||||
use snarkos_models::gadgets::utilities::{alloc::AllocGadget, uint::UInt16};
|
||||
use snarkos_models::gadgets::{
|
||||
r1cs::TestConstraintSystem,
|
||||
utilities::{alloc::AllocGadget, uint::UInt16},
|
||||
};
|
||||
|
||||
const DIRECTORY_NAME: &str = "tests/integers/u16/";
|
||||
|
||||
|
@ -1,15 +1,19 @@
|
||||
use crate::{
|
||||
boolean::{output_expected_boolean, output_false, output_true},
|
||||
compile_program, get_output,
|
||||
compile_program,
|
||||
get_output,
|
||||
integers::{fail_integer, fail_synthesis, IntegerTester},
|
||||
EdwardsConstrainedValue, EdwardsTestCompiler,
|
||||
EdwardsConstrainedValue,
|
||||
EdwardsTestCompiler,
|
||||
};
|
||||
use leo_compiler::ConstrainedValue;
|
||||
use leo_types::{Integer, InputValue};
|
||||
use leo_types::{InputValue, Integer};
|
||||
|
||||
use snarkos_curves::edwards_bls12::Fq;
|
||||
use snarkos_models::gadgets::r1cs::TestConstraintSystem;
|
||||
use snarkos_models::gadgets::utilities::{alloc::AllocGadget, uint::UInt32};
|
||||
use snarkos_models::gadgets::{
|
||||
r1cs::TestConstraintSystem,
|
||||
utilities::{alloc::AllocGadget, uint::UInt32},
|
||||
};
|
||||
|
||||
const DIRECTORY_NAME: &str = "tests/integers/u32/";
|
||||
|
||||
@ -28,9 +32,7 @@ fn output_expected_allocated(program: EdwardsTestCompiler, expected: UInt32) {
|
||||
pub(crate) fn output_zero(program: EdwardsTestCompiler) {
|
||||
let output = get_output(program);
|
||||
assert_eq!(
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Integer(Integer::U32(
|
||||
UInt32::constant(0u32)
|
||||
))])
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Integer(Integer::U32(UInt32::constant(0u32)))])
|
||||
.to_string(),
|
||||
output.to_string()
|
||||
)
|
||||
@ -39,9 +41,7 @@ pub(crate) fn output_zero(program: EdwardsTestCompiler) {
|
||||
pub(crate) fn output_one(program: EdwardsTestCompiler) {
|
||||
let output = get_output(program);
|
||||
assert_eq!(
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Integer(Integer::U32(
|
||||
UInt32::constant(1u32)
|
||||
))])
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Integer(Integer::U32(UInt32::constant(1u32)))])
|
||||
.to_string(),
|
||||
output.to_string()
|
||||
)
|
||||
|
@ -1,15 +1,19 @@
|
||||
use crate::{
|
||||
boolean::{output_expected_boolean, output_false, output_true},
|
||||
compile_program, get_output,
|
||||
compile_program,
|
||||
get_output,
|
||||
integers::{fail_integer, fail_synthesis, IntegerTester},
|
||||
EdwardsConstrainedValue, EdwardsTestCompiler,
|
||||
EdwardsConstrainedValue,
|
||||
EdwardsTestCompiler,
|
||||
};
|
||||
use leo_compiler::ConstrainedValue;
|
||||
use leo_types::{Integer, InputValue};
|
||||
use leo_types::{InputValue, Integer};
|
||||
|
||||
use snarkos_curves::edwards_bls12::Fq;
|
||||
use snarkos_models::gadgets::r1cs::TestConstraintSystem;
|
||||
use snarkos_models::gadgets::utilities::{alloc::AllocGadget, uint::UInt64};
|
||||
use snarkos_models::gadgets::{
|
||||
r1cs::TestConstraintSystem,
|
||||
utilities::{alloc::AllocGadget, uint::UInt64},
|
||||
};
|
||||
|
||||
const DIRECTORY_NAME: &str = "tests/integers/u64/";
|
||||
|
||||
|
@ -1,15 +1,19 @@
|
||||
use crate::{
|
||||
boolean::{output_expected_boolean, output_false, output_true},
|
||||
compile_program, get_output,
|
||||
compile_program,
|
||||
get_output,
|
||||
integers::{fail_integer, fail_synthesis, IntegerTester},
|
||||
EdwardsConstrainedValue, EdwardsTestCompiler,
|
||||
EdwardsConstrainedValue,
|
||||
EdwardsTestCompiler,
|
||||
};
|
||||
use leo_compiler::ConstrainedValue;
|
||||
use leo_types::{Integer, InputValue};
|
||||
use leo_types::{InputValue, Integer};
|
||||
|
||||
use snarkos_curves::edwards_bls12::Fq;
|
||||
use snarkos_models::gadgets::r1cs::TestConstraintSystem;
|
||||
use snarkos_models::gadgets::utilities::{alloc::AllocGadget, uint::UInt8};
|
||||
use snarkos_models::gadgets::{
|
||||
r1cs::TestConstraintSystem,
|
||||
utilities::{alloc::AllocGadget, uint::UInt8},
|
||||
};
|
||||
|
||||
const DIRECTORY_NAME: &str = "tests/integers/u8/";
|
||||
|
||||
|
@ -38,17 +38,12 @@ pub(crate) fn get_error(program: EdwardsTestCompiler) -> CompilerError {
|
||||
|
||||
pub(crate) fn fail_enforce(program: EdwardsTestCompiler) {
|
||||
match get_error(program) {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::AssertionFailed(_, _),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::AssertionFailed(_, _))) => {}
|
||||
error => panic!("Expected evaluate error, got {}", error),
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn compile_program(
|
||||
directory_name: &str,
|
||||
file_name: &str,
|
||||
) -> Result<EdwardsTestCompiler, CompilerError> {
|
||||
pub(crate) fn compile_program(directory_name: &str, file_name: &str) -> Result<EdwardsTestCompiler, CompilerError> {
|
||||
let path = current_dir().map_err(|error| CompilerError::DirectoryError(error))?;
|
||||
|
||||
// Sanitize the package path to the test directory
|
||||
|
@ -16,10 +16,7 @@ fn mut_success(program: EdwardsTestCompiler) {
|
||||
|
||||
assert!(cs.is_satisfied());
|
||||
assert_eq!(
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Integer(Integer::U32(
|
||||
UInt32::constant(0)
|
||||
))])
|
||||
.to_string(),
|
||||
EdwardsConstrainedValue::Return(vec![ConstrainedValue::Integer(Integer::U32(UInt32::constant(0)))]).to_string(),
|
||||
output.to_string()
|
||||
);
|
||||
}
|
||||
@ -31,9 +28,7 @@ fn mut_fail(program: EdwardsTestCompiler) {
|
||||
// It would be ideal if assert_eq!(Error1, Error2) were possible but unfortunately it is not due to
|
||||
// https://github.com/rust-lang/rust/issues/34158#issuecomment-224910299
|
||||
match err {
|
||||
CompilerError::FunctionError(FunctionError::StatementError(
|
||||
StatementError::ImmutableAssign(_string),
|
||||
)) => {}
|
||||
CompilerError::FunctionError(FunctionError::StatementError(StatementError::ImmutableAssign(_string))) => {}
|
||||
err => panic!("Expected immutable assign error, got {}", err),
|
||||
}
|
||||
}
|
||||
|
@ -41,9 +41,7 @@ fn test_assertion_basic() {
|
||||
let mut cs_satisfied = TestConstraintSystem::<Fq>::new();
|
||||
|
||||
program_input_true.set_inputs(vec![Some(InputValue::Boolean(true))]);
|
||||
let _output = program_input_true
|
||||
.compile_constraints(&mut cs_satisfied)
|
||||
.unwrap();
|
||||
let _output = program_input_true.compile_constraints(&mut cs_satisfied).unwrap();
|
||||
|
||||
assert!(cs_satisfied.is_satisfied());
|
||||
|
||||
@ -51,9 +49,7 @@ fn test_assertion_basic() {
|
||||
let mut cs_unsatisfied = TestConstraintSystem::<Fq>::new();
|
||||
|
||||
program_input_false.set_inputs(vec![Some(InputValue::Boolean(false))]);
|
||||
let _output = program_input_false
|
||||
.compile_constraints(&mut cs_unsatisfied)
|
||||
.unwrap();
|
||||
let _output = program_input_false.compile_constraints(&mut cs_unsatisfied).unwrap();
|
||||
|
||||
assert!(!cs_unsatisfied.is_satisfied());
|
||||
}
|
||||
|
@ -5,9 +5,7 @@ const DIRECTORY_NAME: &str = "tests/syntax/";
|
||||
|
||||
#[test]
|
||||
fn test_semicolon() {
|
||||
let error = compile_program(DIRECTORY_NAME, "semicolon.leo")
|
||||
.err()
|
||||
.unwrap();
|
||||
let error = compile_program(DIRECTORY_NAME, "semicolon.leo").err().unwrap();
|
||||
|
||||
match error {
|
||||
CompilerError::ParserError(_) => {}
|
||||
|
11
leo/cli.rs
11
leo/cli.rs
@ -1,5 +1,4 @@
|
||||
use crate::cli_types::*;
|
||||
use crate::errors::CLIError;
|
||||
use crate::{cli_types::*, errors::CLIError};
|
||||
|
||||
use clap::{App, AppSettings, Arg, ArgMatches, SubCommand};
|
||||
|
||||
@ -31,9 +30,7 @@ pub trait CLI {
|
||||
.conflicts_with_all(a.1)
|
||||
.possible_values(a.2)
|
||||
.requires_all(a.3),
|
||||
false => Arg::from_usage(a.0)
|
||||
.conflicts_with_all(a.1)
|
||||
.requires_all(a.3),
|
||||
false => Arg::from_usage(a.0).conflicts_with_all(a.1).requires_all(a.3),
|
||||
})
|
||||
.collect::<Vec<Arg<'static, 'static>>>();
|
||||
let subcommands = Self::SUBCOMMANDS
|
||||
@ -48,9 +45,7 @@ pub trait CLI {
|
||||
.conflicts_with_all(a.1)
|
||||
.possible_values(a.2)
|
||||
.requires_all(a.3),
|
||||
false => Arg::from_usage(a.0)
|
||||
.conflicts_with_all(a.1)
|
||||
.requires_all(a.3),
|
||||
false => Arg::from_usage(a.0).conflicts_with_all(a.1).requires_all(a.3),
|
||||
})
|
||||
.collect::<Vec<Arg<'static, 'static>>>(),
|
||||
)
|
||||
|
@ -21,9 +21,4 @@ pub type OptionType = (
|
||||
&'static [&'static str],
|
||||
);
|
||||
|
||||
pub type SubCommandType = (
|
||||
NameType,
|
||||
AboutType,
|
||||
&'static [OptionType],
|
||||
&'static [AppSettings],
|
||||
);
|
||||
pub type SubCommandType = (NameType, AboutType, &'static [OptionType], &'static [AppSettings]);
|
||||
|
@ -1,15 +1,17 @@
|
||||
use crate::directories::{source::SOURCE_DIRECTORY_NAME, OutputsDirectory};
|
||||
use crate::errors::{BuildError, CLIError};
|
||||
use crate::files::{ChecksumFile, MainFile, Manifest, MAIN_FILE_NAME};
|
||||
use crate::{cli::*, cli_types::*};
|
||||
use crate::{
|
||||
cli::*,
|
||||
cli_types::*,
|
||||
directories::{source::SOURCE_DIRECTORY_NAME, OutputsDirectory},
|
||||
errors::{BuildError, CLIError},
|
||||
files::{ChecksumFile, MainFile, Manifest, MAIN_FILE_NAME},
|
||||
};
|
||||
use leo_compiler::{compiler::Compiler, group::edwards_bls12::EdwardsGroupType};
|
||||
|
||||
use snarkos_algorithms::snark::KeypairAssembly;
|
||||
use snarkos_curves::{bls12_377::Bls12_377, edwards_bls12::Fq};
|
||||
|
||||
use clap::ArgMatches;
|
||||
use std::convert::TryFrom;
|
||||
use std::env::current_dir;
|
||||
use std::{convert::TryFrom, env::current_dir};
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct BuildCommand;
|
||||
@ -18,10 +20,10 @@ impl CLI for BuildCommand {
|
||||
type Options = ();
|
||||
type Output = (Compiler<Fq, EdwardsGroupType>, bool);
|
||||
|
||||
const NAME: NameType = "build";
|
||||
const ABOUT: AboutType = "Compile the current package as a program";
|
||||
const ARGUMENTS: &'static [ArgumentType] = &[];
|
||||
const FLAGS: &'static [FlagType] = &[];
|
||||
const NAME: NameType = "build";
|
||||
const OPTIONS: &'static [OptionType] = &[];
|
||||
const SUBCOMMANDS: &'static [SubCommandType] = &[];
|
||||
|
||||
@ -46,9 +48,7 @@ impl CLI for BuildCommand {
|
||||
|
||||
// Verify the main file exists
|
||||
if !MainFile::exists_at(&package_path) {
|
||||
return Err(
|
||||
BuildError::MainFileDoesNotExist(package_path.as_os_str().to_owned()).into(),
|
||||
);
|
||||
return Err(BuildError::MainFileDoesNotExist(package_path.as_os_str().to_owned()).into());
|
||||
}
|
||||
|
||||
// Create the outputs directory
|
||||
@ -60,8 +60,7 @@ impl CLI for BuildCommand {
|
||||
main_file_path.push(MAIN_FILE_NAME);
|
||||
|
||||
// Compute the current program checksum
|
||||
let program =
|
||||
Compiler::<Fq, EdwardsGroupType>::init(package_name.clone(), main_file_path.clone())?;
|
||||
let program = Compiler::<Fq, EdwardsGroupType>::init(package_name.clone(), main_file_path.clone())?;
|
||||
let program_checksum = program.checksum()?;
|
||||
|
||||
// Generate the program on the constraint system and verify correctness
|
||||
|
@ -1,11 +1,7 @@
|
||||
use crate::commands::BuildCommand;
|
||||
use crate::errors::CLIError;
|
||||
use crate::files::Manifest;
|
||||
use crate::{cli::*, cli_types::*};
|
||||
use crate::{cli::*, cli_types::*, commands::BuildCommand, errors::CLIError, files::Manifest};
|
||||
|
||||
use clap::ArgMatches;
|
||||
use std::convert::TryFrom;
|
||||
use std::env::current_dir;
|
||||
use std::{convert::TryFrom, env::current_dir};
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct DeployCommand;
|
||||
@ -14,10 +10,10 @@ impl CLI for DeployCommand {
|
||||
type Options = ();
|
||||
type Output = ();
|
||||
|
||||
const NAME: NameType = "deploy";
|
||||
const ABOUT: AboutType = "Deploy the current package as a program to the network (*)";
|
||||
const ARGUMENTS: &'static [ArgumentType] = &[];
|
||||
const FLAGS: &'static [FlagType] = &[];
|
||||
const NAME: NameType = "deploy";
|
||||
const OPTIONS: &'static [OptionType] = &[];
|
||||
const SUBCOMMANDS: &'static [SubCommandType] = &[];
|
||||
|
||||
|
@ -1,7 +1,10 @@
|
||||
use crate::directories::{InputsDirectory, SourceDirectory};
|
||||
use crate::errors::{CLIError, InitError};
|
||||
use crate::files::{Gitignore, MainFile, Manifest};
|
||||
use crate::{cli::*, cli_types::*};
|
||||
use crate::{
|
||||
cli::*,
|
||||
cli_types::*,
|
||||
directories::{InputsDirectory, SourceDirectory},
|
||||
errors::{CLIError, InitError},
|
||||
files::{Gitignore, MainFile, Manifest},
|
||||
};
|
||||
|
||||
use clap::ArgMatches;
|
||||
use std::env::current_dir;
|
||||
@ -13,10 +16,10 @@ impl CLI for InitCommand {
|
||||
type Options = Option<String>;
|
||||
type Output = ();
|
||||
|
||||
const NAME: NameType = "init";
|
||||
const ABOUT: AboutType = "Create a new Leo package in an existing directory";
|
||||
const ARGUMENTS: &'static [ArgumentType] = &[];
|
||||
const FLAGS: &'static [FlagType] = &[];
|
||||
const NAME: NameType = "init";
|
||||
const OPTIONS: &'static [OptionType] = &[];
|
||||
const SUBCOMMANDS: &'static [SubCommandType] = &[];
|
||||
|
||||
|
@ -1,11 +1,7 @@
|
||||
use crate::commands::BuildCommand;
|
||||
use crate::errors::CLIError;
|
||||
use crate::files::Manifest;
|
||||
use crate::{cli::*, cli_types::*};
|
||||
use crate::{cli::*, cli_types::*, commands::BuildCommand, errors::CLIError, files::Manifest};
|
||||
|
||||
use clap::ArgMatches;
|
||||
use std::convert::TryFrom;
|
||||
use std::env::current_dir;
|
||||
use std::{convert::TryFrom, env::current_dir};
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct LoadCommand;
|
||||
@ -14,10 +10,10 @@ impl CLI for LoadCommand {
|
||||
type Options = ();
|
||||
type Output = ();
|
||||
|
||||
const NAME: NameType = "load";
|
||||
const ABOUT: AboutType = "Install a package from the package manager (*)";
|
||||
const ARGUMENTS: &'static [ArgumentType] = &[];
|
||||
const FLAGS: &'static [FlagType] = &[];
|
||||
const NAME: NameType = "load";
|
||||
const OPTIONS: &'static [OptionType] = &[];
|
||||
const SUBCOMMANDS: &'static [SubCommandType] = &[];
|
||||
|
||||
|
@ -1,11 +1,13 @@
|
||||
use crate::directories::{InputsDirectory, SourceDirectory};
|
||||
use crate::errors::{CLIError, NewError};
|
||||
use crate::files::{Gitignore, MainFile, Manifest};
|
||||
use crate::{cli::*, cli_types::*};
|
||||
use crate::{
|
||||
cli::*,
|
||||
cli_types::*,
|
||||
directories::{InputsDirectory, SourceDirectory},
|
||||
errors::{CLIError, NewError},
|
||||
files::{Gitignore, MainFile, Manifest},
|
||||
};
|
||||
|
||||
use clap::ArgMatches;
|
||||
use std::env::current_dir;
|
||||
use std::fs;
|
||||
use std::{env::current_dir, fs};
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct NewCommand;
|
||||
@ -14,7 +16,6 @@ impl CLI for NewCommand {
|
||||
type Options = Option<String>;
|
||||
type Output = ();
|
||||
|
||||
const NAME: NameType = "new";
|
||||
const ABOUT: AboutType = "Create a new Leo package in a new directory";
|
||||
const ARGUMENTS: &'static [ArgumentType] = &[
|
||||
// (name, description, required, index)
|
||||
@ -26,6 +27,7 @@ impl CLI for NewCommand {
|
||||
),
|
||||
];
|
||||
const FLAGS: &'static [FlagType] = &[];
|
||||
const NAME: NameType = "new";
|
||||
const OPTIONS: &'static [OptionType] = &[];
|
||||
const SUBCOMMANDS: &'static [SubCommandType] = &[];
|
||||
|
||||
|
@ -1,16 +1,17 @@
|
||||
use crate::commands::SetupCommand;
|
||||
use crate::errors::CLIError;
|
||||
use crate::files::{Manifest, ProofFile};
|
||||
use crate::{cli::*, cli_types::*};
|
||||
use crate::{
|
||||
cli::*,
|
||||
cli_types::*,
|
||||
commands::SetupCommand,
|
||||
errors::CLIError,
|
||||
files::{Manifest, ProofFile},
|
||||
};
|
||||
|
||||
use snarkos_algorithms::snark::{create_random_proof, Proof};
|
||||
use snarkos_curves::bls12_377::Bls12_377;
|
||||
|
||||
use clap::ArgMatches;
|
||||
use rand::thread_rng;
|
||||
use std::convert::TryFrom;
|
||||
use std::env::current_dir;
|
||||
use std::time::Instant;
|
||||
use std::{convert::TryFrom, env::current_dir, time::Instant};
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct ProveCommand;
|
||||
@ -19,10 +20,10 @@ impl CLI for ProveCommand {
|
||||
type Options = ();
|
||||
type Output = Proof<Bls12_377>;
|
||||
|
||||
const NAME: NameType = "prove";
|
||||
const ABOUT: AboutType = "Run the program and produce a proof";
|
||||
const ARGUMENTS: &'static [ArgumentType] = &[];
|
||||
const FLAGS: &'static [FlagType] = &[];
|
||||
const NAME: NameType = "prove";
|
||||
const OPTIONS: &'static [OptionType] = &[];
|
||||
const SUBCOMMANDS: &'static [SubCommandType] = &[];
|
||||
|
||||
@ -45,10 +46,7 @@ impl CLI for ProveCommand {
|
||||
let rng = &mut thread_rng();
|
||||
let program_proof = create_random_proof(program, ¶meters, rng).unwrap();
|
||||
|
||||
log::info!(
|
||||
"Prover completed in {:?} milliseconds",
|
||||
start.elapsed().as_millis()
|
||||
);
|
||||
log::info!("Prover completed in {:?} milliseconds", start.elapsed().as_millis());
|
||||
|
||||
// Write the proof file to the outputs directory
|
||||
let mut proof = vec![];
|
||||
|
@ -1,11 +1,7 @@
|
||||
use crate::commands::BuildCommand;
|
||||
use crate::errors::CLIError;
|
||||
use crate::files::Manifest;
|
||||
use crate::{cli::*, cli_types::*};
|
||||
use crate::{cli::*, cli_types::*, commands::BuildCommand, errors::CLIError, files::Manifest};
|
||||
|
||||
use clap::ArgMatches;
|
||||
use std::convert::TryFrom;
|
||||
use std::env::current_dir;
|
||||
use std::{convert::TryFrom, env::current_dir};
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct PublishCommand;
|
||||
@ -14,10 +10,10 @@ impl CLI for PublishCommand {
|
||||
type Options = ();
|
||||
type Output = ();
|
||||
|
||||
const NAME: NameType = "publish";
|
||||
const ABOUT: AboutType = "Publish the current package to the package manager (*)";
|
||||
const ARGUMENTS: &'static [ArgumentType] = &[];
|
||||
const FLAGS: &'static [FlagType] = &[];
|
||||
const NAME: NameType = "publish";
|
||||
const OPTIONS: &'static [OptionType] = &[];
|
||||
const SUBCOMMANDS: &'static [SubCommandType] = &[];
|
||||
|
||||
|
@ -1,6 +1,9 @@
|
||||
use crate::commands::{ProveCommand, SetupCommand};
|
||||
use crate::errors::CLIError;
|
||||
use crate::{cli::*, cli_types::*};
|
||||
use crate::{
|
||||
cli::*,
|
||||
cli_types::*,
|
||||
commands::{ProveCommand, SetupCommand},
|
||||
errors::CLIError,
|
||||
};
|
||||
|
||||
use snarkos_algorithms::snark::verify_proof;
|
||||
|
||||
@ -14,10 +17,10 @@ impl CLI for RunCommand {
|
||||
type Options = ();
|
||||
type Output = ();
|
||||
|
||||
const NAME: NameType = "run";
|
||||
const ABOUT: AboutType = "Run a program with inputs";
|
||||
const ARGUMENTS: &'static [ArgumentType] = &[];
|
||||
const FLAGS: &'static [FlagType] = &[];
|
||||
const NAME: NameType = "run";
|
||||
const OPTIONS: &'static [OptionType] = &[];
|
||||
const SUBCOMMANDS: &'static [SubCommandType] = &[];
|
||||
|
||||
@ -42,10 +45,7 @@ impl CLI for RunCommand {
|
||||
verifying += start.elapsed();
|
||||
|
||||
println!(" ");
|
||||
println!(
|
||||
" Verifier time : {:?} milliseconds",
|
||||
verifying.as_millis()
|
||||
);
|
||||
println!(" Verifier time : {:?} milliseconds", verifying.as_millis());
|
||||
println!(" Verifier output : {}", is_success);
|
||||
println!(" ");
|
||||
|
||||
|
@ -1,20 +1,19 @@
|
||||
use crate::commands::BuildCommand;
|
||||
use crate::errors::{CLIError, VerificationKeyFileError};
|
||||
use crate::files::{Manifest, ProvingKeyFile, VerificationKeyFile};
|
||||
use crate::{cli::*, cli_types::*};
|
||||
use crate::{
|
||||
cli::*,
|
||||
cli_types::*,
|
||||
commands::BuildCommand,
|
||||
errors::{CLIError, VerificationKeyFileError},
|
||||
files::{Manifest, ProvingKeyFile, VerificationKeyFile},
|
||||
};
|
||||
use leo_compiler::{compiler::Compiler, group::edwards_bls12::EdwardsGroupType};
|
||||
|
||||
use snarkos_algorithms::snark::{
|
||||
generate_random_parameters, prepare_verifying_key, Parameters, PreparedVerifyingKey,
|
||||
};
|
||||
use snarkos_algorithms::snark::{generate_random_parameters, prepare_verifying_key, Parameters, PreparedVerifyingKey};
|
||||
use snarkos_curves::{bls12_377::Bls12_377, edwards_bls12::Fq};
|
||||
use snarkos_utilities::bytes::ToBytes;
|
||||
|
||||
use clap::ArgMatches;
|
||||
use rand::thread_rng;
|
||||
use std::convert::TryFrom;
|
||||
use std::env::current_dir;
|
||||
use std::time::Instant;
|
||||
use std::{convert::TryFrom, env::current_dir, time::Instant};
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct SetupCommand;
|
||||
@ -27,10 +26,10 @@ impl CLI for SetupCommand {
|
||||
PreparedVerifyingKey<Bls12_377>,
|
||||
);
|
||||
|
||||
const NAME: NameType = "setup";
|
||||
const ABOUT: AboutType = "Run a program setup";
|
||||
const ARGUMENTS: &'static [ArgumentType] = &[];
|
||||
const FLAGS: &'static [FlagType] = &[];
|
||||
const NAME: NameType = "setup";
|
||||
const OPTIONS: &'static [OptionType] = &[];
|
||||
const SUBCOMMANDS: &'static [SubCommandType] = &[];
|
||||
|
||||
@ -58,15 +57,11 @@ impl CLI for SetupCommand {
|
||||
|
||||
// Run the program setup operation
|
||||
let rng = &mut thread_rng();
|
||||
let parameters =
|
||||
generate_random_parameters::<Bls12_377, _, _>(program.clone(), rng).unwrap();
|
||||
let parameters = generate_random_parameters::<Bls12_377, _, _>(program.clone(), rng).unwrap();
|
||||
let prepared_verifying_key = prepare_verifying_key::<Bls12_377>(¶meters.vk);
|
||||
|
||||
// End the timer
|
||||
log::info!(
|
||||
"Setup completed in {:?} milliseconds",
|
||||
start.elapsed().as_millis()
|
||||
);
|
||||
log::info!("Setup completed in {:?} milliseconds", start.elapsed().as_millis());
|
||||
|
||||
// TODO (howardwu): Convert parameters to a 'proving key' struct for serialization.
|
||||
// Write the proving key file to the outputs directory
|
||||
@ -95,10 +90,7 @@ impl CLI for SetupCommand {
|
||||
prepared_verifying_key.write(&mut verification_key)?;
|
||||
|
||||
// Check that the constructed prepared verification key matches the stored verification key
|
||||
let compare: Vec<(u8, u8)> = verification_key
|
||||
.into_iter()
|
||||
.zip(stored_vk.into_iter())
|
||||
.collect();
|
||||
let compare: Vec<(u8, u8)> = verification_key.into_iter().zip(stored_vk.into_iter()).collect();
|
||||
for (a, b) in compare {
|
||||
if a != b {
|
||||
return Err(VerificationKeyFileError::IncorrectVerificationKey.into());
|
||||
|
@ -1,16 +1,17 @@
|
||||
use crate::directories::source::SOURCE_DIRECTORY_NAME;
|
||||
use crate::errors::{CLIError, TestError};
|
||||
use crate::files::{MainFile, Manifest, MAIN_FILE_NAME};
|
||||
use crate::{cli::*, cli_types::*};
|
||||
use leo_compiler::compiler::Compiler;
|
||||
use leo_compiler::group::edwards_bls12::EdwardsGroupType;
|
||||
use crate::{
|
||||
cli::*,
|
||||
cli_types::*,
|
||||
directories::source::SOURCE_DIRECTORY_NAME,
|
||||
errors::{CLIError, TestError},
|
||||
files::{MainFile, Manifest, MAIN_FILE_NAME},
|
||||
};
|
||||
use leo_compiler::{compiler::Compiler, group::edwards_bls12::EdwardsGroupType};
|
||||
|
||||
use snarkos_curves::edwards_bls12::Fq;
|
||||
use snarkos_models::gadgets::r1cs::TestConstraintSystem;
|
||||
|
||||
use clap::ArgMatches;
|
||||
use std::convert::TryFrom;
|
||||
use std::env::current_dir;
|
||||
use std::{convert::TryFrom, env::current_dir};
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct TestCommand;
|
||||
@ -19,10 +20,10 @@ impl CLI for TestCommand {
|
||||
type Options = ();
|
||||
type Output = ();
|
||||
|
||||
const NAME: NameType = "test";
|
||||
const ABOUT: AboutType = "Compile and run all tests in the current package";
|
||||
const ARGUMENTS: &'static [ArgumentType] = &[];
|
||||
const FLAGS: &'static [FlagType] = &[];
|
||||
const NAME: NameType = "test";
|
||||
const OPTIONS: &'static [OptionType] = &[];
|
||||
const SUBCOMMANDS: &'static [SubCommandType] = &[];
|
||||
|
||||
@ -47,9 +48,7 @@ impl CLI for TestCommand {
|
||||
|
||||
// Verify the main file exists
|
||||
if !MainFile::exists_at(&package_path) {
|
||||
return Err(
|
||||
TestError::MainFileDoesNotExist(package_path.as_os_str().to_owned()).into(),
|
||||
);
|
||||
return Err(TestError::MainFileDoesNotExist(package_path.as_os_str().to_owned()).into());
|
||||
}
|
||||
|
||||
// Construct the path to the main file in the source directory
|
||||
@ -58,8 +57,7 @@ impl CLI for TestCommand {
|
||||
main_file_path.push(MAIN_FILE_NAME);
|
||||
|
||||
// Compute the current program checksum
|
||||
let program =
|
||||
Compiler::<Fq, EdwardsGroupType>::init(package_name.clone(), main_file_path.clone())?;
|
||||
let program = Compiler::<Fq, EdwardsGroupType>::init(package_name.clone(), main_file_path.clone())?;
|
||||
|
||||
// Generate the program on the constraint system and verify correctness
|
||||
{
|
||||
|
@ -1,11 +1,7 @@
|
||||
use crate::commands::BuildCommand;
|
||||
use crate::errors::CLIError;
|
||||
use crate::files::Manifest;
|
||||
use crate::{cli::*, cli_types::*};
|
||||
use crate::{cli::*, cli_types::*, commands::BuildCommand, errors::CLIError, files::Manifest};
|
||||
|
||||
use clap::ArgMatches;
|
||||
use std::convert::TryFrom;
|
||||
use std::env::current_dir;
|
||||
use std::{convert::TryFrom, env::current_dir};
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct UnloadCommand;
|
||||
@ -14,10 +10,10 @@ impl CLI for UnloadCommand {
|
||||
type Options = ();
|
||||
type Output = ();
|
||||
|
||||
const NAME: NameType = "unload";
|
||||
const ABOUT: AboutType = "Uninstall a package from the current package (*)";
|
||||
const ARGUMENTS: &'static [ArgumentType] = &[];
|
||||
const FLAGS: &'static [FlagType] = &[];
|
||||
const NAME: NameType = "unload";
|
||||
const OPTIONS: &'static [OptionType] = &[];
|
||||
const SUBCOMMANDS: &'static [SubCommandType] = &[];
|
||||
|
||||
|
@ -1,7 +1,6 @@
|
||||
use crate::errors::InputsDirectoryError;
|
||||
|
||||
use std::fs;
|
||||
use std::path::PathBuf;
|
||||
use std::{fs, path::PathBuf};
|
||||
|
||||
pub(crate) static INPUTS_DIRECTORY_NAME: &str = "inputs/";
|
||||
|
||||
@ -32,9 +31,9 @@ impl InputsDirectory {
|
||||
let file_path = file_entry.path();
|
||||
|
||||
// Verify that the entry is structured as a valid file
|
||||
let file_type = file_entry.file_type().map_err(|error| {
|
||||
InputsDirectoryError::GettingFileType(file_path.as_os_str().to_owned(), error)
|
||||
})?;
|
||||
let file_type = file_entry
|
||||
.file_type()
|
||||
.map_err(|error| InputsDirectoryError::GettingFileType(file_path.as_os_str().to_owned(), error))?;
|
||||
if !file_type.is_file() {
|
||||
return Err(InputsDirectoryError::InvalidFileType(
|
||||
file_path.as_os_str().to_owned(),
|
||||
@ -43,9 +42,9 @@ impl InputsDirectory {
|
||||
}
|
||||
|
||||
// Verify that the file has the default file extension
|
||||
let file_extension = file_path.extension().ok_or_else(|| {
|
||||
InputsDirectoryError::GettingFileExtension(file_path.as_os_str().to_owned())
|
||||
})?;
|
||||
let file_extension = file_path
|
||||
.extension()
|
||||
.ok_or_else(|| InputsDirectoryError::GettingFileExtension(file_path.as_os_str().to_owned()))?;
|
||||
if file_extension != INPUTS_FILE_EXTENSION {
|
||||
return Err(InputsDirectoryError::InvalidFileExtension(
|
||||
file_path.as_os_str().to_owned(),
|
||||
|
@ -1,7 +1,6 @@
|
||||
use crate::errors::OutputsDirectoryError;
|
||||
|
||||
use std::fs;
|
||||
use std::path::PathBuf;
|
||||
use std::{fs, path::PathBuf};
|
||||
|
||||
pub(crate) static OUTPUTS_DIRECTORY_NAME: &str = "outputs/";
|
||||
|
||||
|
@ -1,7 +1,6 @@
|
||||
use crate::errors::SourceDirectoryError;
|
||||
|
||||
use std::fs;
|
||||
use std::path::PathBuf;
|
||||
use std::{fs, path::PathBuf};
|
||||
|
||||
pub(crate) static SOURCE_DIRECTORY_NAME: &str = "src/";
|
||||
|
||||
@ -32,9 +31,9 @@ impl SourceDirectory {
|
||||
let file_path = file_entry.path();
|
||||
|
||||
// Verify that the entry is structured as a valid file
|
||||
let file_type = file_entry.file_type().map_err(|error| {
|
||||
SourceDirectoryError::GettingFileType(file_path.as_os_str().to_owned(), error)
|
||||
})?;
|
||||
let file_type = file_entry
|
||||
.file_type()
|
||||
.map_err(|error| SourceDirectoryError::GettingFileType(file_path.as_os_str().to_owned(), error))?;
|
||||
if !file_type.is_file() {
|
||||
return Err(SourceDirectoryError::InvalidFileType(
|
||||
file_path.as_os_str().to_owned(),
|
||||
@ -43,9 +42,9 @@ impl SourceDirectory {
|
||||
}
|
||||
|
||||
// Verify that the file has the default file extension
|
||||
let file_extension = file_path.extension().ok_or_else(|| {
|
||||
SourceDirectoryError::GettingFileExtension(file_path.as_os_str().to_owned())
|
||||
})?;
|
||||
let file_extension = file_path
|
||||
.extension()
|
||||
.ok_or_else(|| SourceDirectoryError::GettingFileExtension(file_path.as_os_str().to_owned()))?;
|
||||
if file_extension != SOURCE_FILE_EXTENSION {
|
||||
return Err(SourceDirectoryError::InvalidFileExtension(
|
||||
file_path.as_os_str().to_owned(),
|
||||
|
@ -1,7 +1,6 @@
|
||||
use crate::errors::ManifestError;
|
||||
|
||||
use std::ffi::OsString;
|
||||
use std::io;
|
||||
use std::{ffi::OsString, io};
|
||||
|
||||
#[derive(Debug, Error)]
|
||||
pub enum InitError {
|
||||
|
@ -1,7 +1,6 @@
|
||||
use crate::errors::ManifestError;
|
||||
|
||||
use std::ffi::OsString;
|
||||
use std::io;
|
||||
use std::{ffi::OsString, io};
|
||||
|
||||
#[derive(Debug, Error)]
|
||||
pub enum NewError {
|
||||
|
@ -1,5 +1,4 @@
|
||||
use std::io;
|
||||
use std::path::PathBuf;
|
||||
use std::{io, path::PathBuf};
|
||||
|
||||
#[derive(Debug, Error)]
|
||||
pub enum ChecksumFileError {
|
||||
|
@ -1,5 +1,4 @@
|
||||
use std::io;
|
||||
use std::path::PathBuf;
|
||||
use std::{io, path::PathBuf};
|
||||
|
||||
#[derive(Debug, Error)]
|
||||
pub enum ProofFileError {
|
||||
|
@ -1,5 +1,4 @@
|
||||
use std::io;
|
||||
use std::path::PathBuf;
|
||||
use std::{io, path::PathBuf};
|
||||
|
||||
#[derive(Debug, Error)]
|
||||
pub enum ProvingKeyFileError {
|
||||
|
@ -1,5 +1,4 @@
|
||||
use std::io;
|
||||
use std::path::PathBuf;
|
||||
use std::{io, path::PathBuf};
|
||||
|
||||
#[derive(Debug, Error)]
|
||||
pub enum VerificationKeyFileError {
|
||||
|
@ -1,12 +1,13 @@
|
||||
//! The build checksum file.
|
||||
|
||||
use crate::directories::outputs::OUTPUTS_DIRECTORY_NAME;
|
||||
use crate::errors::ChecksumFileError;
|
||||
use crate::{directories::outputs::OUTPUTS_DIRECTORY_NAME, errors::ChecksumFileError};
|
||||
|
||||
use serde::Deserialize;
|
||||
use std::fs::{self, File};
|
||||
use std::io::Write;
|
||||
use std::path::PathBuf;
|
||||
use std::{
|
||||
fs::{self, File},
|
||||
io::Write,
|
||||
path::PathBuf,
|
||||
};
|
||||
|
||||
pub static CHECKSUM_FILE_EXTENSION: &str = ".leo.checksum";
|
||||
|
||||
@ -31,10 +32,7 @@ impl ChecksumFile {
|
||||
pub fn read_from(&self, path: &PathBuf) -> Result<String, ChecksumFileError> {
|
||||
let path = self.setup_file_path(path);
|
||||
|
||||
Ok(
|
||||
fs::read_to_string(&path)
|
||||
.map_err(|_| ChecksumFileError::FileReadError(path.clone()))?,
|
||||
)
|
||||
Ok(fs::read_to_string(&path).map_err(|_| ChecksumFileError::FileReadError(path.clone()))?)
|
||||
}
|
||||
|
||||
/// Writes the given checksum to a file.
|
||||
|
@ -3,9 +3,7 @@
|
||||
use crate::errors::GitignoreError;
|
||||
|
||||
use serde::Deserialize;
|
||||
use std::fs::File;
|
||||
use std::io::Write;
|
||||
use std::path::PathBuf;
|
||||
use std::{fs::File, io::Write, path::PathBuf};
|
||||
|
||||
pub static GITIGNORE_FILE_NAME: &str = ".gitignore";
|
||||
|
||||
|
@ -1,12 +1,9 @@
|
||||
//! The `main.leo` file.
|
||||
|
||||
use crate::directories::source::SOURCE_DIRECTORY_NAME;
|
||||
use crate::errors::MainFileError;
|
||||
use crate::{directories::source::SOURCE_DIRECTORY_NAME, errors::MainFileError};
|
||||
|
||||
use serde::Deserialize;
|
||||
use std::fs::File;
|
||||
use std::io::Write;
|
||||
use std::path::PathBuf;
|
||||
use std::{fs::File, io::Write, path::PathBuf};
|
||||
|
||||
pub static MAIN_FILE_NAME: &str = "main.leo";
|
||||
|
||||
|
@ -1,11 +1,12 @@
|
||||
use crate::errors::ManifestError;
|
||||
|
||||
use serde::Deserialize;
|
||||
use std::convert::TryFrom;
|
||||
use std::fs::File;
|
||||
use std::io::Read;
|
||||
use std::io::Write;
|
||||
use std::path::PathBuf;
|
||||
use std::{
|
||||
convert::TryFrom,
|
||||
fs::File,
|
||||
io::{Read, Write},
|
||||
path::PathBuf,
|
||||
};
|
||||
|
||||
pub static MANIFEST_FILE_NAME: &str = "Leo.toml";
|
||||
|
||||
@ -48,8 +49,7 @@ impl Manifest {
|
||||
path.push(PathBuf::from(MANIFEST_FILE_NAME));
|
||||
}
|
||||
|
||||
let mut file = File::create(&path)
|
||||
.map_err(|error| ManifestError::Creating(MANIFEST_FILE_NAME, error))?;
|
||||
let mut file = File::create(&path).map_err(|error| ManifestError::Creating(MANIFEST_FILE_NAME, error))?;
|
||||
file.write_all(self.template().as_bytes())
|
||||
.map_err(|error| ManifestError::Writing(MANIFEST_FILE_NAME, error))
|
||||
}
|
||||
@ -74,8 +74,7 @@ impl TryFrom<&PathBuf> for Manifest {
|
||||
path.push(PathBuf::from(MANIFEST_FILE_NAME));
|
||||
}
|
||||
|
||||
let mut file =
|
||||
File::open(path).map_err(|error| ManifestError::Opening(MANIFEST_FILE_NAME, error))?;
|
||||
let mut file = File::open(path).map_err(|error| ManifestError::Opening(MANIFEST_FILE_NAME, error))?;
|
||||
let size = file
|
||||
.metadata()
|
||||
.map_err(|error| ManifestError::Metadata(MANIFEST_FILE_NAME, error))?
|
||||
@ -85,7 +84,6 @@ impl TryFrom<&PathBuf> for Manifest {
|
||||
file.read_to_string(&mut buffer)
|
||||
.map_err(|error| ManifestError::Reading(MANIFEST_FILE_NAME, error))?;
|
||||
|
||||
Ok(toml::from_str(&buffer)
|
||||
.map_err(|error| ManifestError::Parsing(MANIFEST_FILE_NAME, error))?)
|
||||
Ok(toml::from_str(&buffer).map_err(|error| ManifestError::Parsing(MANIFEST_FILE_NAME, error))?)
|
||||
}
|
||||
}
|
||||
|
@ -1,12 +1,13 @@
|
||||
//! The proof file.
|
||||
|
||||
use crate::directories::outputs::OUTPUTS_DIRECTORY_NAME;
|
||||
use crate::errors::ProofFileError;
|
||||
use crate::{directories::outputs::OUTPUTS_DIRECTORY_NAME, errors::ProofFileError};
|
||||
|
||||
use serde::Deserialize;
|
||||
use std::fs::{self, File};
|
||||
use std::io::Write;
|
||||
use std::path::PathBuf;
|
||||
use std::{
|
||||
fs::{self, File},
|
||||
io::Write,
|
||||
path::PathBuf,
|
||||
};
|
||||
|
||||
pub static PROOF_FILE_EXTENSION: &str = ".leo.proof";
|
||||
|
||||
@ -31,8 +32,7 @@ impl ProofFile {
|
||||
pub fn read_from(&self, path: &PathBuf) -> Result<String, ProofFileError> {
|
||||
let path = self.setup_file_path(path);
|
||||
|
||||
let proof =
|
||||
fs::read_to_string(&path).map_err(|_| ProofFileError::FileReadError(path.clone()))?;
|
||||
let proof = fs::read_to_string(&path).map_err(|_| ProofFileError::FileReadError(path.clone()))?;
|
||||
Ok(proof)
|
||||
}
|
||||
|
||||
@ -54,10 +54,7 @@ impl ProofFile {
|
||||
if !path.ends_with(OUTPUTS_DIRECTORY_NAME) {
|
||||
path.push(PathBuf::from(OUTPUTS_DIRECTORY_NAME));
|
||||
}
|
||||
path.push(PathBuf::from(format!(
|
||||
"{}{}",
|
||||
self.package_name, PROOF_FILE_EXTENSION
|
||||
)));
|
||||
path.push(PathBuf::from(format!("{}{}", self.package_name, PROOF_FILE_EXTENSION)));
|
||||
}
|
||||
path
|
||||
}
|
||||
|
@ -1,12 +1,13 @@
|
||||
//! The proving key file.
|
||||
|
||||
use crate::directories::outputs::OUTPUTS_DIRECTORY_NAME;
|
||||
use crate::errors::ProvingKeyFileError;
|
||||
use crate::{directories::outputs::OUTPUTS_DIRECTORY_NAME, errors::ProvingKeyFileError};
|
||||
|
||||
use serde::Deserialize;
|
||||
use std::fs::{self, File};
|
||||
use std::io::Write;
|
||||
use std::path::PathBuf;
|
||||
use std::{
|
||||
fs::{self, File},
|
||||
io::Write,
|
||||
path::PathBuf,
|
||||
};
|
||||
|
||||
pub static PROVING_KEY_FILE_EXTENSION: &str = ".leo.pk";
|
||||
|
||||
|
@ -1,12 +1,13 @@
|
||||
//! The verification key file.
|
||||
|
||||
use crate::directories::outputs::OUTPUTS_DIRECTORY_NAME;
|
||||
use crate::errors::VerificationKeyFileError;
|
||||
use crate::{directories::outputs::OUTPUTS_DIRECTORY_NAME, errors::VerificationKeyFileError};
|
||||
|
||||
use serde::Deserialize;
|
||||
use std::fs::{self, File};
|
||||
use std::io::Write;
|
||||
use std::path::PathBuf;
|
||||
use std::{
|
||||
fs::{self, File},
|
||||
io::Write,
|
||||
path::PathBuf,
|
||||
};
|
||||
|
||||
pub static VERIFICATION_KEY_FILE_EXTENSION: &str = ".leo.vk";
|
||||
|
||||
@ -35,11 +36,7 @@ impl VerificationKeyFile {
|
||||
}
|
||||
|
||||
/// Writes the given verification key to a file.
|
||||
pub fn write_to(
|
||||
&self,
|
||||
path: &PathBuf,
|
||||
verification_key: &[u8],
|
||||
) -> Result<(), VerificationKeyFileError> {
|
||||
pub fn write_to(&self, path: &PathBuf, verification_key: &[u8]) -> Result<(), VerificationKeyFileError> {
|
||||
let path = self.setup_file_path(path);
|
||||
|
||||
let mut file = File::create(&path)?;
|
||||
|
@ -1,5 +1,4 @@
|
||||
use leo::errors::CLIError;
|
||||
use leo::{cli::*, commands::*, logger};
|
||||
use leo::{cli::*, commands::*, errors::CLIError, logger};
|
||||
|
||||
use clap::{App, AppSettings};
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::{Identifier, CircuitMember};
|
||||
use crate::{CircuitMember, Identifier};
|
||||
use leo_ast::circuits::Circuit as AstCircuit;
|
||||
|
||||
use std::fmt;
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::{Identifier, Expression};
|
||||
use crate::{Expression, Identifier};
|
||||
use leo_ast::circuits::CircuitField;
|
||||
|
||||
#[derive(Clone, Debug, PartialEq, Eq)]
|
||||
|
@ -1,5 +1,9 @@
|
||||
use crate::{Identifier, Function, Type};
|
||||
use leo_ast::circuits::{CircuitFieldDefinition as AstCircuitFieldDefinition, CircuitMember as AstCircuitMember, CircuitFunction as AstCircuitFunction};
|
||||
use crate::{Function, Identifier, Type};
|
||||
use leo_ast::circuits::{
|
||||
CircuitFieldDefinition as AstCircuitFieldDefinition,
|
||||
CircuitFunction as AstCircuitFunction,
|
||||
CircuitMember as AstCircuitMember,
|
||||
};
|
||||
|
||||
use std::fmt;
|
||||
|
||||
@ -9,7 +13,6 @@ pub enum CircuitMember {
|
||||
CircuitFunction(bool, Function),
|
||||
}
|
||||
|
||||
|
||||
impl<'ast> From<AstCircuitFieldDefinition<'ast>> for CircuitMember {
|
||||
fn from(circuit_value: AstCircuitFieldDefinition<'ast>) -> Self {
|
||||
CircuitMember::CircuitField(
|
||||
@ -31,12 +34,8 @@ impl<'ast> From<AstCircuitFunction<'ast>> for CircuitMember {
|
||||
impl<'ast> From<AstCircuitMember<'ast>> for CircuitMember {
|
||||
fn from(object: AstCircuitMember<'ast>) -> Self {
|
||||
match object {
|
||||
AstCircuitMember::CircuitFieldDefinition(circuit_value) => {
|
||||
CircuitMember::from(circuit_value)
|
||||
}
|
||||
AstCircuitMember::CircuitFunction(circuit_function) => {
|
||||
CircuitMember::from(circuit_function)
|
||||
}
|
||||
AstCircuitMember::CircuitFieldDefinition(circuit_value) => CircuitMember::from(circuit_value),
|
||||
AstCircuitMember::CircuitFunction(circuit_function) => CircuitMember::from(circuit_function),
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -44,9 +43,7 @@ impl<'ast> From<AstCircuitMember<'ast>> for CircuitMember {
|
||||
impl fmt::Display for CircuitMember {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match self {
|
||||
CircuitMember::CircuitField(ref identifier, ref _type) => {
|
||||
write!(f, "{}: {}", identifier, _type)
|
||||
}
|
||||
CircuitMember::CircuitField(ref identifier, ref _type) => write!(f, "{}: {}", identifier, _type),
|
||||
CircuitMember::CircuitFunction(ref _static, ref function) => {
|
||||
if *_static {
|
||||
write!(f, "static ")?;
|
||||
|
@ -1,5 +1,8 @@
|
||||
use crate::{Identifier, RangeOrExpression};
|
||||
use leo_ast::{common::{Identifier as AstIdentifier, Assignee as AstAssignee}, access::AssigneeAccess};
|
||||
use leo_ast::{
|
||||
access::AssigneeAccess,
|
||||
common::{Assignee as AstAssignee, Identifier as AstIdentifier},
|
||||
};
|
||||
|
||||
use std::fmt;
|
||||
|
||||
@ -26,14 +29,12 @@ impl<'ast> From<AstAssignee<'ast>> for Assignee {
|
||||
.accesses
|
||||
.into_iter()
|
||||
.fold(variable, |acc, access| match access {
|
||||
AssigneeAccess::Array(array) => Assignee::Array(
|
||||
Box::new(acc),
|
||||
RangeOrExpression::from(array.expression),
|
||||
),
|
||||
AssigneeAccess::Member(circuit_field) => Assignee::CircuitField(
|
||||
Box::new(acc),
|
||||
Identifier::from(circuit_field.identifier),
|
||||
),
|
||||
AssigneeAccess::Array(array) => {
|
||||
Assignee::Array(Box::new(acc), RangeOrExpression::from(array.expression))
|
||||
}
|
||||
AssigneeAccess::Member(circuit_field) => {
|
||||
Assignee::CircuitField(Box::new(acc), Identifier::from(circuit_field.identifier))
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
@ -43,9 +44,7 @@ impl fmt::Display for Assignee {
|
||||
match *self {
|
||||
Assignee::Identifier(ref variable) => write!(f, "{}", variable),
|
||||
Assignee::Array(ref array, ref index) => write!(f, "{}[{}]", array, index),
|
||||
Assignee::CircuitField(ref circuit_variable, ref member) => {
|
||||
write!(f, "{}.{}", circuit_variable, member)
|
||||
}
|
||||
Assignee::CircuitField(ref circuit_variable, ref member) => write!(f, "{}.{}", circuit_variable, member),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::{Integer, Expression};
|
||||
use crate::{Expression, Integer};
|
||||
use leo_ast::common::RangeOrExpression as AstRangeOrExpression;
|
||||
|
||||
use std::fmt;
|
||||
@ -14,30 +14,20 @@ impl<'ast> From<AstRangeOrExpression<'ast>> for RangeOrExpression {
|
||||
fn from(range_or_expression: AstRangeOrExpression<'ast>) -> Self {
|
||||
match range_or_expression {
|
||||
AstRangeOrExpression::Range(range) => {
|
||||
let from = range
|
||||
.from
|
||||
.map(|from| match Expression::from(from.0) {
|
||||
let from = range.from.map(|from| match Expression::from(from.0) {
|
||||
Expression::Integer(number) => number,
|
||||
Expression::Implicit(string) => {
|
||||
Integer::from_implicit(string)
|
||||
}
|
||||
expression => {
|
||||
unimplemented!("Range bounds should be integers, found {}", expression)
|
||||
}
|
||||
Expression::Implicit(string) => Integer::from_implicit(string),
|
||||
expression => unimplemented!("Range bounds should be integers, found {}", expression),
|
||||
});
|
||||
let to = range.to.map(|to| match Expression::from(to.0) {
|
||||
Expression::Integer(number) => number,
|
||||
Expression::Implicit(string) => Integer::from_implicit(string),
|
||||
expression => {
|
||||
unimplemented!("Range bounds should be integers, found {}", expression)
|
||||
}
|
||||
expression => unimplemented!("Range bounds should be integers, found {}", expression),
|
||||
});
|
||||
|
||||
RangeOrExpression::Range(from, to)
|
||||
}
|
||||
AstRangeOrExpression::Expression(expression) => {
|
||||
RangeOrExpression::Expression(Expression::from(expression))
|
||||
}
|
||||
AstRangeOrExpression::Expression(expression) => RangeOrExpression::Expression(Expression::from(expression)),
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -48,12 +38,8 @@ impl fmt::Display for RangeOrExpression {
|
||||
RangeOrExpression::Range(ref from, ref to) => write!(
|
||||
f,
|
||||
"{}..{}",
|
||||
from.as_ref()
|
||||
.map(|e| format!("{}", e))
|
||||
.unwrap_or("".to_string()),
|
||||
to.as_ref()
|
||||
.map(|e| format!("{}", e))
|
||||
.unwrap_or("".to_string())
|
||||
from.as_ref().map(|e| format!("{}", e)).unwrap_or("".to_string()),
|
||||
to.as_ref().map(|e| format!("{}", e)).unwrap_or("".to_string())
|
||||
),
|
||||
RangeOrExpression::Expression(ref e) => write!(f, "{}", e),
|
||||
}
|
||||
|
@ -13,9 +13,7 @@ pub enum SpreadOrExpression {
|
||||
impl<'ast> From<AstSpreadOrExpression<'ast>> for SpreadOrExpression {
|
||||
fn from(s_or_e: AstSpreadOrExpression<'ast>) -> Self {
|
||||
match s_or_e {
|
||||
AstSpreadOrExpression::Spread(spread) => {
|
||||
SpreadOrExpression::Spread(Expression::from(spread.expression))
|
||||
}
|
||||
AstSpreadOrExpression::Spread(spread) => SpreadOrExpression::Spread(Expression::from(spread.expression)),
|
||||
AstSpreadOrExpression::Expression(expression) => {
|
||||
SpreadOrExpression::Expression(Expression::from(expression))
|
||||
}
|
||||
|
@ -1,36 +1,22 @@
|
||||
use crate::{CircuitFieldDefinition, Identifier, Integer, SpreadOrExpression, RangeOrExpression};
|
||||
use crate::{CircuitFieldDefinition, Identifier, Integer, RangeOrExpression, SpreadOrExpression};
|
||||
use leo_ast::{
|
||||
access::{Access, AssigneeAccess},
|
||||
common::{
|
||||
Assignee,
|
||||
Identifier as AstIdentifier,
|
||||
},
|
||||
common::{Assignee, Identifier as AstIdentifier},
|
||||
expressions::{
|
||||
Expression as AstExpression,
|
||||
CircuitInlineExpression,
|
||||
PostfixExpression,
|
||||
ArrayInitializerExpression,
|
||||
ArrayInlineExpression,
|
||||
TernaryExpression,
|
||||
BinaryExpression,
|
||||
NotExpression
|
||||
CircuitInlineExpression,
|
||||
Expression as AstExpression,
|
||||
NotExpression,
|
||||
PostfixExpression,
|
||||
TernaryExpression,
|
||||
},
|
||||
operations::{
|
||||
BinaryOperation,
|
||||
},
|
||||
values::{
|
||||
Value,
|
||||
FieldValue,
|
||||
BooleanValue,
|
||||
GroupValue,
|
||||
NumberImplicitValue,
|
||||
IntegerValue
|
||||
}
|
||||
operations::BinaryOperation,
|
||||
values::{BooleanValue, FieldValue, GroupValue, IntegerValue, NumberImplicitValue, Value},
|
||||
};
|
||||
|
||||
use snarkos_models::gadgets::utilities::{
|
||||
boolean::Boolean,
|
||||
};
|
||||
use snarkos_models::gadgets::utilities::boolean::Boolean;
|
||||
|
||||
use std::fmt;
|
||||
|
||||
@ -88,11 +74,7 @@ impl<'ast> Expression {
|
||||
.value
|
||||
.parse::<usize>()
|
||||
.expect("Unable to read array size"),
|
||||
Value::Implicit(number) => number
|
||||
.number
|
||||
.value
|
||||
.parse::<usize>()
|
||||
.expect("Unable to read array size"),
|
||||
Value::Implicit(number) => number.number.value.parse::<usize>().expect("Unable to read array size"),
|
||||
size => unimplemented!("Array size should be an integer {}", size),
|
||||
}
|
||||
}
|
||||
@ -157,9 +139,7 @@ impl<'ast> fmt::Display for Expression {
|
||||
}
|
||||
write!(f, "}}")
|
||||
}
|
||||
Expression::CircuitMemberAccess(ref circuit_name, ref member) => {
|
||||
write!(f, "{}.{}", circuit_name, member)
|
||||
}
|
||||
Expression::CircuitMemberAccess(ref circuit_name, ref member) => write!(f, "{}.{}", circuit_name, member),
|
||||
Expression::CircuitStaticFunctionAccess(ref circuit_name, ref member) => {
|
||||
write!(f, "{}::{}", circuit_name, member)
|
||||
}
|
||||
@ -179,7 +159,6 @@ impl<'ast> fmt::Display for Expression {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
impl<'ast> From<CircuitInlineExpression<'ast>> for Expression {
|
||||
fn from(expression: CircuitInlineExpression<'ast>) -> Self {
|
||||
let variable = Identifier::from(expression.identifier);
|
||||
@ -195,8 +174,7 @@ impl<'ast> From<CircuitInlineExpression<'ast>> for Expression {
|
||||
|
||||
impl<'ast> From<PostfixExpression<'ast>> for Expression {
|
||||
fn from(expression: PostfixExpression<'ast>) -> Self {
|
||||
let variable =
|
||||
Expression::Identifier(Identifier::from(expression.identifier));
|
||||
let variable = Expression::Identifier(Identifier::from(expression.identifier));
|
||||
|
||||
// ast::PostFixExpression contains an array of "accesses": `a(34)[42]` is represented as `[a, [Call(34), Select(42)]]`, but Access call expressions
|
||||
// are recursive, so it is `Select(Call(a, 34), 42)`. We apply this transformation here
|
||||
@ -207,10 +185,9 @@ impl<'ast> From<PostfixExpression<'ast>> for Expression {
|
||||
.into_iter()
|
||||
.fold(variable, |acc, access| match access {
|
||||
// Handle array accesses
|
||||
Access::Array(array) => Expression::ArrayAccess(
|
||||
Box::new(acc),
|
||||
Box::new(RangeOrExpression::from(array.expression)),
|
||||
),
|
||||
Access::Array(array) => {
|
||||
Expression::ArrayAccess(Box::new(acc), Box::new(RangeOrExpression::from(array.expression)))
|
||||
}
|
||||
|
||||
// Handle function calls
|
||||
Access::Call(function) => Expression::FunctionCall(
|
||||
@ -223,15 +200,11 @@ impl<'ast> From<PostfixExpression<'ast>> for Expression {
|
||||
),
|
||||
|
||||
// Handle circuit member accesses
|
||||
Access::Object(circuit_object) => Expression::CircuitMemberAccess(
|
||||
Box::new(acc),
|
||||
Identifier::from(circuit_object.identifier),
|
||||
),
|
||||
Access::Object(circuit_object) => {
|
||||
Expression::CircuitMemberAccess(Box::new(acc), Identifier::from(circuit_object.identifier))
|
||||
}
|
||||
Access::StaticObject(circuit_object) => {
|
||||
Expression::CircuitStaticFunctionAccess(
|
||||
Box::new(acc),
|
||||
Identifier::from(circuit_object.identifier),
|
||||
)
|
||||
Expression::CircuitStaticFunctionAccess(Box::new(acc), Identifier::from(circuit_object.identifier))
|
||||
}
|
||||
})
|
||||
}
|
||||
@ -264,15 +237,11 @@ impl<'ast> From<Assignee<'ast>> for Expression {
|
||||
.into_iter()
|
||||
.fold(variable, |acc, access| match access {
|
||||
AssigneeAccess::Member(circuit_member) => {
|
||||
Expression::CircuitMemberAccess(
|
||||
Box::new(acc),
|
||||
Identifier::from(circuit_member.identifier),
|
||||
)
|
||||
Expression::CircuitMemberAccess(Box::new(acc), Identifier::from(circuit_member.identifier))
|
||||
}
|
||||
AssigneeAccess::Array(array) => {
|
||||
Expression::ArrayAccess(Box::new(acc), Box::new(RangeOrExpression::from(array.expression)))
|
||||
}
|
||||
AssigneeAccess::Array(array) => Expression::ArrayAccess(
|
||||
Box::new(acc),
|
||||
Box::new(RangeOrExpression::from(array.expression)),
|
||||
),
|
||||
})
|
||||
}
|
||||
}
|
||||
@ -293,9 +262,7 @@ impl<'ast> From<BinaryExpression<'ast>> for Expression {
|
||||
Box::new(Expression::from(*expression.left)),
|
||||
Box::new(Expression::from(*expression.right)),
|
||||
),
|
||||
BinaryOperation::Ne => {
|
||||
Expression::Not(Box::new(Expression::from(expression)))
|
||||
}
|
||||
BinaryOperation::Ne => Expression::Not(Box::new(Expression::from(expression))),
|
||||
BinaryOperation::Ge => Expression::Ge(
|
||||
Box::new(Expression::from(*expression.left)),
|
||||
Box::new(Expression::from(*expression.right)),
|
||||
@ -368,7 +335,6 @@ impl<'ast> From<ArrayInitializerExpression<'ast>> for Expression {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
impl<'ast> From<Value<'ast>> for Expression {
|
||||
fn from(value: Value<'ast>) -> Self {
|
||||
match value {
|
||||
@ -387,7 +353,6 @@ impl<'ast> From<NotExpression<'ast>> for Expression {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
impl<'ast> From<FieldValue<'ast>> for Expression {
|
||||
fn from(field: FieldValue<'ast>) -> Self {
|
||||
Expression::Field(field.number.value)
|
||||
@ -403,10 +368,7 @@ impl<'ast> From<GroupValue<'ast>> for Expression {
|
||||
impl<'ast> From<BooleanValue<'ast>> for Expression {
|
||||
fn from(boolean: BooleanValue<'ast>) -> Self {
|
||||
Expression::Boolean(Boolean::Constant(
|
||||
boolean
|
||||
.value
|
||||
.parse::<bool>()
|
||||
.expect("unable to parse boolean"),
|
||||
boolean.value.parse::<bool>().expect("unable to parse boolean"),
|
||||
))
|
||||
}
|
||||
}
|
||||
@ -417,7 +379,6 @@ impl<'ast> From<NumberImplicitValue<'ast>> for Expression {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
impl<'ast> From<IntegerValue<'ast>> for Expression {
|
||||
fn from(field: IntegerValue<'ast>) -> Self {
|
||||
Expression::Integer(Integer::from(field.number, field._type))
|
||||
|
@ -1,4 +1,4 @@
|
||||
use crate::{Identifier, FunctionInput, Statement, Type};
|
||||
use crate::{FunctionInput, Identifier, Statement, Type};
|
||||
use leo_ast::functions::Function as AstFunction;
|
||||
|
||||
use std::fmt;
|
||||
|
@ -1,5 +1,8 @@
|
||||
use crate::{Identifier, Type};
|
||||
use leo_ast::{common::{Visibility, Private}, functions::FunctionInput as AstFunctionInput};
|
||||
use leo_ast::{
|
||||
common::{Private, Visibility},
|
||||
functions::FunctionInput as AstFunctionInput,
|
||||
};
|
||||
|
||||
use std::fmt;
|
||||
|
||||
@ -17,9 +20,9 @@ impl<'ast> From<AstFunctionInput<'ast>> for FunctionInput {
|
||||
identifier: Identifier::from(parameter.identifier),
|
||||
mutable: parameter.mutable.is_some(),
|
||||
// private by default
|
||||
private: parameter.visibility.map_or(true, |visibility| {
|
||||
visibility.eq(&Visibility::Private(Private {}))
|
||||
}),
|
||||
private: parameter
|
||||
.visibility
|
||||
.map_or(true, |visibility| visibility.eq(&Visibility::Private(Private {}))),
|
||||
_type: Type::from(parameter._type),
|
||||
}
|
||||
}
|
||||
|
@ -1,6 +1,6 @@
|
||||
//! Conversion of integer declarations to constraints in Leo.
|
||||
|
||||
use crate::{errors::IntegerError, IntegerType, InputValue};
|
||||
use crate::{errors::IntegerError, InputValue, IntegerType};
|
||||
use leo_ast::{types::IntegerType as AstIntegerType, values::NumberValue};
|
||||
|
||||
use snarkos_errors::gadgets::SynthesisError;
|
||||
@ -33,17 +33,14 @@ pub enum Integer {
|
||||
impl<'ast> Integer {
|
||||
pub fn from(number: NumberValue<'ast>, _type: AstIntegerType) -> Self {
|
||||
match _type {
|
||||
AstIntegerType::U8Type(_u8) => Integer::U8(UInt8::constant(
|
||||
number.value.parse::<u8>().expect("unable to parse u8"),
|
||||
)),
|
||||
AstIntegerType::U8Type(_u8) => {
|
||||
Integer::U8(UInt8::constant(number.value.parse::<u8>().expect("unable to parse u8")))
|
||||
}
|
||||
AstIntegerType::U16Type(_u16) => Integer::U16(UInt16::constant(
|
||||
number.value.parse::<u16>().expect("unable to parse u16"),
|
||||
)),
|
||||
AstIntegerType::U32Type(_u32) => Integer::U32(UInt32::constant(
|
||||
number
|
||||
.value
|
||||
.parse::<u32>()
|
||||
.expect("unable to parse integers.u32"),
|
||||
number.value.parse::<u32>().expect("unable to parse integers.u32"),
|
||||
)),
|
||||
AstIntegerType::U64Type(_u64) => Integer::U64(UInt64::constant(
|
||||
number.value.parse::<u64>().expect("unable to parse u64"),
|
||||
@ -55,9 +52,7 @@ impl<'ast> Integer {
|
||||
}
|
||||
|
||||
pub fn from_implicit(number: String) -> Self {
|
||||
Integer::U128(UInt128::constant(
|
||||
number.parse::<u128>().expect("unable to parse u128"),
|
||||
))
|
||||
Integer::U128(UInt128::constant(number.parse::<u128>().expect("unable to parse u128")))
|
||||
}
|
||||
}
|
||||
|
||||
@ -105,60 +100,48 @@ impl Integer {
|
||||
IntegerType::U8 => {
|
||||
let u8_option = integer_option.map(|integer| integer as u8);
|
||||
let u8_result = match private {
|
||||
true => UInt8::alloc(cs.ns(|| name), || {
|
||||
u8_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?,
|
||||
false => UInt8::alloc_input(cs.ns(|| name), || {
|
||||
u8_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?,
|
||||
true => UInt8::alloc(cs.ns(|| name), || u8_option.ok_or(SynthesisError::AssignmentMissing))?,
|
||||
false => UInt8::alloc_input(cs.ns(|| name), || u8_option.ok_or(SynthesisError::AssignmentMissing))?,
|
||||
};
|
||||
Integer::U8(u8_result)
|
||||
}
|
||||
IntegerType::U16 => {
|
||||
let u16_option = integer_option.map(|integer| integer as u16);
|
||||
let u16_result = match private {
|
||||
true => UInt16::alloc(cs.ns(|| name), || {
|
||||
u16_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?,
|
||||
false => UInt16::alloc_input(cs.ns(|| name), || {
|
||||
u16_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?,
|
||||
true => UInt16::alloc(cs.ns(|| name), || u16_option.ok_or(SynthesisError::AssignmentMissing))?,
|
||||
false => {
|
||||
UInt16::alloc_input(cs.ns(|| name), || u16_option.ok_or(SynthesisError::AssignmentMissing))?
|
||||
}
|
||||
};
|
||||
Integer::U16(u16_result)
|
||||
}
|
||||
IntegerType::U32 => {
|
||||
let u32_option = integer_option.map(|integer| integer as u32);
|
||||
let u32_result = match private {
|
||||
true => UInt32::alloc(cs.ns(|| name), || {
|
||||
u32_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?,
|
||||
false => UInt32::alloc_input(cs.ns(|| name), || {
|
||||
u32_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?,
|
||||
true => UInt32::alloc(cs.ns(|| name), || u32_option.ok_or(SynthesisError::AssignmentMissing))?,
|
||||
false => {
|
||||
UInt32::alloc_input(cs.ns(|| name), || u32_option.ok_or(SynthesisError::AssignmentMissing))?
|
||||
}
|
||||
};
|
||||
Integer::U32(u32_result)
|
||||
}
|
||||
IntegerType::U64 => {
|
||||
let u64_option = integer_option.map(|integer| integer as u64);
|
||||
let u64_result = match private {
|
||||
true => UInt64::alloc(cs.ns(|| name), || {
|
||||
u64_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?,
|
||||
false => UInt64::alloc_input(cs.ns(|| name), || {
|
||||
u64_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?,
|
||||
true => UInt64::alloc(cs.ns(|| name), || u64_option.ok_or(SynthesisError::AssignmentMissing))?,
|
||||
false => {
|
||||
UInt64::alloc_input(cs.ns(|| name), || u64_option.ok_or(SynthesisError::AssignmentMissing))?
|
||||
}
|
||||
};
|
||||
Integer::U64(u64_result)
|
||||
}
|
||||
IntegerType::U128 => {
|
||||
let u128_option = integer_option.map(|integer| integer as u128);
|
||||
let u128_result = match private {
|
||||
true => UInt128::alloc(cs.ns(|| name), || {
|
||||
u128_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?,
|
||||
false => UInt128::alloc_input(cs.ns(|| name), || {
|
||||
u128_option.ok_or(SynthesisError::AssignmentMissing)
|
||||
})?,
|
||||
true => UInt128::alloc(cs.ns(|| name), || u128_option.ok_or(SynthesisError::AssignmentMissing))?,
|
||||
false => {
|
||||
UInt128::alloc_input(cs.ns(|| name), || u128_option.ok_or(SynthesisError::AssignmentMissing))?
|
||||
}
|
||||
};
|
||||
Integer::U128(u128_result)
|
||||
}
|
||||
@ -173,72 +156,40 @@ impl Integer {
|
||||
Ok(match (self, other) {
|
||||
(Integer::U8(left_u8), Integer::U8(right_u8)) => {
|
||||
let result = UInt8::addmany(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} + {}",
|
||||
left_u8.value.unwrap(),
|
||||
right_u8.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} + {}", left_u8.value.unwrap(), right_u8.value.unwrap())),
|
||||
&[left_u8, right_u8],
|
||||
)?;
|
||||
Integer::U8(result)
|
||||
}
|
||||
(Integer::U16(left_u16), Integer::U16(right_u16)) => {
|
||||
let result = UInt16::addmany(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} + {}",
|
||||
left_u16.value.unwrap(),
|
||||
right_u16.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} + {}", left_u16.value.unwrap(), right_u16.value.unwrap())),
|
||||
&[left_u16, right_u16],
|
||||
)?;
|
||||
Integer::U16(result)
|
||||
}
|
||||
(Integer::U32(left_u32), Integer::U32(right_u32)) => {
|
||||
let result = UInt32::addmany(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} + {}",
|
||||
left_u32.value.unwrap(),
|
||||
right_u32.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} + {}", left_u32.value.unwrap(), right_u32.value.unwrap())),
|
||||
&[left_u32, right_u32],
|
||||
)?;
|
||||
Integer::U32(result)
|
||||
}
|
||||
(Integer::U64(left_u64), Integer::U64(right_u64)) => {
|
||||
let result = UInt64::addmany(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} + {}",
|
||||
left_u64.value.unwrap(),
|
||||
right_u64.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} + {}", left_u64.value.unwrap(), right_u64.value.unwrap())),
|
||||
&[left_u64, right_u64],
|
||||
)?;
|
||||
Integer::U64(result)
|
||||
}
|
||||
(Integer::U128(left_u128), Integer::U128(right_u128)) => {
|
||||
let result = UInt128::addmany(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} + {}",
|
||||
left_u128.value.unwrap(),
|
||||
right_u128.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} + {}", left_u128.value.unwrap(), right_u128.value.unwrap())),
|
||||
&[left_u128, right_u128],
|
||||
)?;
|
||||
Integer::U128(result)
|
||||
}
|
||||
(left, right) => {
|
||||
return Err(IntegerError::CannotEnforce(format!("{} + {}", left, right)))
|
||||
}
|
||||
(left, right) => return Err(IntegerError::CannotEnforce(format!("{} + {}", left, right))),
|
||||
})
|
||||
}
|
||||
|
||||
@ -250,72 +201,40 @@ impl Integer {
|
||||
Ok(match (self, other) {
|
||||
(Integer::U8(left_u8), Integer::U8(right_u8)) => {
|
||||
let result = left_u8.sub(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} - {}",
|
||||
left_u8.value.unwrap(),
|
||||
right_u8.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} - {}", left_u8.value.unwrap(), right_u8.value.unwrap())),
|
||||
&right_u8,
|
||||
)?;
|
||||
Integer::U8(result)
|
||||
}
|
||||
(Integer::U16(left_u16), Integer::U16(right_u16)) => {
|
||||
let result = left_u16.sub(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} - {}",
|
||||
left_u16.value.unwrap(),
|
||||
right_u16.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} - {}", left_u16.value.unwrap(), right_u16.value.unwrap())),
|
||||
&right_u16,
|
||||
)?;
|
||||
Integer::U16(result)
|
||||
}
|
||||
(Integer::U32(left_u32), Integer::U32(right_u32)) => {
|
||||
let result = left_u32.sub(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} - {}",
|
||||
left_u32.value.unwrap(),
|
||||
right_u32.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} - {}", left_u32.value.unwrap(), right_u32.value.unwrap())),
|
||||
&right_u32,
|
||||
)?;
|
||||
Integer::U32(result)
|
||||
}
|
||||
(Integer::U64(left_u64), Integer::U64(right_u64)) => {
|
||||
let result = left_u64.sub(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} - {}",
|
||||
left_u64.value.unwrap(),
|
||||
right_u64.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} - {}", left_u64.value.unwrap(), right_u64.value.unwrap())),
|
||||
&right_u64,
|
||||
)?;
|
||||
Integer::U64(result)
|
||||
}
|
||||
(Integer::U128(left_u128), Integer::U128(right_u128)) => {
|
||||
let result = left_u128.sub(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} - {}",
|
||||
left_u128.value.unwrap(),
|
||||
right_u128.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} - {}", left_u128.value.unwrap(), right_u128.value.unwrap())),
|
||||
&right_u128,
|
||||
)?;
|
||||
Integer::U128(result)
|
||||
}
|
||||
(left, right) => {
|
||||
return Err(IntegerError::CannotEnforce(format!("{} - {}", left, right)))
|
||||
}
|
||||
(left, right) => return Err(IntegerError::CannotEnforce(format!("{} - {}", left, right))),
|
||||
})
|
||||
}
|
||||
|
||||
@ -327,72 +246,40 @@ impl Integer {
|
||||
Ok(match (self, other) {
|
||||
(Integer::U8(left_u8), Integer::U8(right_u8)) => {
|
||||
let result = left_u8.mul(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} * {}",
|
||||
left_u8.value.unwrap(),
|
||||
right_u8.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} * {}", left_u8.value.unwrap(), right_u8.value.unwrap())),
|
||||
&right_u8,
|
||||
)?;
|
||||
Integer::U8(result)
|
||||
}
|
||||
(Integer::U16(left_u16), Integer::U16(right_u16)) => {
|
||||
let result = left_u16.mul(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} * {}",
|
||||
left_u16.value.unwrap(),
|
||||
right_u16.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} * {}", left_u16.value.unwrap(), right_u16.value.unwrap())),
|
||||
&right_u16,
|
||||
)?;
|
||||
Integer::U16(result)
|
||||
}
|
||||
(Integer::U32(left_u32), Integer::U32(right_u32)) => {
|
||||
let result = left_u32.mul(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} * {}",
|
||||
left_u32.value.unwrap(),
|
||||
right_u32.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} * {}", left_u32.value.unwrap(), right_u32.value.unwrap())),
|
||||
&right_u32,
|
||||
)?;
|
||||
Integer::U32(result)
|
||||
}
|
||||
(Integer::U64(left_u64), Integer::U64(right_u64)) => {
|
||||
let result = left_u64.mul(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} * {}",
|
||||
left_u64.value.unwrap(),
|
||||
right_u64.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} * {}", left_u64.value.unwrap(), right_u64.value.unwrap())),
|
||||
&right_u64,
|
||||
)?;
|
||||
Integer::U64(result)
|
||||
}
|
||||
(Integer::U128(left_u128), Integer::U128(right_u128)) => {
|
||||
let result = left_u128.mul(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} * {}",
|
||||
left_u128.value.unwrap(),
|
||||
right_u128.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} * {}", left_u128.value.unwrap(), right_u128.value.unwrap())),
|
||||
&right_u128,
|
||||
)?;
|
||||
Integer::U128(result)
|
||||
}
|
||||
(left, right) => {
|
||||
return Err(IntegerError::CannotEnforce(format!("{} * {}", left, right)))
|
||||
}
|
||||
(left, right) => return Err(IntegerError::CannotEnforce(format!("{} * {}", left, right))),
|
||||
})
|
||||
}
|
||||
|
||||
@ -404,72 +291,40 @@ impl Integer {
|
||||
Ok(match (self, other) {
|
||||
(Integer::U8(left_u8), Integer::U8(right_u8)) => {
|
||||
let result = left_u8.div(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} ÷ {}",
|
||||
left_u8.value.unwrap(),
|
||||
right_u8.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} ÷ {}", left_u8.value.unwrap(), right_u8.value.unwrap())),
|
||||
&right_u8,
|
||||
)?;
|
||||
Integer::U8(result)
|
||||
}
|
||||
(Integer::U16(left_u16), Integer::U16(right_u16)) => {
|
||||
let result = left_u16.div(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} ÷ {}",
|
||||
left_u16.value.unwrap(),
|
||||
right_u16.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} ÷ {}", left_u16.value.unwrap(), right_u16.value.unwrap())),
|
||||
&right_u16,
|
||||
)?;
|
||||
Integer::U16(result)
|
||||
}
|
||||
(Integer::U32(left_u32), Integer::U32(right_u32)) => {
|
||||
let result = left_u32.div(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} ÷ {}",
|
||||
left_u32.value.unwrap(),
|
||||
right_u32.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} ÷ {}", left_u32.value.unwrap(), right_u32.value.unwrap())),
|
||||
&right_u32,
|
||||
)?;
|
||||
Integer::U32(result)
|
||||
}
|
||||
(Integer::U64(left_u64), Integer::U64(right_u64)) => {
|
||||
let result = left_u64.div(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} ÷ {}",
|
||||
left_u64.value.unwrap(),
|
||||
right_u64.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} ÷ {}", left_u64.value.unwrap(), right_u64.value.unwrap())),
|
||||
&right_u64,
|
||||
)?;
|
||||
Integer::U64(result)
|
||||
}
|
||||
(Integer::U128(left_u128), Integer::U128(right_u128)) => {
|
||||
let result = left_u128.div(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} ÷ {}",
|
||||
left_u128.value.unwrap(),
|
||||
right_u128.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} ÷ {}", left_u128.value.unwrap(), right_u128.value.unwrap())),
|
||||
&right_u128,
|
||||
)?;
|
||||
Integer::U128(result)
|
||||
}
|
||||
(left, right) => {
|
||||
return Err(IntegerError::CannotEnforce(format!("{} ÷ {}", left, right)))
|
||||
}
|
||||
(left, right) => return Err(IntegerError::CannotEnforce(format!("{} ÷ {}", left, right))),
|
||||
})
|
||||
}
|
||||
|
||||
@ -481,75 +336,40 @@ impl Integer {
|
||||
Ok(match (self, other) {
|
||||
(Integer::U8(left_u8), Integer::U8(right_u8)) => {
|
||||
let result = left_u8.pow(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} ** {}",
|
||||
left_u8.value.unwrap(),
|
||||
right_u8.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} ** {}", left_u8.value.unwrap(), right_u8.value.unwrap())),
|
||||
&right_u8,
|
||||
)?;
|
||||
Integer::U8(result)
|
||||
}
|
||||
(Integer::U16(left_u16), Integer::U16(right_u16)) => {
|
||||
let result = left_u16.pow(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} ** {}",
|
||||
left_u16.value.unwrap(),
|
||||
right_u16.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} ** {}", left_u16.value.unwrap(), right_u16.value.unwrap())),
|
||||
&right_u16,
|
||||
)?;
|
||||
Integer::U16(result)
|
||||
}
|
||||
(Integer::U32(left_u32), Integer::U32(right_u32)) => {
|
||||
let result = left_u32.pow(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} ** {}",
|
||||
left_u32.value.unwrap(),
|
||||
right_u32.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} ** {}", left_u32.value.unwrap(), right_u32.value.unwrap())),
|
||||
&right_u32,
|
||||
)?;
|
||||
Integer::U32(result)
|
||||
}
|
||||
(Integer::U64(left_u64), Integer::U64(right_u64)) => {
|
||||
let result = left_u64.pow(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} ** {}",
|
||||
left_u64.value.unwrap(),
|
||||
right_u64.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} ** {}", left_u64.value.unwrap(), right_u64.value.unwrap())),
|
||||
&right_u64,
|
||||
)?;
|
||||
Integer::U64(result)
|
||||
}
|
||||
(Integer::U128(left_u128), Integer::U128(right_u128)) => {
|
||||
let result = left_u128.pow(
|
||||
cs.ns(|| {
|
||||
format!(
|
||||
"enforce {} ** {}",
|
||||
left_u128.value.unwrap(),
|
||||
right_u128.value.unwrap()
|
||||
)
|
||||
}),
|
||||
cs.ns(|| format!("enforce {} ** {}", left_u128.value.unwrap(), right_u128.value.unwrap())),
|
||||
&right_u128,
|
||||
)?;
|
||||
Integer::U128(result)
|
||||
}
|
||||
(left, right) => {
|
||||
return Err(IntegerError::CannotEnforce(format!(
|
||||
"{} ** {}",
|
||||
left, right
|
||||
)))
|
||||
}
|
||||
(left, right) => return Err(IntegerError::CannotEnforce(format!("{} ** {}", left, right))),
|
||||
})
|
||||
}
|
||||
}
|
||||
@ -564,9 +384,7 @@ impl<F: Field + PrimeField> ConditionalEqGadget<F> for Integer {
|
||||
condition: &Boolean,
|
||||
) -> Result<(), SynthesisError> {
|
||||
match (self, other) {
|
||||
(Integer::U8(left_u8), Integer::U8(right_u8)) => {
|
||||
left_u8.conditional_enforce_equal(cs, right_u8, condition)
|
||||
}
|
||||
(Integer::U8(left_u8), Integer::U8(right_u8)) => left_u8.conditional_enforce_equal(cs, right_u8, condition),
|
||||
(Integer::U16(left_u16), Integer::U16(right_u16)) => {
|
||||
left_u16.conditional_enforce_equal(cs, right_u16, condition)
|
||||
}
|
||||
@ -596,18 +414,18 @@ impl<F: Field + PrimeField> CondSelectGadget<F> for Integer {
|
||||
second: &Self,
|
||||
) -> Result<Self, SynthesisError> {
|
||||
match (first, second) {
|
||||
(Integer::U8(u8_first), Integer::U8(u8_second)) => Ok(Integer::U8(
|
||||
UInt8::conditionally_select(cs, cond, u8_first, u8_second)?,
|
||||
)),
|
||||
(Integer::U16(u16_first), Integer::U16(u18_second)) => Ok(Integer::U16(
|
||||
UInt16::conditionally_select(cs, cond, u16_first, u18_second)?,
|
||||
)),
|
||||
(Integer::U32(u32_first), Integer::U32(u32_second)) => Ok(Integer::U32(
|
||||
UInt32::conditionally_select(cs, cond, u32_first, u32_second)?,
|
||||
)),
|
||||
(Integer::U64(u64_first), Integer::U64(u64_second)) => Ok(Integer::U64(
|
||||
UInt64::conditionally_select(cs, cond, u64_first, u64_second)?,
|
||||
)),
|
||||
(Integer::U8(u8_first), Integer::U8(u8_second)) => {
|
||||
Ok(Integer::U8(UInt8::conditionally_select(cs, cond, u8_first, u8_second)?))
|
||||
}
|
||||
(Integer::U16(u16_first), Integer::U16(u18_second)) => Ok(Integer::U16(UInt16::conditionally_select(
|
||||
cs, cond, u16_first, u18_second,
|
||||
)?)),
|
||||
(Integer::U32(u32_first), Integer::U32(u32_second)) => Ok(Integer::U32(UInt32::conditionally_select(
|
||||
cs, cond, u32_first, u32_second,
|
||||
)?)),
|
||||
(Integer::U64(u64_first), Integer::U64(u64_second)) => Ok(Integer::U64(UInt64::conditionally_select(
|
||||
cs, cond, u64_first, u64_second,
|
||||
)?)),
|
||||
(Integer::U128(u128_first), Integer::U128(u128_second)) => Ok(Integer::U128(
|
||||
UInt128::conditionally_select(cs, cond, u128_first, u128_second)?,
|
||||
)),
|
||||
|
@ -1,10 +1,8 @@
|
||||
//! A typed Leo program consists of import, circuit, and function definitions.
|
||||
//! Each defined type consists of typed statements and expressions.
|
||||
|
||||
use crate::{Circuit, Identifier, Import, Function, TestFunction};
|
||||
use leo_ast::{
|
||||
files::File,
|
||||
};
|
||||
use crate::{Circuit, Function, Identifier, Import, TestFunction};
|
||||
use leo_ast::files::File;
|
||||
|
||||
use std::collections::HashMap;
|
||||
|
||||
@ -35,10 +33,7 @@ impl<'ast> Program {
|
||||
let mut num_parameters = 0usize;
|
||||
|
||||
file.circuits.into_iter().for_each(|circuit| {
|
||||
circuits.insert(
|
||||
Identifier::from(circuit.identifier.clone()),
|
||||
Circuit::from(circuit),
|
||||
);
|
||||
circuits.insert(Identifier::from(circuit.identifier.clone()), Circuit::from(circuit));
|
||||
});
|
||||
file.functions.into_iter().for_each(|function_def| {
|
||||
functions.insert(
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user