fix Self inside of circuit giving an error, tests

This commit is contained in:
gluax 2021-03-17 14:33:04 -04:00
parent e9bc1159ff
commit dceb8a9744
13 changed files with 812 additions and 6 deletions

View File

@ -18,9 +18,6 @@ use crate::*;
pub struct Canonicalizer;
// TODO fix function input array.
// TODO fix test 0 size array.
impl Canonicalizer {
fn is_self_type(&self, type_option: Option<&Type>) -> bool {
matches!(type_option, Some(Type::SelfType))
@ -161,7 +158,7 @@ impl Canonicalizer {
Expression::CircuitInit(circuit_init) => {
let mut name = circuit_init.name.clone();
if circuit_name.name == *"Self" {
if name.name == *"Self" {
name = circuit_name.clone();
}

View File

@ -638,7 +638,7 @@ impl<R: ReconstructingReducer> ReconstructingDirector<R> {
let mut inputs = vec![];
for input in function.input.iter() {
inputs.push(self.reduce_function_input(input, false)?);
inputs.push(self.reduce_function_input(input, in_circuit)?);
}
let output = match function.output.as_ref() {
@ -646,7 +646,7 @@ impl<R: ReconstructingReducer> ReconstructingDirector<R> {
None => None,
};
let block = self.reduce_block(&function.block, false)?;
let block = self.reduce_block(&function.block, in_circuit)?;
self.reducer
.reduce_function(function, identifier, annotations, inputs, output, block, in_circuit)

View File

@ -0,0 +1,338 @@
{
"name": "",
"expected_input": [],
"imports": [],
"circuits": {},
"functions": {
"{\"name\":\"main\",\"span\":\"{\\\"line_start\\\":1,\\\"line_stop\\\":1,\\\"col_start\\\":10,\\\"col_stop\\\":14,\\\"path\\\":\\\"\\\"}\"}": {
"annotations": [],
"identifier": "{\"name\":\"main\",\"span\":\"{\\\"line_start\\\":1,\\\"line_stop\\\":1,\\\"col_start\\\":10,\\\"col_stop\\\":14,\\\"path\\\":\\\"\\\"}\"}",
"input": [
{
"Variable": {
"identifier": "{\"name\":\"a\",\"span\":\"{\\\"line_start\\\":1,\\\"line_stop\\\":1,\\\"col_start\\\":15,\\\"col_stop\\\":16,\\\"path\\\":\\\"\\\"}\"}",
"const_": false,
"mutable": false,
"type_": {
"Array": [
{
"Array": [
"Group",
[
{
"value": "1"
}
]
]
},
[
{
"value": "2"
}
]
]
},
"span": {
"line_start": 1,
"line_stop": 1,
"col_start": 15,
"col_stop": 16,
"path": ""
}
}
}
],
"output": {
"Tuple": []
},
"block": {
"statements": [
{
"Definition": {
"declaration_type": "Let",
"variable_names": [
{
"mutable": false,
"identifier": "{\"name\":\"b\",\"span\":\"{\\\"line_start\\\":2,\\\"line_stop\\\":2,\\\"col_start\\\":7,\\\"col_stop\\\":8,\\\"path\\\":\\\"\\\"}\"}",
"span": {
"line_start": 2,
"line_stop": 2,
"col_start": 7,
"col_stop": 8,
"path": ""
}
}
],
"type_": null,
"value": {
"ArrayInit": {
"element": {
"ArrayInit": {
"element": {
"ArrayInit": {
"element": {
"ArrayInit": {
"element": {
"ArrayInit": {
"element": {
"Value": {
"Boolean": [
"true",
{
"line_start": 2,
"line_stop": 2,
"col_start": 12,
"col_stop": 16,
"path": ""
}
]
}
},
"dimensions": [
{
"value": "2"
}
],
"span": {
"line_start": 2,
"line_stop": 2,
"col_start": 11,
"col_stop": 34,
"path": ""
}
}
},
"dimensions": [
{
"value": "3"
}
],
"span": {
"line_start": 2,
"line_stop": 2,
"col_start": 11,
"col_stop": 34,
"path": ""
}
}
},
"dimensions": [
{
"value": "4"
}
],
"span": {
"line_start": 2,
"line_stop": 2,
"col_start": 11,
"col_stop": 34,
"path": ""
}
}
},
"dimensions": [
{
"value": "5"
}
],
"span": {
"line_start": 2,
"line_stop": 2,
"col_start": 11,
"col_stop": 34,
"path": ""
}
}
},
"dimensions": [
{
"value": "6"
}
],
"span": {
"line_start": 2,
"line_stop": 2,
"col_start": 11,
"col_stop": 34,
"path": ""
}
}
},
"span": {
"line_start": 2,
"line_stop": 2,
"col_start": 3,
"col_stop": 34,
"path": ""
}
}
},
{
"Definition": {
"declaration_type": "Let",
"variable_names": [
{
"mutable": false,
"identifier": "{\"name\":\"c\",\"span\":\"{\\\"line_start\\\":3,\\\"line_stop\\\":3,\\\"col_start\\\":7,\\\"col_stop\\\":8,\\\"path\\\":\\\"\\\"}\"}",
"span": {
"line_start": 3,
"line_stop": 3,
"col_start": 7,
"col_stop": 8,
"path": ""
}
}
],
"type_": {
"Array": [
{
"Array": [
{
"IntegerType": "U32"
},
[
{
"value": "2"
}
]
]
},
[
{
"value": "1"
}
]
]
},
"value": {
"ArrayInit": {
"element": {
"ArrayInit": {
"element": {
"Value": {
"Integer": [
"U32",
"0",
{
"line_start": 3,
"line_stop": 3,
"col_start": 27,
"col_stop": 31,
"path": ""
}
]
}
},
"dimensions": [
{
"value": "2"
}
],
"span": {
"line_start": 3,
"line_stop": 3,
"col_start": 26,
"col_stop": 40,
"path": ""
}
}
},
"dimensions": [
{
"value": "1"
}
],
"span": {
"line_start": 3,
"line_stop": 3,
"col_start": 26,
"col_stop": 40,
"path": ""
}
}
},
"span": {
"line_start": 3,
"line_stop": 3,
"col_start": 3,
"col_stop": 40,
"path": ""
}
}
},
{
"Definition": {
"declaration_type": "Let",
"variable_names": [
{
"mutable": false,
"identifier": "{\"name\":\"d\",\"span\":\"{\\\"line_start\\\":4,\\\"line_stop\\\":4,\\\"col_start\\\":7,\\\"col_stop\\\":8,\\\"path\\\":\\\"\\\"}\"}",
"span": {
"line_start": 4,
"line_stop": 4,
"col_start": 7,
"col_stop": 8,
"path": ""
}
}
],
"type_": null,
"value": {
"ArrayInit": {
"element": {
"Value": {
"Integer": [
"I8",
"0",
{
"line_start": 4,
"line_stop": 4,
"col_start": 12,
"col_stop": 15,
"path": ""
}
]
}
},
"dimensions": [
{
"value": "1"
}
],
"span": {
"line_start": 4,
"line_stop": 4,
"col_start": 11,
"col_stop": 21,
"path": ""
}
}
},
"span": {
"line_start": 4,
"line_stop": 4,
"col_start": 3,
"col_stop": 21,
"path": ""
}
}
}
],
"span": {
"line_start": 1,
"line_stop": 5,
"col_start": 35,
"col_stop": 2,
"path": ""
}
},
"span": {
"line_start": 1,
"line_stop": 5,
"col_start": 1,
"col_stop": 2,
"path": ""
}
}
}
}

View File

@ -0,0 +1,7 @@
function main(a: [group; (2, 1)]) {
let b = [true; (6, 5, 4, 3, 2)];
let c: [u32; (1, 2)] = [0u32; (1, 2)];
let d = [0i8; (1)];
// let d = [true; 0];
// let e = [true; (0)];
}

View File

@ -0,0 +1,3 @@
function main() {
let a = [true; (0)];
}

View File

@ -0,0 +1,206 @@
{
"name": "",
"expected_input": [],
"imports": [],
"circuits": {
"{\"name\":\"Foo\",\"span\":\"{\\\"line_start\\\":1,\\\"line_stop\\\":1,\\\"col_start\\\":9,\\\"col_stop\\\":12,\\\"path\\\":\\\"\\\"}\"}": {
"circuit_name": "{\"name\":\"Foo\",\"span\":\"{\\\"line_start\\\":1,\\\"line_stop\\\":1,\\\"col_start\\\":9,\\\"col_stop\\\":12,\\\"path\\\":\\\"\\\"}\"}",
"members": [
{
"CircuitVariable": [
"{\"name\":\"x\",\"span\":\"{\\\"line_start\\\":2,\\\"line_stop\\\":2,\\\"col_start\\\":3,\\\"col_stop\\\":4,\\\"path\\\":\\\"\\\"}\"}",
{
"IntegerType": "U32"
}
]
},
{
"CircuitFunction": {
"annotations": [],
"identifier": "{\"name\":\"new\",\"span\":\"{\\\"line_start\\\":4,\\\"line_stop\\\":4,\\\"col_start\\\":12,\\\"col_stop\\\":15,\\\"path\\\":\\\"\\\"}\"}",
"input": [],
"output": {
"Circuit": "{\"name\":\"Foo\",\"span\":\"{\\\"line_start\\\":1,\\\"line_stop\\\":1,\\\"col_start\\\":9,\\\"col_stop\\\":12,\\\"path\\\":\\\"\\\"}\"}"
},
"block": {
"statements": [
{
"Definition": {
"declaration_type": "Let",
"variable_names": [
{
"mutable": false,
"identifier": "{\"name\":\"new\",\"span\":\"{\\\"line_start\\\":5,\\\"line_stop\\\":5,\\\"col_start\\\":9,\\\"col_stop\\\":12,\\\"path\\\":\\\"\\\"}\"}",
"span": {
"line_start": 5,
"line_stop": 5,
"col_start": 9,
"col_stop": 12,
"path": ""
}
}
],
"type_": {
"Circuit": "{\"name\":\"Foo\",\"span\":\"{\\\"line_start\\\":1,\\\"line_stop\\\":1,\\\"col_start\\\":9,\\\"col_stop\\\":12,\\\"path\\\":\\\"\\\"}\"}"
},
"value": {
"CircuitInit": {
"name": "{\"name\":\"Foo\",\"span\":\"{\\\"line_start\\\":1,\\\"line_stop\\\":1,\\\"col_start\\\":9,\\\"col_stop\\\":12,\\\"path\\\":\\\"\\\"}\"}",
"members": [
{
"identifier": "{\"name\":\"x\",\"span\":\"{\\\"line_start\\\":6,\\\"line_stop\\\":6,\\\"col_start\\\":7,\\\"col_stop\\\":8,\\\"path\\\":\\\"\\\"}\"}",
"expression": {
"Value": {
"Integer": [
"U32",
"1",
{
"line_start": 6,
"line_stop": 6,
"col_start": 10,
"col_stop": 14,
"path": ""
}
]
}
}
}
],
"span": {
"line_start": 5,
"line_stop": 7,
"col_start": 21,
"col_stop": 6,
"path": ""
}
}
},
"span": {
"line_start": 5,
"line_stop": 7,
"col_start": 5,
"col_stop": 6,
"path": ""
}
}
},
{
"Return": {
"expression": {
"Identifier": "{\"name\":\"new\",\"span\":\"{\\\"line_start\\\":9,\\\"line_stop\\\":9,\\\"col_start\\\":12,\\\"col_stop\\\":15,\\\"path\\\":\\\"\\\"}\"}"
},
"span": {
"line_start": 9,
"line_stop": 9,
"col_start": 5,
"col_stop": 15,
"path": ""
}
}
}
],
"span": {
"line_start": 4,
"line_stop": 10,
"col_start": 26,
"col_stop": 4,
"path": ""
}
},
"span": {
"line_start": 4,
"line_stop": 10,
"col_start": 3,
"col_stop": 4,
"path": ""
}
}
}
]
}
},
"functions": {
"{\"name\":\"main\",\"span\":\"{\\\"line_start\\\":13,\\\"line_stop\\\":13,\\\"col_start\\\":10,\\\"col_stop\\\":14,\\\"path\\\":\\\"\\\"}\"}": {
"annotations": [],
"identifier": "{\"name\":\"main\",\"span\":\"{\\\"line_start\\\":13,\\\"line_stop\\\":13,\\\"col_start\\\":10,\\\"col_stop\\\":14,\\\"path\\\":\\\"\\\"}\"}",
"input": [],
"output": {
"Tuple": []
},
"block": {
"statements": [
{
"Definition": {
"declaration_type": "Let",
"variable_names": [
{
"mutable": false,
"identifier": "{\"name\":\"foo\",\"span\":\"{\\\"line_start\\\":14,\\\"line_stop\\\":14,\\\"col_start\\\":7,\\\"col_stop\\\":10,\\\"path\\\":\\\"\\\"}\"}",
"span": {
"line_start": 14,
"line_stop": 14,
"col_start": 7,
"col_stop": 10,
"path": ""
}
}
],
"type_": {
"Circuit": "{\"name\":\"Foo\",\"span\":\"{\\\"line_start\\\":14,\\\"line_stop\\\":14,\\\"col_start\\\":12,\\\"col_stop\\\":15,\\\"path\\\":\\\"\\\"}\"}"
},
"value": {
"Call": {
"function": {
"CircuitStaticFunctionAccess": {
"circuit": {
"Identifier": "{\"name\":\"Foo\",\"span\":\"{\\\"line_start\\\":14,\\\"line_stop\\\":14,\\\"col_start\\\":18,\\\"col_stop\\\":21,\\\"path\\\":\\\"\\\"}\"}"
},
"name": "{\"name\":\"new\",\"span\":\"{\\\"line_start\\\":14,\\\"line_stop\\\":14,\\\"col_start\\\":23,\\\"col_stop\\\":26,\\\"path\\\":\\\"\\\"}\"}",
"span": {
"line_start": 14,
"line_stop": 14,
"col_start": 18,
"col_stop": 26,
"path": ""
}
}
},
"arguments": [],
"span": {
"line_start": 14,
"line_stop": 14,
"col_start": 18,
"col_stop": 28,
"path": ""
}
}
},
"span": {
"line_start": 14,
"line_stop": 14,
"col_start": 3,
"col_stop": 28,
"path": ""
}
}
}
],
"span": {
"line_start": 13,
"line_stop": 15,
"col_start": 17,
"col_stop": 2,
"path": ""
}
},
"span": {
"line_start": 13,
"line_stop": 15,
"col_start": 1,
"col_stop": 2,
"path": ""
}
}
}
}

View File

@ -0,0 +1,15 @@
circuit Foo {
x: u32
function new() -> Self {
let new: Self = Self {
x: 1u32
};
return new
}
}
function main() {
let foo: Foo = Foo::new();
}

View File

@ -0,0 +1,15 @@
circuit Foo {
x: u32
function new() -> Self {
let new: Self = Self {
x: 1u32
};
return new
}
}
function main() {
let foo: Self = Foo::new();
}

View File

@ -0,0 +1,128 @@
{
"name": "",
"expected_input": [],
"imports": [],
"circuits": {},
"functions": {
"{\"name\":\"main\",\"span\":\"{\\\"line_start\\\":1,\\\"line_stop\\\":1,\\\"col_start\\\":10,\\\"col_stop\\\":14,\\\"path\\\":\\\"\\\"}\"}": {
"annotations": [],
"identifier": "{\"name\":\"main\",\"span\":\"{\\\"line_start\\\":1,\\\"line_stop\\\":1,\\\"col_start\\\":10,\\\"col_stop\\\":14,\\\"path\\\":\\\"\\\"}\"}",
"input": [],
"output": {
"Tuple": []
},
"block": {
"statements": [
{
"Definition": {
"declaration_type": "Let",
"variable_names": [
{
"mutable": true,
"identifier": "{\"name\":\"x\",\"span\":\"{\\\"line_start\\\":2,\\\"line_stop\\\":2,\\\"col_start\\\":11,\\\"col_stop\\\":12,\\\"path\\\":\\\"\\\"}\"}",
"span": {
"line_start": 2,
"line_stop": 2,
"col_start": 7,
"col_stop": 12,
"path": ""
}
}
],
"type_": null,
"value": {
"Value": {
"Integer": [
"U32",
"10",
{
"line_start": 2,
"line_stop": 2,
"col_start": 15,
"col_stop": 20,
"path": ""
}
]
}
},
"span": {
"line_start": 2,
"line_stop": 2,
"col_start": 3,
"col_stop": 20,
"path": ""
}
}
},
{
"Assign": {
"operation": "Assign",
"assignee": {
"identifier": "{\"name\":\"x\",\"span\":\"{\\\"line_start\\\":3,\\\"line_stop\\\":3,\\\"col_start\\\":3,\\\"col_stop\\\":4,\\\"path\\\":\\\"\\\"}\"}",
"accesses": [],
"span": {
"line_start": 3,
"line_stop": 3,
"col_start": 3,
"col_stop": 4,
"path": ""
}
},
"value": {
"Binary": {
"left": {
"Identifier": "{\"name\":\"x\",\"span\":\"{\\\"line_start\\\":3,\\\"line_stop\\\":3,\\\"col_start\\\":3,\\\"col_stop\\\":4,\\\"path\\\":\\\"\\\"}\"}"
},
"right": {
"Value": {
"Implicit": [
"20",
{
"line_start": 3,
"line_stop": 3,
"col_start": 8,
"col_stop": 10,
"path": ""
}
]
}
},
"op": "Add",
"span": {
"line_start": 3,
"line_stop": 3,
"col_start": 3,
"col_stop": 10,
"path": ""
}
}
},
"span": {
"line_start": 3,
"line_stop": 3,
"col_start": 3,
"col_stop": 10,
"path": ""
}
}
}
],
"span": {
"line_start": 1,
"line_stop": 4,
"col_start": 17,
"col_stop": 2,
"path": ""
}
},
"span": {
"line_start": 1,
"line_stop": 4,
"col_start": 1,
"col_stop": 2,
"path": ""
}
}
}
}

View File

@ -0,0 +1,4 @@
function main() {
let mut x = 10u32;
x += 20;
}

View File

@ -0,0 +1,2 @@
[main]
a: [group; (2, 1)] = [1group; (2, 1)];

View File

@ -0,0 +1,89 @@
// Copyright (C) 2019-2021 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 <https://www.gnu.org/licenses/>.
use crate::{assert_satisfied, parse_program, parse_program_with_input};
use leo_ast::Ast;
use leo_parser::parser;
pub fn parse_program_ast(file_string: &str) -> Ast {
const TEST_PROGRAM_PATH: &str = "";
let test_program_file_path = std::path::PathBuf::from(TEST_PROGRAM_PATH);
let mut ast = Ast::new(
parser::parse(test_program_file_path.to_str().expect("unwrap fail"), &file_string)
.expect("Failed to parse file."),
);
ast.canonicalize().expect("Failed to canonicalize program.");
ast
}
#[test]
fn test_big_self_in_circuit_replacement() {
// Check program is valid.
let program_string = include_str!("big_self_in_circuit_replacement.leo");
let program = parse_program(program_string).unwrap();
assert_satisfied(program);
// Check we get expected ast.
let ast = parse_program_ast(program_string);
let expected_json = include_str!("big_self_in_circuit_replacement.json");
let expected_ast: Ast = Ast::from_json_string(expected_json).expect("Unable to parse json.");
assert_eq!(expected_ast, ast);
}
#[test]
fn test_big_self_outside_circuit_fail() {
// Check program is invalid.
let program_string = include_str!("big_self_outside_circuit_fail.leo");
let program = parse_program(program_string);
assert!(program.is_err());
}
#[test]
fn test_array_expansion() {
let program_string = include_str!("array_expansion.leo");
let input_string = include_str!("input/array_expansion.in");
let program = parse_program_with_input(program_string, input_string).unwrap();
assert_satisfied(program);
let ast = parse_program_ast(program_string);
let expected_json = include_str!("array_expansion.json");
let expected_ast: Ast = Ast::from_json_string(expected_json).expect("Unable to parse json.");
assert_eq!(expected_ast, ast);
}
#[test]
fn test_array_size_zero_fail() {
let program_string = include_str!("array_size_zero_fail.leo");
let program = parse_program(program_string);
assert!(program.is_err());
}
#[test]
fn test_compound_assignment() {
let program_string = include_str!("compound_assignment.leo");
let program = parse_program(program_string).unwrap();
assert_satisfied(program);
let ast = parse_program_ast(program_string);
let expected_json = include_str!("compound_assignment.json");
let expected_ast: Ast = Ast::from_json_string(expected_json).expect("Unable to parse json.");
assert_eq!(expected_ast, ast);
}

View File

@ -15,11 +15,13 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
// allow the use of EdwardsTestCompiler::parse_program_from_string for tests
#![allow(deprecated)]
pub mod address;
pub mod array;
pub mod boolean;
pub mod canonicalization;
pub mod circuits;
pub mod compiler;
pub mod console;