From 2bbf73363b97bd407ac69e100ebba15dc2245f34 Mon Sep 17 00:00:00 2001 From: guorong009 Date: Wed, 18 Sep 2024 18:16:13 +0800 Subject: [PATCH 1/2] feat: add "WitnessMissing" variant to "AssignmentError" --- halo2_frontend/src/circuit.rs | 12 +++++++++++- halo2_frontend/src/dev.rs | 19 ++++++++++++++++--- halo2_frontend/src/plonk/error.rs | 5 +++++ halo2_frontend/src/plonk/keygen.rs | 27 +++++++++++++++++++++++---- 4 files changed, 55 insertions(+), 8 deletions(-) diff --git a/halo2_frontend/src/circuit.rs b/halo2_frontend/src/circuit.rs index 48cbc4c095..f31af42764 100644 --- a/halo2_frontend/src/circuit.rs +++ b/halo2_frontend/src/circuit.rs @@ -198,11 +198,21 @@ impl<'a, F: Field> Assignment for WitnessCollection<'a, F> { })); } + let value = match to().into_field().assign() { + Ok(v) => v, + Err(_) => { + return Err(Error::AssignmentError(AssignmentError::WitnessMissing { + func: "assign_advice".to_string(), + desc: desc().into(), + })) + } + }; + *self .advice .get_mut(column.index()) .and_then(|v| v.get_mut(row)) - .ok_or(Error::BoundsFailure)? = to().into_field().assign()?; + .ok_or(Error::BoundsFailure)? = value; Ok(()) } diff --git a/halo2_frontend/src/dev.rs b/halo2_frontend/src/dev.rs index e08690d267..b34e4c40d6 100644 --- a/halo2_frontend/src/dev.rs +++ b/halo2_frontend/src/dev.rs @@ -504,11 +504,14 @@ impl Assignment for MockProver { .expect("bounds failure"); *value = CellValue::Assigned(to); } - Err(err) => { + Err(_) => { // Propagate `assign` error if the column is in current phase. let phase = self.cs.advice_column_phase[column.index]; if self.in_phase(phase) { - return Err(err); + return Err(Error::AssignmentError(AssignmentError::WitnessMissing { + func: "assign_advice".to_string(), + desc: desc().into(), + })); } } } @@ -552,11 +555,21 @@ impl Assignment for MockProver { .or_default(); } + let value = match to().into_field().evaluate().assign() { + Ok(v) => CellValue::Assigned(v), + Err(_) => { + return Err(Error::AssignmentError(AssignmentError::WitnessMissing { + func: "assign_fixed".to_string(), + desc: desc().into(), + })) + } + }; + *self .fixed .get_mut(column.index()) .and_then(|v| v.get_mut(row)) - .expect("bounds failure") = CellValue::Assigned(to().into_field().evaluate().assign()?); + .expect("bounds failure") = value; Ok(()) } diff --git a/halo2_frontend/src/plonk/error.rs b/halo2_frontend/src/plonk/error.rs index 89f2e97097..1a2f40ab6b 100644 --- a/halo2_frontend/src/plonk/error.rs +++ b/halo2_frontend/src/plonk/error.rs @@ -154,6 +154,10 @@ pub enum AssignmentError { usable_rows: (usize, usize), k: u32, }, + WitnessMissing { + func: String, + desc: String, + }, } impl fmt::Display for AssignmentError { @@ -219,6 +223,7 @@ impl fmt::Display for AssignmentError { start, end, k, ), + AssignmentError::WitnessMissing { func, desc } => write!(f, "witness missing/unknown when {} `{}`", func, desc), } } } diff --git a/halo2_frontend/src/plonk/keygen.rs b/halo2_frontend/src/plonk/keygen.rs index 8e9b829033..809f6ca94d 100644 --- a/halo2_frontend/src/plonk/keygen.rs +++ b/halo2_frontend/src/plonk/keygen.rs @@ -5,7 +5,8 @@ use halo2_middleware::ff::Field; use crate::circuit::Value; use crate::plonk::{ - permutation, Advice, Assigned, Assignment, Challenge, Column, Error, Fixed, Instance, Selector, + permutation, Advice, Assigned, Assignment, AssignmentError, Challenge, Column, Error, Fixed, + Instance, Selector, }; /// Assembly to be used in circuit synthesis. @@ -75,7 +76,7 @@ impl Assignment for Assembly { fn assign_fixed( &mut self, - _: A, + desc: A, column: Column, row: usize, to: V, @@ -90,11 +91,21 @@ impl Assignment for Assembly { return Err(Error::not_enough_rows_available(self.k)); } + let value = match to().into_field().assign() { + Ok(v) => v, + Err(_) => { + return Err(Error::AssignmentError(AssignmentError::WitnessMissing { + func: "assign_fixed".to_string(), + desc: desc().into(), + })) + } + }; + *self .fixed .get_mut(column.index()) .and_then(|v| v.get_mut(row)) - .ok_or(Error::BoundsFailure)? = to().into_field().assign()?; + .ok_or(Error::BoundsFailure)? = value; Ok(()) } @@ -129,7 +140,15 @@ impl Assignment for Assembly { .get_mut(column.index()) .ok_or(Error::BoundsFailure)?; - let filler = to.assign()?; + let filler = match to.assign() { + Ok(v) => v, + Err(_) => { + return Err(Error::AssignmentError(AssignmentError::WitnessMissing { + func: "fill_from_row".to_string(), + desc: "".to_string(), + })) + } + }; for row in self.usable_rows.clone().skip(from_row) { col[row] = filler; } From 4ffff57d53fafac161ee205a9944db0608e9427d Mon Sep 17 00:00:00 2001 From: guorong009 Date: Wed, 18 Sep 2024 18:18:00 +0800 Subject: [PATCH 2/2] feat: rename "AssignmentError" as "AssignError" --- halo2_frontend/src/circuit.rs | 8 ++++---- halo2_frontend/src/dev.rs | 18 +++++++++--------- halo2_frontend/src/plonk/error.rs | 26 +++++++++++++------------- halo2_frontend/src/plonk/keygen.rs | 6 +++--- 4 files changed, 29 insertions(+), 29 deletions(-) diff --git a/halo2_frontend/src/circuit.rs b/halo2_frontend/src/circuit.rs index f31af42764..cef77072da 100644 --- a/halo2_frontend/src/circuit.rs +++ b/halo2_frontend/src/circuit.rs @@ -1,6 +1,6 @@ //! Traits and structs for implementing circuit components. -use crate::plonk::{self, AssignmentError}; +use crate::plonk::{self, AssignError}; use crate::plonk::{ permutation, sealed::{self, SealedPhase}, @@ -154,7 +154,7 @@ impl<'a, F: Field> Assignment for WitnessCollection<'a, F> { fn query_instance(&self, column: Column, row: usize) -> Result, Error> { if !self.usable_rows.contains(&row) { - return Err(Error::AssignmentError(AssignmentError::QueryInstance { + return Err(Error::AssignError(AssignError::QueryInstance { col: column.into(), row, usable_rows: (0, self.usable_rows.end), @@ -189,7 +189,7 @@ impl<'a, F: Field> Assignment for WitnessCollection<'a, F> { } if !self.usable_rows.contains(&row) { - return Err(Error::AssignmentError(AssignmentError::AssignAdvice { + return Err(Error::AssignError(AssignError::AssignAdvice { desc: desc().into(), col: column.into(), row, @@ -201,7 +201,7 @@ impl<'a, F: Field> Assignment for WitnessCollection<'a, F> { let value = match to().into_field().assign() { Ok(v) => v, Err(_) => { - return Err(Error::AssignmentError(AssignmentError::WitnessMissing { + return Err(Error::AssignError(AssignError::WitnessMissing { func: "assign_advice".to_string(), desc: desc().into(), })) diff --git a/halo2_frontend/src/dev.rs b/halo2_frontend/src/dev.rs index b34e4c40d6..cbdaff6aaa 100644 --- a/halo2_frontend/src/dev.rs +++ b/halo2_frontend/src/dev.rs @@ -7,7 +7,7 @@ use std::ops::{Add, Mul, Neg, Range}; use blake2b_simd::blake2b; -use crate::plonk::AssignmentError; +use crate::plonk::AssignError; use crate::{ circuit, plonk::{ @@ -415,7 +415,7 @@ impl Assignment for MockProver { } if !self.usable_rows.contains(&row) { - return Err(Error::AssignmentError(AssignmentError::EnableSelector { + return Err(Error::AssignError(AssignError::EnableSelector { desc: desc().into(), selector: *selector, row, @@ -445,7 +445,7 @@ impl Assignment for MockProver { row: usize, ) -> Result, Error> { if !self.usable_rows.contains(&row) { - return Err(Error::AssignmentError(AssignmentError::QueryInstance { + return Err(Error::AssignError(AssignError::QueryInstance { col: column.into(), row, usable_rows: (self.usable_rows.start, self.usable_rows.end), @@ -476,7 +476,7 @@ impl Assignment for MockProver { { if self.in_phase(FirstPhase) { if !self.usable_rows.contains(&row) { - return Err(Error::AssignmentError(AssignmentError::AssignAdvice { + return Err(Error::AssignError(AssignError::AssignAdvice { desc: desc().into(), col: column.into(), row, @@ -508,7 +508,7 @@ impl Assignment for MockProver { // Propagate `assign` error if the column is in current phase. let phase = self.cs.advice_column_phase[column.index]; if self.in_phase(phase) { - return Err(Error::AssignmentError(AssignmentError::WitnessMissing { + return Err(Error::AssignError(AssignError::WitnessMissing { func: "assign_advice".to_string(), desc: desc().into(), })); @@ -537,7 +537,7 @@ impl Assignment for MockProver { } if !self.usable_rows.contains(&row) { - return Err(Error::AssignmentError(AssignmentError::AssignFixed { + return Err(Error::AssignError(AssignError::AssignFixed { desc: desc().into(), col: column.into(), row, @@ -558,7 +558,7 @@ impl Assignment for MockProver { let value = match to().into_field().evaluate().assign() { Ok(v) => CellValue::Assigned(v), Err(_) => { - return Err(Error::AssignmentError(AssignmentError::WitnessMissing { + return Err(Error::AssignError(AssignError::WitnessMissing { func: "assign_fixed".to_string(), desc: desc().into(), })) @@ -586,7 +586,7 @@ impl Assignment for MockProver { } if !self.usable_rows.contains(&left_row) || !self.usable_rows.contains(&right_row) { - return Err(Error::AssignmentError(AssignmentError::Copy { + return Err(Error::AssignError(AssignError::Copy { left_col: left_column, left_row, right_col: right_column, @@ -611,7 +611,7 @@ impl Assignment for MockProver { } if !self.usable_rows.contains(&from_row) { - return Err(Error::AssignmentError(AssignmentError::FillFromRow { + return Err(Error::AssignError(AssignError::FillFromRow { col: col.into(), from_row, usable_rows: (self.usable_rows.start, self.usable_rows.end), diff --git a/halo2_frontend/src/plonk/error.rs b/halo2_frontend/src/plonk/error.rs index 1a2f40ab6b..61bee86750 100644 --- a/halo2_frontend/src/plonk/error.rs +++ b/halo2_frontend/src/plonk/error.rs @@ -6,7 +6,7 @@ use halo2_middleware::circuit::Any; /// This is an error that could occur during circuit synthesis. /// -/// **NOTE**: [`AssignmentError`] is introduced to provide more debugging info +/// **NOTE**: [`AssignError`] is introduced to provide more debugging info /// to developers when assigning witnesses to circuit cells. /// Hence, they are used for [`MockProver`] and [`WitnessCollection`]. /// The [`keygen`] process use the [`NotEnoughRowsAvailable`], since it is just enough. @@ -32,8 +32,8 @@ pub enum Error { ColumnNotInPermutation(Column), /// An error relating to a lookup table. TableError(TableError), - /// An error relating to an `Assignment`. - AssignmentError(AssignmentError), + /// An error relating to a circuit assignment. + AssignError(AssignError), /// Generic error not covered by previous cases Other(String), } @@ -65,7 +65,7 @@ impl fmt::Display for Error { "Column {column:?} must be included in the permutation. Help: try applying `meta.enable_equalty` on the column", ), Error::TableError(error) => write!(f, "{error}"), - Error::AssignmentError(error) => write!(f, "{error}"), + Error::AssignError(error) => write!(f, "{error}"), Error::Other(error) => write!(f, "Other: {error}"), } } @@ -112,7 +112,7 @@ impl fmt::Display for TableError { /// This is an error that could occur during `assign_advice`, `assign_fixed`, `copy`, etc. #[derive(Debug)] -pub enum AssignmentError { +pub enum AssignError { AssignAdvice { desc: String, col: Column, @@ -160,10 +160,10 @@ pub enum AssignmentError { }, } -impl fmt::Display for AssignmentError { +impl fmt::Display for AssignError { fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { match self { - AssignmentError::AssignAdvice { desc, col, row, usable_rows:(start, end), k } => write!( + AssignError::AssignAdvice { desc, col, row, usable_rows:(start, end), k } => write!( f, "assign_advice `{}` error: column={:?}({}), row={}, usable_rows={}..{}, k={}", desc, @@ -173,7 +173,7 @@ impl fmt::Display for AssignmentError { start, end, k, ), - AssignmentError::AssignFixed {desc, col, row, usable_rows: (start, end), k } => write!( + AssignError::AssignFixed {desc, col, row, usable_rows: (start, end), k } => write!( f, "assign_fixed `{}` error: column={:?}({}), row={}, usable_rows={}..{}, k={}", desc, @@ -183,7 +183,7 @@ impl fmt::Display for AssignmentError { start, end, k, ), - AssignmentError::EnableSelector { desc, selector, row, usable_rows: (start, end), k } => write!( + AssignError::EnableSelector { desc, selector, row, usable_rows: (start, end), k } => write!( f, "enable_selector `{}` error: column=Selector({:?}), row={}, usable_rows={}..{}, k={}", desc, @@ -192,7 +192,7 @@ impl fmt::Display for AssignmentError { start, end, k, ), - AssignmentError::QueryInstance { col, row, usable_rows:(start, end), k } => write!( + AssignError::QueryInstance { col, row, usable_rows:(start, end), k } => write!( f, "query_instance error: column={:?}({}), row={}, usable_rows={}..{}, k={}", col.column_type, @@ -202,7 +202,7 @@ impl fmt::Display for AssignmentError { end, k, ), - AssignmentError::Copy { left_col, left_row, right_col, right_row, usable_rows:(start, end), k } => write!( + AssignError::Copy { left_col, left_row, right_col, right_row, usable_rows:(start, end), k } => write!( f, "copy error: left_column={:?}({}), left_row={}, right_column={:?}({}), right_row={}, usable_rows={}..{}, k={}", left_col.column_type(), @@ -214,7 +214,7 @@ impl fmt::Display for AssignmentError { start, end, k, ), - AssignmentError::FillFromRow { col, from_row, usable_rows:(start, end), k } => write!( + AssignError::FillFromRow { col, from_row, usable_rows:(start, end), k } => write!( f, "fill_from_row error: column={:?}({}), from_row={}, usable_rows={}..{}, k={}", col.column_type(), @@ -223,7 +223,7 @@ impl fmt::Display for AssignmentError { start, end, k, ), - AssignmentError::WitnessMissing { func, desc } => write!(f, "witness missing/unknown when {} `{}`", func, desc), + AssignError::WitnessMissing { func, desc } => write!(f, "witness missing/unknown when {} `{}`", func, desc), } } } diff --git a/halo2_frontend/src/plonk/keygen.rs b/halo2_frontend/src/plonk/keygen.rs index 809f6ca94d..e7afe30349 100644 --- a/halo2_frontend/src/plonk/keygen.rs +++ b/halo2_frontend/src/plonk/keygen.rs @@ -5,7 +5,7 @@ use halo2_middleware::ff::Field; use crate::circuit::Value; use crate::plonk::{ - permutation, Advice, Assigned, Assignment, AssignmentError, Challenge, Column, Error, Fixed, + permutation, Advice, AssignError, Assigned, Assignment, Challenge, Column, Error, Fixed, Instance, Selector, }; @@ -94,7 +94,7 @@ impl Assignment for Assembly { let value = match to().into_field().assign() { Ok(v) => v, Err(_) => { - return Err(Error::AssignmentError(AssignmentError::WitnessMissing { + return Err(Error::AssignError(AssignError::WitnessMissing { func: "assign_fixed".to_string(), desc: desc().into(), })) @@ -143,7 +143,7 @@ impl Assignment for Assembly { let filler = match to.assign() { Ok(v) => v, Err(_) => { - return Err(Error::AssignmentError(AssignmentError::WitnessMissing { + return Err(Error::AssignError(AssignError::WitnessMissing { func: "fill_from_row".to_string(), desc: "".to_string(), }))