diff --git a/.rusty-hook.toml b/.rusty-hook.toml index d09d8365d1..0b18442974 100644 --- a/.rusty-hook.toml +++ b/.rusty-hook.toml @@ -1,5 +1,5 @@ [hooks] -pre-commit = "cargo +nightly fmt --all -- --check" +pre-commit = "cargo +nightly clippy && cargo +nightly fmt --all -- --check" [logging] verbose = false diff --git a/Cargo.lock b/Cargo.lock index 7a4b8c47b5..bab77ee4e2 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2485,9 +2485,9 @@ dependencies = [ [[package]] name = "serde_json" -version = "1.0.59" +version = "1.0.60" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dcac07dbffa1c65e7f816ab9eba78eb142c6d44410f4eeba1e26e4f5dfa56b95" +checksum = "1500e84d27fe482ed1dc791a56eddc2f230046a040fa908c08bda1d9fb615779" dependencies = [ "itoa", "ryu", diff --git a/ast/src/circuits/circuit_member.rs b/ast/src/circuits/circuit_member.rs index f8e885dd9d..c86ae4156b 100644 --- a/ast/src/circuits/circuit_member.rs +++ b/ast/src/circuits/circuit_member.rs @@ -15,10 +15,9 @@ // along with the Leo library. If not, see . use crate::{Function, Identifier, Type}; -use leo_grammar::circuits::{ - CircuitFunction as GrammarCircuitFunction, - CircuitMember as GrammarCircuitMember, - CircuitVariableDefinition as GrammarCircuitVariableDefinition, +use leo_grammar::{ + circuits::{CircuitMember as GrammarCircuitMember, CircuitVariableDefinition as GrammarCircuitVariableDefinition}, + functions::Function as GrammarFunction, }; use serde::{Deserialize, Serialize}; @@ -26,28 +25,24 @@ use std::fmt; #[derive(Clone, PartialEq, Eq, Serialize, Deserialize)] pub enum CircuitMember { - // (is_mutable, variable_name, variable_type) - CircuitVariable(bool, Identifier, Type), - // (is_static, function) - CircuitFunction(bool, Function), + // (variable_name, variable_type) + CircuitVariable(Identifier, Type), + // (function) + CircuitFunction(Function), } impl<'ast> From> for CircuitMember { fn from(circuit_value: GrammarCircuitVariableDefinition<'ast>) -> Self { CircuitMember::CircuitVariable( - circuit_value.mutable.is_some(), Identifier::from(circuit_value.identifier), Type::from(circuit_value.type_), ) } } -impl<'ast> From> for CircuitMember { - fn from(circuit_function: GrammarCircuitFunction<'ast>) -> Self { - CircuitMember::CircuitFunction( - circuit_function._static.is_some(), - Function::from(circuit_function.function), - ) +impl<'ast> From> for CircuitMember { + fn from(circuit_function: GrammarFunction<'ast>) -> Self { + CircuitMember::CircuitFunction(Function::from(circuit_function)) } } @@ -63,16 +58,10 @@ impl<'ast> From> for CircuitMember { impl fmt::Display for CircuitMember { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { match self { - CircuitMember::CircuitVariable(ref mutable, ref identifier, ref type_) => { - if *mutable { - write!(f, "mut ")?; - } + CircuitMember::CircuitVariable(ref identifier, ref type_) => { write!(f, "{}: {}", identifier, type_) } - CircuitMember::CircuitFunction(ref static_, ref function) => { - if *static_ { - write!(f, "static ")?; - } + CircuitMember::CircuitFunction(ref function) => { write!(f, "{}", function) } } diff --git a/ast/src/common/identifier.rs b/ast/src/common/identifier.rs index e6f3f4baf2..84dc49fa87 100644 --- a/ast/src/common/identifier.rs +++ b/ast/src/common/identifier.rs @@ -14,12 +14,18 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::Span; +use crate::{InputKeyword, MutSelfKeyword, SelfKeyword, Span}; use leo_grammar::{ annotations::AnnotationArgument, - common::{Identifier as GrammarIdentifier, KeywordOrIdentifier, SelfKeyword, SelfKeywordOrIdentifier}, + common::{ + Identifier as GrammarIdentifier, + KeywordOrIdentifier, + MutSelfKeyword as GrammarMutSelfKeyword, + SelfKeyword as GrammarSelfKeyword, + SelfKeywordOrIdentifier, + }, expressions::CircuitName, - functions::InputKeyword, + functions::InputKeyword as GrammarInputKeyword, imports::PackageName as GrammarPackageName, types::SelfType, }; @@ -128,20 +134,56 @@ impl<'ast> From> for Identifier { } } -impl<'ast> From> for Identifier { - fn from(self_: SelfKeyword<'ast>) -> Self { +impl<'ast> From> for Identifier { + fn from(grammar: GrammarSelfKeyword<'ast>) -> Self { Self { - name: self_.keyword, - span: Span::from(self_.span), + name: grammar.keyword, + span: Span::from(grammar.span), } } } -impl<'ast> From> for Identifier { - fn from(input: InputKeyword<'ast>) -> Self { +impl From for Identifier { + fn from(keyword: SelfKeyword) -> Self { Self { - name: input.keyword, - span: Span::from(input.span), + name: keyword.to_string(), + span: keyword.span, + } + } +} + +impl<'ast> From> for Identifier { + fn from(grammar: GrammarMutSelfKeyword<'ast>) -> Self { + Self { + name: grammar.to_string(), + span: Span::from(grammar.span), + } + } +} + +impl From for Identifier { + fn from(keyword: MutSelfKeyword) -> Self { + Self { + name: keyword.to_string(), + span: keyword.span, + } + } +} + +impl<'ast> From> for Identifier { + fn from(grammar: GrammarInputKeyword<'ast>) -> Self { + Self { + name: grammar.keyword, + span: Span::from(grammar.span), + } + } +} + +impl From for Identifier { + fn from(keyword: InputKeyword) -> Self { + Self { + name: keyword.to_string(), + span: keyword.span, } } } diff --git a/ast/src/common/input_keyword.rs b/ast/src/common/input_keyword.rs new file mode 100644 index 0000000000..5df0aa7b08 --- /dev/null +++ b/ast/src/common/input_keyword.rs @@ -0,0 +1,42 @@ +// Copyright (C) 2019-2020 Aleo Systems Inc. +// This file is part of the Leo library. + +// The Leo library is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. + +// The Leo library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License +// along with the Leo library. If not, see . + +use crate::Span; +use leo_grammar::functions::InputKeyword as GrammarInputKeyword; + +use serde::{Deserialize, Serialize}; +use std::fmt; + +/// The `input` keyword can view program register, record, and state values. +/// Values cannot be modified. The `input` keyword cannot be made mutable. +#[derive(Clone, Serialize, Deserialize)] +pub struct InputKeyword { + pub span: Span, +} + +impl<'ast> From> for InputKeyword { + fn from(grammar: GrammarInputKeyword<'ast>) -> Self { + Self { + span: Span::from(grammar.span), + } + } +} + +impl fmt::Display for InputKeyword { + fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { + write!(f, "input") + } +} diff --git a/ast/src/common/mod.rs b/ast/src/common/mod.rs index 382d82142c..4d20d843aa 100644 --- a/ast/src/common/mod.rs +++ b/ast/src/common/mod.rs @@ -26,12 +26,21 @@ pub use declare::*; pub mod identifier; pub use identifier::*; +pub mod input_keyword; +pub use input_keyword::*; + +pub mod mut_self_keyword; +pub use mut_self_keyword::*; + pub mod positive_number; pub use positive_number::*; pub mod range_or_expression; pub use range_or_expression::*; +pub mod self_keyword; +pub use self_keyword::*; + pub mod span; pub use span::*; diff --git a/ast/src/common/mut_self_keyword.rs b/ast/src/common/mut_self_keyword.rs new file mode 100644 index 0000000000..b11a8df0ac --- /dev/null +++ b/ast/src/common/mut_self_keyword.rs @@ -0,0 +1,41 @@ +// Copyright (C) 2019-2020 Aleo Systems Inc. +// This file is part of the Leo library. + +// The Leo library is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. + +// The Leo library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License +// along with the Leo library. If not, see . + +use crate::Span; +use leo_grammar::common::MutSelfKeyword as GrammarMutSelfKeyword; + +use serde::{Deserialize, Serialize}; +use std::fmt; + +/// The `mut self` keyword can view and modify circuit values inside of a circuit function. +#[derive(Clone, Serialize, Deserialize)] +pub struct MutSelfKeyword { + pub span: Span, +} + +impl<'ast> From> for MutSelfKeyword { + fn from(grammar: GrammarMutSelfKeyword<'ast>) -> Self { + Self { + span: Span::from(grammar.span), + } + } +} + +impl fmt::Display for MutSelfKeyword { + fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { + write!(f, "mut self") + } +} diff --git a/ast/src/common/self_keyword.rs b/ast/src/common/self_keyword.rs new file mode 100644 index 0000000000..8dfdfecc70 --- /dev/null +++ b/ast/src/common/self_keyword.rs @@ -0,0 +1,42 @@ +// Copyright (C) 2019-2020 Aleo Systems Inc. +// This file is part of the Leo library. + +// The Leo library is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. + +// The Leo library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License +// along with the Leo library. If not, see . + +use crate::Span; +use leo_grammar::common::SelfKeyword as GrammarSelfKeyword; + +use serde::{Deserialize, Serialize}; +use std::fmt; + +/// The `self` keyword can view circuit values inside of a circuit function. +/// Circuit values cannot be modified. To modify values use the `mut self` [MutSelfKeyword]. +#[derive(Clone, Serialize, Deserialize)] +pub struct SelfKeyword { + pub span: Span, +} + +impl<'ast> From> for SelfKeyword { + fn from(grammar: GrammarSelfKeyword<'ast>) -> Self { + Self { + span: Span::from(grammar.span), + } + } +} + +impl fmt::Display for SelfKeyword { + fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { + write!(f, "self") + } +} diff --git a/ast/src/functions/function.rs b/ast/src/functions/function.rs index be15d5131e..e9ee6efe3d 100644 --- a/ast/src/functions/function.rs +++ b/ast/src/functions/function.rs @@ -14,7 +14,7 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{FunctionInput, Identifier, Span, Statement, Type}; +use crate::{Block, FunctionInput, Identifier, Span, Type}; use leo_grammar::functions::Function as GrammarFunction; use serde::{Deserialize, Serialize}; @@ -25,7 +25,7 @@ pub struct Function { pub identifier: Identifier, pub input: Vec, pub output: Option, - pub statements: Vec, + pub block: Block, pub span: Span, } @@ -43,13 +43,13 @@ impl<'ast> From> for Function { let parameters = function.parameters.into_iter().map(FunctionInput::from).collect(); let returns = function.returns.map(Type::from); - let statements = function.statements.into_iter().map(Statement::from).collect(); + let block = Block::from(function.block); Function { identifier: function_name, input: parameters, output: returns, - statements, + block, span: Span::from(function.span), } } @@ -60,21 +60,38 @@ impl Function { &self.identifier.name } + /// + /// Returns `true` if the function has input `self` or `mut self`. + /// Returns `false` otherwise. + /// + pub fn contains_self(&self) -> bool { + self.input.iter().any(|param| param.is_self()) + } + + /// + /// Returns `true` if the function has input `mut self`. + /// Returns `false` otherwise. + /// + pub fn contains_mut_self(&self) -> bool { + self.input.iter().any(|param| param.is_mut_self()) + } + + /// + /// Returns an iterator of [&FunctionInput] removing `self` and `mut self` inputs. + /// + pub fn filter_self_inputs(&self) -> impl Iterator { + self.input.iter().filter(|input| !input.is_self()) + } + fn format(&self, f: &mut fmt::Formatter) -> fmt::Result { write!(f, "function {}", self.identifier)?; let parameters = self.input.iter().map(|x| x.to_string()).collect::>().join(","); let returns = self.output.as_ref().map(|type_| type_.to_string()); - let statements = self - .statements - .iter() - .map(|s| format!("\t{}\n", s)) - .collect::>() - .join(""); if returns.is_none() { - write!(f, "({}) {{\n{}}}", parameters, statements,) + write!(f, "({}) {}", parameters, self.block) } else { - write!(f, "({}) -> {} {{\n{}}}", parameters, returns.unwrap(), statements,) + write!(f, "({}) -> {} {}", parameters, returns.unwrap(), self.block) } } } diff --git a/ast/src/functions/input/input_variable.rs b/ast/src/functions/input/input_variable.rs index cc7c75231c..3286496b89 100644 --- a/ast/src/functions/input/input_variable.rs +++ b/ast/src/functions/input/input_variable.rs @@ -14,29 +14,27 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{FunctionInputVariable, Identifier, Span}; +use crate::{FunctionInputVariable, InputKeyword, MutSelfKeyword, SelfKeyword}; use leo_grammar::functions::input::Input as GrammarInput; use serde::{Deserialize, Serialize}; use std::fmt; -#[derive(Clone, PartialEq, Eq, Serialize, Deserialize)] +/// Enumerates the possible inputs to a function. +#[derive(Clone, Serialize, Deserialize)] pub enum FunctionInput { - InputKeyword(Identifier), + InputKeyword(InputKeyword), + SelfKeyword(SelfKeyword), + MutSelfKeyword(MutSelfKeyword), Variable(FunctionInputVariable), } impl<'ast> From> for FunctionInput { fn from(input: GrammarInput<'ast>) -> Self { match input { - GrammarInput::InputKeyword(input_keyword) => { - let id = Identifier { - name: input_keyword.keyword, - span: Span::from(input_keyword.span), - }; - - FunctionInput::InputKeyword(id) - } + GrammarInput::InputKeyword(keyword) => FunctionInput::InputKeyword(InputKeyword::from(keyword)), + GrammarInput::SelfKeyword(keyword) => FunctionInput::SelfKeyword(SelfKeyword::from(keyword)), + GrammarInput::MutSelfKeyword(keyword) => FunctionInput::MutSelfKeyword(MutSelfKeyword::from(keyword)), GrammarInput::FunctionInput(function_input) => { FunctionInput::Variable(FunctionInputVariable::from(function_input)) } @@ -45,9 +43,37 @@ impl<'ast> From> for FunctionInput { } impl FunctionInput { + /// + /// Returns `true` if the function input is the `self` or `mut self` keyword. + /// Returns `false` otherwise. + /// + pub fn is_self(&self) -> bool { + match self { + FunctionInput::InputKeyword(_) => false, + FunctionInput::SelfKeyword(_) => true, + FunctionInput::MutSelfKeyword(_) => true, + FunctionInput::Variable(_) => false, + } + } + + /// + /// Returns `true` if the function input is the `mut self` keyword. + /// Returns `false` otherwise. + /// + pub fn is_mut_self(&self) -> bool { + match self { + FunctionInput::InputKeyword(_) => false, + FunctionInput::SelfKeyword(_) => false, + FunctionInput::MutSelfKeyword(_) => true, + FunctionInput::Variable(_) => false, + } + } + fn format(&self, f: &mut fmt::Formatter) -> fmt::Result { match self { - FunctionInput::InputKeyword(id) => write!(f, "{}", id), + FunctionInput::InputKeyword(keyword) => write!(f, "{}", keyword), + FunctionInput::SelfKeyword(keyword) => write!(f, "{}", keyword), + FunctionInput::MutSelfKeyword(keyword) => write!(f, "{}", keyword), FunctionInput::Variable(function_input) => write!(f, "{}", function_input), } } @@ -64,3 +90,18 @@ impl fmt::Debug for FunctionInput { self.format(f) } } + +impl PartialEq for FunctionInput { + /// Returns true if `self == other`. Does not compare spans. + fn eq(&self, other: &Self) -> bool { + match (self, other) { + (FunctionInput::InputKeyword(_), FunctionInput::InputKeyword(_)) => true, + (FunctionInput::SelfKeyword(_), FunctionInput::SelfKeyword(_)) => true, + (FunctionInput::MutSelfKeyword(_), FunctionInput::MutSelfKeyword(_)) => true, + (FunctionInput::Variable(left), FunctionInput::Variable(right)) => left.eq(right), + _ => false, + } + } +} + +impl Eq for FunctionInput {} diff --git a/ast/src/statements/block.rs b/ast/src/statements/block.rs new file mode 100644 index 0000000000..aba37cb8c9 --- /dev/null +++ b/ast/src/statements/block.rs @@ -0,0 +1,48 @@ +// Copyright (C) 2019-2020 Aleo Systems Inc. +// This file is part of the Leo library. + +// The Leo library is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. + +// The Leo library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License +// along with the Leo library. If not, see . + +use crate::Statement; +use leo_grammar::statements::Block as GrammarBlock; + +use serde::{Deserialize, Serialize}; +use std::fmt; + +#[derive(Clone, PartialEq, Eq, Serialize, Deserialize)] +pub struct Block { + pub statements: Vec, +} + +impl<'ast> From> for Block { + fn from(block: GrammarBlock<'ast>) -> Self { + Block { + statements: block.statements.into_iter().map(Statement::from).collect(), + } + } +} + +impl fmt::Display for Block { + fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { + writeln!(f, "{{")?; + if self.statements.is_empty() { + writeln!(f, "\t")?; + } else { + self.statements + .iter() + .try_for_each(|statement| writeln!(f, "\t{}", statement))?; + } + write!(f, "}}") + } +} diff --git a/ast/src/statements/conditional_nested_or_end_statement.rs b/ast/src/statements/conditional_nested_or_end_statement.rs index ddb1f75dc1..f972db8a61 100644 --- a/ast/src/statements/conditional_nested_or_end_statement.rs +++ b/ast/src/statements/conditional_nested_or_end_statement.rs @@ -14,7 +14,7 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{ConditionalStatement, Statement}; +use crate::{Block, ConditionalStatement}; use leo_grammar::statements::ConditionalNestedOrEndStatement as GrammarConditionalNestedOrEndStatement; use serde::{Deserialize, Serialize}; @@ -23,7 +23,7 @@ use std::fmt; #[derive(Clone, PartialEq, Eq, Serialize, Deserialize)] pub enum ConditionalNestedOrEndStatement { Nested(Box), - End(Vec), + End(Block), } impl<'ast> From> for ConditionalNestedOrEndStatement { @@ -32,8 +32,8 @@ impl<'ast> From> for ConditionalNes GrammarConditionalNestedOrEndStatement::Nested(nested) => { ConditionalNestedOrEndStatement::Nested(Box::new(ConditionalStatement::from(*nested))) } - GrammarConditionalNestedOrEndStatement::End(statements) => { - ConditionalNestedOrEndStatement::End(statements.into_iter().map(Statement::from).collect()) + GrammarConditionalNestedOrEndStatement::End(block) => { + ConditionalNestedOrEndStatement::End(Block::from(block)) } } } @@ -43,13 +43,7 @@ impl fmt::Display for ConditionalNestedOrEndStatement { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { match *self { ConditionalNestedOrEndStatement::Nested(ref nested) => write!(f, "else {}", nested), - ConditionalNestedOrEndStatement::End(ref statements) => { - writeln!(f, "else {{")?; - for statement in statements.iter() { - writeln!(f, "\t\t{}", statement)?; - } - write!(f, "\t}}") - } + ConditionalNestedOrEndStatement::End(ref block) => write!(f, "else {}", block), } } } diff --git a/ast/src/statements/conditional_statement.rs b/ast/src/statements/conditional_statement.rs index 628b0f9dc4..43006e4126 100644 --- a/ast/src/statements/conditional_statement.rs +++ b/ast/src/statements/conditional_statement.rs @@ -14,7 +14,7 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{ConditionalNestedOrEndStatement, Expression, Statement}; +use crate::{Block, ConditionalNestedOrEndStatement, Expression}; use leo_grammar::statements::ConditionalStatement as GrammarConditionalStatement; use serde::{Deserialize, Serialize}; @@ -23,7 +23,7 @@ use std::fmt; #[derive(Clone, PartialEq, Eq, Serialize, Deserialize)] pub struct ConditionalStatement { pub condition: Expression, - pub statements: Vec, + pub block: Block, pub next: Option, } @@ -31,7 +31,7 @@ impl<'ast> From> for ConditionalStatement { fn from(statement: GrammarConditionalStatement<'ast>) -> Self { ConditionalStatement { condition: Expression::from(statement.condition), - statements: statement.statements.into_iter().map(Statement::from).collect(), + block: Block::from(statement.block), next: statement .next .map(|n_or_e| Some(ConditionalNestedOrEndStatement::from(n_or_e))) @@ -42,13 +42,10 @@ impl<'ast> From> for ConditionalStatement { impl fmt::Display for ConditionalStatement { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - writeln!(f, "if ({}) {{", self.condition)?; - for statement in self.statements.iter() { - writeln!(f, "\t\t{}", statement)?; - } + write!(f, "if ({}) {}", self.condition, self.block)?; match self.next.clone() { - Some(n_or_e) => write!(f, "\t}} {}", n_or_e), - None => write!(f, "\t}}"), + Some(n_or_e) => write!(f, " {}", n_or_e), + None => write!(f, ""), } } } diff --git a/ast/src/statements/mod.rs b/ast/src/statements/mod.rs index 8fcd2b997e..f8a5048bdd 100644 --- a/ast/src/statements/mod.rs +++ b/ast/src/statements/mod.rs @@ -22,3 +22,6 @@ pub use conditional_statement::*; pub mod statement; pub use statement::*; + +pub mod block; +pub use block::*; diff --git a/ast/src/statements/statement.rs b/ast/src/statements/statement.rs index 680ddf7dbd..a4b8463f76 100644 --- a/ast/src/statements/statement.rs +++ b/ast/src/statements/statement.rs @@ -14,7 +14,17 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{Assignee, ConditionalStatement, ConsoleFunctionCall, Declare, Expression, Identifier, Span, Variables}; +use crate::{ + Assignee, + Block, + ConditionalStatement, + ConsoleFunctionCall, + Declare, + Expression, + Identifier, + Span, + Variables, +}; use leo_grammar::{ console::ConsoleFunctionCall as GrammarConsoleFunctionCall, operations::AssignOperation, @@ -38,7 +48,7 @@ pub enum Statement { Definition(Declare, Variables, Expression, Span), Assign(Assignee, Expression, Span), Conditional(ConditionalStatement, Span), - Iteration(Identifier, Box<(Expression, Expression)>, Vec, Span), + Iteration(Identifier, Box<(Expression, Expression)>, Block, Span), Console(ConsoleFunctionCall), Expression(Expression, Span), } @@ -127,7 +137,7 @@ impl<'ast> From> for Statement { Statement::Iteration( Identifier::from(statement.index), Box::new((Expression::from(statement.start), Expression::from(statement.stop))), - statement.statements.into_iter().map(Statement::from).collect(), + Block::from(statement.block), Span::from(statement.span), ) } @@ -176,12 +186,8 @@ impl fmt::Display for Statement { } Statement::Assign(ref variable, ref statement, ref _span) => write!(f, "{} = {};", variable, statement), Statement::Conditional(ref statement, ref _span) => write!(f, "{}", statement), - Statement::Iteration(ref var, ref start_stop, ref list, ref _span) => { - writeln!(f, "for {} in {}..{} {{", var, start_stop.0, start_stop.1)?; - for l in list { - writeln!(f, "\t\t{}", l)?; - } - write!(f, "\t}}") + Statement::Iteration(ref var, ref start_stop, ref block, ref _span) => { + write!(f, "for {} in {}..{} {}", var, start_stop.0, start_stop.1, block) } Statement::Console(ref console) => write!(f, "{}", console), Statement::Expression(ref expression, ref _span) => write!(f, "{};", expression), diff --git a/ast/tests/serialization/expected_leo_ast.json b/ast/tests/serialization/expected_leo_ast.json index f542246816..c5ca6829d0 100644 --- a/ast/tests/serialization/expected_leo_ast.json +++ b/ast/tests/serialization/expected_leo_ast.json @@ -8,50 +8,52 @@ "identifier": "{\"name\":\"main\",\"span\":\"{\\\"text\\\":\\\" function main() {\\\",\\\"line\\\":1,\\\"start\\\":10,\\\"end\\\":14}\"}", "input": [], "output": null, - "statements": [ - { - "Return": [ - { - "Add": [[ - { - "Implicit": [ - "1", - { - "text": " return 1 + 1", - "line": 2, - "start": 12, - "end": 13 - } - ] - }, - { - "Implicit": [ - "1", - { - "text": " return 1 + 1", - "line": 2, - "start": 16, - "end": 17 - } - ] - }], - { - "text": " return 1 + 1", - "line": 2, - "start": 12, - "end": 17 - } - ] - }, - { - "text": " return 1 + 1", - "line": 2, - "start": 5, - "end": 17 - } - ] - } - ], + "block" : { + "statements": [ + { + "Return": [ + { + "Add": [[ + { + "Implicit": [ + "1", + { + "text": " return 1 + 1", + "line": 2, + "start": 12, + "end": 13 + } + ] + }, + { + "Implicit": [ + "1", + { + "text": " return 1 + 1", + "line": 2, + "start": 16, + "end": 17 + } + ] + }], + { + "text": " return 1 + 1", + "line": 2, + "start": 12, + "end": 17 + } + ] + }, + { + "text": " return 1 + 1", + "line": 2, + "start": 5, + "end": 17 + } + ] + } + ] + }, "span": { "text": " function main() {", "line": 1, diff --git a/compiler/src/console/assert.rs b/compiler/src/console/assert.rs index 66465bd11f..e3df68ba9d 100644 --- a/compiler/src/console/assert.rs +++ b/compiler/src/console/assert.rs @@ -16,7 +16,13 @@ //! Enforces an assert equals statement in a compiled Leo program. -use crate::{errors::ConsoleError, program::ConstrainedProgram, value::ConstrainedValue, GroupType}; +use crate::{ + errors::ConsoleError, + get_indicator_value, + program::ConstrainedProgram, + value::ConstrainedValue, + GroupType, +}; use leo_ast::{Expression, Span, Type}; use snarkos_models::{ @@ -30,7 +36,7 @@ impl> ConstrainedProgram { cs: &mut CS, file_scope: &str, function_scope: &str, - indicator: Option, + indicator: &Boolean, expression: Expression, span: &Span, ) -> Result<(), ConsoleError> { @@ -42,12 +48,8 @@ impl> ConstrainedProgram { // If the indicator bit is false, do not evaluate the assertion // This is okay since we are not enforcing any constraints - let false_boolean = Boolean::Constant(false); - - if let Some(indicator_bool) = indicator { - if indicator_bool.eq(&false_boolean) { - return Ok(()); // continue execution - } + if !get_indicator_value(indicator) { + return Ok(()); // Continue execution. } // Unwrap assertion value and handle errors diff --git a/compiler/src/console/console.rs b/compiler/src/console/console.rs index 1be1d801cb..23a7276cfa 100644 --- a/compiler/src/console/console.rs +++ b/compiler/src/console/console.rs @@ -16,7 +16,7 @@ //! Evaluates a macro in a compiled Leo program. -use crate::{errors::ConsoleError, program::ConstrainedProgram, GroupType}; +use crate::{errors::ConsoleError, program::ConstrainedProgram, statement::get_indicator_value, GroupType}; use leo_ast::{ConsoleFunction, ConsoleFunctionCall}; use snarkos_models::{ @@ -30,7 +30,7 @@ impl> ConstrainedProgram { cs: &mut CS, file_scope: &str, function_scope: &str, - indicator: Option, + indicator: &Boolean, console: ConsoleFunctionCall, ) -> Result<(), ConsoleError> { match console.function { @@ -40,21 +40,21 @@ impl> ConstrainedProgram { ConsoleFunction::Debug(string) => { let string = self.format(cs, file_scope, function_scope, string)?; - if unwrap_indicator_value(indicator) { + if get_indicator_value(indicator) { tracing::debug!("{}", string); } } ConsoleFunction::Error(string) => { let string = self.format(cs, file_scope, function_scope, string)?; - if unwrap_indicator_value(indicator) { + if get_indicator_value(indicator) { tracing::error!("{}", string); } } ConsoleFunction::Log(string) => { let string = self.format(cs, file_scope, function_scope, string)?; - if unwrap_indicator_value(indicator) { + if get_indicator_value(indicator) { tracing::info!("{}", string); } } @@ -63,16 +63,3 @@ impl> ConstrainedProgram { Ok(()) } } - -// Return the indicator boolean gadget value or true if it is None -// This is okay since we are not enforcing any constraints -fn unwrap_indicator_value(indicator: Option) -> bool { - let false_boolean = Boolean::constant(false); - - if let Some(indicator_bool) = indicator { - if indicator_bool.eq(&false_boolean) { - return false; - } - } - true -} diff --git a/compiler/src/errors/expression.rs b/compiler/src/errors/expression.rs index 41a83cd6f2..be0deb5925 100644 --- a/compiler/src/errors/expression.rs +++ b/compiler/src/errors/expression.rs @@ -206,7 +206,7 @@ impl ExpressionError { } pub fn undefined_identifier(identifier: Identifier) -> Self { - let message = format!("cannot find value `{}` in this scope", identifier.name); + let message = format!("Cannot find value `{}` in this scope", identifier.name); Self::new_from_span(message, identifier.span) } diff --git a/compiler/src/errors/function.rs b/compiler/src/errors/function.rs index 8f22e1fb87..49dfae9467 100644 --- a/compiler/src/errors/function.rs +++ b/compiler/src/errors/function.rs @@ -82,12 +82,6 @@ impl FunctionError { FunctionError::Error(FormattedError::new_from_span(message, span)) } - pub fn arguments_length(expected: usize, actual: usize, span: Span) -> Self { - let message = format!("function expected {} input variables, found {}", expected, actual); - - Self::new_from_span(message, span) - } - pub fn invalid_array(actual: String, span: Span) -> Self { let message = format!("Expected function input array, found `{}`", actual); diff --git a/compiler/src/errors/statement.rs b/compiler/src/errors/statement.rs index a70770ca53..b1e7cf908d 100644 --- a/compiler/src/errors/statement.rs +++ b/compiler/src/errors/statement.rs @@ -135,6 +135,22 @@ impl StatementError { Self::new_from_span(message, span) } + pub fn multiple_returns(span: Span) -> Self { + let message = "This function returns multiple times and produces unreachable circuits with undefined behavior." + .to_string(); + + Self::new_from_span(message, span) + } + + pub fn no_returns(expected: Type, span: Span) -> Self { + let message = format!( + "function expected `{}` return type but no valid branches returned a result", + expected + ); + + Self::new_from_span(message, span) + } + pub fn select_fail(first: String, second: String, span: Span) -> Self { let message = format!( "Conditional select gadget failed to select between `{}` or `{}`", diff --git a/compiler/src/expression/circuit/access.rs b/compiler/src/expression/circuit/access.rs index 0d3864c295..4172c8c476 100644 --- a/compiler/src/expression/circuit/access.rs +++ b/compiler/src/expression/circuit/access.rs @@ -67,14 +67,17 @@ impl> ConstrainedProgram { match matched_member { Some(member) => { match &member.1 { - ConstrainedValue::Function(ref _circuit_identifier, ref _function) => { - // Pass circuit members into function call by value - for stored_member in members { - let circuit_scope = new_scope(&file_scope, &circuit_name.name); - let self_keyword = new_scope(&circuit_scope, SELF_KEYWORD); - let variable = new_scope(&self_keyword, &stored_member.0.name); + ConstrainedValue::Function(ref _circuit_identifier, ref function) => { + // Check for function input `self` or `mut self`. + if function.contains_self() { + // Pass circuit members into function call by value + for stored_member in members { + let circuit_scope = new_scope(&file_scope, &circuit_name.name); + let self_keyword = new_scope(&circuit_scope, SELF_KEYWORD); + let variable = new_scope(&self_keyword, &stored_member.0.name); - self.store(variable, stored_member.1.clone()); + self.store(variable, stored_member.1.clone()); + } } } ConstrainedValue::Static(value) => { diff --git a/compiler/src/expression/circuit/circuit.rs b/compiler/src/expression/circuit/circuit.rs index e78cd00e91..6a6e129fe3 100644 --- a/compiler/src/expression/circuit/circuit.rs +++ b/compiler/src/expression/circuit/circuit.rs @@ -58,7 +58,7 @@ impl> ConstrainedProgram { for member in circuit.members.into_iter() { match member { - CircuitMember::CircuitVariable(is_mutable, identifier, type_) => { + CircuitMember::CircuitVariable(identifier, type_) => { let matched_variable = members .clone() .into_iter() @@ -66,7 +66,7 @@ impl> ConstrainedProgram { match matched_variable { Some(variable) => { // Resolve and enforce circuit variable - let mut variable_value = self.enforce_expression( + let variable_value = self.enforce_expression( cs, file_scope, function_scope, @@ -74,25 +74,16 @@ impl> ConstrainedProgram { variable.expression, )?; - // Add mutability to circuit variable - if is_mutable { - variable_value = ConstrainedValue::Mutable(Box::new(variable_value)) - } - resolved_members.push(ConstrainedCircuitMember(identifier, variable_value)) } None => return Err(ExpressionError::expected_circuit_member(identifier.to_string(), span)), } } - CircuitMember::CircuitFunction(_static, function) => { + CircuitMember::CircuitFunction(function) => { let identifier = function.identifier.clone(); - let mut constrained_function_value = + let constrained_function_value = ConstrainedValue::Function(Some(circuit_identifier.clone()), function); - if _static { - constrained_function_value = ConstrainedValue::Static(Box::new(constrained_function_value)); - } - resolved_members.push(ConstrainedCircuitMember(identifier, constrained_function_value)); } }; diff --git a/compiler/src/expression/circuit/static_access.rs b/compiler/src/expression/circuit/static_access.rs index 31ed5bb865..27086ac55c 100644 --- a/compiler/src/expression/circuit/static_access.rs +++ b/compiler/src/expression/circuit/static_access.rs @@ -56,22 +56,13 @@ impl> ConstrainedProgram { // Find static circuit function let matched_function = circuit.members.into_iter().find(|member| match member { - CircuitMember::CircuitFunction(_static, function) => function.identifier == circuit_member, + CircuitMember::CircuitFunction(function) => function.identifier == circuit_member, _ => false, }); // Return errors if no static function exists let function = match matched_function { - Some(CircuitMember::CircuitFunction(_static, function)) => { - if _static { - function - } else { - return Err(ExpressionError::invalid_member_access( - function.identifier.to_string(), - span, - )); - } - } + Some(CircuitMember::CircuitFunction(function)) => function, _ => { return Err(ExpressionError::undefined_member_access( circuit.circuit_name.to_string(), diff --git a/compiler/src/function/function.rs b/compiler/src/function/function.rs index ab944103f0..4786fb7d5a 100644 --- a/compiler/src/function/function.rs +++ b/compiler/src/function/function.rs @@ -23,22 +23,13 @@ use crate::{ GroupType, }; -use leo_ast::{Expression, Function, FunctionInput, Span, Type}; +use leo_ast::{Expression, Function, FunctionInput}; use snarkos_models::{ curves::{Field, PrimeField}, - gadgets::r1cs::ConstraintSystem, + gadgets::{r1cs::ConstraintSystem, utilities::boolean::Boolean}, }; -pub fn check_arguments_length(expected: usize, actual: usize, span: &Span) -> Result<(), FunctionError> { - // Make sure we are given the correct number of arguments - if expected != actual { - Err(FunctionError::arguments_length(expected, actual, span.to_owned())) - } else { - Ok(()) - } -} - impl> ConstrainedProgram { pub(crate) fn enforce_function>( &mut self, @@ -51,17 +42,29 @@ impl> ConstrainedProgram { ) -> Result, FunctionError> { let function_name = new_scope(scope, function.get_name()); - // Make sure we are given the correct number of input variables - check_arguments_length(function.input.len(), input.len(), &function.span)?; + // Store if function contains input `mut self`. + let mut_self = function.contains_mut_self(); // Store input values as new variables in resolved program - for (input_model, input_expression) in function.input.iter().zip(input.into_iter()) { + for (input_model, input_expression) in function.filter_self_inputs().zip(input.into_iter()) { let (name, value) = match input_model { - FunctionInput::InputKeyword(identifier) => { - let input_value = + FunctionInput::InputKeyword(keyword) => { + let value = self.enforce_function_input(cs, scope, caller_scope, &function_name, None, input_expression)?; - (&identifier.name, input_value) + (keyword.to_string(), value) + } + FunctionInput::SelfKeyword(keyword) => { + let value = + self.enforce_function_input(cs, scope, caller_scope, &function_name, None, input_expression)?; + + (keyword.to_string(), value) + } + FunctionInput::MutSelfKeyword(keyword) => { + let value = + self.enforce_function_input(cs, scope, caller_scope, &function_name, None, input_expression)?; + + (keyword.to_string(), value) } FunctionInput::Variable(input_model) => { // First evaluate input expression @@ -78,7 +81,7 @@ impl> ConstrainedProgram { input_value = ConstrainedValue::Mutable(Box::new(input_value)) } - (&input_model.identifier.name, input_value) + (input_model.identifier.name.clone(), input_value) } }; @@ -89,42 +92,25 @@ impl> ConstrainedProgram { // Evaluate every statement in the function and save all potential results let mut results = vec![]; + let indicator = Boolean::constant(true); - for statement in function.statements.iter() { + for statement in function.block.statements.iter() { let mut result = self.enforce_statement( cs, scope, &function_name, - None, + &indicator, statement.clone(), function.output.clone(), declared_circuit_reference, + mut_self, )?; results.append(&mut result); } // Conditionally select a result based on returned indicators - let mut return_values = ConstrainedValue::Tuple(vec![]); - - Self::conditionally_select_result(cs, &mut return_values, results, &function.span)?; - - if let ConstrainedValue::Tuple(ref returns) = return_values { - let return_types = match function.output { - Some(Type::Tuple(types)) => types.len(), - Some(_) => 1usize, - None => 0usize, - }; - - if return_types != returns.len() { - return Err(FunctionError::return_arguments_length( - return_types, - returns.len(), - function.span.clone(), - )); - } - } - - Ok(return_values) + Self::conditionally_select_result(cs, function.output, results, &function.span) + .map_err(FunctionError::StatementError) } } diff --git a/compiler/src/function/input/input_keyword.rs b/compiler/src/function/input/input_keyword.rs index 5d74e55f70..3d40090a3f 100644 --- a/compiler/src/function/input/input_keyword.rs +++ b/compiler/src/function/input/input_keyword.rs @@ -15,7 +15,7 @@ // along with the Leo library. If not, see . use crate::{errors::FunctionError, ConstrainedCircuitMember, ConstrainedProgram, ConstrainedValue, GroupType}; -use leo_ast::{Identifier, Input}; +use leo_ast::{Identifier, Input, InputKeyword}; use snarkos_models::{ curves::{Field, PrimeField}, @@ -31,26 +31,26 @@ impl> ConstrainedProgram { pub fn allocate_input_keyword>( &mut self, cs: &mut CS, - identifier: Identifier, + keyword: InputKeyword, input: &Input, ) -> Result, FunctionError> { // Create an identifier for each input variable let registers_name = Identifier { name: REGISTERS_VARIABLE_NAME.to_string(), - span: identifier.span.clone(), + span: keyword.span.clone(), }; let record_name = Identifier { name: RECORD_VARIABLE_NAME.to_string(), - span: identifier.span.clone(), + span: keyword.span.clone(), }; let state_name = Identifier { name: STATE_VARIABLE_NAME.to_string(), - span: identifier.span.clone(), + span: keyword.span.clone(), }; let state_leaf_name = Identifier { name: STATE_LEAF_VARIABLE_NAME.to_string(), - span: identifier.span.clone(), + span: keyword.span.clone(), }; // Fetch each input variable's definitions @@ -82,6 +82,6 @@ impl> ConstrainedProgram { // Return input variable keyword as circuit expression - Ok(ConstrainedValue::CircuitExpression(identifier, members)) + Ok(ConstrainedValue::CircuitExpression(Identifier::from(keyword), members)) } } diff --git a/compiler/src/function/main_function.rs b/compiler/src/function/main_function.rs index 7604a80b28..1d3f5d1380 100644 --- a/compiler/src/function/main_function.rs +++ b/compiler/src/function/main_function.rs @@ -23,7 +23,7 @@ use crate::{ OutputBytes, }; -use leo_ast::{Expression, Function, FunctionInput, Input}; +use leo_ast::{Expression, Function, FunctionInput, Identifier, Input}; use snarkos_models::{ curves::{Field, PrimeField}, @@ -44,11 +44,16 @@ impl> ConstrainedProgram { // Iterate over main function input variables and allocate new values let mut input_variables = Vec::with_capacity(function.input.len()); for input_model in function.input.clone().into_iter() { - let (identifier, value) = match input_model { - FunctionInput::InputKeyword(identifier) => { - let value = self.allocate_input_keyword(cs, identifier.clone(), &input)?; + let (input_id, value) = match input_model { + FunctionInput::InputKeyword(keyword) => { + let input_id = Identifier::new_with_span(&keyword.to_string(), &keyword.span); + let value = self.allocate_input_keyword(cs, keyword, &input)?; - (identifier, value) + (input_id, value) + } + FunctionInput::SelfKeyword(_) => unimplemented!("cannot access self keyword in main function"), + FunctionInput::MutSelfKeyword(_) => { + unimplemented!("cannot access mut self keyword in main function") } FunctionInput::Variable(input_model) => { let name = input_model.identifier.name.clone(); @@ -63,12 +68,12 @@ impl> ConstrainedProgram { }; // Store input as variable with {function_name}_{identifier_name} - let input_name = new_scope(&function_name, &identifier.name); + let input_name = new_scope(&function_name, &input_id.to_string()); // Store a new variable for every allocated main function input self.store(input_name, value); - input_variables.push(Expression::Identifier(identifier)); + input_variables.push(Expression::Identifier(input_id)); } let span = function.span.clone(); diff --git a/compiler/src/function/result/result.rs b/compiler/src/function/result/result.rs index cec2a05810..1971dd7c4e 100644 --- a/compiler/src/function/result/result.rs +++ b/compiler/src/function/result/result.rs @@ -16,9 +16,16 @@ //! Enforces that one return value is produced in a compiled Leo program. -use crate::{errors::StatementError, program::ConstrainedProgram, value::ConstrainedValue, GroupType}; +use crate::{ + check_return_type, + errors::StatementError, + get_indicator_value, + program::ConstrainedProgram, + value::ConstrainedValue, + GroupType, +}; -use leo_ast::Span; +use leo_ast::{Span, Type}; use snarkos_models::{ curves::{Field, PrimeField}, @@ -29,49 +36,82 @@ use snarkos_models::{ }; impl> ConstrainedProgram { - /// iterates through a vector of results and selects one based off of indicators + /// + /// Returns a conditionally selected result from the given possible function returns and + /// given function return type. + /// pub fn conditionally_select_result>( cs: &mut CS, - return_value: &mut ConstrainedValue, - results: Vec<(Option, ConstrainedValue)>, + expected_return: Option, + results: Vec<(Boolean, ConstrainedValue)>, span: &Span, - ) -> Result<(), StatementError> { - // if there are no results, continue - if results.is_empty() { - return Ok(()); + ) -> Result, StatementError> { + // Initialize empty return value. + let mut return_value = ConstrainedValue::Tuple(vec![]); + + // If the function does not expect a return type, then make sure there are no returned results. + let return_type = match expected_return { + Some(return_type) => return_type, + None => { + if results.is_empty() { + // If the function has no returns, then return an empty tuple. + return Ok(return_value); + } else { + return Err(StatementError::invalid_number_of_returns( + 0, + results.len(), + span.to_owned(), + )); + } + } + }; + + // Error if the function or one of its branches does not return. + if results + .iter() + .find(|(indicator, _res)| get_indicator_value(indicator)) + .is_none() + { + return Err(StatementError::no_returns(return_type, span.to_owned())); } - // If all indicators are none, then there are no branch conditions in the function. - // We simply return the last result. + // Find the return value + let mut ignored = vec![]; + let mut found_return = false; + for (indicator, result) in results.into_iter() { + // Error if a statement returned a result with an incorrect type + let result_type = result.to_type(span)?; + check_return_type(&return_type, &result_type, span)?; - if results.iter().all(|(indicator, _res)| indicator.is_none()) { - let result = &results[results.len() - 1].1; - - *return_value = result.clone(); - - return Ok(()); + if get_indicator_value(&indicator) { + // Error if we already have a return value. + if found_return { + return Err(StatementError::multiple_returns(span.to_owned())); + } else { + // Set the function return value. + return_value = result; + found_return = true; + } + } else { + // Ignore a possible function return value. + ignored.push((indicator, result)) + } } + // Conditionally select out the ignored results in the circuit. + // // If there are branches in the function we need to use the `ConditionalSelectGadget` to parse through and select the correct one. // This can be thought of as de-multiplexing all previous wires that may have returned results into one. - for (i, (indicator, result)) in results.into_iter().enumerate() { - // Set the first value as the starting point - if i == 0 { - *return_value = result.clone(); - } - - let condition = indicator.unwrap_or(Boolean::Constant(true)); - let selected_value = ConstrainedValue::conditionally_select( - cs.ns(|| format!("select {} {}:{}", result, span.line, span.start)), - &condition, + for (i, (indicator, result)) in ignored.into_iter().enumerate() { + return_value = ConstrainedValue::conditionally_select( + cs.ns(|| format!("select result {} {}:{}", i, span.line, span.start)), + &indicator, &result, - return_value, + &return_value, ) .map_err(|_| StatementError::select_fail(result.to_string(), return_value.to_string(), span.to_owned()))?; - - *return_value = selected_value; } - Ok(()) + Ok(return_value) } } diff --git a/compiler/src/statement/assign/array.rs b/compiler/src/statement/assign/array.rs index 842cdefbfe..0f56d9461b 100644 --- a/compiler/src/statement/assign/array.rs +++ b/compiler/src/statement/assign/array.rs @@ -34,14 +34,12 @@ impl> ConstrainedProgram { cs: &mut CS, file_scope: &str, function_scope: &str, - indicator: Option, + indicator: &Boolean, name: &str, range_or_expression: RangeOrExpression, mut new_value: ConstrainedValue, span: &Span, ) -> Result<(), StatementError> { - let condition = indicator.unwrap_or(Boolean::Constant(true)); - // 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) => { @@ -54,7 +52,7 @@ impl> ConstrainedProgram { let selected_value = ConstrainedValue::conditionally_select( cs.ns(|| format!("select {} {}:{}", new_value, span.line, span.start)), - &condition, + indicator, &new_value, &old[index], ) @@ -90,7 +88,7 @@ impl> ConstrainedProgram { }; let selected_array = ConstrainedValue::conditionally_select( cs.ns(|| format!("select {} {}:{}", new_array, span.line, span.start)), - &condition, + indicator, &new_array, old_array, ) diff --git a/compiler/src/statement/assign/assign.rs b/compiler/src/statement/assign/assign.rs index 8899c9b286..27c1ecd0f8 100644 --- a/compiler/src/statement/assign/assign.rs +++ b/compiler/src/statement/assign/assign.rs @@ -42,7 +42,8 @@ impl> ConstrainedProgram { file_scope: &str, function_scope: &str, declared_circuit_reference: &str, - indicator: Option, + indicator: &Boolean, + mut_self: bool, assignee: Assignee, expression: Expression, span: &Span, @@ -55,14 +56,13 @@ impl> ConstrainedProgram { // Mutate the old value into the new value if assignee.accesses.is_empty() { - let condition = indicator.unwrap_or(Boolean::Constant(true)); let old_value = self.get_mutable_assignee(&variable_name, span)?; new_value.resolve_type(Some(old_value.to_type(&span)?), span)?; let selected_value = ConstrainedValue::conditionally_select( cs.ns(|| format!("select {} {}:{}", new_value, span.line, span.start)), - &condition, + indicator, &new_value, old_value, ) @@ -88,7 +88,7 @@ impl> ConstrainedProgram { } AssigneeAccess::Member(identifier) => { // Mutate a circuit variable using the self keyword. - if assignee.identifier.is_self() { + if assignee.identifier.is_self() && mut_self { let self_circuit_variable_name = new_scope(&assignee.identifier.name, &identifier.name); let self_variable_name = new_scope(file_scope, &self_circuit_variable_name); let value = self.mutate_circuit_variable( diff --git a/compiler/src/statement/assign/circuit_variable.rs b/compiler/src/statement/assign/circuit_variable.rs index 146c95f983..40f6666671 100644 --- a/compiler/src/statement/assign/circuit_variable.rs +++ b/compiler/src/statement/assign/circuit_variable.rs @@ -31,14 +31,12 @@ impl> ConstrainedProgram { pub fn mutate_circuit_variable>( &mut self, cs: &mut CS, - indicator: Option, + indicator: &Boolean, circuit_name: &str, variable_name: Identifier, mut new_value: ConstrainedValue, span: &Span, ) -> Result, StatementError> { - let condition = indicator.unwrap_or(Boolean::Constant(true)); - // Get the mutable circuit by name match self.get_mutable_assignee(circuit_name, span)? { ConstrainedValue::CircuitExpression(_variable, members) => { @@ -61,16 +59,14 @@ impl> ConstrainedProgram { span.to_owned(), )) } - ConstrainedValue::Mutable(value) => { - // Mutate the circuit variable's value in place - + value => { // Check that the new value type == old value type new_value.resolve_type(Some(value.to_type(span)?), span)?; // Conditionally select the value if this branch is executed. let mut selected_value = ConstrainedValue::conditionally_select( cs.ns(|| format!("select {} {}:{}", new_value, span.line, span.start)), - &condition, + indicator, &new_value, &member.1, ) @@ -89,13 +85,6 @@ impl> ConstrainedProgram { Ok(selected_value) } - _ => { - // Throw an error if we try to mutate an immutable circuit variable - Err(StatementError::immutable_circuit_variable( - variable_name.name, - span.to_owned(), - )) - } }, None => { // Throw an error if the circuit variable does not exist in the circuit diff --git a/compiler/src/statement/assign/tuple.rs b/compiler/src/statement/assign/tuple.rs index 5ecb0dd767..4209a1d570 100644 --- a/compiler/src/statement/assign/tuple.rs +++ b/compiler/src/statement/assign/tuple.rs @@ -31,15 +31,12 @@ impl> ConstrainedProgram { pub fn assign_tuple>( &mut self, cs: &mut CS, - indicator: Option, + indicator: &Boolean, name: &str, index: PositiveNumber, mut new_value: ConstrainedValue, span: &Span, ) -> Result<(), StatementError> { - // Get the indicator value. - let condition = indicator.unwrap_or(Boolean::Constant(true)); - // Parse the index. let index_usize = parse_index(&index, &span)?; @@ -50,7 +47,7 @@ impl> ConstrainedProgram { let selected_value = ConstrainedValue::conditionally_select( cs.ns(|| format!("select {} {}:{}", new_value, span.line, span.start)), - &condition, + indicator, &new_value, &old[index_usize], ) diff --git a/compiler/src/statement/branch/branch.rs b/compiler/src/statement/block/block.rs similarity index 79% rename from compiler/src/statement/branch/branch.rs rename to compiler/src/statement/block/block.rs index 9d0d208036..b2633a0767 100644 --- a/compiler/src/statement/branch/branch.rs +++ b/compiler/src/statement/block/block.rs @@ -17,7 +17,7 @@ //! Enforces a branch of a conditional or iteration statement in a compiled Leo program. use crate::{program::ConstrainedProgram, GroupType, IndicatorAndConstrainedValue, StatementResult}; -use leo_ast::{Statement, Type}; +use leo_ast::{Block, Type}; use snarkos_models::{ curves::{Field, PrimeField}, @@ -25,18 +25,22 @@ use snarkos_models::{ }; impl> ConstrainedProgram { - pub fn evaluate_branch>( + /// Evaluates a branch of one or more statements and returns a result in + /// the given scope. + #[allow(clippy::too_many_arguments)] + pub fn evaluate_block>( &mut self, cs: &mut CS, file_scope: &str, function_scope: &str, - indicator: Option, - statements: Vec, + indicator: &Boolean, + block: Block, return_type: Option, + mut_self: bool, ) -> StatementResult>> { - let mut results = Vec::with_capacity(statements.len()); + let mut results = Vec::with_capacity(block.statements.len()); // Evaluate statements. Only allow a single return argument to be returned. - for statement in statements.into_iter() { + for statement in block.statements.into_iter() { let mut value = self.enforce_statement( cs, file_scope, @@ -45,6 +49,7 @@ impl> ConstrainedProgram { statement, return_type.clone(), "", + mut_self, )?; results.append(&mut value); diff --git a/compiler/src/statement/branch/mod.rs b/compiler/src/statement/block/mod.rs similarity index 95% rename from compiler/src/statement/branch/mod.rs rename to compiler/src/statement/block/mod.rs index 3ebf5cbc69..5b21387b97 100644 --- a/compiler/src/statement/branch/mod.rs +++ b/compiler/src/statement/block/mod.rs @@ -17,5 +17,5 @@ //! Methods to enforce constraints on a branch of a conditional or iteration statement //! in a compiled Leo program. -pub mod branch; -pub use self::branch::*; +pub mod block; +pub use self::block::*; diff --git a/compiler/src/statement/conditional/conditional.rs b/compiler/src/statement/conditional/conditional.rs index 48bad283b8..aebed7cc14 100644 --- a/compiler/src/statement/conditional/conditional.rs +++ b/compiler/src/statement/conditional/conditional.rs @@ -49,15 +49,16 @@ impl> ConstrainedProgram { cs: &mut CS, file_scope: &str, function_scope: &str, - indicator: Option, + indicator: &Boolean, statement: ConditionalStatement, return_type: Option, + mut_self: bool, span: &Span, ) -> StatementResult>> { let statement_string = statement.to_string(); - // Inherit the indicator from a previous conditional statement or assume that we are the outer parent - let outer_indicator = indicator.unwrap_or(Boolean::Constant(true)); + // Inherit an indicator from a previous statement. + let outer_indicator = indicator; // Evaluate the conditional boolean as the inner indicator let inner_indicator = match self.enforce_expression( @@ -72,7 +73,7 @@ impl> ConstrainedProgram { }; // If outer_indicator && inner_indicator, then select branch 1 - let outer_indicator_string = indicator_to_string(&outer_indicator); + let outer_indicator_string = indicator_to_string(outer_indicator); let inner_indicator_string = indicator_to_string(&inner_indicator); let branch_1_name = format!( "branch indicator 1 {} && {}", @@ -80,7 +81,7 @@ impl> ConstrainedProgram { ); let branch_1_indicator = Boolean::and( &mut cs.ns(|| format!("branch 1 {} {}:{}", statement_string, span.line, span.start)), - &outer_indicator, + outer_indicator, &inner_indicator, ) .map_err(|_| StatementError::indicator_calculation(branch_1_name, span.to_owned()))?; @@ -88,13 +89,14 @@ impl> ConstrainedProgram { let mut results = vec![]; // Evaluate branch 1 - let mut branch_1_result = self.evaluate_branch( + let mut branch_1_result = self.evaluate_block( cs, file_scope, function_scope, - Some(branch_1_indicator), - statement.statements, + &branch_1_indicator, + statement.block, return_type.clone(), + mut_self, )?; results.append(&mut branch_1_result); @@ -120,18 +122,20 @@ impl> ConstrainedProgram { cs, file_scope, function_scope, - Some(branch_2_indicator), + &branch_2_indicator, *nested, return_type, + mut_self, span, )?, - ConditionalNestedOrEndStatement::End(statements) => self.evaluate_branch( + ConditionalNestedOrEndStatement::End(block) => self.evaluate_block( cs, file_scope, function_scope, - Some(branch_2_indicator), - statements, + &branch_2_indicator, + block, return_type, + mut_self, )?, }, None => vec![], diff --git a/compiler/src/statement/iteration/iteration.rs b/compiler/src/statement/iteration/iteration.rs index 64104cbb45..c7084143ff 100644 --- a/compiler/src/statement/iteration/iteration.rs +++ b/compiler/src/statement/iteration/iteration.rs @@ -25,7 +25,7 @@ use crate::{ Integer, StatementResult, }; -use leo_ast::{Expression, Identifier, Span, Statement, Type}; +use leo_ast::{Block, Expression, Identifier, Span, Type}; use snarkos_models::{ curves::{Field, PrimeField}, @@ -42,12 +42,13 @@ impl> ConstrainedProgram { cs: &mut CS, file_scope: &str, function_scope: &str, - indicator: Option, + indicator: &Boolean, index: Identifier, start: Expression, stop: Expression, - statements: Vec, + block: Block, return_type: Option, + mut_self: bool, span: &Span, ) -> StatementResult>> { let mut results = vec![]; @@ -67,13 +68,14 @@ impl> ConstrainedProgram { ); // Evaluate statements and possibly return early - let mut result = self.evaluate_branch( + let mut result = self.evaluate_block( &mut cs.ns(|| format!("for loop iteration {} {}:{}", i, span.line, span.start)), file_scope, function_scope, indicator, - statements.clone(), + block.clone(), return_type.clone(), + mut_self, )?; results.append(&mut result); diff --git a/compiler/src/statement/mod.rs b/compiler/src/statement/mod.rs index e70cab01d0..63c00ccd32 100644 --- a/compiler/src/statement/mod.rs +++ b/compiler/src/statement/mod.rs @@ -19,8 +19,8 @@ pub mod assign; pub use self::assign::*; -pub mod branch; -pub use self::branch::*; +pub mod block; +pub use self::block::*; pub mod conditional; pub use self::conditional::*; diff --git a/compiler/src/statement/return_/return_.rs b/compiler/src/statement/return_/return_.rs index f70b69ca79..55d548dbcf 100644 --- a/compiler/src/statement/return_/return_.rs +++ b/compiler/src/statement/return_/return_.rs @@ -24,20 +24,17 @@ use snarkos_models::{ gadgets::r1cs::ConstraintSystem, }; -fn check_return_type(expected: Option, actual: Type, span: &Span) -> Result<(), StatementError> { - match expected { - Some(expected) => { - if expected.ne(&actual) { - if (expected.is_self() && actual.is_circuit()) || expected.eq_flat(&actual) { - return Ok(()); - } else { - return Err(StatementError::arguments_type(&expected, &actual, span.to_owned())); - } - } +/// Returns `Ok` if the expected type == actual type, returns `Err` otherwise. +pub fn check_return_type(expected: &Type, actual: &Type, span: &Span) -> Result<(), StatementError> { + if expected.ne(&actual) { + // If the return type is `SelfType` returning the circuit type is okay. + return if (expected.is_self() && actual.is_circuit()) || expected.eq_flat(&actual) { Ok(()) - } - None => Ok(()), + } else { + Err(StatementError::arguments_type(&expected, &actual, span.to_owned())) + }; } + Ok(()) } impl> ConstrainedProgram { @@ -53,7 +50,9 @@ impl> ConstrainedProgram { let result = self.enforce_operand(cs, file_scope, function_scope, return_type.clone(), expression, span)?; // Make sure we return the correct type. - check_return_type(return_type, result.to_type(&span)?, span)?; + if let Some(expected) = return_type { + check_return_type(&expected, &result.to_type(span)?, span)?; + } Ok(result) } diff --git a/compiler/src/statement/statement.rs b/compiler/src/statement/statement.rs index 763ea328a7..9ca8a39562 100644 --- a/compiler/src/statement/statement.rs +++ b/compiler/src/statement/statement.rs @@ -25,7 +25,7 @@ use snarkos_models::{ }; pub type StatementResult = Result; -pub type IndicatorAndConstrainedValue = (Option, ConstrainedValue); +pub type IndicatorAndConstrainedValue = (Boolean, ConstrainedValue); impl> ConstrainedProgram { /// @@ -41,17 +41,18 @@ impl> ConstrainedProgram { cs: &mut CS, file_scope: &str, function_scope: &str, - indicator: Option, + indicator: &Boolean, statement: Statement, return_type: Option, declared_circuit_reference: &str, + mut_self: bool, ) -> StatementResult>> { let mut results = vec![]; match statement { Statement::Return(expression, span) => { let return_value = ( - indicator, + indicator.to_owned(), self.enforce_return_statement(cs, file_scope, function_scope, expression, return_type, &span)?, ); @@ -75,6 +76,7 @@ impl> ConstrainedProgram { function_scope, declared_circuit_reference, indicator, + mut_self, variable, expression, &span, @@ -88,12 +90,13 @@ impl> ConstrainedProgram { indicator, statement, return_type, + mut_self, &span, )?; results.append(&mut result); } - Statement::Iteration(index, start_stop, statements, span) => { + Statement::Iteration(index, start_stop, block, span) => { let mut result = self.enforce_iteration_statement( cs, file_scope, @@ -102,8 +105,9 @@ impl> ConstrainedProgram { index, start_stop.0, start_stop.1, - statements, + block, return_type, + mut_self, &span, )?; @@ -116,22 +120,25 @@ impl> ConstrainedProgram { let expression_string = expression.to_string(); let value = self.enforce_expression(cs, file_scope, function_scope, None, expression)?; - // handle empty return value cases + // Handle empty return value cases. match &value { ConstrainedValue::Tuple(values) => { if !values.is_empty() { - return Err(StatementError::unassigned(expression_string, span)); + results.push((*indicator, value)); } } _ => return Err(StatementError::unassigned(expression_string, span)), } - - let result = (indicator, value); - - results.push(result); } }; Ok(results) } } + +/// Returns the indicator boolean gadget value. +/// We can directly compare a boolean constant to the indicator since we are not enforcing any +/// constraints +pub fn get_indicator_value(indicator: &Boolean) -> bool { + indicator.eq(&Boolean::constant(true)) +} diff --git a/compiler/src/value/value.rs b/compiler/src/value/value.rs index d50f93f2fb..a1ecb7b995 100644 --- a/compiler/src/value/value.rs +++ b/compiler/src/value/value.rs @@ -229,8 +229,15 @@ impl> ConstrainedValue { } } + /// + /// Modifies the `self` [ConstrainedValue] so there are no `mut` keywords wrapping the `self` value. + /// pub(crate) fn get_inner_mut(&mut self) { if let ConstrainedValue::Mutable(inner) = self { + // Recursively remove `mut` keywords. + inner.get_inner_mut(); + + // Modify the value. *self = *inner.clone() } } diff --git a/compiler/tests/address/mod.rs b/compiler/tests/address/mod.rs index 3d892a5fb7..eb93b660f9 100644 --- a/compiler/tests/address/mod.rs +++ b/compiler/tests/address/mod.rs @@ -22,72 +22,72 @@ static TEST_ADDRESS_2: &str = "aleo18qgam03qe483tdrcc3fkqwpp38ehff4a2xma6lu7hams #[test] fn test_valid() { - let bytes = include_bytes!("valid.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("valid.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program) } #[test] fn test_invalid_prefix() { - let bytes = include_bytes!("invalid_prefix.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("invalid_prefix.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_invalid_length() { - let bytes = include_bytes!("invalid_length.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("invalid_length.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_empty() { - let bytes = include_bytes!("empty.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("empty.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_implicit_valid() { - let bytes = include_bytes!("implicit_valid.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("implicit_valid.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_implicit_invalid() { - let bytes = include_bytes!("implicit_invalid.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("implicit_invalid.leo"); + let program = parse_program(program_string).unwrap(); let _output = expect_compiler_error(program); } #[test] fn test_console_assert_pass() { - let bytes = include_bytes!("console_assert_pass.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("console_assert_pass.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_console_assert_fail() { - let bytes = include_bytes!("console_assert_fail.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("console_assert_fail.leo"); + let program = parse_program(program_string).unwrap(); let _output = expect_compiler_error(program); } #[test] fn test_ternary() { - let bytes = include_bytes!("ternary.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("ternary.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("s", Some(InputValue::Boolean(true))), @@ -98,7 +98,7 @@ fn test_ternary() { assert_satisfied(program); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("s", Some(InputValue::Boolean(false))), @@ -112,8 +112,8 @@ fn test_ternary() { #[test] fn test_equal() { - let bytes = include_bytes!("equal.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("equal.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Address(TEST_ADDRESS_1.to_string()))), @@ -125,7 +125,7 @@ fn test_equal() { assert_satisfied(program); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Address(TEST_ADDRESS_1.to_string()))), diff --git a/compiler/tests/array/mod.rs b/compiler/tests/array/mod.rs index 59610476e5..6d4684ad18 100644 --- a/compiler/tests/array/mod.rs +++ b/compiler/tests/array/mod.rs @@ -41,17 +41,17 @@ pub fn output_zeros(program: EdwardsTestCompiler) { #[test] fn test_registers() { - let program_bytes = include_bytes!("registers.leo"); - let ones_input_bytes = include_bytes!("input/registers_ones.in"); - let zeros_input_bytes = include_bytes!("input/registers_zeros.in"); + let program_string = include_str!("registers.leo"); + let ones_input_string = include_str!("input/registers_ones.in"); + let zeros_input_string = include_str!("input/registers_zeros.in"); // test ones input register => ones output register - let program = parse_program_with_input(program_bytes, ones_input_bytes).unwrap(); + let program = parse_program_with_input(program_string, ones_input_string).unwrap(); output_ones(program); // test zeros input register => zeros output register - let program = parse_program_with_input(program_bytes, zeros_input_bytes).unwrap(); + let program = parse_program_with_input(program_string, zeros_input_string).unwrap(); output_zeros(program); } @@ -60,171 +60,171 @@ fn test_registers() { #[test] fn test_inline() { - let program_bytes = include_bytes!("inline.leo"); - let input_bytes = include_bytes!("input/three_ones.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("inline.leo"); + let input_string = include_str!("input/three_ones.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_inline_fail() { - let program_bytes = include_bytes!("inline.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("inline.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_initializer() { - let program_bytes = include_bytes!("initializer.leo"); - let input_bytes = include_bytes!("input/three_ones.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("initializer.leo"); + let input_string = include_str!("input/three_ones.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_initializer_fail() { - let program_bytes = include_bytes!("initializer_fail.leo"); - let input_bytes = include_bytes!("input/three_ones.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("initializer_fail.leo"); + let input_string = include_str!("input/three_ones.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } #[test] fn test_initializer_input() { - let program_bytes = include_bytes!("initializer_input.leo"); - let input_bytes = include_bytes!("input/six_zeros.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("initializer_input.leo"); + let input_string = include_str!("input/six_zeros.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_initializer_input_fail() { - let program_bytes = include_bytes!("initializer_input.leo"); - let input_bytes = include_bytes!("input/initializer_fail.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("initializer_input.leo"); + let input_string = include_str!("input/initializer_fail.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } #[test] fn test_input_nested_3x2() { - let program_bytes = include_bytes!("input_nested_3x2.leo"); - let input_bytes = include_bytes!("input/input_nested_3x2.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("input_nested_3x2.leo"); + let input_string = include_str!("input/input_nested_3x2.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_input_nested_3x2_fail() { - let program_bytes = include_bytes!("input_nested_3x2_fail.leo"); - let input_bytes = include_bytes!("input/input_nested_3x2_fail.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("input_nested_3x2_fail.leo"); + let input_string = include_str!("input/input_nested_3x2_fail.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } #[test] fn test_input_tuple_3x2() { - let program_bytes = include_bytes!("input_tuple_3x2.leo"); - let input_bytes = include_bytes!("input/input_tuple_3x2.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("input_tuple_3x2.leo"); + let input_string = include_str!("input/input_tuple_3x2.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_input_tuple_3x2_fail() { - let program_bytes = include_bytes!("input_tuple_3x2_fail.leo"); - let input_bytes = include_bytes!("input/input_tuple_3x2_fail.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("input_tuple_3x2_fail.leo"); + let input_string = include_str!("input/input_tuple_3x2_fail.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } #[test] fn test_multi_fail_initializer() { - let program_bytes = include_bytes!("multi_fail_initializer.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("multi_fail_initializer.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_multi_inline_fail() { - let program_bytes = include_bytes!("multi_fail_inline.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("multi_fail_inline.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_multi_initializer() { - let program_bytes = include_bytes!("multi_initializer.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("multi_initializer.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_multi_initializer_fail() { - let program_bytes = include_bytes!("multi_initializer_fail.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("multi_initializer_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_nested_3x2_value() { - let program_bytes = include_bytes!("nested_3x2_value.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("nested_3x2_value.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_nested_3x2_value_fail() { - let program_bytes = include_bytes!("nested_3x2_value_fail.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("nested_3x2_value_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_tuple_3x2_value() { - let program_bytes = include_bytes!("tuple_3x2_value.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("tuple_3x2_value.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_tuple_3x2_value_fail() { - let program_bytes = include_bytes!("tuple_3x2_value_fail.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("tuple_3x2_value_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_spread() { - let program_bytes = include_bytes!("spread.leo"); - let input_bytes = include_bytes!("input/three_ones.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("spread.leo"); + let input_string = include_str!("input/three_ones.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_slice() { - let program_bytes = include_bytes!("slice.leo"); - let input_bytes = include_bytes!("input/three_ones.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("slice.leo"); + let input_string = include_str!("input/three_ones.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } @@ -233,136 +233,136 @@ fn test_slice() { #[test] fn test_type_fail() { - let program_bytes = include_bytes!("type_fail.leo"); - let syntax_error = parse_program(program_bytes).is_err(); + let program_string = include_str!("type_fail.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_type_nested_value_nested_3x2() { - let program_bytes = include_bytes!("type_nested_value_nested_3x2.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_nested_value_nested_3x2.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_type_nested_value_nested_3x2_fail() { - let program_bytes = include_bytes!("type_nested_value_nested_3x2_fail.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_nested_value_nested_3x2_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_type_nested_value_nested_4x3x2() { - let program_bytes = include_bytes!("type_nested_value_nested_4x3x2.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_nested_value_nested_4x3x2.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_type_nested_value_nested_4x3x2_fail() { - let program_bytes = include_bytes!("type_nested_value_nested_4x3x2_fail.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_nested_value_nested_4x3x2_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_type_nested_value_tuple_3x2() { - let program_bytes = include_bytes!("type_nested_value_tuple_3x2.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_nested_value_tuple_3x2.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_type_nested_value_tuple_3x2_fail() { - let program_bytes = include_bytes!("type_nested_value_tuple_3x2_fail.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_nested_value_tuple_3x2_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_type_nested_value_tuple_4x3x2() { - let program_bytes = include_bytes!("type_nested_value_tuple_4x3x2.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_nested_value_tuple_4x3x2.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_type_nested_value_tuple_4x3x2_fail() { - let program_bytes = include_bytes!("type_nested_value_tuple_4x3x2_fail.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_nested_value_tuple_4x3x2_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_type_tuple_value_nested_3x2() { - let program_bytes = include_bytes!("type_tuple_value_nested_3x2.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_tuple_value_nested_3x2.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_type_tuple_value_nested_3x2_fail() { - let program_bytes = include_bytes!("type_tuple_value_nested_3x2_fail.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_tuple_value_nested_3x2_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_type_tuple_value_nested_4x3x2() { - let program_bytes = include_bytes!("type_tuple_value_nested_4x3x2.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_tuple_value_nested_4x3x2.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_type_tuple_value_nested_4x3x2_fail() { - let program_bytes = include_bytes!("type_tuple_value_nested_4x3x2_fail.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_tuple_value_nested_4x3x2_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_type_tuple_value_tuple_3x2() { - let program_bytes = include_bytes!("type_tuple_value_tuple_3x2.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_tuple_value_tuple_3x2.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_type_tuple_value_tuple_3x2_fail() { - let program_bytes = include_bytes!("type_tuple_value_tuple_3x2_fail.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_tuple_value_tuple_3x2_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_type_tuple_value_tuple_4x3x2() { - let program_bytes = include_bytes!("type_tuple_value_tuple_4x3x2.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_tuple_value_tuple_4x3x2.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_type_tuple_value_tuple_4x3x2_fail() { - let program_bytes = include_bytes!("type_tuple_value_tuple_4x3x2_fail.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("type_tuple_value_tuple_4x3x2_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } @@ -371,72 +371,72 @@ fn test_type_tuple_value_tuple_4x3x2_fail() { #[test] fn test_input_type_nested_value_nested_3x2() { - let program_bytes = include_bytes!("type_input_3x2.leo"); - let input_bytes = include_bytes!("input/type_nested_value_nested_3x2.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("type_input_3x2.leo"); + let input_string = include_str!("input/type_nested_value_nested_3x2.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_input_type_nested_value_nested_3x2_fail() { - let program_bytes = include_bytes!("type_input_3x2.leo"); - let input_bytes = include_bytes!("input/type_nested_value_nested_3x2_fail.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("type_input_3x2.leo"); + let input_string = include_str!("input/type_nested_value_nested_3x2_fail.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } #[test] fn test_input_type_nested_value_nested_4x3x2() { - let program_bytes = include_bytes!("type_input_4x3x2.leo"); - let input_bytes = include_bytes!("input/type_nested_value_nested_4x3x2.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("type_input_4x3x2.leo"); + let input_string = include_str!("input/type_nested_value_nested_4x3x2.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_input_type_nested_value_nested_4x3x2_fail() { - let program_bytes = include_bytes!("type_input_4x3x2.leo"); - let input_bytes = include_bytes!("input/type_nested_value_nested_4x3x2_fail.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("type_input_4x3x2.leo"); + let input_string = include_str!("input/type_nested_value_nested_4x3x2_fail.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } #[test] fn test_input_type_nested_value_tuple_3x2() { - let program_bytes = include_bytes!("type_input_3x2.leo"); - let input_bytes = include_bytes!("input/type_nested_value_tuple_3x2.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("type_input_3x2.leo"); + let input_string = include_str!("input/type_nested_value_tuple_3x2.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_input_type_nested_value_tuple_3x2_fail() { - let program_bytes = include_bytes!("type_input_3x2.leo"); - let input_bytes = include_bytes!("input/type_nested_value_tuple_3x2_fail.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("type_input_3x2.leo"); + let input_string = include_str!("input/type_nested_value_tuple_3x2_fail.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } #[test] fn test_input_type_nested_value_tuple_4x3x2() { - let program_bytes = include_bytes!("type_input_4x3x2.leo"); - let input_bytes = include_bytes!("input/type_nested_value_tuple_4x3x2.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("type_input_4x3x2.leo"); + let input_string = include_str!("input/type_nested_value_tuple_4x3x2.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program) } #[test] fn test_input_type_nested_value_tuple_4x3x2_fail() { - let program_bytes = include_bytes!("type_input_4x3x2.leo"); - let input_bytes = include_bytes!("input/type_nested_value_tuple_4x3x2_fail.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("type_input_4x3x2.leo"); + let input_string = include_str!("input/type_nested_value_tuple_4x3x2_fail.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } @@ -445,72 +445,72 @@ fn test_input_type_nested_value_tuple_4x3x2_fail() { #[test] fn test_input_type_tuple_value_nested_3x2() { - let program_bytes = include_bytes!("type_input_3x2.leo"); - let input_bytes = include_bytes!("input/type_tuple_value_nested_3x2.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("type_input_3x2.leo"); + let input_string = include_str!("input/type_tuple_value_nested_3x2.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_input_type_tuple_value_nested_3x2_fail() { - let program_bytes = include_bytes!("type_input_3x2.leo"); - let input_bytes = include_bytes!("input/type_tuple_value_nested_3x2_fail.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("type_input_3x2.leo"); + let input_string = include_str!("input/type_tuple_value_nested_3x2_fail.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } #[test] fn test_input_type_tuple_value_nested_4x3x2() { - let program_bytes = include_bytes!("type_input_4x3x2.leo"); - let input_bytes = include_bytes!("input/type_tuple_value_nested_4x3x2.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("type_input_4x3x2.leo"); + let input_string = include_str!("input/type_tuple_value_nested_4x3x2.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_input_type_tuple_value_nested_4x3x2_fail() { - let program_bytes = include_bytes!("type_input_4x3x2.leo"); - let input_bytes = include_bytes!("input/type_tuple_value_nested_4x3x2_fail.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("type_input_4x3x2.leo"); + let input_string = include_str!("input/type_tuple_value_nested_4x3x2_fail.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } #[test] fn test_input_type_tuple_value_tuple_3x2() { - let program_bytes = include_bytes!("type_input_3x2.leo"); - let input_bytes = include_bytes!("input/type_tuple_value_tuple_3x2.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("type_input_3x2.leo"); + let input_string = include_str!("input/type_tuple_value_tuple_3x2.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_input_type_tuple_value_tuple_3x2_fail() { - let program_bytes = include_bytes!("type_input_3x2.leo"); - let input_bytes = include_bytes!("input/type_tuple_value_tuple_3x2_fail.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("type_input_3x2.leo"); + let input_string = include_str!("input/type_tuple_value_tuple_3x2_fail.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } #[test] fn test_input_type_tuple_value_tuple_4x3x2() { - let program_bytes = include_bytes!("type_input_4x3x2.leo"); - let input_bytes = include_bytes!("input/type_tuple_value_tuple_4x3x2.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program_string = include_str!("type_input_4x3x2.leo"); + let input_string = include_str!("input/type_tuple_value_tuple_4x3x2.in"); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_input_type_tuple_value_tuple_4x3x2_fail() { - let program_bytes = include_bytes!("type_input_4x3x2.leo"); - let input_bytes = include_bytes!("input/type_tuple_value_tuple_4x3x2_fail.in"); - let syntax_error = parse_program_with_input(program_bytes, input_bytes).is_err(); + let program_string = include_str!("type_input_4x3x2.leo"); + let input_string = include_str!("input/type_tuple_value_tuple_4x3x2_fail.in"); + let syntax_error = parse_program_with_input(program_string, input_string).is_err(); assert!(syntax_error); } diff --git a/compiler/tests/boolean/mod.rs b/compiler/tests/boolean/mod.rs index 82eaeb8cf2..02d5dad962 100644 --- a/compiler/tests/boolean/mod.rs +++ b/compiler/tests/boolean/mod.rs @@ -40,37 +40,37 @@ pub fn output_false(program: EdwardsTestCompiler) { #[test] fn test_input_pass() { - let program_bytes = include_bytes!("assert_eq_input.leo"); - let input_bytes = include_bytes!("input/true_true.in"); + let program_string = include_str!("assert_eq_input.leo"); + let input_string = include_str!("input/true_true.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_input_fail() { - let program_bytes = include_bytes!("assert_eq_input.leo"); - let input_bytes = include_bytes!("input/true_false.in"); + let program_string = include_str!("assert_eq_input.leo"); + let input_string = include_str!("input/true_false.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program = parse_program_with_input(program_string, input_string).unwrap(); expect_compiler_error(program); } #[test] fn test_registers() { - let program_bytes = include_bytes!("output_register.leo"); - let true_input_bytes = include_bytes!("input/registers_true.in"); - let false_input_bytes = include_bytes!("input/registers_false.in"); + let program_string = include_str!("output_register.leo"); + let true_input_string = include_str!("input/registers_true.in"); + let false_input_string = include_str!("input/registers_false.in"); // test true input register => true output register - let program = parse_program_with_input(program_bytes, true_input_bytes).unwrap(); + let program = parse_program_with_input(program_string, true_input_string).unwrap(); output_true(program); // test false input register => false output register - let program = parse_program_with_input(program_bytes, false_input_bytes).unwrap(); + let program = parse_program_with_input(program_string, false_input_string).unwrap(); output_false(program); } @@ -79,32 +79,32 @@ fn test_registers() { #[test] fn test_not_true() { - let bytes = include_bytes!("not_true.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("not_true.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_not_false() { - let bytes = include_bytes!("not_false.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("not_false.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_not_mutable() { - let bytes = include_bytes!("not_mutable.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("not_mutable.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_not_u32() { - let bytes = include_bytes!("not_u32.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("not_u32.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } @@ -113,32 +113,32 @@ fn test_not_u32() { #[test] fn test_true_or_true() { - let bytes = include_bytes!("true_or_true.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("true_or_true.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_true_or_false() { - let bytes = include_bytes!("true_or_false.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("true_or_false.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_false_or_false() { - let bytes = include_bytes!("false_or_false.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("false_or_false.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_true_or_u32() { - let bytes = include_bytes!("true_or_u32.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("true_or_u32.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } @@ -147,32 +147,32 @@ fn test_true_or_u32() { #[test] fn test_true_and_true() { - let bytes = include_bytes!("true_and_true.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("true_and_true.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_true_and_false() { - let bytes = include_bytes!("true_and_false.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("true_and_false.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_false_and_false() { - let bytes = include_bytes!("false_and_false.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("false_and_false.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_true_and_u32() { - let bytes = include_bytes!("true_and_u32.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("true_and_u32.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } @@ -181,8 +181,8 @@ fn test_true_and_u32() { #[test] fn test_all() { - let bytes = include_bytes!("all.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("all.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } diff --git a/compiler/tests/circuits/define_circuit_inside_circuit_function.leo b/compiler/tests/circuits/define_circuit_inside_circuit_function.leo index 17a8522b97..8c25c1e9d9 100644 --- a/compiler/tests/circuits/define_circuit_inside_circuit_function.leo +++ b/compiler/tests/circuits/define_circuit_inside_circuit_function.leo @@ -3,7 +3,7 @@ circuit Foo { } circuit Bar { - static function bar() { + function bar() { let f = Foo { a: 0u32 }; } } diff --git a/compiler/tests/circuits/member_function_invalid.leo b/compiler/tests/circuits/member_function_invalid.leo index d0a7271a07..bb834e9562 100644 --- a/compiler/tests/circuits/member_function_invalid.leo +++ b/compiler/tests/circuits/member_function_invalid.leo @@ -1,5 +1,5 @@ circuit Foo { - static function echo(x: u32) -> u32 { + function echo(x: u32) -> u32 { return x } } diff --git a/compiler/tests/circuits/member_function_nested.leo b/compiler/tests/circuits/member_function_nested.leo index 4146ef9492..9e07cc9acf 100644 --- a/compiler/tests/circuits/member_function_nested.leo +++ b/compiler/tests/circuits/member_function_nested.leo @@ -1,18 +1,18 @@ circuit Foo { x: u32, - function add_x(y: u32) -> u32 { + function add_x(self, y: u32) -> u32 { return self.x + y } - function call_add_x(y: u32) -> u32 { + function call_add_x(self, y: u32) -> u32 { return self.add_x(y) } } function main() { let a = Foo { x: 1u32 }; - let b = a.call_add_x(1u32); + let b = a.add_x(1u32); console.assert(b == 2u32); } diff --git a/compiler/tests/circuits/member_static_function.leo b/compiler/tests/circuits/member_static_function.leo index ac96c89088..4bf51190f0 100644 --- a/compiler/tests/circuits/member_static_function.leo +++ b/compiler/tests/circuits/member_static_function.leo @@ -1,5 +1,5 @@ circuit Foo { - static function echo(x: u32) -> u32 { + function echo(x: u32) -> u32 { return x } } diff --git a/compiler/tests/circuits/member_static_function_invalid.leo b/compiler/tests/circuits/member_static_function_invalid.leo index b2782bfed4..09fec386d9 100644 --- a/compiler/tests/circuits/member_static_function_invalid.leo +++ b/compiler/tests/circuits/member_static_function_invalid.leo @@ -5,5 +5,5 @@ circuit Foo { } function main() { - let err = Foo::echo(1u32); // echo is a non-static function and must be accessed using `.` + let err = Foo.echo(1u32); // Invalid, echo is a static function and must be accessed using `::` } \ No newline at end of file diff --git a/compiler/tests/circuits/member_static_function_nested.leo b/compiler/tests/circuits/member_static_function_nested.leo index 8f717f3f7c..ef536e3f6e 100644 --- a/compiler/tests/circuits/member_static_function_nested.leo +++ b/compiler/tests/circuits/member_static_function_nested.leo @@ -1,11 +1,11 @@ circuit Foo { - static function qux() {} + function qux() {} - static function bar() { + function bar() { Self::qux(); } - static function baz() { + function baz() { Self::bar(); } } diff --git a/compiler/tests/circuits/member_static_function_undefined.leo b/compiler/tests/circuits/member_static_function_undefined.leo index e8e5cb20bc..cf9f98c7b4 100644 --- a/compiler/tests/circuits/member_static_function_undefined.leo +++ b/compiler/tests/circuits/member_static_function_undefined.leo @@ -1,5 +1,5 @@ circuit Foo { - static function echo(x: u32) -> u32 { + function echo(x: u32) -> u32 { return x } } diff --git a/compiler/tests/circuits/member_variable_and_function.leo b/compiler/tests/circuits/member_variable_and_function.leo index 35f413a361..074feab7b8 100644 --- a/compiler/tests/circuits/member_variable_and_function.leo +++ b/compiler/tests/circuits/member_variable_and_function.leo @@ -1,7 +1,7 @@ circuit Foo { foo: u32, - static function bar() -> u32 { + function bar() -> u32 { return 1u32 } } diff --git a/compiler/tests/circuits/mod.rs b/compiler/tests/circuits/mod.rs index 33d0d41ea9..d3d31dc144 100644 --- a/compiler/tests/circuits/mod.rs +++ b/compiler/tests/circuits/mod.rs @@ -20,24 +20,24 @@ use crate::{assert_satisfied, expect_compiler_error, expect_type_inference_error #[test] fn test_inline() { - let bytes = include_bytes!("inline.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("inline.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_inline_fail() { - let bytes = include_bytes!("inline_fail.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("inline_fail.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_inline_undefined() { - let bytes = include_bytes!("inline_undefined.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("inline_undefined.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } @@ -46,88 +46,88 @@ fn test_inline_undefined() { #[test] fn test_member_variable() { - let bytes = include_bytes!("member_variable.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("member_variable.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_member_variable_fail() { - let bytes = include_bytes!("member_variable_fail.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("member_variable_fail.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_member_variable_and_function() { - let bytes = include_bytes!("member_variable_and_function.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("member_variable_and_function.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_member_function() { - let bytes = include_bytes!("member_function.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("member_function.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_member_function_fail() { - let bytes = include_bytes!("member_function_fail.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("member_function_fail.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_member_function_invalid() { - let bytes = include_bytes!("member_function_invalid.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("member_function_invalid.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_member_function_nested() { - let bytes = include_bytes!("member_function_nested.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("member_function_nested.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_member_static_function() { - let bytes = include_bytes!("member_static_function.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("member_static_function.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_member_static_function_nested() { - let bytes = include_bytes!("member_static_function_nested.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("member_static_function_nested.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_member_static_function_invalid() { - let bytes = include_bytes!("member_static_function_invalid.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("member_static_function_invalid.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error) } #[test] fn test_member_static_function_undefined() { - let bytes = include_bytes!("member_static_function_undefined.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("member_static_function_undefined.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error) } @@ -136,64 +136,64 @@ fn test_member_static_function_undefined() { #[test] fn test_mutate_function_fail() { - let bytes = include_bytes!("mut_function_fail.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("mut_function_fail.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_mutate_self_variable() { - let bytes = include_bytes!("mut_self_variable.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("mut_self_variable.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_mutate_self_variable_fail() { - let bytes = include_bytes!("mut_self_variable_fail.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("mut_self_variable_fail.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_mutate_self_function_fail() { - let bytes = include_bytes!("mut_self_function_fail.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("mut_self_function_fail.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_mutate_self_static_function_fail() { - let bytes = include_bytes!("mut_self_static_function_fail.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("mut_self_static_function_fail.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_mutate_static_function_fail() { - let bytes = include_bytes!("mut_static_function_fail.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("mut_static_function_fail.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_mutate_variable() { - let bytes = include_bytes!("mut_variable.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("mut_variable.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_mutate_variable_fail() { - let bytes = include_bytes!("mut_variable_fail.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("mut_variable_fail.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } @@ -202,32 +202,32 @@ fn test_mutate_variable_fail() { #[test] fn test_self_fail() { - let bytes = include_bytes!("self_fail.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("self_fail.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_self_member_pass() { - let bytes = include_bytes!("self_member.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("self_member.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_self_member_invalid() { - let bytes = include_bytes!("self_member_invalid.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("self_member_invalid.leo"); + let error = parse_program(program_string).err().unwrap(); - let _err = expect_compiler_error(program); + expect_type_inference_error(error); } #[test] fn test_self_member_undefined() { - let bytes = include_bytes!("self_member_undefined.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("self_member_undefined.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } @@ -236,16 +236,16 @@ fn test_self_member_undefined() { #[test] fn test_pedersen_mock() { - let bytes = include_bytes!("pedersen_mock.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("pedersen_mock.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_define_circuit_inside_circuit_function() { - let bytes = include_bytes!("define_circuit_inside_circuit_function.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("define_circuit_inside_circuit_function.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } diff --git a/compiler/tests/circuits/mut_self_function_fail.leo b/compiler/tests/circuits/mut_self_function_fail.leo index 18da32c5fb..8c9b99f6ae 100644 --- a/compiler/tests/circuits/mut_self_function_fail.leo +++ b/compiler/tests/circuits/mut_self_function_fail.leo @@ -3,7 +3,7 @@ circuit Foo { function bar() {} - function set_a(new: u8) { + function set_a(mut self, new: u8) { self.bar = new; } } diff --git a/compiler/tests/circuits/mut_self_static_function_fail.leo b/compiler/tests/circuits/mut_self_static_function_fail.leo index de87c5fadf..8c9b99f6ae 100644 --- a/compiler/tests/circuits/mut_self_static_function_fail.leo +++ b/compiler/tests/circuits/mut_self_static_function_fail.leo @@ -1,9 +1,9 @@ circuit Foo { a: u8, - static function bar() {} + function bar() {} - function set_a(new: u8) { + function set_a(mut self, new: u8) { self.bar = new; } } diff --git a/compiler/tests/circuits/mut_self_variable.leo b/compiler/tests/circuits/mut_self_variable.leo index 47b9aeed70..f5a35ec754 100644 --- a/compiler/tests/circuits/mut_self_variable.leo +++ b/compiler/tests/circuits/mut_self_variable.leo @@ -1,7 +1,7 @@ circuit Foo { - mut a: u8, + a: u8, - function set_a(new: u8) { + function set_a(mut self, new: u8) { self.a = new; console.assert(self.a == new); } diff --git a/compiler/tests/circuits/mut_self_variable_fail.leo b/compiler/tests/circuits/mut_self_variable_fail.leo index 551b041c9e..fdbb556bca 100644 --- a/compiler/tests/circuits/mut_self_variable_fail.leo +++ b/compiler/tests/circuits/mut_self_variable_fail.leo @@ -1,7 +1,7 @@ circuit Foo { a: u8, - function set_a(new: u8) { + function set_a(self, new: u8) { self.a = new; } } diff --git a/compiler/tests/circuits/mut_static_function_fail.leo b/compiler/tests/circuits/mut_static_function_fail.leo index f1bccaaf89..ed3092c656 100644 --- a/compiler/tests/circuits/mut_static_function_fail.leo +++ b/compiler/tests/circuits/mut_static_function_fail.leo @@ -1,5 +1,5 @@ circuit Foo { - static function bar() {} + function bar() {} } function main() { diff --git a/compiler/tests/circuits/mut_variable.leo b/compiler/tests/circuits/mut_variable.leo index eaf61ddf02..243d7a2cf2 100644 --- a/compiler/tests/circuits/mut_variable.leo +++ b/compiler/tests/circuits/mut_variable.leo @@ -1,5 +1,5 @@ circuit Foo { - mut a: u8, + a: u8, } function main() { diff --git a/compiler/tests/circuits/mut_variable_fail.leo b/compiler/tests/circuits/mut_variable_fail.leo index bb2e653ee3..4d58150c95 100644 --- a/compiler/tests/circuits/mut_variable_fail.leo +++ b/compiler/tests/circuits/mut_variable_fail.leo @@ -3,7 +3,7 @@ circuit Foo { } function main() { - let mut f = Foo { a: 0u8 }; + let f = Foo { a: 0u8 }; f.a = 1u8; } \ No newline at end of file diff --git a/compiler/tests/circuits/pedersen_mock.leo b/compiler/tests/circuits/pedersen_mock.leo index 2b58019d8d..0b42c64a6e 100644 --- a/compiler/tests/circuits/pedersen_mock.leo +++ b/compiler/tests/circuits/pedersen_mock.leo @@ -1,11 +1,11 @@ circuit PedersenHash { parameters: [u32; 512] - static function new(parameters: [u32; 512]) -> Self { + function new(parameters: [u32; 512]) -> Self { return Self { parameters: parameters } } - function hash(bits: [bool; 512]) -> u32 { + function hash(self, bits: [bool; 512]) -> u32 { let mut digest: u32 = 0; for i in 0..512 { let base = if bits[i] ? self.parameters[i] : 0u32; diff --git a/compiler/tests/circuits/self_member.leo b/compiler/tests/circuits/self_member.leo index a075894af0..1bd978433d 100644 --- a/compiler/tests/circuits/self_member.leo +++ b/compiler/tests/circuits/self_member.leo @@ -1,7 +1,7 @@ circuit Foo { f: u32, - function bar() -> u32 { + function bar(self) -> u32 { return self.f } } diff --git a/compiler/tests/console/mod.rs b/compiler/tests/console/mod.rs index ba7c48aae9..15b7c309a9 100644 --- a/compiler/tests/console/mod.rs +++ b/compiler/tests/console/mod.rs @@ -19,63 +19,63 @@ use leo_ast::InputValue; #[test] fn test_log() { - let bytes = include_bytes!("log.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("log.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_log_fail() { - let bytes = include_bytes!("log_fail.leo"); + let program_string = include_str!("log_fail.leo"); - assert!(parse_program(bytes).is_err()); + assert!(parse_program(program_string).is_err()); } #[test] fn test_log_parameter() { - let bytes = include_bytes!("log_parameter.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("log_parameter.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_log_parameter_many() { - let bytes = include_bytes!("log_parameter_many.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("log_parameter_many.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_log_parameter_fail_unknown() { - let bytes = include_bytes!("log_parameter_fail_unknown.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("log_parameter_fail_unknown.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_log_parameter_fail_empty() { - let bytes = include_bytes!("log_parameter_fail_empty.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("log_parameter_fail_empty.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_log_parameter_fail_none() { - let bytes = include_bytes!("log_parameter_fail_empty.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("log_parameter_fail_empty.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_log_input() { - let bytes = include_bytes!("log_input.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("log_input.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![("a", Some(InputValue::Boolean(true)))]); @@ -88,8 +88,8 @@ fn test_log_input() { #[test] fn test_debug() { - let bytes = include_bytes!("debug.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("debug.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } @@ -98,8 +98,8 @@ fn test_debug() { #[test] fn test_error() { - let bytes = include_bytes!("error.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("error.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } @@ -108,8 +108,8 @@ fn test_error() { #[test] fn test_assert() { - let bytes = include_bytes!("assert.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("assert.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![("a", Some(InputValue::Boolean(true)))]); @@ -117,7 +117,7 @@ fn test_assert() { assert_satisfied(program); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![("a", Some(InputValue::Boolean(false)))]); @@ -128,15 +128,15 @@ fn test_assert() { #[test] fn test_conditional_assert() { - let bytes = include_bytes!("conditional_assert.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("conditional_assert.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![("a", Some(InputValue::Boolean(true)))]); program.set_main_input(main_input); assert_satisfied(program); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![("a", Some(InputValue::Boolean(false)))]); diff --git a/compiler/tests/core/mod.rs b/compiler/tests/core/mod.rs index 20943b7c36..11ad5f71df 100644 --- a/compiler/tests/core/mod.rs +++ b/compiler/tests/core/mod.rs @@ -20,40 +20,40 @@ use crate::{assert_satisfied, expect_symbol_table_error, parse_program}; #[test] fn test_core_circuit_invalid() { - let program_bytes = include_bytes!("core_package_invalid.leo"); - let program = parse_program(program_bytes).err().unwrap(); + let program_string = include_str!("core_package_invalid.leo"); + let error = parse_program(program_string).err().unwrap(); - expect_symbol_table_error(program); + expect_symbol_table_error(error); } #[test] fn test_core_circuit_star_fail() { - let program_bytes = include_bytes!("core_circuit_star_fail.leo"); - let error = parse_program(program_bytes).err().unwrap(); + let program_string = include_str!("core_circuit_star_fail.leo"); + let error = parse_program(program_string).err().unwrap(); expect_symbol_table_error(error); } #[test] fn test_core_package_invalid() { - let program_bytes = include_bytes!("core_package_invalid.leo"); - let error = parse_program(program_bytes).err().unwrap(); + let program_string = include_str!("core_package_invalid.leo"); + let error = parse_program(program_string).err().unwrap(); expect_symbol_table_error(error); } #[test] fn test_core_unstable_package_invalid() { - let program_bytes = include_bytes!("core_unstable_package_invalid.leo"); - let error = parse_program(program_bytes).err().unwrap(); + let program_string = include_str!("core_unstable_package_invalid.leo"); + let error = parse_program(program_string).err().unwrap(); expect_symbol_table_error(error); } #[test] fn test_unstable_blake2s_sanity() { - let program_bytes = include_bytes!("unstable_blake2s.leo"); - let program = parse_program(program_bytes).unwrap(); + let program_string = include_str!("unstable_blake2s.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } diff --git a/compiler/tests/core/packages/unstable/blake2s/mod.rs b/compiler/tests/core/packages/unstable/blake2s/mod.rs index 2b308db42e..7bef75b1c4 100644 --- a/compiler/tests/core/packages/unstable/blake2s/mod.rs +++ b/compiler/tests/core/packages/unstable/blake2s/mod.rs @@ -32,33 +32,32 @@ use snarkos_models::algorithms::PRF; #[test] fn test_arguments_length_fail() { - let program_bytes = include_bytes!("arguments_length_fail.leo"); - let error = parse_program(program_bytes).err().unwrap(); + let program_string = include_str!("arguments_length_fail.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_arguments_type_fail() { - let program_bytes = include_bytes!("arguments_type_fail.leo"); - let error = parse_program(program_bytes).err().unwrap(); + let program_string = include_str!("arguments_type_fail.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_blake2s_input() { - let input_bytes = include_bytes!("inputs/valid_input.in"); - let program_bytes = include_bytes!("blake2s_input.leo"); - let expected_bytes = include_bytes!("outputs/valid_output.out"); + let input_string = include_str!("inputs/valid_input.in"); + let program_string = include_str!("blake2s_input.leo"); + let expected_string = include_str!("outputs/valid_output.out"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program = parse_program_with_input(program_string, input_string).unwrap(); - let expected = std::str::from_utf8(expected_bytes).unwrap(); let actual_bytes = get_output(program); - let actual = std::str::from_utf8(actual_bytes.bytes().as_slice()).unwrap(); + let actual_string = std::str::from_utf8(actual_bytes.bytes().as_slice()).unwrap(); - assert_eq!(expected, actual) + assert_eq!(expected_string, actual_string) } #[test] @@ -81,7 +80,7 @@ fn test_blake2s_random() { // The `blake2s_random.leo` program will compute a blake2s hash digest and compare it against // the expected value - let bytes = include_bytes!("blake2s_random.leo"); + let bytes = include_str!("blake2s_random.leo"); let mut program = parse_program(bytes).unwrap(); let main_input = generate_main_input(vec![ diff --git a/compiler/tests/definition/mod.rs b/compiler/tests/definition/mod.rs index 7b38d695fc..75dff4e557 100644 --- a/compiler/tests/definition/mod.rs +++ b/compiler/tests/definition/mod.rs @@ -18,9 +18,9 @@ use crate::{assert_satisfied, import::set_local_dir, parse_program}; #[test] fn test_out_of_order() { - let program_bytes = include_bytes!("out_of_order.leo"); + let program_string = include_str!("out_of_order.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } @@ -30,9 +30,9 @@ fn test_out_of_order() { fn test_out_of_order_with_import() { set_local_dir(); - let program_bytes = include_bytes!("out_of_order_with_import.leo"); + let program_string = include_str!("out_of_order_with_import.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } diff --git a/compiler/tests/field/mod.rs b/compiler/tests/field/mod.rs index 0cb5e4198c..fa57001223 100644 --- a/compiler/tests/field/mod.rs +++ b/compiler/tests/field/mod.rs @@ -52,8 +52,8 @@ fn test_negate() { let a_string = field_to_decimal_string(a); let b_string = field_to_decimal_string(b); - let bytes = include_bytes!("negate.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("negate.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Field(a_string))), @@ -81,8 +81,8 @@ fn test_add() { let b_string = field_to_decimal_string(b); let c_string = field_to_decimal_string(c); - let bytes = include_bytes!("add.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("add.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Field(a_string))), @@ -111,8 +111,8 @@ fn test_sub() { let b_string = field_to_decimal_string(b); let c_string = field_to_decimal_string(c); - let bytes = include_bytes!("sub.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("sub.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Field(a_string))), @@ -140,8 +140,8 @@ fn test_div() { let b_string = field_to_decimal_string(b); let c_string = field_to_decimal_string(c); - let bytes = include_bytes!("div.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("div.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Field(a_string))), @@ -169,8 +169,8 @@ fn test_mul() { let b_string = field_to_decimal_string(b); let c_string = field_to_decimal_string(c); - let bytes = include_bytes!("mul.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("mul.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Field(a_string))), @@ -197,8 +197,8 @@ fn test_eq() { // test equal - let bytes = include_bytes!("eq.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("eq.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Field(a_string.clone()))), @@ -214,7 +214,7 @@ fn test_eq() { let c = a.eq(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Field(a_string))), @@ -237,8 +237,8 @@ fn test_console_assert_pass() { let a_string = field_to_decimal_string(a); - let bytes = include_bytes!("console_assert.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("console_assert.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Field(a_string.clone()))), @@ -266,8 +266,8 @@ fn test_console_assert_fail() { let a_string = field_to_decimal_string(a); let b_string = field_to_decimal_string(b); - let bytes = include_bytes!("console_assert.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("console_assert.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Field(a_string))), @@ -290,8 +290,8 @@ fn test_ternary() { let a_string = field_to_decimal_string(a); let b_string = field_to_decimal_string(b); - let bytes = include_bytes!("ternary.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("ternary.leo"); + let mut program = parse_program(program_string).unwrap(); // true -> field a let main_input = generate_main_input(vec![ @@ -305,7 +305,7 @@ fn test_ternary() { assert_satisfied(program); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); // false -> field b let main_input = generate_main_input(vec![ @@ -322,24 +322,24 @@ fn test_ternary() { // // pub fn output_one(program: EdwardsTestCompiler) { -// let expected = include_bytes!("output_/register_one.out"); +// let expected = include_str!("output_/register_one.out"); // let actual = get_output(program); // -// assert_eq!(expected, actual.bytes().as_slice()); +// assert_eq!(expected, actual.program_string().as_slice()); // } // // pub fn output_zero(program: EdwardsTestCompiler) { -// let expected = include_bytes!("output_/register_zero.out"); +// let expected = include_str!("output_/register_zero.out"); // let actual = get_output(program); // -// assert_eq!(expected, actual.bytes().as_slice()); +// assert_eq!(expected, actual.program_string().as_slice()); // } // // #[test] // fn test_registers() { -// let program_bytes = include_bytes!("output_register.leo"); -// let one_input_bytes = include_bytes!("input/register_one.in"); -// let zero_input_bytes = include_bytes!("input/register_zero.in"); +// let program_bytes = include_str!("output_register.leo"); +// let one_input_bytes = include_str!("input/register_one.in"); +// let zero_input_bytes = include_str!("input/register_zero.in"); // // // test 1field input register => 1field output register // let program = parse_program_with_input(program_bytes, one_input_bytes).unwrap(); diff --git a/compiler/tests/function/mod.rs b/compiler/tests/function/mod.rs index dc31094f76..652964fafb 100644 --- a/compiler/tests/function/mod.rs +++ b/compiler/tests/function/mod.rs @@ -26,85 +26,99 @@ use leo_compiler::errors::{CompilerError, ExpressionError, FunctionError, Statem #[test] fn test_empty() { - let bytes = include_bytes!("empty.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("empty.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_iteration() { - let bytes = include_bytes!("iteration.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("iteration.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_iteration_repeated() { - let bytes = include_bytes!("iteration_repeated.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("iteration_repeated.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_newlines() { - let input_bytes = include_bytes!("input/newlines.in"); - let program_bytes = include_bytes!("newlines.leo"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let input_string = include_str!("input/newlines.in"); + let program_string = include_str!("newlines.leo"); + let program = parse_program_with_input(program_string, input_string).unwrap(); - let expected_bytes = include_bytes!("output/newlines.out"); - let expected = std::str::from_utf8(expected_bytes).unwrap(); + let expected_string = include_str!("output/newlines.out"); let actual_bytes = get_output(program); - let actual = std::str::from_utf8(actual_bytes.bytes().as_slice()).unwrap(); + let actual_string = std::str::from_utf8(actual_bytes.bytes().as_slice()).unwrap(); - assert_eq!(expected, actual); + assert_eq!(expected_string, actual_string); } #[test] fn test_multiple_returns() { - let bytes = include_bytes!("multiple.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("multiple_returns.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } +#[test] +fn test_multiple_returns_fail() { + let program_string = include_str!("multiple_returns_fail.leo"); + let program = parse_program(program_string).unwrap(); + + expect_compiler_error(program); +} + +#[test] +fn test_multiple_returns_fail_conditional() { + let program_string = include_str!("multiple_returns_fail_conditional.leo"); + let program = parse_program(program_string).unwrap(); + + expect_compiler_error(program); +} + #[test] fn test_multiple_returns_main() { - let program_bytes = include_bytes!("multiple_main.leo"); - let input_bytes = include_bytes!("input/registers.in"); + let program_string = include_str!("multiple_returns_main.leo"); + let input_string = include_str!("input/registers.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program = parse_program_with_input(program_string, input_string).unwrap(); - let expected_bytes = include_bytes!("output/registers.out"); - let expected = std::str::from_utf8(expected_bytes).unwrap(); + let expected_string = include_str!("output/registers.out"); let actual_bytes = get_output(program); - let actual = std::str::from_utf8(actual_bytes.bytes().as_slice()).unwrap(); + let actual_string = std::str::from_utf8(actual_bytes.bytes().as_slice()).unwrap(); - assert_eq!(expected, actual); + assert_eq!(expected_string, actual_string); } #[test] fn test_repeated_function_call() { - let bytes = include_bytes!("repeated.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("repeated.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_return() { - let bytes = include_bytes!("return.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("return.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_scope_fail() { - let bytes = include_bytes!("scope_fail.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("scope_fail.leo"); + let program = parse_program(program_string).unwrap(); match expect_compiler_error(program) { CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError( @@ -119,24 +133,24 @@ fn test_scope_fail() { #[test] fn test_undefined() { - let bytes = include_bytes!("undefined.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("undefined.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_value_unchanged() { - let bytes = include_bytes!("value_unchanged.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("value_unchanged.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_array_input() { - let bytes = include_bytes!("array_input.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("array_input.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error) } @@ -145,32 +159,32 @@ fn test_array_input() { #[test] fn test_return_array_nested_fail() { - let bytes = include_bytes!("return_array_nested_fail.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("return_array_nested_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_return_array_nested_pass() { - let bytes = include_bytes!("return_array_nested_pass.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("return_array_nested_pass.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_return_array_tuple_fail() { - let bytes = include_bytes!("return_array_tuple_fail.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("return_array_tuple_fail.leo"); + let program = parse_program(program_string).unwrap(); let _err = expect_compiler_error(program); } #[test] fn test_return_array_tuple_pass() { - let bytes = include_bytes!("return_array_tuple_pass.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("return_array_tuple_pass.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } @@ -179,16 +193,16 @@ fn test_return_array_tuple_pass() { #[test] fn test_return_tuple() { - let bytes = include_bytes!("return_tuple.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("return_tuple.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_return_tuple_conditional() { - let bytes = include_bytes!("return_tuple_conditional.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("return_tuple_conditional.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } diff --git a/compiler/tests/function/multiple.leo b/compiler/tests/function/multiple_returns.leo similarity index 100% rename from compiler/tests/function/multiple.leo rename to compiler/tests/function/multiple_returns.leo diff --git a/compiler/tests/function/multiple_returns_fail.leo b/compiler/tests/function/multiple_returns_fail.leo new file mode 100644 index 0000000000..d4a8b36eac --- /dev/null +++ b/compiler/tests/function/multiple_returns_fail.leo @@ -0,0 +1,7 @@ +function main () -> i8 { + if true { + return 1i8 //ignored + } + return 2i8 //ignored + return 3i8 //returns +} \ No newline at end of file diff --git a/compiler/tests/function/multiple_returns_fail_conditional.leo b/compiler/tests/function/multiple_returns_fail_conditional.leo new file mode 100644 index 0000000000..04ebb9e306 --- /dev/null +++ b/compiler/tests/function/multiple_returns_fail_conditional.leo @@ -0,0 +1,9 @@ +function main () -> u16 { + if false { + let a = 1u16; + let b = a + 1u16; + return b + } else if false { + return 0u16 + } +} \ No newline at end of file diff --git a/compiler/tests/function/multiple_main.leo b/compiler/tests/function/multiple_returns_main.leo similarity index 100% rename from compiler/tests/function/multiple_main.leo rename to compiler/tests/function/multiple_returns_main.leo diff --git a/compiler/tests/group/mod.rs b/compiler/tests/group/mod.rs index c560afdc57..ca383a33e3 100644 --- a/compiler/tests/group/mod.rs +++ b/compiler/tests/group/mod.rs @@ -15,8 +15,13 @@ // along with the Leo library. If not, see . use crate::{ - assert_satisfied, expect_compiler_error, expect_synthesis_error, field::field_to_decimal_string, - generate_main_input, parse_program, parse_program_with_input, + assert_satisfied, + expect_compiler_error, + expect_synthesis_error, + field::field_to_decimal_string, + generate_main_input, + parse_program, + parse_program_with_input, }; use leo_ast::{GroupCoordinate, GroupTuple, GroupValue, InputValue, Span}; @@ -47,124 +52,124 @@ pub fn group_element_to_input_value(g: EdwardsAffine) -> GroupValue { #[test] fn test_one() { - let bytes = include_bytes!("one.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("one.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_zero() { - let bytes = include_bytes!("zero.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("zero.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_point() { - let bytes = include_bytes!("point.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("point.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_x_sign_high() { - let bytes = include_bytes!("x_sign_high.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("x_sign_high.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_x_sign_low() { - let bytes = include_bytes!("x_sign_low.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("x_sign_low.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_x_sign_inferred() { - let bytes = include_bytes!("x_sign_inferred.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("x_sign_inferred.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_y_sign_high() { - let bytes = include_bytes!("y_sign_high.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("y_sign_high.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_y_sign_low() { - let bytes = include_bytes!("y_sign_low.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("y_sign_low.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_y_sign_inferred() { - let bytes = include_bytes!("y_sign_inferred.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("y_sign_inferred.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_both_sign_high() { - let bytes = include_bytes!("both_sign_high.leo"); + let program_string = include_str!("both_sign_high.leo"); - let program = parse_program(bytes).unwrap(); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_both_sign_low() { - let bytes = include_bytes!("both_sign_low.leo"); + let program_string = include_str!("both_sign_low.leo"); - let program = parse_program(bytes).unwrap(); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_both_sign_inferred() { - let bytes = include_bytes!("both_sign_inferred.leo"); + let program_string = include_str!("both_sign_inferred.leo"); - let program = parse_program(bytes).unwrap(); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_point_input() { - let program_bytes = include_bytes!("point_input.leo"); - let input_bytes = include_bytes!("input/point.in"); + let program_string = include_str!("point_input.leo"); + let input_bytes = include_str!("input/point.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program = parse_program_with_input(program_string, input_bytes).unwrap(); assert_satisfied(program); } #[test] fn test_input() { - let program_bytes = include_bytes!("input.leo"); - let input_bytes_pass = include_bytes!("input/valid.in"); - let input_bytes_fail = include_bytes!("input/invalid.in"); + let program_string = include_str!("input.leo"); + let input_string_pass = include_str!("input/valid.in"); + let input_string_fail = include_str!("input/invalid.in"); - let program = parse_program_with_input(program_bytes, input_bytes_pass).unwrap(); + let program = parse_program_with_input(program_string, input_string_pass).unwrap(); assert_satisfied(program); - let program = parse_program_with_input(program_bytes, input_bytes_fail).unwrap(); + let program = parse_program_with_input(program_string, input_string_fail).unwrap(); expect_compiler_error(program); } @@ -182,8 +187,8 @@ fn test_negate() { let a_element = group_element_to_input_value(a); let b_element = group_element_to_input_value(b); - let bytes = include_bytes!("negate.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("negate.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Group(a_element))), @@ -210,8 +215,8 @@ fn test_add() { let b_element = group_element_to_input_value(b); let c_element = group_element_to_input_value(c); - let bytes = include_bytes!("add.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("add.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Group(a_element))), @@ -239,8 +244,8 @@ fn test_sub() { let b_element = group_element_to_input_value(b); let c_element = group_element_to_input_value(c); - let bytes = include_bytes!("sub.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("sub.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Group(a_element))), @@ -262,8 +267,8 @@ fn test_console_assert_pass() { let a_element = group_element_to_input_value(a); - let bytes = include_bytes!("assert_eq.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("assert_eq.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Group(a_element.clone()))), @@ -291,8 +296,8 @@ fn test_console_assert_fail() { let a_element = group_element_to_input_value(a); let b_element = group_element_to_input_value(b); - let bytes = include_bytes!("assert_eq.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("assert_eq.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Group(a_element))), @@ -318,8 +323,8 @@ fn test_eq() { // test equal - let bytes = include_bytes!("eq.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("eq.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Group(a_element.clone()))), @@ -335,7 +340,7 @@ fn test_eq() { let c = a.eq(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Group(a_element))), @@ -359,8 +364,8 @@ fn test_ternary() { let a_element = group_element_to_input_value(a); let b_element = group_element_to_input_value(b); - let bytes = include_bytes!("ternary.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("ternary.leo"); + let mut program = parse_program(program_string).unwrap(); // true -> field a let main_input = generate_main_input(vec![ @@ -374,7 +379,7 @@ fn test_ternary() { assert_satisfied(program); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); // false -> field b let main_input = generate_main_input(vec![ diff --git a/compiler/tests/import/mod.rs b/compiler/tests/import/mod.rs index d4bd578c0b..2218046389 100644 --- a/compiler/tests/import/mod.rs +++ b/compiler/tests/import/mod.rs @@ -34,8 +34,8 @@ pub fn set_local_dir() { fn test_basic() { set_local_dir(); - let bytes = include_bytes!("basic.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("basic.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } @@ -45,8 +45,8 @@ fn test_basic() { fn test_multiple() { set_local_dir(); - let bytes = include_bytes!("multiple.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("multiple.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } @@ -56,8 +56,8 @@ fn test_multiple() { fn test_star() { set_local_dir(); - let bytes = include_bytes!("star.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("star.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } @@ -67,8 +67,8 @@ fn test_star() { fn test_star_fail() { set_local_dir(); - let bytes = include_bytes!("star_fail.leo"); - assert!(parse_program(bytes).is_err()); + let program_string = include_str!("star_fail.leo"); + assert!(parse_program(program_string).is_err()); } #[test] @@ -76,8 +76,8 @@ fn test_star_fail() { fn test_alias() { set_local_dir(); - let bytes = include_bytes!("alias.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("alias.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } @@ -88,8 +88,8 @@ fn test_alias() { fn test_names_pass() { set_local_dir(); - let bytes = include_bytes!("names.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("names.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } @@ -99,8 +99,8 @@ fn test_names_pass() { fn test_names_fail_1() { set_local_dir(); - let bytes = include_bytes!("names_dash_a.leo"); - assert!(parse_program(bytes).is_err()); + let program_string = include_str!("names_dash_a.leo"); + assert!(parse_program(program_string).is_err()); } #[test] @@ -108,8 +108,8 @@ fn test_names_fail_1() { fn test_names_fail_2() { set_local_dir(); - let bytes = include_bytes!("names_a_dash.leo"); - assert!(parse_program(bytes).is_err()); + let program_string = include_str!("names_a_dash.leo"); + assert!(parse_program(program_string).is_err()); } #[test] @@ -117,8 +117,8 @@ fn test_names_fail_2() { fn test_names_fail_3() { set_local_dir(); - let bytes = include_bytes!("names_underscore.leo"); - assert!(parse_program(bytes).is_err()); + let program_string = include_str!("names_underscore.leo"); + assert!(parse_program(program_string).is_err()); } #[test] @@ -126,8 +126,8 @@ fn test_names_fail_3() { fn test_names_fail_4() { set_local_dir(); - let bytes = include_bytes!("names_dollar.leo"); - assert!(parse_program(bytes).is_err()); + let program_string = include_str!("names_dollar.leo"); + assert!(parse_program(program_string).is_err()); } // more complex tests @@ -136,8 +136,8 @@ fn test_names_fail_4() { fn test_many_import() { set_local_dir(); - let bytes = include_bytes!("many_import.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("many_import.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } @@ -147,8 +147,8 @@ fn test_many_import() { fn test_many_import_star() { set_local_dir(); - let bytes = include_bytes!("many_import_star.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("many_import_star.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } diff --git a/compiler/tests/input_files/program_input/mod.rs b/compiler/tests/input_files/program_input/mod.rs index 830e3b8651..befe97057e 100644 --- a/compiler/tests/input_files/program_input/mod.rs +++ b/compiler/tests/input_files/program_input/mod.rs @@ -26,40 +26,40 @@ fn expect_fail(program: EdwardsTestCompiler) { #[test] fn test_input_pass() { - let program_bytes = include_bytes!("main.leo"); - let input_bytes = include_bytes!("input/main.in"); + let program_string = include_str!("main.leo"); + let input_string = include_str!("input/main.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } #[test] fn test_input_fail_name() { - let program_bytes = include_bytes!("main.leo"); - let input_bytes = include_bytes!("input/main_fail_name.in"); + let program_string = include_str!("main.leo"); + let input_string = include_str!("input/main_fail_name.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program = parse_program_with_input(program_string, input_string).unwrap(); expect_fail(program); } #[test] fn test_input_fail_type() { - let program_bytes = include_bytes!("main.leo"); - let input_bytes = include_bytes!("input/main_fail_type.in"); + let program_string = include_str!("main.leo"); + let input_string = include_str!("input/main_fail_type.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program = parse_program_with_input(program_string, input_string).unwrap(); expect_fail(program); } #[test] fn test_input_multiple() { - let program_bytes = include_bytes!("main_multiple.leo"); - let input_bytes = include_bytes!("input/main_multiple.in"); + let program_string = include_str!("main_multiple.leo"); + let input_string = include_str!("input/main_multiple.in"); - let program = parse_program_with_input(program_bytes, input_bytes).unwrap(); + let program = parse_program_with_input(program_string, input_string).unwrap(); assert_satisfied(program); } diff --git a/compiler/tests/input_files/program_input_and_program_state/mod.rs b/compiler/tests/input_files/program_input_and_program_state/mod.rs index c80bd98b7b..26f2fead35 100644 --- a/compiler/tests/input_files/program_input_and_program_state/mod.rs +++ b/compiler/tests/input_files/program_input_and_program_state/mod.rs @@ -18,27 +18,27 @@ use crate::{assert_satisfied, parse_input_and_state, parse_program_with_input_an #[test] fn test_basic() { - let input_bytes = include_bytes!("input/basic.in"); - let state_bytes = include_bytes!("input/basic.state"); + let input_string = include_str!("input/basic.in"); + let state_string = include_str!("input/basic.state"); - parse_input_and_state(input_bytes, state_bytes).unwrap(); + parse_input_and_state(input_string, state_string).unwrap(); } #[test] fn test_full() { - let input_bytes = include_bytes!("input/token_withdraw.in"); - let state_bytes = include_bytes!("input/token_withdraw.state"); + let input_string = include_str!("input/token_withdraw.in"); + let state_string = include_str!("input/token_withdraw.state"); - parse_input_and_state(input_bytes, state_bytes).unwrap(); + parse_input_and_state(input_string, state_string).unwrap(); } #[test] fn test_access() { - let program_bytes = include_bytes!("access.leo"); - let input_bytes = include_bytes!("input/token_withdraw.in"); - let state_bytes = include_bytes!("input/token_withdraw.state"); + let program_string = include_str!("access.leo"); + let input_string = include_str!("input/token_withdraw.in"); + let state_string = include_str!("input/token_withdraw.state"); - let program = parse_program_with_input_and_state(program_bytes, input_bytes, state_bytes).unwrap(); + let program = parse_program_with_input_and_state(program_string, input_string, state_string).unwrap(); assert_satisfied(program); } diff --git a/compiler/tests/input_files/program_state/mod.rs b/compiler/tests/input_files/program_state/mod.rs index d3e46194b1..ac775270b1 100644 --- a/compiler/tests/input_files/program_state/mod.rs +++ b/compiler/tests/input_files/program_state/mod.rs @@ -18,61 +18,61 @@ use crate::{assert_satisfied, parse_program_with_state, parse_state}; #[test] fn test_basic() { - let bytes = include_bytes!("input/basic.state"); + let state_string = include_str!("input/basic.state"); - parse_state(bytes).unwrap(); + parse_state(state_string).unwrap(); } #[test] fn test_token_withdraw() { - let bytes = include_bytes!("input/token_withdraw.state"); + let state_string = include_str!("input/token_withdraw.state"); - parse_state(bytes).unwrap(); + parse_state(state_string).unwrap(); } #[test] fn test_access_state() { - let program_bytes = include_bytes!("access_state.leo"); - let state_bytes = include_bytes!("input/token_withdraw.state"); + let program_string = include_str!("access_state.leo"); + let state_string = include_str!("input/token_withdraw.state"); - let program = parse_program_with_state(program_bytes, state_bytes).unwrap(); + let program = parse_program_with_state(program_string, state_string).unwrap(); assert_satisfied(program); } #[test] fn test_access_all() { - let program_bytes = include_bytes!("access_all.leo"); - let state_bytes = include_bytes!("input/token_withdraw.state"); + let program_string = include_str!("access_all.leo"); + let state_string = include_str!("input/token_withdraw.state"); - let program = parse_program_with_state(program_bytes, state_bytes).unwrap(); + let program = parse_program_with_state(program_string, state_string).unwrap(); assert_satisfied(program); } #[test] fn test_visibility_fail() { - let state_bytes = include_bytes!("input/visibility_fail.state"); + let state_string = include_str!("input/visibility_fail.state"); - let is_err = parse_state(state_bytes).is_err(); + let is_err = parse_state(state_string).is_err(); assert!(is_err); } #[test] fn test_section_undefined() { - let state_bytes = include_bytes!("input/section_undefined.state"); + let state_string = include_str!("input/section_undefined.state"); - let is_err = parse_state(state_bytes).is_err(); + let is_err = parse_state(state_string).is_err(); assert!(is_err); } #[test] fn test_section_invalid() { - let state_bytes = include_bytes!("input/section_invalid.state"); + let state_string = include_str!("input/section_invalid.state"); - let is_err = parse_state(state_bytes).is_err(); + let is_err = parse_state(state_string).is_err(); assert!(is_err); } diff --git a/compiler/tests/integers/int_macro.rs b/compiler/tests/integers/int_macro.rs index cdcd3e7f3d..9346ced2d8 100644 --- a/compiler/tests/integers/int_macro.rs +++ b/compiler/tests/integers/int_macro.rs @@ -28,8 +28,8 @@ macro_rules! test_int { None => continue, }; - let bytes = include_bytes!("negate.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("negate.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), ("b", Some(InputValue::Integer($integer_type, b.to_string()))), @@ -42,15 +42,15 @@ macro_rules! test_int { } fn test_negate_min_fail() { - let bytes = include_bytes!("negate_min.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("negate_min.leo"); + let program = parse_program(program_string).unwrap(); expect_computation_error(program); } fn test_negate_zero() { - let bytes = include_bytes!("negate_zero.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("negate_zero.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } @@ -58,29 +58,29 @@ macro_rules! test_int { impl IntegerTester for $name { fn test_min() { - let bytes = include_bytes!("min.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("min.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } fn test_min_fail() { - let bytes = include_bytes!("min_fail.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("min_fail.leo"); + let program = parse_program(program_string).unwrap(); expect_parsing_error(program); } fn test_max() { - let bytes = include_bytes!("max.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("max.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } fn test_max_fail() { - let bytes = include_bytes!("max_fail.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("max_fail.leo"); + let program = parse_program(program_string).unwrap(); expect_parsing_error(program); } @@ -95,8 +95,8 @@ macro_rules! test_int { None => continue, }; - let bytes = include_bytes!("add.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("add.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -124,8 +124,8 @@ macro_rules! test_int { None => continue, }; - let bytes = include_bytes!("sub.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("sub.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -149,8 +149,8 @@ macro_rules! test_int { None => continue, }; - let bytes = include_bytes!("mul.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("mul.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -176,8 +176,8 @@ macro_rules! test_int { continue; } - let bytes = include_bytes!("div.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("div.leo"); + let mut program = parse_program(program_string).unwrap(); // expect an error when dividing by zero if b == 0 { @@ -220,8 +220,8 @@ macro_rules! test_int { None => continue, }; - let bytes = include_bytes!("pow.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("pow.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -242,8 +242,8 @@ macro_rules! test_int { // test equal - let bytes = include_bytes!("eq.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("eq.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -259,7 +259,7 @@ macro_rules! test_int { let c = a.eq(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -280,8 +280,8 @@ macro_rules! test_int { // test a != a == false - let bytes = include_bytes!("ne.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("ne.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -297,7 +297,7 @@ macro_rules! test_int { let c = a.ne(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -318,8 +318,8 @@ macro_rules! test_int { // test equal - let bytes = include_bytes!("ge.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("ge.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -335,7 +335,7 @@ macro_rules! test_int { let c = a.ge(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -356,8 +356,8 @@ macro_rules! test_int { // test equal - let bytes = include_bytes!("gt.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("gt.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -373,7 +373,7 @@ macro_rules! test_int { let c = a.gt(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -394,8 +394,8 @@ macro_rules! test_int { // test equal - let bytes = include_bytes!("le.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("le.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -411,7 +411,7 @@ macro_rules! test_int { let c = a.le(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -432,8 +432,8 @@ macro_rules! test_int { // test equal - let bytes = include_bytes!("lt.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("lt.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -449,7 +449,7 @@ macro_rules! test_int { let c = a.lt(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -468,8 +468,8 @@ macro_rules! test_int { let a: $type_ = rand::random(); // test equal - let bytes = include_bytes!("console_assert.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("console_assert.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -487,7 +487,7 @@ macro_rules! test_int { continue; } - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -504,8 +504,8 @@ macro_rules! test_int { let a: $type_ = rand::random(); let b: $type_ = rand::random(); - let bytes = include_bytes!("ternary.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("ternary.leo"); + let mut program = parse_program(program_string).unwrap(); // true -> field 1 let main_input = generate_main_input(vec![ @@ -520,7 +520,7 @@ macro_rules! test_int { assert_satisfied(program); // false -> field 2 - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("s", Some(InputValue::Boolean(false))), diff --git a/compiler/tests/integers/uint_macro.rs b/compiler/tests/integers/uint_macro.rs index c85b6a68c4..e220a82be7 100644 --- a/compiler/tests/integers/uint_macro.rs +++ b/compiler/tests/integers/uint_macro.rs @@ -20,29 +20,29 @@ macro_rules! test_uint { impl IntegerTester for $name { fn test_min() { - let bytes = include_bytes!("min.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("min.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } fn test_min_fail() { - let bytes = include_bytes!("min_fail.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("min_fail.leo"); + let program = parse_program(program_string).unwrap(); expect_parsing_error(program); } fn test_max() { - let bytes = include_bytes!("max.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("max.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } fn test_max_fail() { - let bytes = include_bytes!("max_fail.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("max_fail.leo"); + let program = parse_program(program_string).unwrap(); expect_parsing_error(program); } @@ -57,8 +57,8 @@ macro_rules! test_uint { None => continue, }; - let bytes = include_bytes!("add.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("add.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -82,8 +82,8 @@ macro_rules! test_uint { None => continue, }; - let bytes = include_bytes!("sub.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("sub.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -107,8 +107,8 @@ macro_rules! test_uint { None => continue, }; - let bytes = include_bytes!("mul.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("mul.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -132,8 +132,8 @@ macro_rules! test_uint { None => continue, }; - let bytes = include_bytes!("div.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("div.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -158,8 +158,8 @@ macro_rules! test_uint { None => continue, }; - let bytes = include_bytes!("pow.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("pow.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -180,8 +180,8 @@ macro_rules! test_uint { // test equal - let bytes = include_bytes!("eq.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("eq.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -197,7 +197,7 @@ macro_rules! test_uint { let c = a.eq(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -218,8 +218,8 @@ macro_rules! test_uint { // test a != a == false - let bytes = include_bytes!("ne.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("ne.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -235,7 +235,7 @@ macro_rules! test_uint { let c = a.ne(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -256,8 +256,8 @@ macro_rules! test_uint { // test equal - let bytes = include_bytes!("ge.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("ge.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -273,7 +273,7 @@ macro_rules! test_uint { let c = a.ge(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -294,8 +294,8 @@ macro_rules! test_uint { // test equal - let bytes = include_bytes!("gt.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("gt.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -311,7 +311,7 @@ macro_rules! test_uint { let c = a.gt(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -332,8 +332,8 @@ macro_rules! test_uint { // test equal - let bytes = include_bytes!("le.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("le.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -349,7 +349,7 @@ macro_rules! test_uint { let c = a.le(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -370,8 +370,8 @@ macro_rules! test_uint { // test equal - let bytes = include_bytes!("lt.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("lt.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -387,7 +387,7 @@ macro_rules! test_uint { let c = a.lt(&b); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -406,8 +406,8 @@ macro_rules! test_uint { let a: $type_ = rand::random(); // test equal - let bytes = include_bytes!("console_assert.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("console_assert.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -425,7 +425,7 @@ macro_rules! test_uint { continue; } - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Integer($integer_type, a.to_string()))), @@ -442,8 +442,8 @@ macro_rules! test_uint { let a: $type_ = rand::random(); let b: $type_ = rand::random(); - let bytes = include_bytes!("ternary.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("ternary.leo"); + let mut program = parse_program(program_string).unwrap(); // true -> field 1 let main_input = generate_main_input(vec![ @@ -458,7 +458,7 @@ macro_rules! test_uint { assert_satisfied(program); // false -> field 2 - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("s", Some(InputValue::Boolean(false))), diff --git a/compiler/tests/mod.rs b/compiler/tests/mod.rs index a18efa9428..434a19ff16 100644 --- a/compiler/tests/mod.rs +++ b/compiler/tests/mod.rs @@ -64,94 +64,79 @@ fn new_compiler() -> EdwardsTestCompiler { EdwardsTestCompiler::new(program_name, path, output_dir) } -pub(crate) fn parse_program(bytes: &[u8]) -> Result { +pub(crate) fn parse_program(program_string: &str) -> Result { let mut compiler = new_compiler(); - let program_string = String::from_utf8_lossy(bytes); - compiler.parse_program_from_string(&program_string)?; + compiler.parse_program_from_string(program_string)?; Ok(compiler) } -pub(crate) fn parse_input(bytes: &[u8]) -> Result { +pub(crate) fn parse_input(input_string: &str) -> Result { let mut compiler = new_compiler(); - let input_string = String::from_utf8_lossy(bytes); let path = PathBuf::new(); - compiler.parse_input(&input_string, &path, EMPTY_FILE, &path)?; + compiler.parse_input(input_string, &path, EMPTY_FILE, &path)?; Ok(compiler) } -pub(crate) fn parse_state(bytes: &[u8]) -> Result { +pub(crate) fn parse_state(state_string: &str) -> Result { let mut compiler = new_compiler(); - let state_string = String::from_utf8_lossy(bytes); let path = PathBuf::new(); - compiler.parse_input(EMPTY_FILE, &path, &state_string, &path)?; + compiler.parse_input(EMPTY_FILE, &path, state_string, &path)?; Ok(compiler) } pub(crate) fn parse_input_and_state( - input_bytes: &[u8], - state_bytes: &[u8], + input_string: &str, + state_string: &str, ) -> Result { let mut compiler = new_compiler(); - let input_string = String::from_utf8_lossy(input_bytes); - let state_string = String::from_utf8_lossy(state_bytes); let path = PathBuf::new(); - compiler.parse_input(&input_string, &path, &state_string, &path)?; + compiler.parse_input(input_string, &path, state_string, &path)?; Ok(compiler) } pub fn parse_program_with_input( - program_bytes: &[u8], - input_bytes: &[u8], + program_string: &str, + input_string: &str, ) -> Result { let mut compiler = new_compiler(); - - let program_string = String::from_utf8_lossy(program_bytes); - let input_string = String::from_utf8_lossy(input_bytes); let path = PathBuf::new(); - compiler.parse_input(&input_string, &path, EMPTY_FILE, &path)?; - compiler.parse_program_from_string(&program_string)?; + compiler.parse_input(input_string, &path, EMPTY_FILE, &path)?; + compiler.parse_program_from_string(program_string)?; Ok(compiler) } pub fn parse_program_with_state( - program_bytes: &[u8], - state_bytes: &[u8], + program_string: &str, + state_string: &str, ) -> Result { let mut compiler = new_compiler(); - - let program_string = String::from_utf8_lossy(program_bytes); - let state_string = String::from_utf8_lossy(state_bytes); let path = PathBuf::new(); - compiler.parse_input(EMPTY_FILE, &path, &state_string, &path)?; - compiler.parse_program_from_string(&program_string)?; + compiler.parse_input(EMPTY_FILE, &path, state_string, &path)?; + compiler.parse_program_from_string(program_string)?; Ok(compiler) } pub fn parse_program_with_input_and_state( - program_bytes: &[u8], - input_bytes: &[u8], - state_bytes: &[u8], + program_string: &str, + input_string: &str, + state_string: &str, ) -> Result { let mut compiler = new_compiler(); - - let program_string = String::from_utf8_lossy(program_bytes); - let input_string = String::from_utf8_lossy(input_bytes); - let state_string = String::from_utf8_lossy(state_bytes); let path = PathBuf::new(); - compiler.parse_input(&input_string, &path, &state_string, &path)?; + compiler.parse_input(input_string, &path, state_string, &path)?; compiler.parse_program_from_string(&program_string)?; Ok(compiler) diff --git a/compiler/tests/mutability/circuit_static_function_mut.leo b/compiler/tests/mutability/circuit_static_function_mut.leo index 0717f51c44..eba1d02c0e 100644 --- a/compiler/tests/mutability/circuit_static_function_mut.leo +++ b/compiler/tests/mutability/circuit_static_function_mut.leo @@ -1,6 +1,6 @@ // Adding the `mut` keyword makes a circuit variable mutable. circuit Foo { - static function bar() {} + function bar() {} } function main() { diff --git a/compiler/tests/mutability/circuit_variable_mut.leo b/compiler/tests/mutability/circuit_variable_mut.leo index f87668c48e..27bd6109b2 100644 --- a/compiler/tests/mutability/circuit_variable_mut.leo +++ b/compiler/tests/mutability/circuit_variable_mut.leo @@ -1,6 +1,6 @@ // Adding the `mut` keyword makes a circuit variable mutable. circuit Foo { - mut x: u32 + x: u32 } function main() { diff --git a/compiler/tests/mutability/let_mut_nested.leo b/compiler/tests/mutability/let_mut_nested.leo new file mode 100644 index 0000000000..27121f6e48 --- /dev/null +++ b/compiler/tests/mutability/let_mut_nested.leo @@ -0,0 +1,5 @@ +function main () { + let mut x = 2u8; + let mut y = x; + let z = y / 2u8; +} \ No newline at end of file diff --git a/compiler/tests/mutability/mod.rs b/compiler/tests/mutability/mod.rs index 8442357044..4c2ab869e5 100644 --- a/compiler/tests/mutability/mod.rs +++ b/compiler/tests/mutability/mod.rs @@ -19,96 +19,104 @@ use leo_ast::InputValue; #[test] fn test_let() { - let bytes = include_bytes!("let.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("let.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_let_mut() { - let bytes = include_bytes!("let_mut.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("let_mut.leo"); + let program = parse_program(program_string).unwrap(); + + assert_satisfied(program); +} + +#[test] +fn test_let_mut_nested() { + let program_string = include_str!("let_mut_nested.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_const_fail() { - let bytes = include_bytes!("const.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("const.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_const_mut_fail() { - let bytes = include_bytes!("const_mut.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("const_mut.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_array() { - let bytes = include_bytes!("array.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("array.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_array_mut() { - let bytes = include_bytes!("array_mut.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("array_mut.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_circuit() { - let bytes = include_bytes!("circuit.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("circuit.leo"); + let program = parse_program(program_string).unwrap(); expect_compiler_error(program); } #[test] fn test_circuit_mut() { - let bytes = include_bytes!("circuit_mut.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("circuit_mut.leo"); + let program = parse_program(program_string).unwrap(); - expect_compiler_error(program); + assert_satisfied(program); } #[test] fn test_circuit_variable_mut() { - let bytes = include_bytes!("circuit_variable_mut.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("circuit_variable_mut.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_circuit_function_mut() { - let bytes = include_bytes!("circuit_function_mut.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("circuit_function_mut.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_circuit_static_function_mut() { - let bytes = include_bytes!("circuit_static_function_mut.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("circuit_static_function_mut.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } #[test] fn test_function_input() { - let bytes = include_bytes!("function_input.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("function_input.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![("a", Some(InputValue::Boolean(true)))]); @@ -119,8 +127,8 @@ fn test_function_input() { #[test] fn test_function_input_mut() { - let bytes = include_bytes!("function_input_mut.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("function_input_mut.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![("a", Some(InputValue::Boolean(true)))]); diff --git a/compiler/tests/statements/conditional/mod.rs b/compiler/tests/statements/conditional/mod.rs index 3c243c9804..84d03eb71b 100644 --- a/compiler/tests/statements/conditional/mod.rs +++ b/compiler/tests/statements/conditional/mod.rs @@ -28,8 +28,8 @@ use leo_ast::InputValue; #[test] fn test_assert() { - let bytes = include_bytes!("assert.leo"); - let mut program_1_pass = parse_program(bytes).unwrap(); + let program_string = include_str!("assert.leo"); + let mut program_1_pass = parse_program(program_string).unwrap(); let mut program_0_pass = program_1_pass.clone(); let mut program_2_fail = program_1_pass.clone(); @@ -60,8 +60,8 @@ fn test_assert() { #[test] fn test_mutate() { - let bytes = include_bytes!("mutate.leo"); - let mut program_1_pass = parse_program(bytes).unwrap(); + let program_string = include_str!("mutate.leo"); + let mut program_1_pass = parse_program(program_string).unwrap(); let mut program_0_pass = program_1_pass.clone(); // Check that an input value of 1 satisfies the constraint system @@ -83,8 +83,8 @@ fn test_mutate() { #[test] fn test_for_loop() { - let bytes = include_bytes!("for_loop.leo"); - let mut program_true_6 = parse_program(bytes).unwrap(); + let program_string = include_str!("for_loop.leo"); + let mut program_true_6 = parse_program(program_string).unwrap(); let mut program_false_0 = program_true_6.clone(); // Check that an input value of true satisfies the constraint system @@ -106,8 +106,8 @@ fn test_for_loop() { #[test] fn test_chain() { - let bytes = include_bytes!("chain.leo"); - let mut program_1_1 = parse_program(bytes).unwrap(); + let program_string = include_str!("chain.leo"); + let mut program_1_1 = parse_program(program_string).unwrap(); let mut program_2_2 = program_1_1.clone(); let mut program_4_3 = program_1_1.clone(); @@ -147,8 +147,8 @@ fn test_chain() { #[test] fn test_nested() { - let bytes = include_bytes!("nested.leo"); - let mut program_true_true_3 = parse_program(bytes).unwrap(); + let program_string = include_str!("nested.leo"); + let mut program_true_true_3 = parse_program(program_string).unwrap(); let mut program_true_false_1 = program_true_true_3.clone(); let mut program_false_false_0 = program_true_true_3.clone(); @@ -205,19 +205,19 @@ fn output_zero(program: EdwardsTestCompiler) { #[test] fn test_multiple_returns() { - let program_bytes = include_bytes!("multiple_returns.leo"); + let program_string = include_str!("multiple_returns.leo"); // Check that an input value of 1 writes 1 to the output registers - let registers_one_bytes = include_bytes!("input/registers_one.in"); - let program = parse_program_with_input(program_bytes, registers_one_bytes).unwrap(); + let registers_one_string = include_str!("input/registers_one.in"); + let program = parse_program_with_input(program_string, registers_one_string).unwrap(); output_one(program); // Check that an input value of 0 writes 0 to the output registers - let registers_zero_bytes = include_bytes!("input/registers_zero.in"); - let program = parse_program_with_input(program_bytes, registers_zero_bytes).unwrap(); + let registers_zero_string = include_str!("input/registers_zero.in"); + let program = parse_program_with_input(program_string, registers_zero_string).unwrap(); output_zero(program); } diff --git a/compiler/tests/statements/mod.rs b/compiler/tests/statements/mod.rs index 4680bee86d..b06386769c 100644 --- a/compiler/tests/statements/mod.rs +++ b/compiler/tests/statements/mod.rs @@ -23,8 +23,8 @@ pub mod conditional; #[test] fn test_ternary_basic() { - let bytes = include_bytes!("ternary_basic.leo"); - let mut program = parse_program(bytes).unwrap(); + let program_string = include_str!("ternary_basic.leo"); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Boolean(true))), @@ -35,7 +35,7 @@ fn test_ternary_basic() { assert_satisfied(program); - let mut program = parse_program(bytes).unwrap(); + let mut program = parse_program(program_string).unwrap(); let main_input = generate_main_input(vec![ ("a", Some(InputValue::Boolean(false))), @@ -51,16 +51,16 @@ fn test_ternary_basic() { #[test] fn test_iteration_basic() { - let bytes = include_bytes!("iteration_basic.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("iteration_basic.leo"); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_num_returns_fail() { - let bytes = include_bytes!("num_returns_fail.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("num_returns_fail.leo"); + let error = parse_program(program_string).err().unwrap(); expect_type_inference_error(error); } diff --git a/compiler/tests/syntax/identifiers/mod.rs b/compiler/tests/syntax/identifiers/mod.rs index c1d6fb7f86..1adf8697d9 100644 --- a/compiler/tests/syntax/identifiers/mod.rs +++ b/compiler/tests/syntax/identifiers/mod.rs @@ -18,80 +18,80 @@ use crate::parse_program; #[test] fn test_address_name_fail() { - let bytes = include_bytes!("address_fail.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("address_fail.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_console_name_fail() { - let bytes = include_bytes!("console_fail.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("console_fail.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_field_name_fail() { - let bytes = include_bytes!("field_fail.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("field_fail.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_group_name_fail() { - let bytes = include_bytes!("group_fail.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("group_fail.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_i8_name_fail() { - let bytes = include_bytes!("i8_fail.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("i8_fail.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_input_name_fail() { - let bytes = include_bytes!("input_fail.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("input_fail.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_self_type_name_fail() { - let bytes = include_bytes!("self_type_fail.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("self_type_fail.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_self_keyword_name_fail() { - let bytes = include_bytes!("self_keyword_fail.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("self_keyword_fail.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_true_name_fail() { - let bytes = include_bytes!("true_fail.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("true_fail.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } #[test] fn test_u8_name_fail() { - let bytes = include_bytes!("u8_fail.leo"); - let syntax_error = parse_program(bytes).is_err(); + let program_string = include_str!("u8_fail.leo"); + let syntax_error = parse_program(program_string).is_err(); assert!(syntax_error); } diff --git a/compiler/tests/syntax/mod.rs b/compiler/tests/syntax/mod.rs index 55b7292d2a..1bb6493d4b 100644 --- a/compiler/tests/syntax/mod.rs +++ b/compiler/tests/syntax/mod.rs @@ -25,8 +25,8 @@ pub mod identifiers; #[test] #[ignore] fn test_semicolon() { - let bytes = include_bytes!("semicolon.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("semicolon.leo"); + let error = parse_program(program_string).err().unwrap(); match error { CompilerError::ParserError(ParserError::SyntaxError(_)) => {} @@ -36,8 +36,8 @@ fn test_semicolon() { #[test] fn test_undefined() { - let bytes = include_bytes!("undefined.leo"); - let program = parse_program(bytes).unwrap(); + let program_string = include_str!("undefined.leo"); + let program = parse_program(program_string).unwrap(); let error = expect_compiler_error(program); @@ -53,7 +53,7 @@ fn test_undefined() { " 2 | return a", " | ^", " |", - " = cannot find value `a` in this scope", + " = Cannot find value `a` in this scope", ] .join("\n") ); @@ -63,10 +63,9 @@ fn test_undefined() { } #[test] -#[ignore] fn input_syntax_error() { - let bytes = include_bytes!("input_semicolon.leo"); - let error = parse_input(bytes).err().unwrap(); + let input_string = include_str!("input_semicolon.leo"); + let error = parse_input(input_string).err().unwrap(); // Expect an input parser error. match error { @@ -77,8 +76,8 @@ fn input_syntax_error() { #[test] fn test_compare_mismatched_types() { - let bytes = include_bytes!("compare_mismatched_types.leo"); - let error = parse_program(bytes).err().unwrap(); + let program_string = include_str!("compare_mismatched_types.leo"); + let error = parse_program(program_string).err().unwrap(); // Expect a type inference error. match error { diff --git a/compiler/tests/tuples/mod.rs b/compiler/tests/tuples/mod.rs index 9c52764c5f..5ed5cd357f 100644 --- a/compiler/tests/tuples/mod.rs +++ b/compiler/tests/tuples/mod.rs @@ -18,105 +18,105 @@ use crate::{assert_satisfied, parse_program}; #[test] fn test_tuple_basic() { - let program_bytes = include_bytes!("basic.leo"); + let program_string = include_str!("basic.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_tuple_access() { - let program_bytes = include_bytes!("access.leo"); + let program_string = include_str!("access.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_tuple_typed() { - let program_bytes = include_bytes!("typed.leo"); + let program_string = include_str!("typed.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_multiple() { - let program_bytes = include_bytes!("multiple.leo"); + let program_string = include_str!("multiple.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_multiple_typed() { - let program_bytes = include_bytes!("multiple_typed.leo"); + let program_string = include_str!("multiple_typed.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_function() { - let program_bytes = include_bytes!("function.leo"); + let program_string = include_str!("function.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_function_typed() { - let program_bytes = include_bytes!("function_typed.leo"); + let program_string = include_str!("function_typed.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_function_multiple() { - let progam_bytes = include_bytes!("function_multiple.leo"); + let progam_string = include_str!("function_multiple.leo"); - let program = parse_program(progam_bytes).unwrap(); + let program = parse_program(progam_string).unwrap(); assert_satisfied(program); } #[test] fn test_nested() { - let program_bytes = include_bytes!("nested.leo"); + let program_string = include_str!("nested.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_nested_access() { - let program_bytes = include_bytes!("nested_access.leo"); + let program_string = include_str!("nested_access.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } #[test] fn test_nested_typed() { - let program_bytes = include_bytes!("nested_typed.leo"); + let program_string = include_str!("nested_typed.leo"); - let program = parse_program(program_bytes).unwrap(); + let program = parse_program(program_string).unwrap(); assert_satisfied(program); } // #[test] // fn test_input() { -// let input_bytes = include_bytes!("inputs/input.in"); -// let program_bytes = include_bytes!("") +// let input_string = include_str!("inputs/input.in"); +// let program_string = include_str!("") // } diff --git a/core/src/packages/unstable/blake2s.rs b/core/src/packages/unstable/blake2s.rs index c4c37c4c91..8e7e4b800f 100644 --- a/core/src/packages/unstable/blake2s.rs +++ b/core/src/packages/unstable/blake2s.rs @@ -18,6 +18,7 @@ use crate::{CoreCircuit, CoreCircuitError, Value}; use leo_ast::{ ArrayDimensions, + Block, Circuit, CircuitMember, Expression, @@ -61,52 +62,51 @@ impl CoreCircuit for Blake2sCircuit { fn ast(circuit_name: Identifier, span: Span) -> Circuit { Circuit { circuit_name, - members: vec![CircuitMember::CircuitFunction( - true, // static function - Function { - identifier: Identifier { - name: "hash".to_owned(), + members: vec![CircuitMember::CircuitFunction(Function { + identifier: Identifier { + name: "hash".to_owned(), + span: span.clone(), + }, + input: vec![ + FunctionInput::Variable(FunctionInputVariable { + identifier: Identifier { + name: "seed".to_owned(), + span: span.clone(), + }, + mutable: false, + type_: Type::Array( + Box::new(Type::IntegerType(IntegerType::U8)), + ArrayDimensions(vec![PositiveNumber { + value: 32usize.to_string(), + span: span.clone(), + }]), + ), span: span.clone(), - }, - input: vec![ - FunctionInput::Variable(FunctionInputVariable { - identifier: Identifier { - name: "seed".to_owned(), + }), + FunctionInput::Variable(FunctionInputVariable { + identifier: Identifier { + name: "message".to_owned(), + span: span.clone(), + }, + mutable: false, + type_: Type::Array( + Box::new(Type::IntegerType(IntegerType::U8)), + ArrayDimensions(vec![PositiveNumber { + value: 32usize.to_string(), span: span.clone(), - }, - mutable: false, - type_: Type::Array( - Box::new(Type::IntegerType(IntegerType::U8)), - ArrayDimensions(vec![PositiveNumber { - value: 32usize.to_string(), - span: span.clone(), - }]), - ), - span: span.clone(), - }), - FunctionInput::Variable(FunctionInputVariable { - identifier: Identifier { - name: "message".to_owned(), - span: span.clone(), - }, - mutable: false, - type_: Type::Array( - Box::new(Type::IntegerType(IntegerType::U8)), - ArrayDimensions(vec![PositiveNumber { - value: 32usize.to_string(), - span: span.clone(), - }]), - ), - span: span.clone(), - }), - ], - output: Some(Type::Array( - Box::new(Type::IntegerType(IntegerType::U8)), - ArrayDimensions(vec![PositiveNumber { - value: 32usize.to_string(), - span: span.clone(), - }]), - )), + }]), + ), + span: span.clone(), + }), + ], + output: Some(Type::Array( + Box::new(Type::IntegerType(IntegerType::U8)), + ArrayDimensions(vec![PositiveNumber { + value: 32usize.to_string(), + span: span.clone(), + }]), + )), + block: Block { statements: vec![Statement::Return( Expression::CoreFunctionCall( Self::name(), @@ -124,9 +124,9 @@ impl CoreCircuit for Blake2sCircuit { ), span.clone(), )], - span, }, - )], + span, + })], } } diff --git a/grammar/src/circuits/circuit_member.rs b/grammar/src/circuits/circuit_member.rs index d3d949e99b..32da1ca4d3 100644 --- a/grammar/src/circuits/circuit_member.rs +++ b/grammar/src/circuits/circuit_member.rs @@ -14,10 +14,7 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{ - ast::Rule, - circuits::{CircuitFunction, CircuitVariableDefinition}, -}; +use crate::{ast::Rule, circuits::CircuitVariableDefinition, functions::Function}; use pest_ast::FromPest; use serde::Serialize; @@ -26,5 +23,5 @@ use serde::Serialize; #[pest_ast(rule(Rule::circuit_member))] pub enum CircuitMember<'ast> { CircuitVariableDefinition(CircuitVariableDefinition<'ast>), - CircuitFunction(CircuitFunction<'ast>), + CircuitFunction(Function<'ast>), } diff --git a/grammar/src/circuits/circuit_variable_definition.rs b/grammar/src/circuits/circuit_variable_definition.rs index 8bd462a099..b3a84ef629 100644 --- a/grammar/src/circuits/circuit_variable_definition.rs +++ b/grammar/src/circuits/circuit_variable_definition.rs @@ -14,12 +14,7 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{ - ast::Rule, - common::{Identifier, Mutable}, - types::Type, - SpanDef, -}; +use crate::{ast::Rule, common::Identifier, types::Type, SpanDef}; use pest::Span; use pest_ast::FromPest; @@ -28,7 +23,6 @@ use serde::Serialize; #[derive(Clone, Debug, FromPest, PartialEq, Serialize)] #[pest_ast(rule(Rule::circuit_variable_definition))] pub struct CircuitVariableDefinition<'ast> { - pub mutable: Option, pub identifier: Identifier<'ast>, pub type_: Type<'ast>, #[pest_ast(outer())] diff --git a/grammar/src/circuits/mod.rs b/grammar/src/circuits/mod.rs index 768a36fd7e..c967ed655e 100644 --- a/grammar/src/circuits/mod.rs +++ b/grammar/src/circuits/mod.rs @@ -23,8 +23,5 @@ pub use circuit_variable::*; pub mod circuit_variable_definition; pub use circuit_variable_definition::*; -pub mod circuit_function; -pub use circuit_function::*; - pub mod circuit_member; pub use circuit_member::*; diff --git a/grammar/src/common/mod.rs b/grammar/src/common/mod.rs index 119287f5cc..6a45652fc7 100644 --- a/grammar/src/common/mod.rs +++ b/grammar/src/common/mod.rs @@ -35,6 +35,9 @@ pub use line_end::*; pub mod mutable; pub use mutable::*; +pub mod mut_self_keyword; +pub use mut_self_keyword::*; + pub mod range; pub use range::*; diff --git a/grammar/src/circuits/circuit_function.rs b/grammar/src/common/mut_self_keyword.rs similarity index 70% rename from grammar/src/circuits/circuit_function.rs rename to grammar/src/common/mut_self_keyword.rs index 3fdeac1d02..12d269e191 100644 --- a/grammar/src/circuits/circuit_function.rs +++ b/grammar/src/common/mut_self_keyword.rs @@ -14,18 +14,29 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{ast::Rule, common::Static, functions::Function, SpanDef}; +use crate::{ + ast::Rule, + common::{Mutable, SelfKeyword}, + SpanDef, +}; use pest::Span; use pest_ast::FromPest; use serde::Serialize; +use std::fmt; #[derive(Clone, Debug, FromPest, PartialEq, Serialize)] -#[pest_ast(rule(Rule::circuit_function))] -pub struct CircuitFunction<'ast> { - pub _static: Option, - pub function: Function<'ast>, +#[pest_ast(rule(Rule::mut_self_keyword))] +pub struct MutSelfKeyword<'ast> { + pub mutable: Mutable, + pub self_keyword: SelfKeyword<'ast>, #[pest_ast(outer())] #[serde(with = "SpanDef")] pub span: Span<'ast>, } + +impl<'ast> fmt::Display for MutSelfKeyword<'ast> { + fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { + write!(f, "mut {}", self.self_keyword) + } +} diff --git a/grammar/src/functions/function.rs b/grammar/src/functions/function.rs index 4129422ed0..503ae65ef3 100644 --- a/grammar/src/functions/function.rs +++ b/grammar/src/functions/function.rs @@ -14,7 +14,7 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{ast::Rule, common::Identifier, functions::input::Input, statements::Statement, types::Type, SpanDef}; +use crate::{ast::Rule, common::Identifier, functions::input::Input, statements::Block, types::Type, SpanDef}; use pest::Span; use pest_ast::FromPest; @@ -26,7 +26,7 @@ pub struct Function<'ast> { pub identifier: Identifier<'ast>, pub parameters: Vec>, pub returns: Option>, - pub statements: Vec>, + pub block: Block<'ast>, #[pest_ast(outer())] #[serde(with = "SpanDef")] pub span: Span<'ast>, diff --git a/grammar/src/functions/input/input.rs b/grammar/src/functions/input/input.rs index d3cddee215..d6eb28250c 100644 --- a/grammar/src/functions/input/input.rs +++ b/grammar/src/functions/input/input.rs @@ -16,6 +16,7 @@ use crate::{ ast::Rule, + common::{MutSelfKeyword, SelfKeyword}, functions::{FunctionInput, InputKeyword}, }; @@ -26,5 +27,7 @@ use serde::Serialize; #[pest_ast(rule(Rule::input))] pub enum Input<'ast> { InputKeyword(InputKeyword<'ast>), + SelfKeyword(SelfKeyword<'ast>), + MutSelfKeyword(MutSelfKeyword<'ast>), FunctionInput(FunctionInput<'ast>), } diff --git a/grammar/src/leo.pest b/grammar/src/leo.pest index e695e3bb9f..3fccb668eb 100644 --- a/grammar/src/leo.pest +++ b/grammar/src/leo.pest @@ -47,6 +47,9 @@ protected_name = { // Declared in common/self_keyword.rs self_keyword = { "self" } +// Declared in common/mut_self_keyword.rs +mut_self_keyword = { mutable ~ self_keyword } + // Declared in common/self_keyword_or_identifier.rs self_keyword_or_identifier = { self_keyword @@ -319,13 +322,10 @@ circuit = { "circuit " ~ identifier ~ "{" ~ NEWLINE* ~ circuit_member* ~ NEWLINE circuit_variable = { identifier ~ ":" ~ expression } // Declared in circuits/circuit_variable_definition.rs -circuit_variable_definition = { mutable? ~ identifier ~ ":" ~ type_ ~ ","?} - -// Declared in circuits/circuit_function.rs -circuit_function = { static_? ~ function } +circuit_variable_definition = { identifier ~ ":" ~ type_ ~ ","?} // Declared in circuits/circuit_member.rs -circuit_member = { circuit_function | circuit_variable_definition ~ NEWLINE*} +circuit_member = { function | circuit_variable_definition ~ NEWLINE*} /// Conditionals @@ -396,9 +396,11 @@ statement = { // Declared in statements/assign_statement.rs statement_assign = { assignee ~ operation_assign ~ expression ~ LINE_END } +block = { "{" ~ NEWLINE* ~ statement* ~ NEWLINE* ~ "}" } + // Declared in statements/conditional_statement.rs -statement_conditional = {"if " ~ expression ~ "{" ~ NEWLINE* ~ statement+ ~ "}" ~ ("else " ~ conditional_nested_or_end_statement)?} -conditional_nested_or_end_statement = { statement_conditional | "{" ~ NEWLINE* ~ statement+ ~ "}"} +statement_conditional = {"if " ~ expression ~ block ~ ("else " ~ conditional_nested_or_end_statement)?} +conditional_nested_or_end_statement = { statement_conditional | block } // Declared in statements/definition_statement.rs statement_definition = { declare ~ variables ~ "=" ~ expression ~ LINE_END} @@ -407,7 +409,7 @@ statement_definition = { declare ~ variables ~ "=" ~ expression ~ LINE_END} statement_expression = { expression ~ LINE_END } // Declared in statements/for_statement.rs -statement_for = { "for " ~ identifier ~ "in " ~ expression ~ ".." ~ expression ~ "{" ~ NEWLINE* ~ statement+ ~ "}"} +statement_for = { "for " ~ identifier ~ "in " ~ expression ~ ".." ~ expression ~ block } // Declared in statements/return_statement.rs statement_return = { "return " ~ expression} @@ -418,7 +420,7 @@ statement_return = { "return " ~ expression} test_function = { "test " ~ function } // Declared in functions/function.rs -function = { "function " ~ identifier ~ input_tuple ~ ("->" ~ type_)? ~ "{" ~ NEWLINE* ~ statement* ~ NEWLINE* ~ "}" ~ NEWLINE* } +function = { "function " ~ identifier ~ input_tuple ~ ("->" ~ type_)? ~ block ~ NEWLINE* } // Declared in functions/input/function_input.rs function_input = { mutable? ~ identifier ~ ":" ~ type_ } @@ -429,6 +431,8 @@ input_keyword = { "input" } // Declared in functions/input/input.rs input = { input_keyword + | self_keyword + | mut_self_keyword | function_input } input_tuple = _{ "(" ~ NEWLINE* ~ (input ~ ("," ~ NEWLINE* ~ input)* ~ ","?)? ~ NEWLINE* ~ ")"} diff --git a/grammar/src/statements/block.rs b/grammar/src/statements/block.rs new file mode 100644 index 0000000000..660b20e8a1 --- /dev/null +++ b/grammar/src/statements/block.rs @@ -0,0 +1,45 @@ +// Copyright (C) 2019-2020 Aleo Systems Inc. +// This file is part of the Leo library. + +// The Leo library is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. + +// The Leo library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License +// along with the Leo library. If not, see . + +use crate::{ast::Rule, statements::Statement, SpanDef}; + +use pest::Span; +use pest_ast::FromPest; +use serde::Serialize; +use std::fmt; + +#[derive(Clone, Debug, FromPest, PartialEq, Serialize)] +#[pest_ast(rule(Rule::block))] +pub struct Block<'ast> { + pub statements: Vec>, + #[pest_ast(outer())] + #[serde(with = "SpanDef")] + pub span: Span<'ast>, +} + +impl<'ast> fmt::Display for Block<'ast> { + fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { + writeln!(f, "{{")?; + if self.statements.is_empty() { + writeln!(f, "\t")?; + } else { + self.statements + .iter() + .try_for_each(|statement| writeln!(f, "\t{}", statement))?; + } + write!(f, "}}") + } +} diff --git a/grammar/src/statements/conditional_nested_or_end_statement.rs b/grammar/src/statements/conditional_nested_or_end_statement.rs index 120fc2ba7e..42f0246f37 100644 --- a/grammar/src/statements/conditional_nested_or_end_statement.rs +++ b/grammar/src/statements/conditional_nested_or_end_statement.rs @@ -16,7 +16,7 @@ use crate::{ ast::Rule, - statements::{ConditionalStatement, Statement}, + statements::{Block, ConditionalStatement}, }; use pest_ast::FromPest; @@ -27,14 +27,14 @@ use std::fmt; #[pest_ast(rule(Rule::conditional_nested_or_end_statement))] pub enum ConditionalNestedOrEndStatement<'ast> { Nested(Box>), - End(Vec>), + End(Block<'ast>), } 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 block) => write!(f, "else {}", block), } } } diff --git a/grammar/src/statements/conditional_statement.rs b/grammar/src/statements/conditional_statement.rs index 6cfd97d97e..f0cc149f3c 100644 --- a/grammar/src/statements/conditional_statement.rs +++ b/grammar/src/statements/conditional_statement.rs @@ -17,7 +17,7 @@ use crate::{ ast::Rule, expressions::Expression, - statements::{ConditionalNestedOrEndStatement, Statement}, + statements::{Block, ConditionalNestedOrEndStatement}, SpanDef, }; @@ -30,7 +30,7 @@ use std::fmt; #[pest_ast(rule(Rule::statement_conditional))] pub struct ConditionalStatement<'ast> { pub condition: Expression<'ast>, - pub statements: Vec>, + pub block: Block<'ast>, pub next: Option>, #[pest_ast(outer())] #[serde(with = "SpanDef")] @@ -39,11 +39,10 @@ pub struct ConditionalStatement<'ast> { impl<'ast> fmt::Display for ConditionalStatement<'ast> { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - writeln!(f, "if ({}) {{", self.condition)?; - writeln!(f, "\t{:#?}", self.statements)?; + write!(f, "if ({}) {}", self.condition, self.block)?; self.next .as_ref() - .map(|n_or_e| write!(f, "}} {}", n_or_e)) - .unwrap_or_else(|| write!(f, "}}")) + .map(|n_or_e| write!(f, " {}", n_or_e)) + .unwrap_or_else(|| write!(f, "")) } } diff --git a/grammar/src/statements/for_statement.rs b/grammar/src/statements/for_statement.rs index a31ed51f0f..90cb2f40c8 100644 --- a/grammar/src/statements/for_statement.rs +++ b/grammar/src/statements/for_statement.rs @@ -14,7 +14,7 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{ast::Rule, common::Identifier, expressions::Expression, statements::Statement, SpanDef}; +use crate::{ast::Rule, common::Identifier, expressions::Expression, statements::Block, SpanDef}; use pest::Span; use pest_ast::FromPest; @@ -27,7 +27,7 @@ pub struct ForStatement<'ast> { pub index: Identifier<'ast>, pub start: Expression<'ast>, pub stop: Expression<'ast>, - pub statements: Vec>, + pub block: Block<'ast>, #[pest_ast(outer())] #[serde(with = "SpanDef")] pub span: Span<'ast>, @@ -35,10 +35,6 @@ pub struct ForStatement<'ast> { impl<'ast> fmt::Display for ForStatement<'ast> { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - write!( - f, - "for {} in {}..{} {{ {:#?} }}", - self.index, self.start, self.stop, self.statements - ) + write!(f, "for {} in {}..{} {}", self.index, self.start, self.stop, self.block) } } diff --git a/grammar/src/statements/mod.rs b/grammar/src/statements/mod.rs index 95978fa8af..7edba95216 100644 --- a/grammar/src/statements/mod.rs +++ b/grammar/src/statements/mod.rs @@ -37,3 +37,6 @@ pub use return_statement::*; pub mod statement; pub use statement::*; + +pub mod block; +pub use block::*; diff --git a/grammar/tests/display.rs b/grammar/tests/display.rs new file mode 100644 index 0000000000..7f8750cd2e --- /dev/null +++ b/grammar/tests/display.rs @@ -0,0 +1,38 @@ +// Copyright (C) 2019-2020 Aleo Systems Inc. +// This file is part of the Leo library. + +// The Leo library is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. + +// The Leo library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License +// along with the Leo library. If not, see . + +use from_pest::FromPest; +use leo_grammar::{ + ast::{LanguageParser, Rule}, + statements::ConditionalStatement, +}; + +use pest::*; + +#[test] +fn conditional_statement_display() { + let input = r#"if (true) { + +} else { + +}"#; + let conditional_statement = + ConditionalStatement::from_pest(&mut LanguageParser::parse(Rule::statement_conditional, input).unwrap()) + .unwrap(); + let displayed = format!("{}", conditional_statement); + + assert_eq!(input, displayed); +} diff --git a/grammar/tests/function.rs b/grammar/tests/function.rs index f2b4fa3629..42f24f184b 100644 --- a/grammar/tests/function.rs +++ b/grammar/tests/function.rs @@ -75,7 +75,7 @@ fn empty_def() { input: "function x() {}", rule: Rule::function, tokens: [ - function(0, 15, [identifier(9, 10, [])]) + function(0, 15, [identifier(9, 10, []), block(13, 15, [])]) ] } } @@ -87,7 +87,7 @@ fn returning_unit_type() { input: "function x() -> () {}", rule: Rule::function, tokens: [ - function(0, 21, [identifier(9, 10, []), type_(16, 18, [type_tuple(16, 18, [])])]) + function(0, 21, [identifier(9, 10, []), type_(16, 18, [type_tuple(16, 18, [])]), block(19, 21, [])]) ] } } @@ -99,8 +99,10 @@ fn returning_unit_value() { input: "function x() { return () }", rule: Rule::function, tokens: [ - function(0, 26, [identifier(9, 10, []), statement(15, 25, [ - statement_return(15, 25, [expression(22, 25, [expression_term(22, 24, [expression_tuple(22, 24, [])])])]) + function(0, 26, [identifier(9, 10, []), block(13, 26, [ + statement(15, 25, [ + statement_return(15, 25, [expression(22, 25, [expression_term(22, 24, [expression_tuple(22, 24, [])])])]) + ]) ])]) ] } @@ -122,9 +124,11 @@ fn id_def() { ]) ]), type_(22, 24, [type_data(22, 24, [type_integer(22, 24, [type_integer_unsigned(22, 24, [type_u8(22, 24, [])])])])]), - statement(27, 36, [statement_return(27, 36, [ - expression(34, 36, [expression_term(34, 35, [identifier(34, 35, [])])]) - ])]) + block(25, 37, [ + statement(27, 36, [statement_return(27, 36, [ + expression(34, 36, [expression_term(34, 35, [identifier(34, 35, [])])]) + ])]) + ]), ]) ] } diff --git a/grammar/tests/mod.rs b/grammar/tests/mod.rs index b4ed4e6d07..516d586ba0 100644 --- a/grammar/tests/mod.rs +++ b/grammar/tests/mod.rs @@ -14,6 +14,7 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . +mod display; mod expression; mod function; mod serialization; diff --git a/grammar/tests/serialization/expected_ast.json b/grammar/tests/serialization/expected_ast.json index 888008dd46..24e2b41170 100644 --- a/grammar/tests/serialization/expected_ast.json +++ b/grammar/tests/serialization/expected_ast.json @@ -12,55 +12,62 @@ }, "parameters": [], "returns": null, - "statements": [ - { - "Return": { - "expression": { - "Binary": { - "operation": "Add", - "left": { - "Value": { - "Implicit": { - "Positive": { - "value": "1", - "span": { - "input": "1", - "start": 29, - "end": 30 + "block": { + "statements": [ + { + "Return": { + "expression": { + "Binary": { + "operation": "Add", + "left": { + "Value": { + "Implicit": { + "Positive": { + "value": "1", + "span": { + "input": "1", + "start": 29, + "end": 30 + } } } } - } - }, - "right": { - "Value": { - "Implicit": { - "Positive": { - "value": "1", - "span": { - "input": "1", - "start": 33, - "end": 34 + }, + "right": { + "Value": { + "Implicit": { + "Positive": { + "value": "1", + "span": { + "input": "1", + "start": 33, + "end": 34 + } } } } + }, + "span": { + "input": "1 + 1", + "start": 29, + "end": 34 } - }, - "span": { - "input": "1 + 1", - "start": 29, - "end": 34 } + }, + "span": { + "input": "return 1 + 1", + "start": 22, + "end": 34 } - }, - "span": { - "input": "return 1 + 1", - "start": 22, - "end": 34 } } + ], + "span": { + "input": "{\n return 1 + 1\n}", + "start": 16, + "end": 36 } - ], + }, "span": { "input": "function main() {\n return 1 + 1\n}\n", "start": 0, diff --git a/leo/errors/mod.rs b/leo/errors/mod.rs index bc7859ca5d..9fa3bd3d12 100644 --- a/leo/errors/mod.rs +++ b/leo/errors/mod.rs @@ -19,3 +19,6 @@ pub use self::cli::*; pub mod commands; pub use self::commands::*; + +pub mod updater; +pub use self::updater::*; diff --git a/symbol-table/src/types/circuits/circuit_function.rs b/leo/errors/updater.rs similarity index 61% rename from symbol-table/src/types/circuits/circuit_function.rs rename to leo/errors/updater.rs index 4c6d8686a9..8bfa4bdec9 100644 --- a/symbol-table/src/types/circuits/circuit_function.rs +++ b/leo/errors/updater.rs @@ -14,14 +14,18 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{types::FunctionType, Attribute}; +#[derive(Debug, Error)] +pub enum UpdaterError { + #[error("{}: {}", _0, _1)] + Crate(&'static str, String), -use serde::{Deserialize, Serialize}; - -#[derive(Clone, Debug, PartialEq, Eq, Hash, Serialize, Deserialize)] -pub struct CircuitFunctionType { - /// The function signature of the circuit function - pub function: FunctionType, - /// The attributes of the circuit function - pub attribute: Option, + #[error("The current version {} is more recent than the release version {}", _0, _1)] + OldReleaseVersion(String, String), +} + +impl From for UpdaterError { + fn from(error: self_update::errors::Error) -> Self { + tracing::error!("{}\n", error); + UpdaterError::Crate("self_update", error.to_string()) + } } diff --git a/leo/updater.rs b/leo/updater.rs index 84f088f68f..a37ee7d184 100644 --- a/leo/updater.rs +++ b/leo/updater.rs @@ -13,7 +13,7 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::config::Config; +use crate::{config::Config, errors::UpdaterError}; use colored::Colorize; use self_update::{backends::github, version::bump_is_greater, Status}; @@ -27,7 +27,7 @@ impl Updater { const LEO_REPO_OWNER: &'static str = "AleoHQ"; /// Show all available releases for `leo`. - pub fn show_available_releases() -> Result<(), self_update::errors::Error> { + pub fn show_available_releases() -> Result<(), UpdaterError> { let releases = github::ReleaseList::configure() .repo_owner(Self::LEO_REPO_OWNER) .repo_name(Self::LEO_REPO_NAME) @@ -42,7 +42,7 @@ impl Updater { } /// Update `leo` to the latest release. - pub fn update_to_latest_release(show_output: bool) -> Result { + pub fn update_to_latest_release(show_output: bool) -> Result { let status = github::Update::configure() .repo_owner(Self::LEO_REPO_OWNER) .repo_name(Self::LEO_REPO_NAME) @@ -58,7 +58,7 @@ impl Updater { } /// Check if there is an available update for `leo` and return the newest release. - pub fn update_available() -> Result, self_update::errors::Error> { + pub fn update_available() -> Result { let updater = github::Update::configure() .repo_owner(Self::LEO_REPO_OWNER) .repo_name(Self::LEO_REPO_NAME) @@ -70,9 +70,9 @@ impl Updater { let latest_release = updater.get_latest_release()?; if bump_is_greater(¤t_version, &latest_release.version)? { - Ok(Some(latest_release.version)) + Ok(latest_release.version) } else { - Ok(None) + Err(UpdaterError::OldReleaseVersion(current_version, latest_release.version)) } } @@ -89,7 +89,7 @@ impl Updater { } } else { // If the auto update configuration is off, notify the user to update leo. - if let Some(latest_version) = Self::update_available().unwrap() { + if let Ok(latest_version) = Self::update_available() { let mut message = "🟢 A new version is available! Run".bold().green().to_string(); message += &" `leo update` ".bold().white(); message += &format!("to update to v{}.", latest_version).bold().green(); diff --git a/state/src/utilities/input_value.rs b/state/src/utilities/input_value.rs index a6ad950ce8..5e896ed564 100644 --- a/state/src/utilities/input_value.rs +++ b/state/src/utilities/input_value.rs @@ -30,11 +30,8 @@ pub fn find_input( .find(|(parameter, _value)| parameter.variable.name == name); match matched_parameter { - Some((_parameter, value_option)) => match value_option { - Some(value) => Ok(value.clone()), - None => Err(InputValueError::MissingParameter(name)), - }, - None => Err(InputValueError::MissingParameter(name)), + Some((_parameter, Some(value))) => Ok(value.clone()), + _ => Err(InputValueError::MissingParameter(name)), } } diff --git a/symbol-table/src/types/circuits/circuit.rs b/symbol-table/src/types/circuits/circuit.rs index 53ca088aad..b0b123879c 100644 --- a/symbol-table/src/types/circuits/circuit.rs +++ b/symbol-table/src/types/circuits/circuit.rs @@ -14,14 +14,7 @@ // You should have received a copy of the GNU General Public License // along with the Leo library. If not, see . -use crate::{ - types::circuits::{CircuitFunctionType, CircuitVariableType}, - Attribute, - FunctionType, - SymbolTable, - Type, - TypeError, -}; +use crate::{types::circuits::CircuitVariableType, FunctionType, SymbolTable, Type, TypeError}; use leo_ast::{Circuit, CircuitMember, Identifier, InputValue, Parameter, Span}; use indexmap::IndexMap; @@ -41,7 +34,7 @@ pub struct CircuitType { pub variables: Vec, /// The circuit functions. - pub functions: Vec, + pub functions: Vec, } impl CircuitType { @@ -59,7 +52,7 @@ impl CircuitType { // Resolve the type of every circuit member. for member in unresolved.members { match member { - CircuitMember::CircuitVariable(is_mutable, variable_identifier, type_) => { + CircuitMember::CircuitVariable(variable_identifier, type_) => { // Resolve the type of the circuit member variable. let type_ = Type::new_from_circuit( table, @@ -68,34 +61,22 @@ impl CircuitType { circuit_identifier.span.clone(), )?; - // Check if the circuit member variable is mutable. - let attribute = if is_mutable { Some(Attribute::Mutable) } else { None }; - // Create a new circuit variable type. let variable = CircuitVariableType { identifier: variable_identifier, type_, - attribute, + attribute: None, }; // Store the circuit variable type. variables.push(variable); } - CircuitMember::CircuitFunction(is_static, function) => { + CircuitMember::CircuitFunction(function) => { // Resolve the type of the circuit member function. let function_type = FunctionType::from_circuit(table, circuit_identifier.clone(), function)?; - // Check if the circuit member function is static. - let attribute = if is_static { Some(Attribute::Static) } else { None }; - - // Create a new circuit function type. - let function = CircuitFunctionType { - function: function_type, - attribute, - }; - // Store the circuit function type. - functions.push(function); + functions.push(function_type); } } } @@ -111,10 +92,10 @@ impl CircuitType { /// /// Returns the function type of a circuit member given an identifier. /// - pub fn member_function_type(&self, identifier: &Identifier) -> Option<&CircuitFunctionType> { + pub fn member_function_type(&self, identifier: &Identifier) -> Option<&FunctionType> { self.functions .iter() - .find(|function| function.function.identifier.eq(identifier)) + .find(|function| function.identifier.eq(identifier)) } /// @@ -137,7 +118,7 @@ impl CircuitType { let matched_function = self.member_function_type(identifier); match matched_function { - Some(function) => Ok(Type::Function(function.function.identifier.to_owned())), + Some(function) => Ok(Type::Function(function.identifier.to_owned())), None => Err(TypeError::undefined_circuit_member(identifier.clone())), } } diff --git a/symbol-table/src/types/circuits/mod.rs b/symbol-table/src/types/circuits/mod.rs index 8205016c50..5af76a09fe 100644 --- a/symbol-table/src/types/circuits/mod.rs +++ b/symbol-table/src/types/circuits/mod.rs @@ -17,8 +17,5 @@ pub mod circuit; pub use self::circuit::*; -pub mod circuit_function; -pub use self::circuit_function::*; - pub mod circuit_variable; pub use self::circuit_variable::*; diff --git a/symbol-table/src/types/functions/function.rs b/symbol-table/src/types/functions/function.rs index 0abdc87aa9..05fc6c43fb 100644 --- a/symbol-table/src/types/functions/function.rs +++ b/symbol-table/src/types/functions/function.rs @@ -119,6 +119,29 @@ impl FunctionType { Ok(()) } + + /// + /// Returns `true` if the input `self` or `mut self` is present. + /// Returns `false` otherwise. + /// + pub fn contains_self(&self) -> bool { + self.inputs.iter().any(|param| param.is_self()) + } + + /// + /// Returns an iterator of [&FunctionInputType] removing `self` and `mut self` inputs. + /// + pub fn filter_self_inputs(&self) -> impl Iterator { + self.inputs.iter().filter(|input| !input.is_self()) + } + + /// + /// Returns the number of input variables to the function. + /// The `self` and `mut self` keywords are not counted as input variables. + /// + pub fn num_inputs(&self) -> usize { + self.filter_self_inputs().count() + } } impl PartialEq for FunctionType { diff --git a/symbol-table/src/types/functions/function_input.rs b/symbol-table/src/types/functions/function_input.rs index 297e09287f..cee5ed1df5 100644 --- a/symbol-table/src/types/functions/function_input.rs +++ b/symbol-table/src/types/functions/function_input.rs @@ -22,6 +22,8 @@ use serde::{Deserialize, Serialize}; #[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)] pub enum FunctionInputType { InputKeyword(Identifier), + SelfKeyword(Identifier), + MutSelfKeyword(Identifier), Variable(FunctionInputVariableType), } @@ -32,6 +34,8 @@ impl FunctionInputType { pub fn identifier(&self) -> &Identifier { match self { FunctionInputType::InputKeyword(identifier) => identifier, + FunctionInputType::SelfKeyword(identifier) => identifier, + FunctionInputType::MutSelfKeyword(identifier) => identifier, FunctionInputType::Variable(variable) => &variable.identifier, } } @@ -42,6 +46,8 @@ impl FunctionInputType { pub fn type_(&self) -> Type { match self { FunctionInputType::InputKeyword(identifier) => Type::Circuit(identifier.to_owned()), + FunctionInputType::SelfKeyword(identifier) => Type::Circuit(identifier.to_owned()), + FunctionInputType::MutSelfKeyword(identifier) => Type::Circuit(identifier.to_owned()), FunctionInputType::Variable(variable) => variable.type_.to_owned(), } } @@ -52,10 +58,25 @@ impl FunctionInputType { pub fn span(&self) -> &Span { match self { FunctionInputType::InputKeyword(identifier) => &identifier.span, + FunctionInputType::SelfKeyword(identifier) => &identifier.span, + FunctionInputType::MutSelfKeyword(identifier) => &identifier.span, FunctionInputType::Variable(variable) => &variable.span, } } + /// + /// Returns `true` if input `self` or `mut self` is present. + /// Returns `false` otherwise. + /// + pub fn is_self(&self) -> bool { + match self { + FunctionInputType::InputKeyword(_) => false, + FunctionInputType::SelfKeyword(_) => true, + FunctionInputType::MutSelfKeyword(_) => true, + FunctionInputType::Variable(_) => false, + } + } + /// /// Return a new `FunctionInputType` from a given `FunctionInput`. /// @@ -64,7 +85,9 @@ impl FunctionInputType { /// pub fn new(table: &SymbolTable, unresolved: FunctionInput) -> Result { Ok(match unresolved { - FunctionInput::InputKeyword(identifier) => FunctionInputType::InputKeyword(identifier), + FunctionInput::InputKeyword(keyword) => FunctionInputType::InputKeyword(Identifier::from(keyword)), + FunctionInput::SelfKeyword(_) => unimplemented!("cannot call self keyword from non-circuit context"), + FunctionInput::MutSelfKeyword(_) => unimplemented!("cannot call mut self keyword from non-circuit context"), FunctionInput::Variable(variable) => { let variable_resolved = FunctionInputVariableType::new(table, variable)?; @@ -88,7 +111,13 @@ impl FunctionInputType { circuit_name: Identifier, ) -> Result { Ok(match unresolved { - FunctionInput::InputKeyword(identifier) => FunctionInputType::InputKeyword(identifier), + FunctionInput::InputKeyword(keyword) => FunctionInputType::InputKeyword(Identifier::from(keyword)), + FunctionInput::SelfKeyword(keyword) => { + FunctionInputType::SelfKeyword(Identifier::new_with_span(&circuit_name.name, &keyword.span)) + } + FunctionInput::MutSelfKeyword(keyword) => { + FunctionInputType::MutSelfKeyword(Identifier::new_with_span(&circuit_name.name, &keyword.span)) + } FunctionInput::Variable(unresolved_function_input) => { let function_input = FunctionInputVariableType::new_from_circuit(table, unresolved_function_input, circuit_name)?; diff --git a/symbol-table/tests/mod.rs b/symbol-table/tests/mod.rs index fb8a5ee290..21c7710cb6 100644 --- a/symbol-table/tests/mod.rs +++ b/symbol-table/tests/mod.rs @@ -34,15 +34,12 @@ impl TestSymbolTable { /// /// Returns a Leo syntax tree given a Leo program. /// - pub fn new(bytes: &[u8]) -> Self { - // Get file string from bytes. - let file_string = String::from_utf8_lossy(bytes); - + pub fn new(program_string: &str) -> Self { // Get test file path. let file_path = PathBuf::from(TEST_PROGRAM_PATH); // Get parser syntax tree. - let grammar = Grammar::new(&file_path, &*file_string).unwrap(); + let grammar = Grammar::new(&file_path, program_string).unwrap(); // Get Leo syntax tree. let ast = Ast::new(TEST_PROGRAM_PATH, &grammar); diff --git a/symbol-table/tests/symbol_table/mod.rs b/symbol-table/tests/symbol_table/mod.rs index 4d40891377..e5b820d4a4 100644 --- a/symbol-table/tests/symbol_table/mod.rs +++ b/symbol-table/tests/symbol_table/mod.rs @@ -25,8 +25,8 @@ use crate::TestSymbolTable; /// #[test] fn test_duplicate_circuit() { - let program_bytes = include_bytes!("duplicate_circuit.leo"); - let resolver = TestSymbolTable::new(program_bytes); + let program_string = include_str!("duplicate_circuit.leo"); + let resolver = TestSymbolTable::new(program_string); resolver.expect_pass_one_error(); } @@ -40,8 +40,8 @@ fn test_duplicate_circuit() { /// #[test] fn test_duplicate_function() { - let program_bytes = include_bytes!("duplicate_function.leo"); - let resolver = TestSymbolTable::new(program_bytes); + let program_string = include_str!("duplicate_function.leo"); + let resolver = TestSymbolTable::new(program_string); resolver.expect_pass_one_error(); } @@ -54,8 +54,8 @@ fn test_duplicate_function() { /// #[test] fn test_self_not_available() { - let program_bytes = include_bytes!("self_not_available.leo"); - let resolver = TestSymbolTable::new(program_bytes); + let program_string = include_str!("self_not_available.leo"); + let resolver = TestSymbolTable::new(program_string); resolver.expect_pass_two_error(); } @@ -68,8 +68,8 @@ fn test_self_not_available() { /// #[test] fn test_undefined_circuit() { - let program_bytes = include_bytes!("undefined_circuit.leo"); - let resolver = TestSymbolTable::new(program_bytes); + let program_string = include_str!("undefined_circuit.leo"); + let resolver = TestSymbolTable::new(program_string); resolver.expect_pass_two_error(); } diff --git a/type-inference/src/errors/frame.rs b/type-inference/src/errors/frame.rs index 36e8576832..814d2e8ff2 100644 --- a/type-inference/src/errors/frame.rs +++ b/type-inference/src/errors/frame.rs @@ -172,6 +172,27 @@ impl FrameError { Self::new_from_span(message, span) } + /// + /// The `self` keyword was used in a static circuit function signature. + /// + pub fn self_not_available(span: &Span) -> Self { + let message = "keyword `self` is only available in static circuit functions.".to_string(); + + Self::new_from_span(message, span) + } + + /// + /// A static function was accessed using dot `.` syntax instead of double colon `::` syntax. + /// + pub fn static_call_invalid(identifier: &Identifier) -> Self { + let message = format!( + "Static function `{}` must be called using double colon `::` syntax.", + identifier.name + ); + + Self::new_from_span(message, &identifier.span) + } + /// /// Attempted to access the index of a non-tuple type. /// diff --git a/type-inference/src/objects/frame.rs b/type-inference/src/objects/frame.rs index 6a455e61de..e76702dddd 100644 --- a/type-inference/src/objects/frame.rs +++ b/type-inference/src/objects/frame.rs @@ -19,6 +19,7 @@ use leo_ast::{ ArrayDimensions, Assignee, AssigneeAccess, + Block, CircuitVariableDefinition, ConditionalNestedOrEndStatement, ConditionalStatement, @@ -34,7 +35,7 @@ use leo_ast::{ Statement, Variables, }; -use leo_symbol_table::{Attribute, CircuitFunctionType, CircuitType, FunctionType, SymbolTable, Type, TypeVariable}; +use leo_symbol_table::{CircuitType, FunctionType, SymbolTable, Type, TypeVariable}; /// A vector of `TypeAssertion` predicates created from a function body. #[derive(Clone)] @@ -42,7 +43,7 @@ pub struct Frame { pub function_type: FunctionType, pub self_type: Option, pub scopes: Vec, - pub statements: Vec, + pub block: Block, pub type_assertions: Vec, pub user_defined_types: SymbolTable, } @@ -77,7 +78,7 @@ impl Frame { function_type, self_type, scopes, - statements: function.statements, + block: function.block, type_assertions: vec![], user_defined_types, }; @@ -100,13 +101,13 @@ impl Frame { let identifier = &function.identifier; // Find function name in circuit members. - let circuit_function_type = self_type.member_function_type(identifier).unwrap().to_owned(); + let function_type = self_type.member_function_type(identifier).unwrap().to_owned(); // Create a new scope for the function variables. let mut scope = Scope::new(Some(parent_scope)); // Initialize function inputs as variables. - scope.insert_function_inputs(&circuit_function_type.function.inputs)?; + scope.insert_function_inputs(&function_type.inputs)?; // Create new list of scopes for frame. let scopes = vec![scope]; @@ -114,10 +115,10 @@ impl Frame { // Create new frame struct. // Update variables when encountering let/const variable definitions. let mut frame = Self { - function_type: circuit_function_type.function, + function_type, self_type: Some(self_type), scopes, - statements: function.statements, + block: function.block, type_assertions: Vec::new(), user_defined_types, }; @@ -230,7 +231,7 @@ impl Frame { /// Collects a vector of `TypeAssertion` predicates from a vector of statements. /// fn parse_statements(&mut self) -> Result<(), FrameError> { - for statement in self.statements.clone() { + for statement in self.block.statements.clone() { self.parse_statement(&statement)?; } @@ -248,8 +249,8 @@ impl Frame { } Statement::Assign(assignee, expression, span) => self.parse_assign(assignee, expression, span), Statement::Conditional(conditional, span) => self.parse_statement_conditional(conditional, span), - Statement::Iteration(identifier, from_to, statements, span) => { - self.parse_iteration(identifier, from_to, statements, span) + Statement::Iteration(identifier, from_to, block, span) => { + self.parse_iteration(identifier, from_to, block, span) } Statement::Expression(expression, span) => self.parse_statement_expression(expression, span), Statement::Console(_console_call) => Ok(()), // Console function calls do not generate type assertions. @@ -386,13 +387,13 @@ impl Frame { /// /// Collects `TypeAssertion` predicates from a block of statements. /// - fn parse_block(&mut self, statements: &[Statement], _span: &Span) -> Result<(), FrameError> { + fn parse_block(&mut self, block: &Block, _span: &Span) -> Result<(), FrameError> { // Push new scope. let scope = Scope::new(self.scopes.last().cloned()); self.push_scope(scope); // Parse all statements. - for statement in statements { + for statement in &block.statements { self.parse_statement(&statement)?; } @@ -420,7 +421,7 @@ impl Frame { self.assert_equal(boolean_type, condition, span); // Parse conditional statements. - self.parse_block(&conditional.statements, span)?; + self.parse_block(&conditional.block, span)?; // Parse conditional or end. if let Some(cond_or_end) = &conditional.next { @@ -451,7 +452,7 @@ impl Frame { &mut self, identifier: &Identifier, from_to: &(Expression, Expression), - statements: &[Statement], + statements: &Block, span: &Span, ) -> Result<(), FrameError> { // Insert variable into symbol table with u32 type. @@ -955,22 +956,6 @@ impl Frame { Ok(Type::Circuit(circuit_type.identifier)) } - /// - /// Returns the type of the accessed circuit member when called as an expression. - /// - fn parse_expression_circuit_member_access( - &mut self, - expression: &Expression, - identifier: &Identifier, - span: &Span, - ) -> Result { - // Parse circuit name. - let type_ = self.parse_expression(expression)?; - - // Parse the circuit member access. - self.parse_circuit_member_access(type_, identifier, span) - } - /// /// Returns the type of the accessed circuit member. /// @@ -987,6 +972,22 @@ impl Frame { Ok(circuit_type.member_type(&identifier)?) } + /// + /// Returns the type of the accessed circuit member when called as an expression. + /// + fn parse_expression_circuit_member_access( + &mut self, + expression: &Expression, + identifier: &Identifier, + span: &Span, + ) -> Result { + // Parse circuit name. + let type_ = self.parse_expression(expression)?; + + // Parse the circuit member access. + self.parse_circuit_member_access(type_, identifier, span) + } + /// /// Returns the type returned by calling the static circuit function. /// @@ -1029,10 +1030,10 @@ impl Frame { match expression { Expression::Identifier(identifier) => self.parse_program_function(identifier, span), Expression::CircuitMemberAccess(expression, identifier, span) => { - self.parse_circuit_function(expression, identifier, span) + self.parse_circuit_function(expression, identifier, span, false) } Expression::CircuitStaticFunctionAccess(expression, identifier, span) => { - self.parse_static_circuit_function(expression, identifier, span) + self.parse_circuit_function(expression, identifier, span, true) } expression => Err(FrameError::invalid_function(expression, span)), } @@ -1056,7 +1057,7 @@ impl Frame { expression: &Expression, identifier: &Identifier, span: &Span, - ) -> Result<&CircuitFunctionType, FrameError> { + ) -> Result<&FunctionType, FrameError> { // Parse circuit name. let type_ = self.parse_expression(expression)?; @@ -1077,37 +1078,23 @@ impl Frame { expression: &Expression, identifier: &Identifier, span: &Span, + is_static: bool, ) -> Result { // Find circuit function type. - let circuit_function_type = self.parse_circuit_function_type(expression, identifier, span)?; + let function_type = self.parse_circuit_function_type(expression, identifier, span)?; - // Check that the function is non-static. - if let Some(Attribute::Static) = circuit_function_type.attribute { - return Err(FrameError::invalid_static_access(identifier)); + // Case 1: static call + self keyword => Error + // Case 2: no static call + no self keywords => Error + // Case 3: static call + no self keywords => Ok + // Case 4: no static call + self keyword => Ok + if is_static && function_type.contains_self() { + return Err(FrameError::self_not_available(&identifier.span)); + } else if !is_static && !function_type.contains_self() { + return Err(FrameError::static_call_invalid(&identifier)); } // Return the function type. - Ok(circuit_function_type.function.to_owned()) - } - - /// - /// Returns a `FunctionType` given a circuit expression and static function identifier. - /// - fn parse_static_circuit_function( - &mut self, - expression: &Expression, - identifier: &Identifier, - span: &Span, - ) -> Result { - // Find circuit function type. - let circuit_function_type = self.parse_circuit_function_type(expression, identifier, span)?; - - // Check that the function is static. - if let Some(Attribute::Static) = circuit_function_type.attribute { - Ok(circuit_function_type.function.to_owned()) - } else { - Err(FrameError::invalid_member_access(identifier)) - } + Ok(function_type.to_owned()) } /// @@ -1125,12 +1112,15 @@ impl Frame { let function_type = self.parse_function_name(expression, span)?; // Check the length of arguments - if function_type.inputs.len() != inputs.len() { - return Err(FrameError::num_inputs(function_type.inputs.len(), inputs.len(), span)); + let num_inputs = function_type.num_inputs(); + + if num_inputs != inputs.len() { + return Err(FrameError::num_inputs(num_inputs, inputs.len(), span)); } + // Filter out `self` and `mut self` keywords. // Assert function inputs are correct types. - for (expected_input, actual_input) in function_type.inputs.iter().zip(inputs) { + for (expected_input, actual_input) in function_type.filter_self_inputs().zip(inputs) { // Parse expected input type. let expected_type = expected_input.type_(); diff --git a/type-inference/src/type_inference.rs b/type-inference/src/type_inference.rs index fee87bb035..17baf6db4c 100644 --- a/type-inference/src/type_inference.rs +++ b/type-inference/src/type_inference.rs @@ -82,7 +82,7 @@ impl TypeInference { // Create a new function for each circuit member function. for circuit_member in &circuit.members { // ignore circuit member variables - if let CircuitMember::CircuitFunction(_, function) = circuit_member { + if let CircuitMember::CircuitFunction(function) = circuit_member { // Collect `TypeAssertion` predicates from the function. // Pass down circuit self type and circuit variable types to each function. let frame = Frame::new_circuit_function( diff --git a/type-inference/tests/arrays/mod.rs b/type-inference/tests/arrays/mod.rs index 72ab79478e..6877b90b76 100644 --- a/type-inference/tests/arrays/mod.rs +++ b/type-inference/tests/arrays/mod.rs @@ -18,27 +18,27 @@ use crate::TestTypeInference; #[test] fn test_empty_array() { - let bytes = include_bytes!("empty_array.leo"); + let program_string = include_str!("empty_array.leo"); - let check = TestTypeInference::new(bytes); + let check = TestTypeInference::new(program_string); check.expect_error(); } #[test] fn test_invalid_array_access() { - let bytes = include_bytes!("invalid_array_access.leo"); + let program_string = include_str!("invalid_array_access.leo"); - let check = TestTypeInference::new(bytes); + let check = TestTypeInference::new(program_string); check.expect_error(); } #[test] fn test_invalid_spread() { - let bytes = include_bytes!("invalid_spread.leo"); + let program_string = include_str!("invalid_spread.leo"); - let check = TestTypeInference::new(bytes); + let check = TestTypeInference::new(program_string); check.expect_error(); } diff --git a/type-inference/tests/circuits/mod.rs b/type-inference/tests/circuits/mod.rs index 8b8d585bd6..e05837c4d0 100644 --- a/type-inference/tests/circuits/mod.rs +++ b/type-inference/tests/circuits/mod.rs @@ -18,8 +18,8 @@ use crate::TestTypeInference; #[test] fn test_invalid_circuit() { - let bytes = include_bytes!("invalid_circuit.leo"); - let check = TestTypeInference::new(bytes); + let program_string = include_str!("invalid_circuit.leo"); + let check = TestTypeInference::new(program_string); check.expect_error(); } diff --git a/type-inference/tests/functions/mod.rs b/type-inference/tests/functions/mod.rs index 20e873cbaf..c353cad388 100644 --- a/type-inference/tests/functions/mod.rs +++ b/type-inference/tests/functions/mod.rs @@ -18,8 +18,8 @@ use crate::TestTypeInference; #[test] fn test_invalid_function() { - let bytes = include_bytes!("invalid_function.leo"); - let check = TestTypeInference::new(bytes); + let program_string = include_str!("invalid_function.leo"); + let check = TestTypeInference::new(program_string); check.expect_error(); } diff --git a/type-inference/tests/mod.rs b/type-inference/tests/mod.rs index e72bb9f005..40924eabfe 100644 --- a/type-inference/tests/mod.rs +++ b/type-inference/tests/mod.rs @@ -38,15 +38,12 @@ pub struct TestTypeInference { } impl TestTypeInference { - pub fn new(bytes: &[u8]) -> Self { - // Get file string from bytes. - let file_string = String::from_utf8_lossy(bytes); - + pub fn new(program_string: &str) -> Self { // Get test file path. let file_path = PathBuf::from(TEST_PROGRAM_PATH); // Get parser syntax tree. - let ast = Grammar::new(&file_path, &*file_string).unwrap(); + let ast = Grammar::new(&file_path, program_string).unwrap(); // Get typed syntax tree. let typed = Ast::new(TEST_PROGRAM_NAME, &ast); @@ -76,9 +73,9 @@ impl TestTypeInference { #[test] fn test_new() { - let bytes = include_bytes!("empty.leo"); + let program_string = include_str!("empty.leo"); - let type_inference = TestTypeInference::new(bytes); + let type_inference = TestTypeInference::new(program_string); type_inference.check() } diff --git a/type-inference/tests/tuples/mod.rs b/type-inference/tests/tuples/mod.rs index cc0549cffe..9667e11971 100644 --- a/type-inference/tests/tuples/mod.rs +++ b/type-inference/tests/tuples/mod.rs @@ -18,8 +18,8 @@ use crate::TestTypeInference; #[test] fn test_invalid_tuple_access() { - let bytes = include_bytes!("invalid_tuple_access.leo"); - let check = TestTypeInference::new(bytes); + let program_string = include_str!("invalid_tuple_access.leo"); + let check = TestTypeInference::new(program_string); check.expect_error(); } diff --git a/type-inference/tests/variables/mod.rs b/type-inference/tests/variables/mod.rs index 9e7b3dd1ea..1cadaa5e68 100644 --- a/type-inference/tests/variables/mod.rs +++ b/type-inference/tests/variables/mod.rs @@ -18,32 +18,32 @@ use crate::TestTypeInference; #[test] fn test_duplicate_variable() { - let bytes = include_bytes!("duplicate_variable.leo"); - let check = TestTypeInference::new(bytes); + let program_string = include_str!("duplicate_variable.leo"); + let check = TestTypeInference::new(program_string); check.expect_error(); } #[test] fn test_duplicate_variable_multi() { - let bytes = include_bytes!("duplicate_variable_multi.leo"); - let check = TestTypeInference::new(bytes); + let program_string = include_str!("duplicate_variable_multi.leo"); + let check = TestTypeInference::new(program_string); check.expect_error(); } #[test] fn test_not_enough_values() { - let bytes = include_bytes!("not_enough_values.leo"); - let check = TestTypeInference::new(bytes); + let program_string = include_str!("not_enough_values.leo"); + let check = TestTypeInference::new(program_string); check.expect_error(); } #[test] fn test_too_many_values() { - let bytes = include_bytes!("too_many_values.leo"); - let check = TestTypeInference::new(bytes); + let program_string = include_str!("too_many_values.leo"); + let check = TestTypeInference::new(program_string); check.expect_error(); }