mirror of
https://github.com/logos-storage/plonky2.git
synced 2026-01-05 23:33:07 +00:00
Constrain next row's stack length
This commit is contained in:
parent
a0b2b48992
commit
8beba56903
@ -247,8 +247,8 @@ impl<F: RichField + Extendable<D>, const D: usize> Stark<F, D> for CpuStark<F, D
|
|||||||
pc::eval_packed(local_values, yield_constr);
|
pc::eval_packed(local_values, yield_constr);
|
||||||
push0::eval_packed(local_values, yield_constr);
|
push0::eval_packed(local_values, yield_constr);
|
||||||
shift::eval_packed(local_values, yield_constr);
|
shift::eval_packed(local_values, yield_constr);
|
||||||
simple_logic::eval_packed(local_values, yield_constr);
|
simple_logic::eval_packed(local_values, next_values, yield_constr);
|
||||||
stack::eval_packed(local_values, yield_constr);
|
stack::eval_packed(local_values, next_values, yield_constr);
|
||||||
stack_bounds::eval_packed(local_values, yield_constr);
|
stack_bounds::eval_packed(local_values, yield_constr);
|
||||||
syscalls_exceptions::eval_packed(local_values, next_values, yield_constr);
|
syscalls_exceptions::eval_packed(local_values, next_values, yield_constr);
|
||||||
}
|
}
|
||||||
@ -274,8 +274,8 @@ impl<F: RichField + Extendable<D>, const D: usize> Stark<F, D> for CpuStark<F, D
|
|||||||
pc::eval_ext_circuit(builder, local_values, yield_constr);
|
pc::eval_ext_circuit(builder, local_values, yield_constr);
|
||||||
push0::eval_ext_circuit(builder, local_values, yield_constr);
|
push0::eval_ext_circuit(builder, local_values, yield_constr);
|
||||||
shift::eval_ext_circuit(builder, local_values, yield_constr);
|
shift::eval_ext_circuit(builder, local_values, yield_constr);
|
||||||
simple_logic::eval_ext_circuit(builder, local_values, yield_constr);
|
simple_logic::eval_ext_circuit(builder, local_values, next_values, yield_constr);
|
||||||
stack::eval_ext_circuit(builder, local_values, yield_constr);
|
stack::eval_ext_circuit(builder, local_values, next_values, yield_constr);
|
||||||
stack_bounds::eval_ext_circuit(builder, local_values, yield_constr);
|
stack_bounds::eval_ext_circuit(builder, local_values, yield_constr);
|
||||||
syscalls_exceptions::eval_ext_circuit(builder, local_values, next_values, yield_constr);
|
syscalls_exceptions::eval_ext_circuit(builder, local_values, next_values, yield_constr);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -75,8 +75,8 @@ pub fn eval_packed_jump_jumpi<P: PackedField>(
|
|||||||
let is_jumpi = filter * lv.opcode_bits[0];
|
let is_jumpi = filter * lv.opcode_bits[0];
|
||||||
|
|
||||||
// Stack constraints.
|
// Stack constraints.
|
||||||
stack::eval_packed_one(lv, is_jump, stack::JUMP_OP.unwrap(), yield_constr);
|
stack::eval_packed_one(lv, nv, is_jump, stack::JUMP_OP.unwrap(), yield_constr);
|
||||||
stack::eval_packed_one(lv, is_jumpi, stack::JUMPI_OP.unwrap(), yield_constr);
|
stack::eval_packed_one(lv, nv, is_jumpi, stack::JUMPI_OP.unwrap(), yield_constr);
|
||||||
|
|
||||||
// If `JUMP`, re-use the `JUMPI` logic, but setting the second input (the predicate) to be 1.
|
// If `JUMP`, re-use the `JUMPI` logic, but setting the second input (the predicate) to be 1.
|
||||||
// In other words, we implement `JUMP(dst)` as `JUMPI(dst, cond=1)`.
|
// In other words, we implement `JUMP(dst)` as `JUMPI(dst, cond=1)`.
|
||||||
@ -151,10 +151,18 @@ pub fn eval_ext_circuit_jump_jumpi<F: RichField + Extendable<D>, const D: usize>
|
|||||||
let is_jumpi = builder.mul_extension(filter, lv.opcode_bits[0]);
|
let is_jumpi = builder.mul_extension(filter, lv.opcode_bits[0]);
|
||||||
|
|
||||||
// Stack constraints.
|
// Stack constraints.
|
||||||
stack::eval_ext_circuit_one(builder, lv, is_jump, stack::JUMP_OP.unwrap(), yield_constr);
|
|
||||||
stack::eval_ext_circuit_one(
|
stack::eval_ext_circuit_one(
|
||||||
builder,
|
builder,
|
||||||
lv,
|
lv,
|
||||||
|
nv,
|
||||||
|
is_jump,
|
||||||
|
stack::JUMP_OP.unwrap(),
|
||||||
|
yield_constr,
|
||||||
|
);
|
||||||
|
stack::eval_ext_circuit_one(
|
||||||
|
builder,
|
||||||
|
lv,
|
||||||
|
nv,
|
||||||
is_jumpi,
|
is_jumpi,
|
||||||
stack::JUMPI_OP.unwrap(),
|
stack::JUMPI_OP.unwrap(),
|
||||||
yield_constr,
|
yield_constr,
|
||||||
|
|||||||
@ -51,6 +51,7 @@ pub fn generate_pinv_diff<F: Field>(val0: U256, val1: U256, lv: &mut CpuColumnsV
|
|||||||
|
|
||||||
pub fn eval_packed<P: PackedField>(
|
pub fn eval_packed<P: PackedField>(
|
||||||
lv: &CpuColumnsView<P>,
|
lv: &CpuColumnsView<P>,
|
||||||
|
nv: &CpuColumnsView<P>,
|
||||||
yield_constr: &mut ConstraintConsumer<P>,
|
yield_constr: &mut ConstraintConsumer<P>,
|
||||||
) {
|
) {
|
||||||
let logic = lv.general.logic();
|
let logic = lv.general.logic();
|
||||||
@ -94,9 +95,10 @@ pub fn eval_packed<P: PackedField>(
|
|||||||
yield_constr.constraint(eq_or_iszero_filter * (dot - unequal));
|
yield_constr.constraint(eq_or_iszero_filter * (dot - unequal));
|
||||||
|
|
||||||
// Stack constraints.
|
// Stack constraints.
|
||||||
stack::eval_packed_one(lv, eq_filter, EQ_STACK_BEHAVIOR.unwrap(), yield_constr);
|
stack::eval_packed_one(lv, nv, eq_filter, EQ_STACK_BEHAVIOR.unwrap(), yield_constr);
|
||||||
stack::eval_packed_one(
|
stack::eval_packed_one(
|
||||||
lv,
|
lv,
|
||||||
|
nv,
|
||||||
iszero_filter,
|
iszero_filter,
|
||||||
IS_ZERO_STACK_BEHAVIOR.unwrap(),
|
IS_ZERO_STACK_BEHAVIOR.unwrap(),
|
||||||
yield_constr,
|
yield_constr,
|
||||||
@ -106,6 +108,7 @@ pub fn eval_packed<P: PackedField>(
|
|||||||
pub fn eval_ext_circuit<F: RichField + Extendable<D>, const D: usize>(
|
pub fn eval_ext_circuit<F: RichField + Extendable<D>, const D: usize>(
|
||||||
builder: &mut plonky2::plonk::circuit_builder::CircuitBuilder<F, D>,
|
builder: &mut plonky2::plonk::circuit_builder::CircuitBuilder<F, D>,
|
||||||
lv: &CpuColumnsView<ExtensionTarget<D>>,
|
lv: &CpuColumnsView<ExtensionTarget<D>>,
|
||||||
|
nv: &CpuColumnsView<ExtensionTarget<D>>,
|
||||||
yield_constr: &mut RecursiveConstraintConsumer<F, D>,
|
yield_constr: &mut RecursiveConstraintConsumer<F, D>,
|
||||||
) {
|
) {
|
||||||
let zero = builder.zero_extension();
|
let zero = builder.zero_extension();
|
||||||
@ -173,6 +176,7 @@ pub fn eval_ext_circuit<F: RichField + Extendable<D>, const D: usize>(
|
|||||||
stack::eval_ext_circuit_one(
|
stack::eval_ext_circuit_one(
|
||||||
builder,
|
builder,
|
||||||
lv,
|
lv,
|
||||||
|
nv,
|
||||||
eq_filter,
|
eq_filter,
|
||||||
EQ_STACK_BEHAVIOR.unwrap(),
|
EQ_STACK_BEHAVIOR.unwrap(),
|
||||||
yield_constr,
|
yield_constr,
|
||||||
@ -180,6 +184,7 @@ pub fn eval_ext_circuit<F: RichField + Extendable<D>, const D: usize>(
|
|||||||
stack::eval_ext_circuit_one(
|
stack::eval_ext_circuit_one(
|
||||||
builder,
|
builder,
|
||||||
lv,
|
lv,
|
||||||
|
nv,
|
||||||
iszero_filter,
|
iszero_filter,
|
||||||
IS_ZERO_STACK_BEHAVIOR.unwrap(),
|
IS_ZERO_STACK_BEHAVIOR.unwrap(),
|
||||||
yield_constr,
|
yield_constr,
|
||||||
|
|||||||
@ -11,17 +11,19 @@ use crate::cpu::columns::CpuColumnsView;
|
|||||||
|
|
||||||
pub fn eval_packed<P: PackedField>(
|
pub fn eval_packed<P: PackedField>(
|
||||||
lv: &CpuColumnsView<P>,
|
lv: &CpuColumnsView<P>,
|
||||||
|
nv: &CpuColumnsView<P>,
|
||||||
yield_constr: &mut ConstraintConsumer<P>,
|
yield_constr: &mut ConstraintConsumer<P>,
|
||||||
) {
|
) {
|
||||||
not::eval_packed(lv, yield_constr);
|
not::eval_packed(lv, yield_constr);
|
||||||
eq_iszero::eval_packed(lv, yield_constr);
|
eq_iszero::eval_packed(lv, nv, yield_constr);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn eval_ext_circuit<F: RichField + Extendable<D>, const D: usize>(
|
pub fn eval_ext_circuit<F: RichField + Extendable<D>, const D: usize>(
|
||||||
builder: &mut plonky2::plonk::circuit_builder::CircuitBuilder<F, D>,
|
builder: &mut plonky2::plonk::circuit_builder::CircuitBuilder<F, D>,
|
||||||
lv: &CpuColumnsView<ExtensionTarget<D>>,
|
lv: &CpuColumnsView<ExtensionTarget<D>>,
|
||||||
|
nv: &CpuColumnsView<ExtensionTarget<D>>,
|
||||||
yield_constr: &mut RecursiveConstraintConsumer<F, D>,
|
yield_constr: &mut RecursiveConstraintConsumer<F, D>,
|
||||||
) {
|
) {
|
||||||
not::eval_ext_circuit(builder, lv, yield_constr);
|
not::eval_ext_circuit(builder, lv, yield_constr);
|
||||||
eq_iszero::eval_ext_circuit(builder, lv, yield_constr);
|
eq_iszero::eval_ext_circuit(builder, lv, nv, yield_constr);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -140,6 +140,7 @@ pub(crate) const IS_ZERO_STACK_BEHAVIOR: Option<StackBehavior> = BASIC_UNARY_OP;
|
|||||||
|
|
||||||
pub(crate) fn eval_packed_one<P: PackedField>(
|
pub(crate) fn eval_packed_one<P: PackedField>(
|
||||||
lv: &CpuColumnsView<P>,
|
lv: &CpuColumnsView<P>,
|
||||||
|
nv: &CpuColumnsView<P>,
|
||||||
filter: P,
|
filter: P,
|
||||||
stack_behavior: StackBehavior,
|
stack_behavior: StackBehavior,
|
||||||
yield_constr: &mut ConstraintConsumer<P>,
|
yield_constr: &mut ConstraintConsumer<P>,
|
||||||
@ -185,15 +186,21 @@ pub(crate) fn eval_packed_one<P: PackedField>(
|
|||||||
yield_constr.constraint(filter * channel.used);
|
yield_constr.constraint(filter * channel.used);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Constrain new stack length.
|
||||||
|
let num_pops = P::Scalar::from_canonical_usize(stack_behavior.num_pops);
|
||||||
|
let push = P::Scalar::from_canonical_usize(stack_behavior.pushes as usize);
|
||||||
|
yield_constr.constraint_transition(filter * (nv.stack_len - (lv.stack_len - num_pops + push)));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn eval_packed<P: PackedField>(
|
pub fn eval_packed<P: PackedField>(
|
||||||
lv: &CpuColumnsView<P>,
|
lv: &CpuColumnsView<P>,
|
||||||
|
nv: &CpuColumnsView<P>,
|
||||||
yield_constr: &mut ConstraintConsumer<P>,
|
yield_constr: &mut ConstraintConsumer<P>,
|
||||||
) {
|
) {
|
||||||
for (op, stack_behavior) in izip!(lv.op.into_iter(), STACK_BEHAVIORS.into_iter()) {
|
for (op, stack_behavior) in izip!(lv.op.into_iter(), STACK_BEHAVIORS.into_iter()) {
|
||||||
if let Some(stack_behavior) = stack_behavior {
|
if let Some(stack_behavior) = stack_behavior {
|
||||||
eval_packed_one(lv, op, stack_behavior, yield_constr);
|
eval_packed_one(lv, nv, op, stack_behavior, yield_constr);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -201,6 +208,7 @@ pub fn eval_packed<P: PackedField>(
|
|||||||
pub(crate) fn eval_ext_circuit_one<F: RichField + Extendable<D>, const D: usize>(
|
pub(crate) fn eval_ext_circuit_one<F: RichField + Extendable<D>, const D: usize>(
|
||||||
builder: &mut plonky2::plonk::circuit_builder::CircuitBuilder<F, D>,
|
builder: &mut plonky2::plonk::circuit_builder::CircuitBuilder<F, D>,
|
||||||
lv: &CpuColumnsView<ExtensionTarget<D>>,
|
lv: &CpuColumnsView<ExtensionTarget<D>>,
|
||||||
|
nv: &CpuColumnsView<ExtensionTarget<D>>,
|
||||||
filter: ExtensionTarget<D>,
|
filter: ExtensionTarget<D>,
|
||||||
stack_behavior: StackBehavior,
|
stack_behavior: StackBehavior,
|
||||||
yield_constr: &mut RecursiveConstraintConsumer<F, D>,
|
yield_constr: &mut RecursiveConstraintConsumer<F, D>,
|
||||||
@ -298,16 +306,27 @@ pub(crate) fn eval_ext_circuit_one<F: RichField + Extendable<D>, const D: usize>
|
|||||||
yield_constr.constraint(builder, constr);
|
yield_constr.constraint(builder, constr);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Constrain new stack length.
|
||||||
|
let diff = builder.constant_extension(
|
||||||
|
F::Extension::from_canonical_usize(stack_behavior.num_pops)
|
||||||
|
- F::Extension::from_canonical_usize(stack_behavior.pushes as usize),
|
||||||
|
);
|
||||||
|
let diff = builder.sub_extension(lv.stack_len, diff);
|
||||||
|
let diff = builder.sub_extension(nv.stack_len, diff);
|
||||||
|
let constr = builder.mul_extension(filter, diff);
|
||||||
|
yield_constr.constraint_transition(builder, constr);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn eval_ext_circuit<F: RichField + Extendable<D>, const D: usize>(
|
pub fn eval_ext_circuit<F: RichField + Extendable<D>, const D: usize>(
|
||||||
builder: &mut plonky2::plonk::circuit_builder::CircuitBuilder<F, D>,
|
builder: &mut plonky2::plonk::circuit_builder::CircuitBuilder<F, D>,
|
||||||
lv: &CpuColumnsView<ExtensionTarget<D>>,
|
lv: &CpuColumnsView<ExtensionTarget<D>>,
|
||||||
|
nv: &CpuColumnsView<ExtensionTarget<D>>,
|
||||||
yield_constr: &mut RecursiveConstraintConsumer<F, D>,
|
yield_constr: &mut RecursiveConstraintConsumer<F, D>,
|
||||||
) {
|
) {
|
||||||
for (op, stack_behavior) in izip!(lv.op.into_iter(), STACK_BEHAVIORS.into_iter()) {
|
for (op, stack_behavior) in izip!(lv.op.into_iter(), STACK_BEHAVIORS.into_iter()) {
|
||||||
if let Some(stack_behavior) = stack_behavior {
|
if let Some(stack_behavior) = stack_behavior {
|
||||||
eval_ext_circuit_one(builder, lv, op, stack_behavior, yield_constr);
|
eval_ext_circuit_one(builder, lv, nv, op, stack_behavior, yield_constr);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user