Skip to content

Commit

Permalink
Add final lookup constraint.
Browse files Browse the repository at this point in the history
  • Loading branch information
alonh5 committed Jun 23, 2024
1 parent 8320e79 commit 9061e0b
Show file tree
Hide file tree
Showing 2 changed files with 84 additions and 22 deletions.
31 changes: 28 additions & 3 deletions crates/prover/src/examples/wide_fibonacci/component.rs
Original file line number Diff line number Diff line change
Expand Up @@ -88,13 +88,14 @@ impl WideFibComponent {
}
}

fn evaluate_lookup_boundary_constraint_at_point(
fn evaluate_lookup_boundary_constraints_at_point(
&self,
point: CirclePoint<SecureField>,
mask: &ColumnVec<Vec<SecureField>>,
evaluation_accumulator: &mut PointEvaluationAccumulator,
constraint_zero_domain: Coset,
interaction_elements: &InteractionElements,
lookup_values: &LookupValues,
) {
let (alpha, z) = (interaction_elements[ALPHA_ID], interaction_elements[Z_ID]);
let value =
Expand All @@ -110,6 +111,29 @@ impl WideFibComponent {
- shifted_secure_combination(&[mask[0][0], mask[1][0]], alpha, z);
let denom = point_vanishing(constraint_zero_domain.at(0), point);
evaluation_accumulator.accumulate(numerator / denom);

let numerator = (value
* shifted_secure_combination(
&[
lookup_values[LOOKUP_VALUE_N_MINUS_2_ID],
lookup_values[LOOKUP_VALUE_N_MINUS_1_ID],
],
alpha,
z,
))
- shifted_secure_combination(
&[
lookup_values[LOOKUP_VALUE_0_ID],
lookup_values[LOOKUP_VALUE_1_ID],
],
alpha,
z,
);
let denom = point_vanishing(
constraint_zero_domain.at(constraint_zero_domain.size()),
point,
);
evaluation_accumulator.accumulate(numerator / denom);
}

fn evaluate_lookup_step_constraints_at_point(
Expand Down Expand Up @@ -154,7 +178,7 @@ impl Air for WideFibAir {

impl Component for WideFibComponent {
fn n_constraints(&self) -> usize {
self.n_columns() + 4
self.n_columns() + 5
}

fn max_constraint_log_degree_bound(&self) -> u32 {
Expand Down Expand Up @@ -210,12 +234,13 @@ impl Component for WideFibComponent {
constraint_zero_domain,
interaction_elements,
);
self.evaluate_lookup_boundary_constraint_at_point(
self.evaluate_lookup_boundary_constraints_at_point(
point,
mask,
evaluation_accumulator,
constraint_zero_domain,
interaction_elements,
lookup_values,
);
self.evaluate_trace_step_constraints_at_point(
point,
Expand Down
75 changes: 56 additions & 19 deletions crates/prover/src/examples/wide_fibonacci/constraint_eval.rs
Original file line number Diff line number Diff line change
Expand Up @@ -94,14 +94,14 @@ impl WideFibComponent {

#[allow(clippy::needless_range_loop)]
for i in 0..trace_eval_domain.size() {
first_point_numerators[i] = accum.random_coeff_powers[self.n_columns() + 3]
first_point_numerators[i] = accum.random_coeff_powers[self.n_columns() + 4]
* (trace_evals[0][0][i] - lookup_values[LOOKUP_VALUE_0_ID])
+ accum.random_coeff_powers[self.n_columns() + 2]
+ accum.random_coeff_powers[self.n_columns() + 3]
* (trace_evals[0][1][i] - lookup_values[LOOKUP_VALUE_1_ID]);
last_point_numerators[i] = accum.random_coeff_powers[self.n_columns() + 1]
last_point_numerators[i] = accum.random_coeff_powers[self.n_columns() + 2]
* (trace_evals[0][self.n_columns() - 2][i]
- lookup_values[LOOKUP_VALUE_N_MINUS_2_ID])
+ accum.random_coeff_powers[self.n_columns()]
+ accum.random_coeff_powers[self.n_columns() + 1]
* (trace_evals[0][self.n_columns() - 1][i]
- lookup_values[LOOKUP_VALUE_N_MINUS_1_ID]);
}
Expand Down Expand Up @@ -151,23 +151,30 @@ impl WideFibComponent {
}
}

fn evaluate_lookup_boundary_constraint(
fn evaluate_lookup_boundary_constraints(
&self,
trace_evals: &TreeVec<Vec<&CircleEvaluation<CpuBackend, BaseField, BitReversedOrder>>>,
trace_eval_domain: CircleDomain,
zero_domain: Coset,
accum: &mut ColumnAccumulator<'_, CpuBackend>,
interaction_elements: &InteractionElements,
lookup_values: &LookupValues,
) {
let max_constraint_degree = self.max_constraint_log_degree_bound();
let mut denoms = vec![];
let mut first_point_denoms = vec![];
let mut last_point_denoms = vec![];
for point in trace_eval_domain.iter() {
denoms.push(point_vanishing(zero_domain.at(0), point));
first_point_denoms.push(point_vanishing(zero_domain.at(0), point));
last_point_denoms.push(point_vanishing(zero_domain.at(zero_domain.size()), point));
}
bit_reverse(&mut denoms);
let mut denom_inverses = vec![BaseField::zero(); 1 << (max_constraint_degree)];
BaseField::batch_inverse(&denoms, &mut denom_inverses);
let mut numerators = vec![SecureField::zero(); 1 << (max_constraint_degree)];
bit_reverse(&mut first_point_denoms);
bit_reverse(&mut last_point_denoms);
let mut first_point_denom_inverses = vec![BaseField::zero(); 1 << (max_constraint_degree)];
let mut last_point_denom_inverses = vec![BaseField::zero(); 1 << (max_constraint_degree)];
BaseField::batch_inverse(&first_point_denoms, &mut first_point_denom_inverses);
BaseField::batch_inverse(&last_point_denoms, &mut last_point_denom_inverses);
let mut first_point_numerators = vec![SecureField::zero(); 1 << (max_constraint_degree)];
let mut last_point_numerators = vec![SecureField::zero(); 1 << (max_constraint_degree)];
let (alpha, z) = (interaction_elements[ALPHA_ID], interaction_elements[Z_ID]);

#[allow(clippy::needless_range_loop)]
Expand All @@ -176,7 +183,7 @@ impl WideFibComponent {
SecureCirclePoly::<CpuBackend>::eval_from_partial_evals(std::array::from_fn(|j| {
trace_evals[1][j][i].into()
}));
numerators[i] = accum.random_coeff_powers[self.n_columns() - 2]
first_point_numerators[i] = accum.random_coeff_powers[self.n_columns() - 1]
* ((value
* shifted_secure_combination(
&[
Expand All @@ -191,8 +198,37 @@ impl WideFibComponent {
alpha,
z,
));
last_point_numerators[i] = accum.random_coeff_powers[self.n_columns() - 2]
* ((value
* shifted_secure_combination(
&[
lookup_values[LOOKUP_VALUE_N_MINUS_2_ID],
lookup_values[LOOKUP_VALUE_N_MINUS_1_ID],
],
alpha,
z,
))
- shifted_secure_combination(
&[
lookup_values[LOOKUP_VALUE_0_ID],
lookup_values[LOOKUP_VALUE_1_ID],
],
alpha,
z,
));
}
for (i, (num, denom_inverse)) in numerators.iter().zip(denom_inverses.iter()).enumerate() {
for (i, (num, denom_inverse)) in first_point_numerators
.iter()
.zip(first_point_denom_inverses.iter())
.enumerate()
{
accum.accumulate(i, *num * *denom_inverse);
}
for (i, (num, denom_inverse)) in last_point_numerators
.iter()
.zip(last_point_denom_inverses.iter())
.enumerate()
{
accum.accumulate(i, *num * *denom_inverse);
}
}
Expand Down Expand Up @@ -230,7 +266,7 @@ impl WideFibComponent {
SecureCirclePoly::<CpuBackend>::eval_from_partial_evals(std::array::from_fn(|j| {
trace_evals[1][j][prev_index].into()
}));
numerators[i] = accum.random_coeff_powers[self.n_columns() - 1]
numerators[i] = accum.random_coeff_powers[self.n_columns()]
* ((value
* shifted_secure_combination(
&[
Expand Down Expand Up @@ -275,26 +311,27 @@ impl ComponentProver<CpuBackend> for WideFibComponent {
&mut accum,
lookup_values,
);
self.evaluate_trace_step_constraints(
self.evaluate_lookup_step_constraints(
trace_evals,
trace_eval_domain,
zero_domain,
&mut accum,
interaction_elements,
);
self.evaluate_lookup_boundary_constraint(
self.evaluate_lookup_boundary_constraints(
trace_evals,
trace_eval_domain,
zero_domain,
&mut accum,
interaction_elements,
lookup_values,
);
self.evaluate_lookup_step_constraints(
self.evaluate_trace_step_constraints(
trace_evals,
trace_eval_domain,
zero_domain,
&mut accum,
interaction_elements,
)
);
}

fn lookup_values(&self, trace: &ComponentTrace<'_, CpuBackend>) -> LookupValues {
Expand Down

0 comments on commit 9061e0b

Please sign in to comment.