pub struct ValueTable<Data = Vec<Word>> { /* private fields */ }Expand description
The witness for a batch of 2^k independent instances of one circuit, in wire-major order.
Each wire’s values across all instances are grouped together, one wire per row (wire-major):
instance 0 instance 1 ... instance K-1
wire 0 [ w | w | ... | w ] <- one row
wire 1 [ w | w | ... | w ]
...Each row is one wire and each column is one instance. So a batched interpreter can advance every instance of a wire in a single pass.
This is the batched counterpart of ValueVec: one instance read back out with
Self::instance_value_vec is bit-for-bit the value vector populating that instance on its own
would produce.
This table is specialized for the M4 accelerator setting, where the value vector splits with
the inout values on the hidden side (InoutSegment::Hidden):
- Inout wires are committed. Every instance chooses its own inout words, so they are not one set of shared values a verifier can evaluate. They are committed with the private values instead, at the front of the hidden segment.
- Constants are not stored. The constants live once on the constraint system as a
Vec<Word>, not replicated per instance. Only the hidden segment — the inout, witness and internal words — is stored here. Reading an instance back takes the constants as an argument.
So the stored data holds exactly the hidden segment of every instance: n_hidden_words rows by
2^log_instances columns.
The committed inout words are not tied to any value the verifier knows, so the statement a proof over this table makes is that some inout values complete every instance.
Populating one is the circuit frontend’s business, since it takes a circuit to evaluate — see
Circuit::populate_batch.
Data is the buffer backing the words. It defaults to Vec<Word>, but the prover populates
a table straight into a buffer drawn from its pool, so any Deref<Target = [Word]> will do.
Implementations§
Source§impl<Data: Deref<Target = [Word]>> ValueTable<Data>
impl<Data: Deref<Target = [Word]>> ValueTable<Data>
Builds a table from the hidden words of every instance, in wire-major order.
data is what Self::as_words returns: the rows of the hidden segment laid out
contiguously, each holding one wire’s value in every instance. The row count follows from
the layout, so it is not passed separately.
This is the seam the frontend populates through; nothing in this crate can evaluate a circuit to produce the words.
§Panics
Panics if data is not n_hidden_words << log_instances words long.
Sourcepub const fn log_instances(&self) -> usize
pub const fn log_instances(&self) -> usize
The base-2 logarithm of the number of instances.
Sourcepub const fn n_instances(&self) -> usize
pub const fn n_instances(&self) -> usize
The number of instances in the batch.
Sourcepub const fn layout(&self) -> &ValueVecLayout
pub const fn layout(&self) -> &ValueVecLayout
The per-instance value layout shared by every instance.
The number of hidden-word rows per instance, including the protocol’s zero padding.
Sourcepub fn as_words(&self) -> &[Word]
pub fn as_words(&self) -> &[Word]
The whole batch as one flat, wire-major word buffer.
Row r (hidden wire r) occupies data[r << log_instances .. (r + 1) << log_instances],
holding that wire’s value in every instance.
Sourcepub fn instance_value_vec(
&self,
instance: usize,
constants: &[Word],
) -> ValueVec
pub fn instance_value_vec( &self, instance: usize, constants: &[Word], ) -> ValueVec
Reconstructs one instance as a standalone single-instance value vector.
Because the constants are not stored in the table, the caller supplies them (they live on the constraint system). The result is bit-for-bit what populating this instance on its own would produce, so it can be fed directly to single-instance constraint checking.
§Panics
Panics if the index is not below the instance count, or if constants does not match the
layout’s constant count.
Trait Implementations§
Source§impl<Data: Clone> Clone for ValueTable<Data>
impl<Data: Clone> Clone for ValueTable<Data>
Source§fn clone(&self) -> ValueTable<Data>
fn clone(&self) -> ValueTable<Data>
1.0.0 (const: unstable) · Source§fn clone_from(&mut self, source: &Self)
fn clone_from(&mut self, source: &Self)
source. Read moreAuto Trait Implementations§
impl<Data> Freeze for ValueTable<Data>where
Data: Freeze,
impl<Data> RefUnwindSafe for ValueTable<Data>where
Data: RefUnwindSafe,
impl<Data> Send for ValueTable<Data>where
Data: Send,
impl<Data> Sync for ValueTable<Data>where
Data: Sync,
impl<Data> Unpin for ValueTable<Data>where
Data: Unpin,
impl<Data> UnsafeUnpin for ValueTable<Data>where
Data: UnsafeUnpin,
impl<Data> UnwindSafe for ValueTable<Data>where
Data: UnwindSafe,
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
§impl<T> Instrument for T
impl<T> Instrument for T
§fn instrument(self, span: Span) -> Instrumented<Self>
fn instrument(self, span: Span) -> Instrumented<Self>
§fn in_current_span(self) -> Instrumented<Self>
fn in_current_span(self) -> Instrumented<Self>
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read more