p3_sumcheck/jagged/error.rs
1//! Errors returned by the jagged sparse-to-dense reduction.
2
3use thiserror::Error;
4
5use crate::SumcheckError;
6
7/// A malformed sparse layout.
8#[derive(Clone, Debug, Error, PartialEq, Eq)]
9pub enum JaggedLayoutError {
10 /// The layout has no column to address.
11 #[error("a jagged layout needs at least one column")]
12 NoColumns,
13 /// The column count cannot be addressed by a Boolean point.
14 #[error("the jagged column count must be a power of two, got {columns}")]
15 ColumnCountNotPowerOfTwo {
16 /// Number of columns supplied by the caller.
17 columns: usize,
18 },
19 /// The row bound cannot be represented by a machine index.
20 #[error("the row-variable count {variables} does not fit in a machine index")]
21 RowVariablesOverflow {
22 /// Number of row variables supplied by the caller.
23 variables: usize,
24 },
25 /// A live column extends past the declared row space.
26 #[error("column {column} has height {height}, above the row bound {maximum}")]
27 HeightExceedsRowBound {
28 /// Index of the invalid column.
29 column: usize,
30 /// Number of live entries in the invalid column.
31 height: usize,
32 /// Maximum number of rows described by the row variables.
33 maximum: usize,
34 },
35 /// The sum of live column lengths overflowed a machine index.
36 #[error("the jagged trace area overflows a machine index at column {column}")]
37 AreaOverflow {
38 /// Column whose height made the running area overflow.
39 column: usize,
40 },
41 /// The padded dense area cannot be represented by a machine index.
42 #[error("the jagged trace area {area} has no representable power-of-two envelope")]
43 DenseAreaOverflow {
44 /// Sum of all live column lengths.
45 area: usize,
46 },
47 /// The requested envelope arity cannot be represented by a machine index.
48 #[error("an envelope of {variables} variables does not fit in a machine index")]
49 DenseVariablesOverflow {
50 /// Number of envelope variables the floor asks for.
51 variables: usize,
52 },
53}
54
55/// A malformed prover input or rejected jagged proof.
56#[derive(Debug, Error, PartialEq, Eq)]
57pub enum JaggedError {
58 /// The row point does not match the public row bound.
59 #[error("the row point has {actual} coordinates, expected {expected}")]
60 RowPointWidthMismatch {
61 /// Number of coordinates required by the layout.
62 expected: usize,
63 /// Number of coordinates supplied by the caller.
64 actual: usize,
65 },
66 /// The column point cannot address the public column count.
67 #[error("the column point has {actual} coordinates, expected {expected}")]
68 ColumnPointWidthMismatch {
69 /// Number of coordinates required by the layout.
70 expected: usize,
71 /// Number of coordinates supplied by the caller.
72 actual: usize,
73 },
74 /// The dense witness does not fill the power-of-two envelope exactly.
75 #[error("the dense witness has {actual} cells, expected {expected}")]
76 DenseLengthMismatch {
77 /// Envelope size fixed by the layout.
78 expected: usize,
79 /// Number of cells supplied by the prover.
80 actual: usize,
81 },
82 /// The witness does not take the value the caller asked to have proved.
83 #[error("the dense witness does not evaluate to the claimed sparse value")]
84 ClaimMismatch,
85 /// The delegated quadratic sumcheck rejected.
86 #[error(transparent)]
87 Sumcheck(#[from] SumcheckError),
88 /// The terminal product does not equal the sumcheck claim.
89 #[error("the terminal jagged relation is inconsistent")]
90 TerminalMismatch,
91}
92
93/// A trace a jagged geometry cannot read.
94#[derive(Clone, Debug, Error, PartialEq, Eq)]
95pub enum JaggedIngestError {
96 /// The producer supplies a different number of columns than the geometry has.
97 #[error("the trace has {actual} columns, expected {expected}")]
98 ColumnCountMismatch {
99 /// Number of columns the geometry reserves.
100 expected: usize,
101 /// Number of columns the producer supplies.
102 actual: usize,
103 },
104 /// One column supplies a different number of cells than the geometry reserves.
105 #[error("column {column} supplies {actual} cells, expected {expected}")]
106 ColumnHeightMismatch {
107 /// Index of the disagreeing column.
108 column: usize,
109 /// Number of cells the geometry reserves.
110 expected: usize,
111 /// Number of cells the producer supplies.
112 actual: usize,
113 },
114 /// An interleaved column would read past the block it is drawn from.
115 #[error("column {column} needs {required} cells of its block, which holds {available}")]
116 StrideOutOfRange {
117 /// Index of the invalid column.
118 column: usize,
119 /// Position one past the last cell the column reads.
120 required: usize,
121 /// Number of cells in the block.
122 available: usize,
123 },
124 /// An interleaved column declares a step of zero.
125 #[error("column {column} declares a step of zero between its cells")]
126 ZeroStride {
127 /// Index of the invalid column.
128 column: usize,
129 },
130 /// A packed column holds fewer words than its height needs.
131 #[error("column {column} needs {required} packed words and holds {available}")]
132 PackedWordsTooShort {
133 /// Index of the invalid column.
134 column: usize,
135 /// Number of words the height needs.
136 required: usize,
137 /// Number of words the producer supplies.
138 available: usize,
139 },
140 /// A pre-concatenated trace is shorter than the envelope the geometry commits.
141 #[error("the committed vector holds {available} cells and the envelope needs {required}")]
142 CommittedVectorTooShort {
143 /// Size of the envelope.
144 required: usize,
145 /// Number of cells the producer supplies.
146 available: usize,
147 },
148}
149
150/// A sparse claim the dense commitment did not authenticate.
151#[derive(Debug, Error, PartialEq, Eq)]
152pub enum JaggedOpeningError<E> {
153 /// The sparse-to-dense reduction failed.
154 #[error(transparent)]
155 Reduction(#[from] JaggedError),
156 /// The dense commitment scheme failed.
157 #[error("the dense commitment scheme reported {0:?}")]
158 Commitment(E),
159 /// No sparse claim was supplied to discharge.
160 #[error("a jagged opening must carry at least one sparse claim")]
161 NoClaims,
162 /// The proof carries a different number of reductions than there are claims.
163 #[error("the proof carries {actual} reductions for {expected} claims")]
164 ReductionCountMismatch {
165 /// Number of claims the caller stated.
166 expected: usize,
167 /// Number of reductions the proof carries.
168 actual: usize,
169 },
170 /// The dense opening returned a different number of readings than there are claims.
171 #[error("the dense opening returned {actual} readings for {expected} claims")]
172 OpeningCountMismatch {
173 /// Number of claims the caller stated.
174 expected: usize,
175 /// Number of readings the opening returned.
176 actual: usize,
177 },
178 /// One dense reading does not have the shape a claim asked for.
179 #[error("reading {reading} returned {direct} direct and {successor} successor values")]
180 OpeningShape {
181 /// Position of the malformed reading.
182 reading: usize,
183 /// Number of direct readings it returned.
184 direct: usize,
185 /// Number of successor readings it returned.
186 successor: usize,
187 },
188 /// The committed vector does not take a reduced value at its reduced point.
189 #[error("the dense commitment does not carry the value reduction {reading} produced")]
190 DenseMismatch {
191 /// Position of the claim the commitment refused.
192 reading: usize,
193 },
194}