Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: handle warnings in evaluator #3205

Merged
merged 26 commits into from
Oct 26, 2023
Merged
Show file tree
Hide file tree
Changes from 10 commits
Commits
Show all changes
26 commits
Select commit Hold shift + click to select a range
af39408
return warnings from evaluator
guipublic Oct 17, 2023
f3c0094
cargo.lock
guipublic Oct 17, 2023
ddac566
Merge branch 'master' into gd/issue_3131
guipublic Oct 17, 2023
18da5dd
contracts do not handle warnings
guipublic Oct 17, 2023
6a856ed
Merge branch 'master' into gd/issue_3131
guipublic Oct 17, 2023
70a64f9
Merge branch 'master' into gd/issue_3131
guipublic Oct 20, 2023
116ef16
separate warnings from errors in the evaluator
guipublic Oct 20, 2023
44c866a
Merge branch 'master' into gd/issue_3131
guipublic Oct 20, 2023
4f8fb9a
fix some cargo fmt
guipublic Oct 20, 2023
9b95d56
cargo fmt
guipublic Oct 20, 2023
39b2f0b
Merge branch 'master' into gd/issue_3131
guipublic Oct 23, 2023
9ed7209
remove comments
guipublic Oct 23, 2023
b4931c8
Merge branch 'master' into gd/issue_3131
kevaundray Oct 23, 2023
848a870
Merge branch 'master' into gd/issue_3131
guipublic Oct 24, 2023
24ec025
chore: Update ACIR artifacts (#3263)
kevaundray Oct 24, 2023
09f8a6d
fix: recompile artefacts from a different noir version (#3248)
guipublic Oct 24, 2023
d3f7be2
feat(debugger): Print limited source code context (#3217)
mverzilli Oct 24, 2023
5db9514
chore(docs): Document `nargo fmt` (#3262)
Savio-Sou Oct 24, 2023
6d116f7
chore(docs): Rearrange NoirJS section (#3260)
Savio-Sou Oct 24, 2023
19ab5b7
feat: noir-wasm takes dependency graph (#3213)
alexghr Oct 24, 2023
d05a423
feat!: Switch to new pedersen implementation (#3151)
kevaundray Oct 24, 2023
a82543a
fmt
guipublic Oct 24, 2023
ef6f1e8
Merge branch 'master' into gd/issue_3131
guipublic Oct 24, 2023
b12974b
fmt
guipublic Oct 24, 2023
17fc22d
Merge branch 'master' into gd/issue_3131
guipublic Oct 24, 2023
2303495
Merge branch 'master' into gd/issue_3131
guipublic Oct 26, 2023
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions compiler/noirc_driver/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ noirc_frontend.workspace = true
noirc_evaluator.workspace = true
noirc_abi.workspace = true
acvm.workspace = true
iter-extended.workspace = true
fm.workspace = true
serde.workspace = true
base64.workspace = true
Expand Down
24 changes: 16 additions & 8 deletions compiler/noirc_driver/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,11 @@
use clap::Args;
use debug::filter_relevant_files;
use fm::FileId;
use iter_extended::vecmap;
use noirc_abi::{AbiParameter, AbiType, ContractEvent};
use noirc_errors::{CustomDiagnostic, FileDiagnostic};
use noirc_evaluator::errors::RuntimeError;
use noirc_evaluator::errors::SsaReport;
use noirc_evaluator::{create_circuit, into_abi_params};
use noirc_frontend::graph::{CrateId, CrateName};
use noirc_frontend::hir::def_map::{Contract, CrateDefMap};
Expand Down Expand Up @@ -155,7 +157,7 @@ pub fn compile_main(
cached_program: Option<CompiledProgram>,
force_compile: bool,
) -> CompilationResult<CompiledProgram> {
let (_, warnings) = check_crate(context, crate_id, options.deny_warnings)?;
let (_, mut warnings) = check_crate(context, crate_id, options.deny_warnings)?;

let main = match context.get_main_function(&crate_id) {
Some(m) => m,
Expand All @@ -169,8 +171,14 @@ pub fn compile_main(
}
};

let compiled_program = compile_no_check(context, options, main, cached_program, force_compile)
.map_err(FileDiagnostic::from)?;
let (compiled_program, compilation_warnings) =
compile_no_check(context, options, main, cached_program, force_compile)
.map_err(FileDiagnostic::from)?;
let compilation_warnings = vecmap(compilation_warnings, FileDiagnostic::from);
if options.deny_warnings && !compilation_warnings.is_empty() {
return Err(compilation_warnings);
}
warnings.extend(compilation_warnings);

if options.print_acir {
println!("Compiled ACIR for main (unoptimized):");
Expand Down Expand Up @@ -265,7 +273,7 @@ fn compile_contract_inner(
}

let function = match compile_no_check(context, options, function_id, None, true) {
Ok(function) => function,
Ok((function, _warnings)) => function,
guipublic marked this conversation as resolved.
Show resolved Hide resolved
Err(new_error) => {
errors.push(FileDiagnostic::from(new_error));
continue;
Expand Down Expand Up @@ -322,7 +330,7 @@ pub fn compile_no_check(
main_function: FuncId,
cached_program: Option<CompiledProgram>,
force_compile: bool,
) -> Result<CompiledProgram, RuntimeError> {
) -> Result<(CompiledProgram, Vec<SsaReport>), RuntimeError> {
let program = monomorphize(main_function, &context.def_interner);

let hash = fxhash::hash64(&program);
Expand All @@ -332,15 +340,15 @@ pub fn compile_no_check(
if !(force_compile || options.print_acir || options.show_brillig || options.show_ssa) {
if let Some(cached_program) = cached_program {
if hash == cached_program.hash {
return Ok(cached_program);
return Ok((cached_program, Vec::new()));
guipublic marked this conversation as resolved.
Show resolved Hide resolved
}
}
}

let (circuit, debug, abi) =
let (circuit, debug, abi, warnings) =
create_circuit(context, program, options.show_ssa, options.show_brillig)?;

let file_map = filter_relevant_files(&[debug.clone()], &context.file_manager);

Ok(CompiledProgram { hash, circuit, debug, abi, file_map })
Ok((CompiledProgram { hash, circuit, debug, abi, file_map }, warnings))
}
48 changes: 38 additions & 10 deletions compiler/noirc_evaluator/src/errors.rs
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,37 @@ fn format_failed_constraint(message: &Option<String>) -> String {
}
}

#[derive(Debug)]
pub enum SsaReport {
Warning(InternalWarning),
}

impl From<SsaReport> for FileDiagnostic {
fn from(error: SsaReport) -> FileDiagnostic {
match error {
SsaReport::Warning(warning) => {
let InternalWarning::ReturnConstant { ref call_stack } = warning;
let call_stack = vecmap(call_stack, |location| *location);
let file_id = call_stack.last().map(|location| location.file).unwrap_or_default();
let message = warning.to_string();
let location = call_stack.last().expect("Expected RuntimeError to have a location");
let diagnostic = Diagnostic::simple_warning(
message,
"constant value".to_string(),
location.span,
);
diagnostic.in_file(file_id).with_call_stack(call_stack)
}
}
}
}

#[derive(Debug, PartialEq, Eq, Clone, Error)]
pub enum InternalWarning {
#[error("Returning a constant value is not allowed")]
ReturnConstant { call_stack: CallStack },
}

#[derive(Debug, PartialEq, Eq, Clone, Error)]
pub enum InternalError {
#[error("ICE: Both expressions should have degree<=1")]
Expand All @@ -67,8 +98,6 @@ pub enum InternalError {
UndeclaredAcirVar { call_stack: CallStack },
#[error("ICE: Expected {expected:?}, found {found:?}")]
UnExpected { expected: String, found: String, call_stack: CallStack },
#[error("Returning a constant value is not allowed")]
ReturnConstant { call_stack: CallStack },
}

impl RuntimeError {
Expand All @@ -81,8 +110,7 @@ impl RuntimeError {
| InternalError::MissingArg { call_stack, .. }
| InternalError::NotAConstant { call_stack, .. }
| InternalError::UndeclaredAcirVar { call_stack }
| InternalError::UnExpected { call_stack, .. }
| InternalError::ReturnConstant { call_stack, .. },
| InternalError::UnExpected { call_stack, .. }, // | InternalError::ReturnConstant { call_stack, .. },
guipublic marked this conversation as resolved.
Show resolved Hide resolved
)
| RuntimeError::FailedConstraint { call_stack, .. }
| RuntimeError::IndexOutOfBounds { call_stack, .. }
Expand All @@ -108,12 +136,12 @@ impl From<RuntimeError> for FileDiagnostic {
impl RuntimeError {
fn into_diagnostic(self) -> Diagnostic {
match self {
RuntimeError::InternalError(InternalError::ReturnConstant { ref call_stack }) => {
let message = self.to_string();
let location =
call_stack.back().expect("Expected RuntimeError to have a location");
Diagnostic::simple_error(message, "constant value".to_string(), location.span)
}
// RuntimeError::InternalError(InternalError::ReturnConstant { ref call_stack }) => {
// let message = self.to_string();
// let location =
// call_stack.back().expect("Expected RuntimeError to have a location");
// Diagnostic::simple_warning(message, "constant value".to_string(), location.span)
// }
guipublic marked this conversation as resolved.
Show resolved Hide resolved
RuntimeError::InternalError(cause) => {
Diagnostic::simple_error(
"Internal Consistency Evaluators Errors: \n
Expand Down
7 changes: 4 additions & 3 deletions compiler/noirc_evaluator/src/ssa.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@

use std::collections::BTreeSet;

use crate::errors::RuntimeError;
use crate::errors::{RuntimeError, SsaReport};
use acvm::acir::{
circuit::{Circuit, PublicInputs},
native_types::Witness,
Expand Down Expand Up @@ -72,7 +72,7 @@ pub fn create_circuit(
program: Program,
enable_ssa_logging: bool,
enable_brillig_logging: bool,
) -> Result<(Circuit, DebugInfo, Abi), RuntimeError> {
) -> Result<(Circuit, DebugInfo, Abi, Vec<SsaReport>), RuntimeError> {
let func_sig = program.main_function_signature.clone();
let mut generated_acir =
optimize_into_acir(program, enable_ssa_logging, enable_brillig_logging)?;
Expand All @@ -83,6 +83,7 @@ pub fn create_circuit(
locations,
input_witnesses,
assert_messages,
warnings,
..
} = generated_acir;

Expand Down Expand Up @@ -119,7 +120,7 @@ pub fn create_circuit(
let (optimized_circuit, transformation_map) = acvm::compiler::optimize(circuit);
debug_info.update_acir(transformation_map);

Ok((optimized_circuit, debug_info, abi))
Ok((optimized_circuit, debug_info, abi, warnings))
}

// This is just a convenience object to bundle the ssa with `print_ssa_passes` for debug printing.
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
use super::generated_acir::GeneratedAcir;
use crate::brillig::brillig_gen::brillig_directive;
use crate::brillig::brillig_ir::artifact::GeneratedBrillig;
use crate::errors::{InternalError, RuntimeError};
use crate::errors::{InternalError, RuntimeError, SsaReport};
use crate::ssa::acir_gen::{AcirDynamicArray, AcirValue};
use crate::ssa::ir::dfg::CallStack;
use crate::ssa::ir::types::Type as SsaType;
Expand Down Expand Up @@ -847,8 +847,9 @@ impl AcirContext {
}

/// Terminates the context and takes the resulting `GeneratedAcir`
pub(crate) fn finish(mut self, inputs: Vec<u32>) -> GeneratedAcir {
pub(crate) fn finish(mut self, inputs: Vec<u32>, warnings: Vec<SsaReport>) -> GeneratedAcir {
self.acir_ir.input_witnesses = vecmap(inputs, Witness);
self.acir_ir.warnings = warnings;
self.acir_ir
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

use crate::{
brillig::{brillig_gen::brillig_directive, brillig_ir::artifact::GeneratedBrillig},
errors::{InternalError, RuntimeError},
errors::{InternalError, RuntimeError, SsaReport},
ssa::ir::dfg::CallStack,
};

Expand Down Expand Up @@ -53,6 +53,8 @@

/// Correspondence between an opcode index and the error message associated with it.
pub(crate) assert_messages: BTreeMap<OpcodeLocation, String>,

pub(crate) warnings: Vec<SsaReport>,
}

impl GeneratedAcir {
Expand Down Expand Up @@ -616,7 +618,7 @@
// we now have lhs+offset <= rhs <=> lhs_offset <= rhs_offset

let bit_size = bit_size_u128(rhs_offset);
// r = 2^bit_size - rhs_offset -1, is of bit size 'bit_size' by construtction

Check warning on line 621 in compiler/noirc_evaluator/src/ssa/acir_gen/acir_ir/generated_acir.rs

View workflow job for this annotation

GitHub Actions / Spellcheck / Spellcheck

Unknown word (construtction)
let r = (1_u128 << bit_size) - rhs_offset - 1;
// however, since it is a constant, we can compute it's actual bit size
let r_bit_size = bit_size_u128(r);
Expand Down
26 changes: 13 additions & 13 deletions compiler/noirc_evaluator/src/ssa/acir_gen/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@
use crate::brillig::brillig_ir::artifact::GeneratedBrillig;
use crate::brillig::brillig_ir::BrilligContext;
use crate::brillig::{brillig_gen::brillig_fn::FunctionContext as BrilligFunctionContext, Brillig};
use crate::errors::{InternalError, RuntimeError};
use crate::errors::{InternalError, InternalWarning, RuntimeError, SsaReport};
pub(crate) use acir_ir::generated_acir::GeneratedAcir;
use acvm::{
acir::{circuit::opcodes::BlockId, native_types::Expression},
Expand Down Expand Up @@ -201,9 +201,9 @@
self.convert_ssa_instruction(*instruction_id, dfg, ssa, &brillig, last_array_uses)?;
}

self.convert_ssa_return(entry_block.unwrap_terminator(), dfg)?;
let warnings = self.convert_ssa_return(entry_block.unwrap_terminator(), dfg)?;

Ok(self.acir_context.finish(input_witness.collect()))
Ok(self.acir_context.finish(input_witness.collect(), warnings))
}

fn convert_brillig_main(
Expand Down Expand Up @@ -240,7 +240,7 @@
self.acir_context.return_var(acir_var)?;
}

Ok(self.acir_context.finish(witness_inputs))
Ok(self.acir_context.finish(witness_inputs, Vec::new()))
}

/// Adds and binds `AcirVar`s for each numeric block parameter or block parameter array element.
Expand Down Expand Up @@ -836,7 +836,7 @@
// Read the value from the array at the specified index
let read = self.acir_context.read_from_memory(block_id, var_index)?;

// Incremement the var_index in case of a nested array

Check warning on line 839 in compiler/noirc_evaluator/src/ssa/acir_gen/mod.rs

View workflow job for this annotation

GitHub Actions / Spellcheck / Spellcheck

Unknown word (Incremement)
*var_index = self.acir_context.add_var(*var_index, one)?;

let typ = AcirType::NumericType(numeric_type);
Expand Down Expand Up @@ -947,7 +947,7 @@
AcirValue::Var(store_var, _) => {
// Write the new value into the new array at the specified index
self.acir_context.write_to_memory(block_id, var_index, &store_var)?;
// Incremement the var_index in case of a nested array

Check warning on line 950 in compiler/noirc_evaluator/src/ssa/acir_gen/mod.rs

View workflow job for this annotation

GitHub Actions / Spellcheck / Spellcheck

Unknown word (Incremement)
*var_index = self.acir_context.add_var(*var_index, one)?;
}
AcirValue::Array(values) => {
Expand Down Expand Up @@ -1247,8 +1247,8 @@
&mut self,
terminator: &TerminatorInstruction,
dfg: &DataFlowGraph,
) -> Result<(), InternalError> {
let (return_values, _call_stack) = match terminator {
) -> Result<Vec<SsaReport>, InternalError> {
let (return_values, call_stack) = match terminator {
TerminatorInstruction::Return { return_values, call_stack } => {
(return_values, call_stack)
}
Expand All @@ -1258,16 +1258,16 @@
// The return value may or may not be an array reference. Calling `flatten_value_list`
// will expand the array if there is one.
let return_acir_vars = self.flatten_value_list(return_values, dfg);
let mut warnings = Vec::new();
for acir_var in return_acir_vars {
// TODO(Guillaume) -- disabled as it has shown to break
// TODO with important programs. We will add it back once
// TODO we change it to a warning.
// if self.acir_context.is_constant(&acir_var) {
// return Err(InternalError::ReturnConstant { call_stack: call_stack.clone() });
// }
if self.acir_context.is_constant(&acir_var) {
warnings.push(SsaReport::Warning(InternalWarning::ReturnConstant {
call_stack: call_stack.clone(),
}));
}
self.acir_context.return_var(acir_var)?;
}
Ok(())
Ok(warnings)
}

/// Gets the cached `AcirVar` that was converted from the corresponding `ValueId`. If it does
Expand Down
2 changes: 1 addition & 1 deletion tooling/nargo/src/ops/test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ pub fn run_test<B: BlackBoxFunctionSolver>(
) -> TestStatus {
let program = compile_no_check(context, config, test_function.get_id(), None, false);
match program {
Ok(program) => {
Ok((program, _)) => {
// Run the backend to ensure the PWG evaluates functions like std::hash::pedersen,
// otherwise constraints involving these expressions will not error.
let circuit_execution =
Expand Down
Loading