diff --git a/compiler/src/compiler.rs b/compiler/src/compiler.rs index ceab0529b5..4b5ea8be63 100644 --- a/compiler/src/compiler.rs +++ b/compiler/src/compiler.rs @@ -76,7 +76,12 @@ impl> Compiler { self, cs: &mut CS, ) -> Result, CompilerError> { - generate_constraints(cs, self.program, self.program_inputs.get_inputs()) + let path = self.main_file_path; + generate_constraints(cs, self.program, self.program_inputs.get_inputs()).map_err(|mut error| { + error.set_path(path); + + error + }) } pub fn compile_test_constraints(self, cs: &mut TestConstraintSystem) -> Result<(), CompilerError> { diff --git a/compiler/src/constraints/import.rs b/compiler/src/constraints/import.rs index 7d8c59c36f..0c351a64d5 100644 --- a/compiler/src/constraints/import.rs +++ b/compiler/src/constraints/import.rs @@ -40,9 +40,7 @@ impl> ConstrainedProgram { // * -> import all imports, circuits, functions in the current scope if import.is_star() { // recursively evaluate program statements - self.resolve_definitions(program).unwrap(); - - Ok(()) + self.resolve_definitions(program) } else { let program_name = program.name.clone(); @@ -67,7 +65,7 @@ impl> ConstrainedProgram { match matched_function { Some((_function_name, function)) => ConstrainedValue::Function(None, function), - None => return Err(ImportError::unknown_symbol(symbol, program_name)), + None => return Err(ImportError::unknown_symbol(symbol, program_name, file_path)), } } }; diff --git a/compiler/src/errors/compiler.rs b/compiler/src/errors/compiler.rs index cb5ce08e25..be659587ce 100644 --- a/compiler/src/errors/compiler.rs +++ b/compiler/src/errors/compiler.rs @@ -27,3 +27,12 @@ pub enum CompilerError { #[error("{}", _0)] ParserError(#[from] ParserError), } + +impl CompilerError { + pub fn set_path(&mut self, path: PathBuf) { + match self { + CompilerError::FunctionError(error) => error.set_path(path), + _ => {} + } + } +} diff --git a/compiler/src/errors/constraints/boolean.rs b/compiler/src/errors/constraints/boolean.rs index 991115ceec..bea08d67e4 100644 --- a/compiler/src/errors/constraints/boolean.rs +++ b/compiler/src/errors/constraints/boolean.rs @@ -1,6 +1,7 @@ use leo_types::{Error as FormattedError, Span}; use snarkos_errors::gadgets::SynthesisError; +use std::path::PathBuf; #[derive(Debug, Error)] pub enum BooleanError { @@ -9,6 +10,12 @@ pub enum BooleanError { } impl BooleanError { + pub fn set_path(&mut self, path: PathBuf) { + match self { + BooleanError::Error(error) => error.set_path(path), + } + } + fn new_from_span(message: String, span: Span) -> Self { BooleanError::Error(FormattedError::new_from_span(message, span)) } diff --git a/compiler/src/errors/constraints/expression.rs b/compiler/src/errors/constraints/expression.rs index 06004f3663..630602f482 100644 --- a/compiler/src/errors/constraints/expression.rs +++ b/compiler/src/errors/constraints/expression.rs @@ -2,6 +2,7 @@ use crate::errors::{BooleanError, FieldError, FunctionError, GroupError, ValueEr use leo_types::{Error as FormattedError, Identifier, IntegerError, Span}; use snarkos_errors::gadgets::SynthesisError; +use std::path::PathBuf; #[derive(Debug, Error)] pub enum ExpressionError { @@ -11,9 +12,6 @@ pub enum ExpressionError { #[error("{}", _0)] Error(#[from] FormattedError), - #[error("{}", _0)] - IntegerError(#[from] IntegerError), - #[error("{}", _0)] FieldError(#[from] FieldError), @@ -23,11 +21,26 @@ pub enum ExpressionError { #[error("{}", _0)] GroupError(#[from] GroupError), + #[error("{}", _0)] + IntegerError(#[from] IntegerError), + #[error("{}", _0)] ValueError(#[from] ValueError), } impl ExpressionError { + pub fn set_path(&mut self, path: PathBuf) { + match self { + ExpressionError::BooleanError(error) => error.set_path(path), + ExpressionError::Error(error) => error.set_path(path), + ExpressionError::FieldError(error) => error.set_path(path), + ExpressionError::FunctionError(error) => error.set_path(path), + ExpressionError::GroupError(error) => error.set_path(path), + ExpressionError::IntegerError(error) => error.set_path(path), + ExpressionError::ValueError(error) => error.set_path(path), + } + } + fn new_from_span(message: String, span: Span) -> Self { ExpressionError::Error(FormattedError::new_from_span(message, span)) } diff --git a/compiler/src/errors/constraints/field.rs b/compiler/src/errors/constraints/field.rs index 272a63bc8a..05e1d2f437 100644 --- a/compiler/src/errors/constraints/field.rs +++ b/compiler/src/errors/constraints/field.rs @@ -1,6 +1,7 @@ use leo_types::{Error as FormattedError, Span}; use snarkos_errors::gadgets::SynthesisError; +use std::path::PathBuf; #[derive(Debug, Error)] pub enum FieldError { @@ -9,6 +10,12 @@ pub enum FieldError { } impl FieldError { + pub fn set_path(&mut self, path: PathBuf) { + match self { + FieldError::Error(error) => error.set_path(path), + } + } + fn new_from_span(message: String, span: Span) -> Self { FieldError::Error(FormattedError::new_from_span(message, span)) } diff --git a/compiler/src/errors/constraints/function.rs b/compiler/src/errors/constraints/function.rs index 80cf5794ee..6c7a269bf2 100644 --- a/compiler/src/errors/constraints/function.rs +++ b/compiler/src/errors/constraints/function.rs @@ -1,5 +1,6 @@ use crate::errors::{BooleanError, ExpressionError, FieldError, GroupError, StatementError, ValueError}; use leo_types::{Error as FormattedError, IntegerError, Span}; +use std::path::PathBuf; #[derive(Debug, Error)] pub enum FunctionError { @@ -29,6 +30,19 @@ pub enum FunctionError { } impl FunctionError { + pub fn set_path(&mut self, path: PathBuf) { + match self { + FunctionError::BooleanError(error) => error.set_path(path), + FunctionError::ExpressionError(error) => error.set_path(path), + FunctionError::Error(error) => error.set_path(path), + FunctionError::FieldError(error) => error.set_path(path), + FunctionError::GroupError(error) => error.set_path(path), + FunctionError::IntegerError(error) => error.set_path(path), + FunctionError::StatementError(error) => error.set_path(path), + FunctionError::ValueError(error) => error.set_path(path), + } + } + fn new_from_span(message: String, span: Span) -> Self { FunctionError::Error(FormattedError::new_from_span(message, span)) } diff --git a/compiler/src/errors/constraints/group.rs b/compiler/src/errors/constraints/group.rs index 2f3544c103..5e7fdcefd6 100644 --- a/compiler/src/errors/constraints/group.rs +++ b/compiler/src/errors/constraints/group.rs @@ -1,6 +1,7 @@ use leo_types::{Error as FormattedError, Span}; use snarkos_errors::gadgets::SynthesisError; +use std::path::PathBuf; #[derive(Debug, Error)] pub enum GroupError { @@ -9,6 +10,12 @@ pub enum GroupError { } impl GroupError { + pub fn set_path(&mut self, path: PathBuf) { + match self { + GroupError::Error(error) => error.set_path(path), + } + } + fn new_from_span(message: String, span: Span) -> Self { GroupError::Error(FormattedError::new_from_span(message, span)) } diff --git a/compiler/src/errors/constraints/import.rs b/compiler/src/errors/constraints/import.rs index bbe317ab35..c5d3c238d9 100644 --- a/compiler/src/errors/constraints/import.rs +++ b/compiler/src/errors/constraints/import.rs @@ -1,7 +1,7 @@ use leo_ast::ParserError; use leo_types::{Error as FormattedError, ImportSymbol, Span}; -use std::io; +use std::{io, path::PathBuf}; #[derive(Debug, Error)] pub enum ImportError { @@ -23,9 +23,12 @@ impl ImportError { Self::new_from_span(message, span) } - pub fn unknown_symbol(symbol: ImportSymbol, file: String) -> Self { + pub fn unknown_symbol(symbol: ImportSymbol, file: String, file_path: &PathBuf) -> Self { let message = format!("cannot find imported symbol `{}` in imported file `{}`", symbol, file); + let mut error = FormattedError::new_from_span(message, symbol.span); - Self::new_from_span(message, symbol.span) + error.path = Some(format!("{:?}", file_path)); + + ImportError::Error(error) } } diff --git a/compiler/src/errors/constraints/statement.rs b/compiler/src/errors/constraints/statement.rs index 8cd23f86c3..147ef38109 100644 --- a/compiler/src/errors/constraints/statement.rs +++ b/compiler/src/errors/constraints/statement.rs @@ -1,5 +1,6 @@ use crate::errors::{BooleanError, ExpressionError, ValueError}; use leo_types::{Error as FormattedError, IntegerError, Span}; +use std::path::PathBuf; #[derive(Debug, Error)] pub enum StatementError { @@ -20,6 +21,16 @@ pub enum StatementError { } impl StatementError { + pub fn set_path(&mut self, path: PathBuf) { + match self { + StatementError::BooleanError(error) => error.set_path(path), + StatementError::Error(error) => error.set_path(path), + StatementError::ExpressionError(error) => error.set_path(path), + StatementError::IntegerError(error) => error.set_path(path), + StatementError::ValueError(error) => error.set_path(path), + } + } + fn new_from_span(message: String, span: Span) -> Self { StatementError::Error(FormattedError::new_from_span(message, span)) } diff --git a/compiler/src/errors/constraints/value.rs b/compiler/src/errors/constraints/value.rs index 46b2825990..43504c144b 100644 --- a/compiler/src/errors/constraints/value.rs +++ b/compiler/src/errors/constraints/value.rs @@ -1,5 +1,6 @@ use crate::errors::{BooleanError, FieldError, GroupError}; use leo_types::{Error as FormattedError, IntegerError, Span}; +use std::path::PathBuf; #[derive(Debug, Error)] pub enum ValueError { @@ -20,6 +21,16 @@ pub enum ValueError { } impl ValueError { + pub fn set_path(&mut self, path: PathBuf) { + match self { + ValueError::BooleanError(error) => error.set_path(path), + ValueError::Error(error) => error.set_path(path), + ValueError::FieldError(error) => error.set_path(path), + ValueError::GroupError(error) => error.set_path(path), + ValueError::IntegerError(error) => error.set_path(path), + } + } + fn new_from_span(message: String, span: Span) -> Self { ValueError::Error(FormattedError::new_from_span(message, span)) } diff --git a/compiler/tests/array/mod.rs b/compiler/tests/array/mod.rs index 97f60aa17c..9e547f5d1b 100644 --- a/compiler/tests/array/mod.rs +++ b/compiler/tests/array/mod.rs @@ -49,7 +49,7 @@ fn output_multi(program: EdwardsTestCompiler) { fn fail_array(program: EdwardsTestCompiler) { match get_error(program) { CompilerError::FunctionError(FunctionError::Error(_string)) => {} - error => panic!("Expected invalid array error, got {}", error), + error => panic!("Expected function error, found {}", error), } } diff --git a/compiler/tests/mod.rs b/compiler/tests/mod.rs index 34b92803af..167328cf20 100644 --- a/compiler/tests/mod.rs +++ b/compiler/tests/mod.rs @@ -20,6 +20,7 @@ use leo_compiler::{ use snarkos_curves::edwards_bls12::Fq; use snarkos_models::gadgets::r1cs::TestConstraintSystem; +use std::path::PathBuf; pub type EdwardsTestCompiler = Compiler; pub type EdwardsConstrainedValue = ConstrainedValue; @@ -45,8 +46,11 @@ pub(crate) fn fail_enforce(program: EdwardsTestCompiler) { fn new_compiler() -> EdwardsTestCompiler { let program_name = "test".to_string(); + let path = PathBuf::from("/test/src/main.leo"); + let mut compiler = EdwardsTestCompiler::new(program_name); + compiler.set_path(path); - EdwardsTestCompiler::new(program_name) + compiler } pub(crate) fn parse_program(bytes: &[u8]) -> Result { diff --git a/compiler/tests/syntax/mod.rs b/compiler/tests/syntax/mod.rs index 994a972322..cbfa88bc50 100644 --- a/compiler/tests/syntax/mod.rs +++ b/compiler/tests/syntax/mod.rs @@ -25,10 +25,11 @@ fn test_undefined() { CompilerError::FunctionError(FunctionError::StatementError(StatementError::ExpressionError( ExpressionError::Error(error), ))) => { + println!("{}", error); assert_eq!( format!("{}", error), vec![ - " --> 2:10", + " --> \"/test/src/main.leo\": 2:10", " |", " 2 | return a", " | ^", diff --git a/types/src/errors/error.rs b/types/src/errors/error.rs index 20f7d0f16a..04723c2cfa 100644 --- a/types/src/errors/error.rs +++ b/types/src/errors/error.rs @@ -1,6 +1,6 @@ use crate::Span; -use std::fmt; +use std::{fmt, path::PathBuf}; /// Formatted compiler error type /// --> file.leo 2:8 @@ -37,6 +37,10 @@ impl Error { } } + pub fn set_path(&mut self, path: PathBuf) { + self.path = Some(format!("{:?}", path)); + } + pub fn format(&self) -> String { let indent = " ".to_string(); let path = self.path.as_ref().map(|path| format!("{}:", path)).unwrap_or_default(); diff --git a/types/src/errors/integer.rs b/types/src/errors/integer.rs index d00f79278b..a8777536d3 100644 --- a/types/src/errors/integer.rs +++ b/types/src/errors/integer.rs @@ -1,6 +1,7 @@ use crate::{error::Error as FormattedError, Span}; use snarkos_errors::gadgets::SynthesisError; +use std::path::PathBuf; #[derive(Debug, Error)] pub enum IntegerError { @@ -9,6 +10,12 @@ pub enum IntegerError { } impl IntegerError { + pub fn set_path(&mut self, path: PathBuf) { + match self { + IntegerError::Error(error) => error.set_path(path), + } + } + fn new_from_span(message: String, span: Span) -> Self { IntegerError::Error(FormattedError::new_from_span(message, span)) }