Skip to content

Commit 9b7591d

Browse files
authored
Fix overspilling of MULTI_OBSERVE constraints due to indicator insufficiency (#7)
* Fix multi_observe constraints * Remove debug flags * fmt
1 parent e4e261b commit 9b7591d

File tree

4 files changed

+26
-4
lines changed

4 files changed

+26
-4
lines changed

extensions/native/circuit/src/poseidon2/air.rs

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -698,6 +698,7 @@ impl<AB: InteractionBuilder, const SBOX_REGISTERS: usize> Air<AB>
698698
end_idx,
699699
aux_after_start,
700700
aux_before_end,
701+
aux_read_enabled,
701702
read_data,
702703
write_data,
703704
data,
@@ -783,7 +784,7 @@ impl<AB: InteractionBuilder, const SBOX_REGISTERS: usize> Air<AB>
783784
start_timestamp + i_var * AB::F::TWO - start_idx * AB::F::TWO,
784785
&read_data[i]
785786
)
786-
.eval(builder, aux_after_start[i] * aux_before_end[i]);
787+
.eval(builder, multi_observe_row * aux_read_enabled[i]);
787788

788789
self.memory_bridge
789790
.write(
@@ -795,21 +796,29 @@ impl<AB: InteractionBuilder, const SBOX_REGISTERS: usize> Air<AB>
795796
start_timestamp + i_var * AB::F::TWO - start_idx * AB::F::TWO + AB::F::ONE,
796797
&write_data[i],
797798
)
798-
.eval(builder, aux_after_start[i] * aux_before_end[i]);
799+
.eval(builder, multi_observe_row * aux_read_enabled[i]);
799800
}
800801

801802
for i in 0..(CHUNK - 1) {
802803
builder
804+
.when(multi_observe_row)
803805
.when(aux_after_start[i])
804806
.assert_one(aux_after_start[i + 1]);
805807
}
806808

807809
for i in 1..CHUNK {
808810
builder
811+
.when(multi_observe_row)
809812
.when(aux_before_end[i])
810813
.assert_one(aux_before_end[i - 1]);
811814
}
812815

816+
for i in 0..CHUNK {
817+
builder
818+
.when(multi_observe_row)
819+
.assert_eq(aux_after_start[i] * aux_before_end[i], aux_read_enabled[i]);
820+
}
821+
813822
builder
814823
.when(multi_observe_row)
815824
.when(not(is_first))

extensions/native/circuit/src/poseidon2/columns.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -224,6 +224,7 @@ pub struct MultiObserveCols<T> {
224224
pub end_idx: T,
225225
pub aux_after_start: [T; CHUNK],
226226
pub aux_before_end: [T; CHUNK],
227+
pub aux_read_enabled: [T; CHUNK],
227228

228229
// Transcript observation
229230
pub read_data: [MemoryReadAuxCols<T>; CHUNK],

extensions/native/circuit/src/poseidon2/trace.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -473,6 +473,11 @@ impl<F: PrimeField32, const SBOX_REGISTERS: usize> NativePoseidon2Chip<F, SBOX_R
473473
for i in 0..record.end_idx {
474474
specific.aux_before_end[i] = F::ONE;
475475
}
476+
for i in 0..CHUNK {
477+
if specific.aux_after_start[i] + specific.aux_before_end[i] >= F::TWO {
478+
specific.aux_read_enabled[i] = F::ONE;
479+
}
480+
}
476481
for i in record.start_idx..record.end_idx {
477482
let read_data_record = memory.record_by_id(record.read_input_data[i]);
478483
let write_data_record = memory.record_by_id(record.write_input_data[i]);

extensions/native/recursion/tests/recursion.rs

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ use openvm_native_compiler::{
55
asm::{AsmBuilder, AsmCompiler}, ir::Felt,
66
conversion::{convert_program, CompilerOptions},
77
};
8-
use openvm_native_recursion::{testing_utils::inner::run_recursive_test, challenger::duplex::DuplexChallengerVariable};
8+
use openvm_native_recursion::{testing_utils::inner::run_recursive_test, challenger::{duplex::DuplexChallengerVariable, CanObserveVariable}};
99
use openvm_stark_backend::{
1010
config::{Domain, StarkGenericConfig},
1111
p3_commit::PolynomialSpace,
@@ -148,7 +148,14 @@ fn build_test_program<C: Config>(
148148
let sample_lens: Vec<usize> = vec![10, 2, 0, 3, 20];
149149

150150
let mut rng = create_seeded_rng();
151-
let challenger = DuplexChallengerVariable::new(builder);
151+
let mut challenger = DuplexChallengerVariable::new(builder);
152+
153+
// Observe a setup label
154+
let label_f: Vec<u64> = vec![128, 3098, 192, 394, 1662, 928, 374, 281, 598, 182, 475, 729];
155+
for n in label_f {
156+
let f: Felt<C::F> = builder.constant(C::F::from_canonical_u64(n));
157+
challenger.observe(builder, f);
158+
}
152159

153160
for l in sample_lens {
154161
let sample_input: Array<C, Felt<C::F>> = builder.dyn_array(l);

0 commit comments

Comments
 (0)