mirror of
https://github.com/ProvableHQ/leo.git
synced 2024-09-11 05:45:30 +03:00
constraints for loops
This commit is contained in:
parent
0a8cda3d7f
commit
455c0b631a
@ -1,9 +1,6 @@
|
||||
struct Foo {
|
||||
bool x
|
||||
}
|
||||
def main() -> (field):
|
||||
field[3] a = [1, 2, 3] // initialize the array
|
||||
field[4] b = [42; 4]
|
||||
c = a[1..3] // helloo???
|
||||
bool[3] d = [true, false, true]
|
||||
return a[0]
|
||||
a = 1
|
||||
for i in 0..4 do
|
||||
a = a + 1
|
||||
endfor
|
||||
return a
|
@ -639,21 +639,50 @@ impl ResolvedProgram {
|
||||
)
|
||||
}
|
||||
|
||||
// fn enforce_statement<F: Field + PrimeField, CS: ConstraintSystem<F>>(
|
||||
// &mut self,
|
||||
// cs: &mut CS,
|
||||
// statement: Statement,
|
||||
// ) {
|
||||
// match statement {
|
||||
// Statement::Definition(variable, expression) => {
|
||||
// self.enforce_definition_statement(cs, variable, expression);
|
||||
// }
|
||||
// Statement::Return(statements) => {
|
||||
// let res = self.enforce_return_statement(cs, statements);
|
||||
//
|
||||
// }
|
||||
// };
|
||||
// }
|
||||
fn enforce_statement<F: Field + PrimeField, CS: ConstraintSystem<F>>(
|
||||
&mut self,
|
||||
cs: &mut CS,
|
||||
statement: Statement,
|
||||
) {
|
||||
match statement {
|
||||
Statement::Definition(variable, expression) => {
|
||||
self.enforce_definition_statement(cs, variable, expression);
|
||||
}
|
||||
Statement::For(index, start, stop, statements) => {
|
||||
self.enforce_for_statement(cs, index, start, stop, statements);
|
||||
}
|
||||
Statement::Return(statements) => {
|
||||
// TODO: add support for early termination
|
||||
let _res = self.enforce_return_statement(cs, statements);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
fn enforce_for_statement<F: Field + PrimeField, CS: ConstraintSystem<F>>(
|
||||
&mut self,
|
||||
cs: &mut CS,
|
||||
index: Variable,
|
||||
start: FieldExpression,
|
||||
stop: FieldExpression,
|
||||
statements: Vec<Statement>,
|
||||
) {
|
||||
let start_index = self.enforce_index(cs, start);
|
||||
let stop_index = self.enforce_index(cs, stop);
|
||||
|
||||
for i in start_index..stop_index {
|
||||
// Store index
|
||||
self.resolved_variables.insert(
|
||||
index.clone(),
|
||||
ResolvedValue::FieldElement(UInt32::constant(i as u32)),
|
||||
);
|
||||
|
||||
// Evaluate statements
|
||||
statements
|
||||
.clone()
|
||||
.into_iter()
|
||||
.for_each(|statement| self.enforce_statement(cs, statement));
|
||||
}
|
||||
}
|
||||
|
||||
fn enforce_function<F: Field + PrimeField, CS: ConstraintSystem<F>>(
|
||||
&mut self,
|
||||
@ -715,7 +744,10 @@ impl ResolvedProgram {
|
||||
.into_iter()
|
||||
.for_each(|statement| match statement {
|
||||
Statement::Definition(variable, expression) => {
|
||||
self.enforce_definition_statement(cs, variable, expression)
|
||||
self.enforce_definition_statement(cs, variable, expression);
|
||||
}
|
||||
Statement::For(index, start, stop, statements) => {
|
||||
self.enforce_for_statement(cs, index, start, stop, statements);
|
||||
}
|
||||
Statement::Return(expressions) => {
|
||||
return_values = self.enforce_return_statement(cs, expressions)
|
||||
|
@ -103,6 +103,7 @@ pub enum Expression {
|
||||
pub enum Statement {
|
||||
// Declaration(Variable),
|
||||
Definition(Variable, Expression),
|
||||
For(Variable, FieldExpression, FieldExpression, Vec<Statement>),
|
||||
Return(Vec<Expression>),
|
||||
}
|
||||
|
||||
@ -120,12 +121,6 @@ pub struct StructMember {
|
||||
pub expression: Expression,
|
||||
}
|
||||
|
||||
// #[derive(Clone, Debug)]
|
||||
// pub struct StructExpression {
|
||||
// pub variable: Variable,
|
||||
// pub members: Vec<StructMember>
|
||||
// }
|
||||
|
||||
#[derive(Clone)]
|
||||
pub struct StructField {
|
||||
pub variable: Variable,
|
||||
|
@ -6,8 +6,8 @@
|
||||
|
||||
use crate::aleo_program::{
|
||||
BooleanExpression, BooleanSpread, BooleanSpreadOrExpression, Expression, FieldExpression,
|
||||
FieldRangeOrExpression, FieldSpread, FieldSpreadOrExpression, Function, FunctionName, Parameter, Statement,
|
||||
Struct, StructField, Type, Variable,
|
||||
FieldRangeOrExpression, FieldSpread, FieldSpreadOrExpression, Function, FunctionName,
|
||||
Parameter, Statement, Struct, StructField, Type, Variable,
|
||||
};
|
||||
|
||||
use std::fmt;
|
||||
@ -166,15 +166,22 @@ impl<'ast> fmt::Display for Expression {
|
||||
impl fmt::Display for Statement {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
Statement::Definition(ref variable, ref statement) => {
|
||||
write!(f, "{} = {}", variable, statement)
|
||||
}
|
||||
Statement::For(ref var, ref start, ref stop, ref list) => {
|
||||
write!(f, "for {} in {}..{} do\n", var, start, stop)?;
|
||||
for l in list {
|
||||
write!(f, "\t\t{}\n", l)?;
|
||||
}
|
||||
write!(f, "\tendfor")
|
||||
}
|
||||
Statement::Return(ref statements) => {
|
||||
statements.iter().for_each(|statement| {
|
||||
write!(f, "return {}", statement).unwrap();
|
||||
});
|
||||
write!(f, "\n")
|
||||
}
|
||||
Statement::Definition(ref variable, ref statement) => {
|
||||
write!(f, "{} = {}", variable, statement)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -182,15 +189,22 @@ impl fmt::Display for Statement {
|
||||
impl fmt::Debug for Statement {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
Statement::Definition(ref variable, ref statement) => {
|
||||
write!(f, "{} = {}", variable, statement)
|
||||
}
|
||||
Statement::For(ref var, ref start, ref stop, ref list) => {
|
||||
write!(f, "for {:?} in {:?}..{:?} do\n", var, start, stop)?;
|
||||
for l in list {
|
||||
write!(f, "\t\t{:?}\n", l)?;
|
||||
}
|
||||
write!(f, "\tendfor")
|
||||
}
|
||||
Statement::Return(ref statements) => {
|
||||
statements.iter().for_each(|statement| {
|
||||
write!(f, "return {}", statement).unwrap();
|
||||
});
|
||||
write!(f, "\n")
|
||||
}
|
||||
Statement::Definition(ref variable, ref statement) => {
|
||||
write!(f, "{} = {}", variable, statement)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -561,10 +561,18 @@ impl<'ast> From<ast::ReturnStatement<'ast>> for types::Statement {
|
||||
}
|
||||
}
|
||||
|
||||
impl<'ast> From<ast::IterationStatement<'ast>> for types::Statement {
|
||||
fn from(statement: ast::IterationStatement<'ast>) -> Self {
|
||||
println!("{:#?}", statement);
|
||||
unimplemented!()
|
||||
impl<'ast> From<ast::ForStatement<'ast>> for types::Statement {
|
||||
fn from(statement: ast::ForStatement<'ast>) -> Self {
|
||||
types::Statement::For(
|
||||
types::Variable::from(statement.index),
|
||||
types::FieldExpression::from(statement.start),
|
||||
types::FieldExpression::from(statement.stop),
|
||||
statement
|
||||
.statements
|
||||
.into_iter()
|
||||
.map(|statement| types::Statement::from(statement))
|
||||
.collect(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@ -704,7 +712,8 @@ impl<'ast> From<ast::Function<'ast>> for types::Function {
|
||||
|
||||
impl<'ast> From<ast::File<'ast>> for types::Program {
|
||||
fn from(file: ast::File<'ast>) -> Self {
|
||||
// 1. compile ast -> aleo program representation
|
||||
// Compiled ast -> aleo program representation
|
||||
|
||||
let mut structs = HashMap::new();
|
||||
let mut functions = HashMap::new();
|
||||
|
||||
@ -721,17 +730,10 @@ impl<'ast> From<ast::File<'ast>> for types::Program {
|
||||
);
|
||||
});
|
||||
|
||||
// let statements: Vec<types::Statement> = file
|
||||
// .statements
|
||||
// .into_iter()
|
||||
// .map(|statement| types::Statement::from(statement))
|
||||
// .collect();
|
||||
|
||||
types::Program {
|
||||
id: "main".into(),
|
||||
structs,
|
||||
functions,
|
||||
// statements,
|
||||
arguments: vec![],
|
||||
returns: vec![],
|
||||
}
|
||||
|
17
src/ast.rs
17
src/ast.rs
@ -701,12 +701,11 @@ pub struct DefinitionStatement<'ast> {
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, FromPest, PartialEq)]
|
||||
#[pest_ast(rule(Rule::statement_iteration))]
|
||||
pub struct IterationStatement<'ast> {
|
||||
pub ty: Type<'ast>,
|
||||
#[pest_ast(rule(Rule::statement_for))]
|
||||
pub struct ForStatement<'ast> {
|
||||
pub index: Variable<'ast>,
|
||||
pub from: Expression<'ast>,
|
||||
pub to: Expression<'ast>,
|
||||
pub start: Expression<'ast>,
|
||||
pub stop: Expression<'ast>,
|
||||
pub statements: Vec<Statement<'ast>>,
|
||||
#[pest_ast(outer())]
|
||||
pub span: Span<'ast>,
|
||||
@ -725,7 +724,7 @@ pub struct ReturnStatement<'ast> {
|
||||
pub enum Statement<'ast> {
|
||||
Assign(AssignStatement<'ast>),
|
||||
Definition(DefinitionStatement<'ast>),
|
||||
Iteration(IterationStatement<'ast>),
|
||||
Iteration(ForStatement<'ast>),
|
||||
Return(ReturnStatement<'ast>),
|
||||
}
|
||||
|
||||
@ -741,12 +740,12 @@ impl<'ast> fmt::Display for DefinitionStatement<'ast> {
|
||||
}
|
||||
}
|
||||
|
||||
impl<'ast> fmt::Display for IterationStatement<'ast> {
|
||||
impl<'ast> fmt::Display for ForStatement<'ast> {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
write!(
|
||||
f,
|
||||
"for {} {} in {}..{} do {:#?} endfor",
|
||||
self.ty, self.index, self.from, self.to, self.statements
|
||||
"for {} in {}..{} do {:#?} endfor",
|
||||
self.index, self.start, self.stop, self.statements
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -135,11 +135,11 @@ expression_tuple = _{ (expression ~ ("," ~ expression)*)? }
|
||||
statement_assign = { variable ~ "=" ~ expression }
|
||||
statement_definition = { ty ~ variable ~ "=" ~ expression }
|
||||
statement_return = { "return" ~ expression_tuple }
|
||||
statement_iteration = { "for" ~ ty ~ variable ~ "in" ~ expression ~ ".." ~ expression ~ "do" ~ NEWLINE* ~ statement* ~ "endfor"}
|
||||
statement_for = { "for" ~ variable ~ "in" ~ expression ~ ".." ~ expression ~ "do" ~ NEWLINE* ~ statement* ~ "endfor"}
|
||||
|
||||
statement = {
|
||||
(statement_return
|
||||
| (statement_iteration
|
||||
| (statement_for
|
||||
| statement_definition
|
||||
| statement_assign
|
||||
) ~ NEWLINE
|
||||
|
Loading…
Reference in New Issue
Block a user