diff --git a/src/circuit.rs b/src/circuit.rs index 903cd86..2df473d 100644 --- a/src/circuit.rs +++ b/src/circuit.rs @@ -146,12 +146,13 @@ pub trait Layouter { /// closure, the `Layouter` is allowed to optimise as it sees fit. /// /// ```ignore - /// fn assign_region(&mut self, |region| { + /// fn assign_region(&mut self, || "region name", |region| { /// region.assign_advice(self.config.a, offset, || { Some(value)}); /// }); /// ``` - fn assign_region( - &mut self, - assignment: impl FnMut(Region<'_, C>) -> Result<(), Error>, - ) -> Result<(), Error>; + fn assign_region(&mut self, name: N, assignment: A) -> Result<(), Error> + where + A: FnMut(Region<'_, C>) -> Result<(), Error>, + N: Fn() -> NR, + NR: Into; } diff --git a/src/circuit/layouter.rs b/src/circuit/layouter.rs index fcd8155..f1c4a0e 100644 --- a/src/circuit/layouter.rs +++ b/src/circuit/layouter.rs @@ -104,10 +104,12 @@ impl<'a, C: Chip, CS: Assignment + 'a> Layouter for SingleChip<'a, &self.config } - fn assign_region( - &mut self, - mut assignment: impl FnMut(Region<'_, C>) -> Result<(), Error>, - ) -> Result<(), Error> { + fn assign_region(&mut self, name: N, mut assignment: A) -> Result<(), Error> + where + A: FnMut(Region<'_, C>) -> Result<(), Error>, + N: Fn() -> NR, + NR: Into, + { let region_index = self.regions.len(); // Get shape of the region. @@ -130,11 +132,13 @@ impl<'a, C: Chip, CS: Assignment + 'a> Layouter for SingleChip<'a, self.columns.insert(column, region_start + shape.row_count); } + self.cs.enter_region(name); let mut region = SingleChipRegion::new(self, region_index); { let region: &mut dyn RegionLayouter = &mut region; assignment(region.into())?; } + self.cs.exit_region(); Ok(()) } diff --git a/src/dev.rs b/src/dev.rs index 7cd2208..18058f7 100644 --- a/src/dev.rs +++ b/src/dev.rs @@ -147,6 +147,15 @@ pub struct MockProver { } impl Assignment for MockProver { + fn enter_region(&mut self, _: N) + where + NR: Into, + N: FnOnce() -> NR, + { + } + + fn exit_region(&mut self) {} + fn assign_advice( &mut self, _: A, diff --git a/src/plonk/circuit.rs b/src/plonk/circuit.rs index d0ae0a2..4616d9e 100644 --- a/src/plonk/circuit.rs +++ b/src/plonk/circuit.rs @@ -126,6 +126,27 @@ impl TryFrom> for Column { /// This trait allows a [`Circuit`] to direct some backend to assign a witness /// for a constraint system. pub trait Assignment { + /// Creates a new region and enters into it. + /// + /// Panics if we are currently in a region (if `exit_region` was not called). + /// + /// Not intended for downstream consumption; use [`Layouter::assign_region`] instead. + /// + /// [`Layouter::assign_region`]: crate::circuit::Layouter#method.assign_region + fn enter_region(&mut self, name_fn: N) + where + NR: Into, + N: FnOnce() -> NR; + + /// Exits the current region. + /// + /// Panics if we are not currently in a region (if `enter_region` was not called). + /// + /// Not intended for downstream consumption; use [`Layouter::assign_region`] instead. + /// + /// [`Layouter::assign_region`]: crate::circuit::Layouter#method.assign_region + fn exit_region(&mut self); + /// Assign an advice column value (witness) fn assign_advice( &mut self, diff --git a/src/plonk/keygen.rs b/src/plonk/keygen.rs index bb1e388..885a3a9 100644 --- a/src/plonk/keygen.rs +++ b/src/plonk/keygen.rs @@ -64,6 +64,18 @@ struct Assembly { } impl Assignment for Assembly { + fn enter_region(&mut self, _: N) + where + NR: Into, + N: FnOnce() -> NR, + { + // Do nothing; we don't care about regions in this context. + } + + fn exit_region(&mut self) { + // Do nothing; we don't care about regions in this context. + } + fn assign_advice( &mut self, _: A, diff --git a/src/plonk/prover.rs b/src/plonk/prover.rs index 5f7d830..ed230a1 100644 --- a/src/plonk/prover.rs +++ b/src/plonk/prover.rs @@ -100,6 +100,18 @@ pub fn create_proof, ConcreteCircuit: Circ } impl Assignment for WitnessCollection { + fn enter_region(&mut self, _: N) + where + NR: Into, + N: FnOnce() -> NR, + { + // Do nothing; we don't care about regions in this context. + } + + fn exit_region(&mut self) { + // Do nothing; we don't care about regions in this context. + } + fn assign_advice( &mut self, _: A,