From c4ff514bd2420ccfb50d9ac19ac74ad3016c228d Mon Sep 17 00:00:00 2001 From: Maddiaa0 <47148561+Maddiaa0@users.noreply.github.com> Date: Tue, 2 Jan 2024 12:03:28 +0000 Subject: [PATCH 1/4] feat: add standalone jump opcode --- barretenberg/cpp/pil/avm/avm_mini.pil | 27 ++- barretenberg/cpp/pil/avm/avm_mini_opt.pil | 68 ------- .../flavor/generated/AvmMini_flavor.hpp | 44 ++--- .../circuit_builder/AvmMini_trace.cpp | 36 +++- .../circuit_builder/AvmMini_trace.hpp | 3 + .../generated/AvmMini_circuit_builder.hpp | 14 +- .../relations/generated/AvmMini/avm_mini.hpp | 169 ++++++++++-------- .../generated/AvmMini/declare_views.hpp | 7 +- .../relations/generated/AvmMini/mem_trace.hpp | 32 ++-- .../vm/generated/AvmMini_verifier.cpp | 2 + .../vm/tests/AvmMini_control_flow.test.cpp | 83 +++++++-- 11 files changed, 273 insertions(+), 212 deletions(-) delete mode 100644 barretenberg/cpp/pil/avm/avm_mini_opt.pil diff --git a/barretenberg/cpp/pil/avm/avm_mini.pil b/barretenberg/cpp/pil/avm/avm_mini.pil index b2e10e30cca0..483dda98de6b 100644 --- a/barretenberg/cpp/pil/avm/avm_mini.pil +++ b/barretenberg/cpp/pil/avm/avm_mini.pil @@ -16,6 +16,7 @@ namespace avmMini(256); pol commit sel_internal_call; pol commit sel_internal_return; + pol commit sel_jump; // Halt program execution pol commit sel_halt; @@ -80,6 +81,7 @@ namespace avmMini(256); sel_internal_call * (1 - sel_internal_call) = 0; sel_internal_return * (1 - sel_internal_return) = 0; + sel_jump * (1 - sel_jump) = 0; sel_halt * (1 - sel_halt) = 0; op_err * (1 - op_err) = 0; @@ -147,25 +149,32 @@ namespace avmMini(256); // This works in combination with op_div_err * (sel_op_div - 1) = 0; // Drawback is the need to paralllelize the latter. + //===== JUMP =============================================================== + // TOOD: constrain that the jump location comes from the instruction's operands + sel_jump * (pc' - ia) = 0; //===== CALL_RETURN ======================================================== + // TODO: update this comment to be correct alongside the jump implementation + // The program counter in the next row should be equal to the value loaded from the ia register // This implies that a load from memory must occur at the same time // Imply that we must load the return location into mem_idx_a #[RETURN_POINTER_INCREMENT] - sel_internal_call * ( internal_return_ptr' - ( internal_return_ptr + 1)) = 0; - sel_internal_call * ( internal_return_ptr - mem_idx_a) = 0; - sel_internal_call * ((pc + 1) - ia) = 0; + sel_internal_call * (internal_return_ptr' - (internal_return_ptr + 1)) = 0; + sel_internal_call * (internal_return_ptr - mem_idx_b) = 0; + sel_internal_call * ((pc + 1) - ib) = 0; + + sel_internal_call - (sel_jump * sel_internal_call) = 0; // TODO(md): Below relations may be removed through sub-op table lookup - sel_internal_call * (rwa - 1) = 0; - sel_internal_call * (mem_op_a - 1) = 0; + sel_internal_call * (rwb - 1) = 0; + sel_internal_call * (mem_op_b - 1) = 0; // We must load the memory pointer to be the internal_return_ptr #[RETURN_POINTER_DECREMENT] - sel_internal_return * ( internal_return_ptr' - ( internal_return_ptr - 1)) = 0; - sel_internal_return * ( (internal_return_ptr - 1) - mem_idx_a) = 0; + sel_internal_return * (internal_return_ptr' - (internal_return_ptr - 1)) = 0; + sel_internal_return * ((internal_return_ptr - 1) - mem_idx_a) = 0; sel_internal_return * (pc' - ia) = 0; // TODO(md): Below relations may be removed through sub-op table lookup @@ -173,7 +182,7 @@ namespace avmMini(256); sel_internal_return * (mem_op_a - 1) = 0; //===== CONTROL_FLOW_CONSISTENCY ============================================ - pol CONTROL_FLOW_SELECTORS = (first + sel_internal_call + sel_internal_return + sel_halt); + pol INTERNAL_CALL_STACK_SELECTORS = (first + sel_internal_call + sel_internal_return + sel_halt); pol OPCODE_SELECTORS = (sel_op_add + sel_op_sub + sel_op_div + sel_op_mul); // Program counter must increment if not jumping or returning @@ -182,7 +191,7 @@ namespace avmMini(256); // first == 0 && sel_internal_call == 0 && sel_internal_return == 0 && sel_halt == 0 ==> internal_return_ptr == internal_return_ptr' #[INTERNAL_RETURN_POINTER_CONSISTENCY] - (1 - CONTROL_FLOW_SELECTORS) * (internal_return_ptr' - internal_return_ptr) = 0; + (1 - INTERNAL_CALL_STACK_SELECTORS) * (internal_return_ptr' - internal_return_ptr) = 0; // TODO: we want to set an initial number for the reserved memory of the jump pointer diff --git a/barretenberg/cpp/pil/avm/avm_mini_opt.pil b/barretenberg/cpp/pil/avm/avm_mini_opt.pil deleted file mode 100644 index f3a75411a99d..000000000000 --- a/barretenberg/cpp/pil/avm/avm_mini_opt.pil +++ /dev/null @@ -1,68 +0,0 @@ -namespace memTrace(256); - col witness m_clk; - col witness m_sub_clk; - col witness m_addr; - col witness m_tag; - col witness m_val; - col witness m_lastAccess; - col witness m_last; - col witness m_rw; - col witness m_in_tag; - col witness m_tag_err; - col witness m_one_min_inv; - (memTrace.m_lastAccess * (1 - memTrace.m_lastAccess)) = 0; - (memTrace.m_last * (1 - memTrace.m_last)) = 0; - (memTrace.m_rw * (1 - memTrace.m_rw)) = 0; - (memTrace.m_tag_err * (1 - memTrace.m_tag_err)) = 0; - ((1 - memTrace.m_lastAccess) * (memTrace.m_addr' - memTrace.m_addr)) = 0; - (((1 - memTrace.m_lastAccess) * (1 - memTrace.m_rw')) * (memTrace.m_val' - memTrace.m_val)) = 0; - (((1 - memTrace.m_lastAccess) * (1 - memTrace.m_rw')) * (memTrace.m_tag' - memTrace.m_tag)) = 0; - ((memTrace.m_lastAccess * (1 - memTrace.m_rw')) * memTrace.m_val') = 0; - ((memTrace.m_in_tag - memTrace.m_tag) * (1 - memTrace.m_one_min_inv)) = memTrace.m_tag_err; - ((1 - memTrace.m_tag_err) * memTrace.m_one_min_inv) = 0; -namespace avmMini(256); - col fixed clk(i) { i }; - col fixed first = [1] + [0]*; - col witness sel_op_add; - col witness sel_op_sub; - col witness sel_op_mul; - col witness sel_op_div; - col witness in_tag; - col witness op_err; - col witness tag_err; - col witness inv; - col witness ia; - col witness ib; - col witness ic; - col witness mem_op_a; - col witness mem_op_b; - col witness mem_op_c; - col witness rwa; - col witness rwb; - col witness rwc; - col witness mem_idx_a; - col witness mem_idx_b; - col witness mem_idx_c; - col witness last; - (avmMini.sel_op_add * (1 - avmMini.sel_op_add)) = 0; - (avmMini.sel_op_sub * (1 - avmMini.sel_op_sub)) = 0; - (avmMini.sel_op_mul * (1 - avmMini.sel_op_mul)) = 0; - (avmMini.sel_op_div * (1 - avmMini.sel_op_div)) = 0; - (avmMini.op_err * (1 - avmMini.op_err)) = 0; - (avmMini.tag_err * (1 - avmMini.tag_err)) = 0; - (avmMini.mem_op_a * (1 - avmMini.mem_op_a)) = 0; - (avmMini.mem_op_b * (1 - avmMini.mem_op_b)) = 0; - (avmMini.mem_op_c * (1 - avmMini.mem_op_c)) = 0; - (avmMini.rwa * (1 - avmMini.rwa)) = 0; - (avmMini.rwb * (1 - avmMini.rwb)) = 0; - (avmMini.rwc * (1 - avmMini.rwc)) = 0; - (avmMini.tag_err * avmMini.ia) = 0; - (avmMini.tag_err * avmMini.ib) = 0; - (avmMini.tag_err * avmMini.ic) = 0; - (avmMini.sel_op_add * ((avmMini.ia + avmMini.ib) - avmMini.ic)) = 0; - (avmMini.sel_op_sub * ((avmMini.ia - avmMini.ib) - avmMini.ic)) = 0; - (avmMini.sel_op_mul * ((avmMini.ia * avmMini.ib) - avmMini.ic)) = 0; - ((avmMini.sel_op_div * (1 - avmMini.op_err)) * ((avmMini.ic * avmMini.ib) - avmMini.ia)) = 0; - (avmMini.sel_op_div * (((avmMini.ib * avmMini.inv) - 1) + avmMini.op_err)) = 0; - ((avmMini.sel_op_div * avmMini.op_err) * (1 - avmMini.inv)) = 0; - (avmMini.op_err * (avmMini.sel_op_div - 1)) = 0; diff --git a/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp b/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp index d9b5edb8c61c..7907a1238c29 100644 --- a/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp +++ b/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp @@ -36,11 +36,11 @@ class AvmMiniFlavor { using VerifierCommitmentKey = pcs::VerifierCommitmentKey; static constexpr size_t NUM_PRECOMPUTED_ENTITIES = 2; - static constexpr size_t NUM_WITNESS_ENTITIES = 37; + static constexpr size_t NUM_WITNESS_ENTITIES = 38; static constexpr size_t NUM_WIRES = NUM_WITNESS_ENTITIES + NUM_PRECOMPUTED_ENTITIES; // We have two copies of the witness entities, so we subtract the number of fixed ones (they have no shift), one for // the unshifted and one for the shifted - static constexpr size_t NUM_ALL_ENTITIES = 45; + static constexpr size_t NUM_ALL_ENTITIES = 46; using Relations = std::tuple, AvmMini_vm::mem_trace>; @@ -91,6 +91,7 @@ class AvmMiniFlavor { avmMini_internal_return_ptr, avmMini_sel_internal_call, avmMini_sel_internal_return, + avmMini_sel_jump, avmMini_sel_halt, avmMini_sel_op_add, avmMini_sel_op_sub, @@ -131,6 +132,7 @@ class AvmMiniFlavor { avmMini_internal_return_ptr, avmMini_sel_internal_call, avmMini_sel_internal_return, + avmMini_sel_jump, avmMini_sel_halt, avmMini_sel_op_add, avmMini_sel_op_sub, @@ -177,6 +179,7 @@ class AvmMiniFlavor { avmMini_internal_return_ptr, avmMini_sel_internal_call, avmMini_sel_internal_return, + avmMini_sel_jump, avmMini_sel_halt, avmMini_sel_op_add, avmMini_sel_op_sub, @@ -199,12 +202,12 @@ class AvmMiniFlavor { avmMini_mem_idx_b, avmMini_mem_idx_c, avmMini_last, - avmMini_internal_return_ptr_shift, avmMini_pc_shift, - memTrace_m_tag_shift, + avmMini_internal_return_ptr_shift, memTrace_m_val_shift, memTrace_m_rw_shift, - memTrace_m_addr_shift) + memTrace_m_addr_shift, + memTrace_m_tag_shift) RefVector get_wires() { @@ -225,6 +228,7 @@ class AvmMiniFlavor { avmMini_internal_return_ptr, avmMini_sel_internal_call, avmMini_sel_internal_return, + avmMini_sel_jump, avmMini_sel_halt, avmMini_sel_op_add, avmMini_sel_op_sub, @@ -247,12 +251,12 @@ class AvmMiniFlavor { avmMini_mem_idx_b, avmMini_mem_idx_c, avmMini_last, - avmMini_internal_return_ptr_shift, avmMini_pc_shift, - memTrace_m_tag_shift, + avmMini_internal_return_ptr_shift, memTrace_m_val_shift, memTrace_m_rw_shift, - memTrace_m_addr_shift }; + memTrace_m_addr_shift, + memTrace_m_tag_shift }; }; RefVector get_unshifted() { @@ -273,6 +277,7 @@ class AvmMiniFlavor { avmMini_internal_return_ptr, avmMini_sel_internal_call, avmMini_sel_internal_return, + avmMini_sel_jump, avmMini_sel_halt, avmMini_sel_op_add, avmMini_sel_op_sub, @@ -298,18 +303,14 @@ class AvmMiniFlavor { }; RefVector get_to_be_shifted() { - return { - avmMini_internal_return_ptr, avmMini_pc, memTrace_m_tag, memTrace_m_val, memTrace_m_rw, memTrace_m_addr - }; + return { avmMini_pc, avmMini_internal_return_ptr, memTrace_m_val, memTrace_m_rw, memTrace_m_addr, + memTrace_m_tag }; }; RefVector get_shifted() { - return { avmMini_internal_return_ptr_shift, - avmMini_pc_shift, - memTrace_m_tag_shift, - memTrace_m_val_shift, - memTrace_m_rw_shift, - memTrace_m_addr_shift }; + return { avmMini_pc_shift, avmMini_internal_return_ptr_shift, + memTrace_m_val_shift, memTrace_m_rw_shift, + memTrace_m_addr_shift, memTrace_m_tag_shift }; }; }; @@ -322,9 +323,8 @@ class AvmMiniFlavor { RefVector get_to_be_shifted() { - return { - avmMini_internal_return_ptr, avmMini_pc, memTrace_m_tag, memTrace_m_val, memTrace_m_rw, memTrace_m_addr - }; + return { avmMini_pc, avmMini_internal_return_ptr, memTrace_m_val, memTrace_m_rw, memTrace_m_addr, + memTrace_m_tag }; }; // The plookup wires that store plookup read data. @@ -418,6 +418,7 @@ class AvmMiniFlavor { Base::avmMini_internal_return_ptr = "AVMMINI_INTERNAL_RETURN_PTR"; Base::avmMini_sel_internal_call = "AVMMINI_SEL_INTERNAL_CALL"; Base::avmMini_sel_internal_return = "AVMMINI_SEL_INTERNAL_RETURN"; + Base::avmMini_sel_jump = "AVMMINI_SEL_JUMP"; Base::avmMini_sel_halt = "AVMMINI_SEL_HALT"; Base::avmMini_sel_op_add = "AVMMINI_SEL_OP_ADD"; Base::avmMini_sel_op_sub = "AVMMINI_SEL_OP_SUB"; @@ -474,6 +475,7 @@ class AvmMiniFlavor { Commitment avmMini_internal_return_ptr; Commitment avmMini_sel_internal_call; Commitment avmMini_sel_internal_return; + Commitment avmMini_sel_jump; Commitment avmMini_sel_halt; Commitment avmMini_sel_op_add; Commitment avmMini_sel_op_sub; @@ -530,6 +532,7 @@ class AvmMiniFlavor { avmMini_internal_return_ptr = deserialize_from_buffer(Transcript::proof_data, num_bytes_read); avmMini_sel_internal_call = deserialize_from_buffer(Transcript::proof_data, num_bytes_read); avmMini_sel_internal_return = deserialize_from_buffer(Transcript::proof_data, num_bytes_read); + avmMini_sel_jump = deserialize_from_buffer(Transcript::proof_data, num_bytes_read); avmMini_sel_halt = deserialize_from_buffer(Transcript::proof_data, num_bytes_read); avmMini_sel_op_add = deserialize_from_buffer(Transcript::proof_data, num_bytes_read); avmMini_sel_op_sub = deserialize_from_buffer(Transcript::proof_data, num_bytes_read); @@ -590,6 +593,7 @@ class AvmMiniFlavor { serialize_to_buffer(avmMini_internal_return_ptr, Transcript::proof_data); serialize_to_buffer(avmMini_sel_internal_call, Transcript::proof_data); serialize_to_buffer(avmMini_sel_internal_return, Transcript::proof_data); + serialize_to_buffer(avmMini_sel_jump, Transcript::proof_data); serialize_to_buffer(avmMini_sel_halt, Transcript::proof_data); serialize_to_buffer(avmMini_sel_op_add, Transcript::proof_data); serialize_to_buffer(avmMini_sel_op_sub, Transcript::proof_data); diff --git a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.cpp b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.cpp index 9c6721160f8b..db1a58cee3a2 100644 --- a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.cpp +++ b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.cpp @@ -566,6 +566,30 @@ void AvmMiniTraceBuilder::halt() }); } +/** + * @brief JUMP OPCODE + * Jumps to a new `jmpDest` + * This function must: + * - Set the next program counter to the provided `jmpDest`. + * + * @param jmpDest - The destination to jump to + */ +void AvmMiniTraceBuilder::jump(uint32_t jmpDest) +{ + auto clk = mainTrace.size(); + + mainTrace.push_back(Row{ + .avmMini_clk = clk, + .avmMini_pc = FF(pc), + .avmMini_internal_return_ptr = FF(internal_return_ptr), + .avmMini_sel_jump = FF(1), + .avmMini_ia = FF(jmpDest), + }); + + // Adjust parameters for the next row + pc = jmpDest; +} + /** * @brief INTERNAL_CALL OPCODE * This opcode effectively jumps to a new `jmpDest` and stores the return program counter @@ -588,7 +612,7 @@ void AvmMiniTraceBuilder::internal_call(uint32_t jmpDest) internal_call_stack.push(stored_pc); // Add the return location to the memory trace - storeInMemTrace(IntermRegister::ia, internal_return_ptr, FF(stored_pc), AvmMemoryTag::ff); + storeInMemTrace(IntermRegister::ib, internal_return_ptr, FF(stored_pc), AvmMemoryTag::ff); memory.at(internal_return_ptr) = stored_pc; mainTrace.push_back(Row{ @@ -596,10 +620,12 @@ void AvmMiniTraceBuilder::internal_call(uint32_t jmpDest) .avmMini_pc = FF(pc), .avmMini_internal_return_ptr = FF(internal_return_ptr), .avmMini_sel_internal_call = FF(1), - .avmMini_ia = stored_pc, - .avmMini_mem_op_a = FF(1), - .avmMini_rwa = FF(1), - .avmMini_mem_idx_a = FF(internal_return_ptr), + .avmMini_sel_jump = FF(1), + .avmMini_ia = FF(jmpDest), + .avmMini_ib = stored_pc, + .avmMini_mem_op_b = FF(1), + .avmMini_rwb = FF(1), + .avmMini_mem_idx_b = FF(internal_return_ptr), }); // Adjust parameters for the next row diff --git a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.hpp b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.hpp index f7dd66f3b3e2..0185d76cf973 100644 --- a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.hpp +++ b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.hpp @@ -60,6 +60,9 @@ class AvmMiniTraceBuilder { void div(uint32_t aOffset, uint32_t bOffset, uint32_t dstOffset, AvmMemoryTag inTag); // Jump to a given program counter. + void jump(uint32_t jmpDest); + + // Jump to a given program counter; storing the return location on a call stack. // TODO(md): this program counter MUST be an operand to the OPCODE. void internal_call(uint32_t jmpDest); diff --git a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp index a41fb694b9c5..041ff3c29c4d 100644 --- a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp +++ b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp @@ -36,6 +36,7 @@ template struct AvmMiniFullRow { FF avmMini_internal_return_ptr{}; FF avmMini_sel_internal_call{}; FF avmMini_sel_internal_return{}; + FF avmMini_sel_jump{}; FF avmMini_sel_halt{}; FF avmMini_sel_op_add{}; FF avmMini_sel_op_sub{}; @@ -58,12 +59,12 @@ template struct AvmMiniFullRow { FF avmMini_mem_idx_b{}; FF avmMini_mem_idx_c{}; FF avmMini_last{}; - FF avmMini_internal_return_ptr_shift{}; FF avmMini_pc_shift{}; - FF memTrace_m_tag_shift{}; + FF avmMini_internal_return_ptr_shift{}; FF memTrace_m_val_shift{}; FF memTrace_m_rw_shift{}; FF memTrace_m_addr_shift{}; + FF memTrace_m_tag_shift{}; }; class AvmMiniCircuitBuilder { @@ -76,8 +77,8 @@ class AvmMiniCircuitBuilder { using Polynomial = Flavor::Polynomial; using ProverPolynomials = Flavor::ProverPolynomials; - static constexpr size_t num_fixed_columns = 45; - static constexpr size_t num_polys = 39; + static constexpr size_t num_fixed_columns = 46; + static constexpr size_t num_polys = 40; std::vector rows; void set_trace(std::vector&& trace) { rows = std::move(trace); } @@ -110,6 +111,7 @@ class AvmMiniCircuitBuilder { polys.avmMini_internal_return_ptr[i] = rows[i].avmMini_internal_return_ptr; polys.avmMini_sel_internal_call[i] = rows[i].avmMini_sel_internal_call; polys.avmMini_sel_internal_return[i] = rows[i].avmMini_sel_internal_return; + polys.avmMini_sel_jump[i] = rows[i].avmMini_sel_jump; polys.avmMini_sel_halt[i] = rows[i].avmMini_sel_halt; polys.avmMini_sel_op_add[i] = rows[i].avmMini_sel_op_add; polys.avmMini_sel_op_sub[i] = rows[i].avmMini_sel_op_sub; @@ -134,12 +136,12 @@ class AvmMiniCircuitBuilder { polys.avmMini_last[i] = rows[i].avmMini_last; } - polys.avmMini_internal_return_ptr_shift = Polynomial(polys.avmMini_internal_return_ptr.shifted()); polys.avmMini_pc_shift = Polynomial(polys.avmMini_pc.shifted()); - polys.memTrace_m_tag_shift = Polynomial(polys.memTrace_m_tag.shifted()); + polys.avmMini_internal_return_ptr_shift = Polynomial(polys.avmMini_internal_return_ptr.shifted()); polys.memTrace_m_val_shift = Polynomial(polys.memTrace_m_val.shifted()); polys.memTrace_m_rw_shift = Polynomial(polys.memTrace_m_rw.shifted()); polys.memTrace_m_addr_shift = Polynomial(polys.memTrace_m_addr.shifted()); + polys.memTrace_m_tag_shift = Polynomial(polys.memTrace_m_tag.shifted()); return polys; } diff --git a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp index 46d9a5bc9e95..bbf6a5d877a0 100644 --- a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp +++ b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp @@ -7,68 +7,70 @@ namespace proof_system::AvmMini_vm { template struct Avm_miniRow { - FF avmMini_rwa{}; + FF avmMini_mem_idx_b{}; FF avmMini_sel_op_div{}; - FF avmMini_inv{}; - FF avmMini_internal_return_ptr{}; - FF avmMini_sel_internal_call{}; FF avmMini_ic{}; - FF avmMini_rwb{}; - FF avmMini_sel_halt{}; + FF avmMini_sel_jump{}; + FF avmMini_pc{}; + FF avmMini_mem_idx_a{}; + FF avmMini_sel_op_sub{}; + FF avmMini_internal_return_ptr{}; FF avmMini_sel_op_add{}; + FF avmMini_ib{}; + FF avmMini_inv{}; + FF avmMini_pc_shift{}; + FF avmMini_tag_err{}; FF avmMini_mem_op_b{}; + FF avmMini_sel_internal_return{}; FF avmMini_op_err{}; + FF avmMini_rwb{}; + FF avmMini_mem_op_c{}; FF avmMini_rwc{}; - FF avmMini_ib{}; - FF avmMini_mem_idx_a{}; - FF avmMini_sel_op_sub{}; - FF avmMini_sel_op_mul{}; FF avmMini_ia{}; FF avmMini_internal_return_ptr_shift{}; - FF avmMini_pc{}; - FF avmMini_pc_shift{}; - FF avmMini_tag_err{}; - FF avmMini_mem_op_c{}; + FF avmMini_sel_op_mul{}; + FF avmMini_rwa{}; FF avmMini_mem_op_a{}; - FF avmMini_sel_internal_return{}; + FF avmMini_sel_halt{}; FF avmMini_first{}; + FF avmMini_sel_internal_call{}; }; inline std::string get_relation_label_avm_mini(int index) { switch (index) { - case 20: - return "SUBOP_MULTIPLICATION_FF"; + case 24: + return "SUBOP_DIVISION_ZERO_ERR2"; + + case 19: + return "SUBOP_ADDITION_FF"; + + case 25: + return "SUBOP_ERROR_RELEVANT_OP"; case 22: - return "SUBOP_DIVISION_ZERO_ERR1"; + return "SUBOP_DIVISION_FF"; + + case 33: + return "RETURN_POINTER_DECREMENT"; case 23: - return "SUBOP_DIVISION_ZERO_ERR2"; + return "SUBOP_DIVISION_ZERO_ERR1"; - case 24: - return "SUBOP_ERROR_RELEVANT_OP"; + case 21: + return "SUBOP_MULTIPLICATION_FF"; - case 25: + case 27: return "RETURN_POINTER_INCREMENT"; - case 30: - return "RETURN_POINTER_DECREMENT"; - - case 35: + case 38: return "PC_INCREMENT"; - case 19: + case 20: return "SUBOP_SUBTRACTION_FF"; - case 21: - return "SUBOP_DIVISION_FF"; - - case 36: + case 39: return "INTERNAL_RETURN_POINTER_CONSISTENCY"; - - case 18: - return "SUBOP_ADDITION_FF"; } return std::to_string(index); } @@ -77,8 +79,9 @@ template class avm_miniImpl { public: using FF = FF_; - static constexpr std::array SUBRELATION_PARTIAL_LENGTHS{ - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 5, 4, 4, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 5, 3, + static constexpr std::array SUBRELATION_PARTIAL_LENGTHS{ + 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, + 3, 4, 5, 4, 4, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 5, 3, }; template @@ -140,7 +143,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(6); - auto tmp = (avmMini_sel_halt * (-avmMini_sel_halt + FF(1))); + auto tmp = (avmMini_sel_jump * (-avmMini_sel_jump + FF(1))); tmp *= scaling_factor; std::get<6>(evals) += tmp; } @@ -148,7 +151,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(7); - auto tmp = (avmMini_op_err * (-avmMini_op_err + FF(1))); + auto tmp = (avmMini_sel_halt * (-avmMini_sel_halt + FF(1))); tmp *= scaling_factor; std::get<7>(evals) += tmp; } @@ -156,7 +159,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(8); - auto tmp = (avmMini_tag_err * (-avmMini_tag_err + FF(1))); + auto tmp = (avmMini_op_err * (-avmMini_op_err + FF(1))); tmp *= scaling_factor; std::get<8>(evals) += tmp; } @@ -164,7 +167,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(9); - auto tmp = (avmMini_mem_op_a * (-avmMini_mem_op_a + FF(1))); + auto tmp = (avmMini_tag_err * (-avmMini_tag_err + FF(1))); tmp *= scaling_factor; std::get<9>(evals) += tmp; } @@ -172,7 +175,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(10); - auto tmp = (avmMini_mem_op_b * (-avmMini_mem_op_b + FF(1))); + auto tmp = (avmMini_mem_op_a * (-avmMini_mem_op_a + FF(1))); tmp *= scaling_factor; std::get<10>(evals) += tmp; } @@ -180,7 +183,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(11); - auto tmp = (avmMini_mem_op_c * (-avmMini_mem_op_c + FF(1))); + auto tmp = (avmMini_mem_op_b * (-avmMini_mem_op_b + FF(1))); tmp *= scaling_factor; std::get<11>(evals) += tmp; } @@ -188,7 +191,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(12); - auto tmp = (avmMini_rwa * (-avmMini_rwa + FF(1))); + auto tmp = (avmMini_mem_op_c * (-avmMini_mem_op_c + FF(1))); tmp *= scaling_factor; std::get<12>(evals) += tmp; } @@ -196,7 +199,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(13); - auto tmp = (avmMini_rwb * (-avmMini_rwb + FF(1))); + auto tmp = (avmMini_rwa * (-avmMini_rwa + FF(1))); tmp *= scaling_factor; std::get<13>(evals) += tmp; } @@ -204,7 +207,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(14); - auto tmp = (avmMini_rwc * (-avmMini_rwc + FF(1))); + auto tmp = (avmMini_rwb * (-avmMini_rwb + FF(1))); tmp *= scaling_factor; std::get<14>(evals) += tmp; } @@ -212,7 +215,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(15); - auto tmp = (avmMini_tag_err * avmMini_ia); + auto tmp = (avmMini_rwc * (-avmMini_rwc + FF(1))); tmp *= scaling_factor; std::get<15>(evals) += tmp; } @@ -220,7 +223,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(16); - auto tmp = (avmMini_tag_err * avmMini_ib); + auto tmp = (avmMini_tag_err * avmMini_ia); tmp *= scaling_factor; std::get<16>(evals) += tmp; } @@ -228,7 +231,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(17); - auto tmp = (avmMini_tag_err * avmMini_ic); + auto tmp = (avmMini_tag_err * avmMini_ib); tmp *= scaling_factor; std::get<17>(evals) += tmp; } @@ -236,7 +239,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(18); - auto tmp = (avmMini_sel_op_add * ((avmMini_ia + avmMini_ib) - avmMini_ic)); + auto tmp = (avmMini_tag_err * avmMini_ic); tmp *= scaling_factor; std::get<18>(evals) += tmp; } @@ -244,7 +247,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(19); - auto tmp = (avmMini_sel_op_sub * ((avmMini_ia - avmMini_ib) - avmMini_ic)); + auto tmp = (avmMini_sel_op_add * ((avmMini_ia + avmMini_ib) - avmMini_ic)); tmp *= scaling_factor; std::get<19>(evals) += tmp; } @@ -252,7 +255,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(20); - auto tmp = (avmMini_sel_op_mul * ((avmMini_ia * avmMini_ib) - avmMini_ic)); + auto tmp = (avmMini_sel_op_sub * ((avmMini_ia - avmMini_ib) - avmMini_ic)); tmp *= scaling_factor; std::get<20>(evals) += tmp; } @@ -260,7 +263,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(21); - auto tmp = ((avmMini_sel_op_div * (-avmMini_op_err + FF(1))) * ((avmMini_ic * avmMini_ib) - avmMini_ia)); + auto tmp = (avmMini_sel_op_mul * ((avmMini_ia * avmMini_ib) - avmMini_ic)); tmp *= scaling_factor; std::get<21>(evals) += tmp; } @@ -268,7 +271,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(22); - auto tmp = (avmMini_sel_op_div * (((avmMini_ib * avmMini_inv) - FF(1)) + avmMini_op_err)); + auto tmp = ((avmMini_sel_op_div * (-avmMini_op_err + FF(1))) * ((avmMini_ic * avmMini_ib) - avmMini_ia)); tmp *= scaling_factor; std::get<22>(evals) += tmp; } @@ -276,7 +279,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(23); - auto tmp = ((avmMini_sel_op_div * avmMini_op_err) * (-avmMini_inv + FF(1))); + auto tmp = (avmMini_sel_op_div * (((avmMini_ib * avmMini_inv) - FF(1)) + avmMini_op_err)); tmp *= scaling_factor; std::get<23>(evals) += tmp; } @@ -284,7 +287,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(24); - auto tmp = (avmMini_op_err * (avmMini_sel_op_div - FF(1))); + auto tmp = ((avmMini_sel_op_div * avmMini_op_err) * (-avmMini_inv + FF(1))); tmp *= scaling_factor; std::get<24>(evals) += tmp; } @@ -292,8 +295,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(25); - auto tmp = (avmMini_sel_internal_call * - (avmMini_internal_return_ptr_shift - (avmMini_internal_return_ptr + FF(1)))); + auto tmp = (avmMini_op_err * (avmMini_sel_op_div - FF(1))); tmp *= scaling_factor; std::get<25>(evals) += tmp; } @@ -301,7 +303,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(26); - auto tmp = (avmMini_sel_internal_call * (avmMini_internal_return_ptr - avmMini_mem_idx_a)); + auto tmp = (avmMini_sel_jump * (avmMini_pc_shift - avmMini_ia)); tmp *= scaling_factor; std::get<26>(evals) += tmp; } @@ -309,7 +311,8 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(27); - auto tmp = (avmMini_sel_internal_call * ((avmMini_pc + FF(1)) - avmMini_ia)); + auto tmp = (avmMini_sel_internal_call * + (avmMini_internal_return_ptr_shift - (avmMini_internal_return_ptr + FF(1)))); tmp *= scaling_factor; std::get<27>(evals) += tmp; } @@ -317,7 +320,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(28); - auto tmp = (avmMini_sel_internal_call * (avmMini_rwa - FF(1))); + auto tmp = (avmMini_sel_internal_call * (avmMini_internal_return_ptr - avmMini_mem_idx_b)); tmp *= scaling_factor; std::get<28>(evals) += tmp; } @@ -325,7 +328,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(29); - auto tmp = (avmMini_sel_internal_call * (avmMini_mem_op_a - FF(1))); + auto tmp = (avmMini_sel_internal_call * ((avmMini_pc + FF(1)) - avmMini_ib)); tmp *= scaling_factor; std::get<29>(evals) += tmp; } @@ -333,8 +336,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(30); - auto tmp = (avmMini_sel_internal_return * - (avmMini_internal_return_ptr_shift - (avmMini_internal_return_ptr - FF(1)))); + auto tmp = (avmMini_sel_internal_call - (avmMini_sel_jump * avmMini_sel_internal_call)); tmp *= scaling_factor; std::get<30>(evals) += tmp; } @@ -342,7 +344,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(31); - auto tmp = (avmMini_sel_internal_return * ((avmMini_internal_return_ptr - FF(1)) - avmMini_mem_idx_a)); + auto tmp = (avmMini_sel_internal_call * (avmMini_rwb - FF(1))); tmp *= scaling_factor; std::get<31>(evals) += tmp; } @@ -350,7 +352,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(32); - auto tmp = (avmMini_sel_internal_return * (avmMini_pc_shift - avmMini_ia)); + auto tmp = (avmMini_sel_internal_call * (avmMini_mem_op_b - FF(1))); tmp *= scaling_factor; std::get<32>(evals) += tmp; } @@ -358,7 +360,8 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(33); - auto tmp = (avmMini_sel_internal_return * avmMini_rwa); + auto tmp = (avmMini_sel_internal_return * + (avmMini_internal_return_ptr_shift - (avmMini_internal_return_ptr - FF(1)))); tmp *= scaling_factor; std::get<33>(evals) += tmp; } @@ -366,7 +369,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(34); - auto tmp = (avmMini_sel_internal_return * (avmMini_mem_op_a - FF(1))); + auto tmp = (avmMini_sel_internal_return * ((avmMini_internal_return_ptr - FF(1)) - avmMini_mem_idx_a)); tmp *= scaling_factor; std::get<34>(evals) += tmp; } @@ -374,9 +377,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(35); - auto tmp = ((((-avmMini_first + FF(1)) * (-avmMini_sel_halt + FF(1))) * - (((avmMini_sel_op_add + avmMini_sel_op_sub) + avmMini_sel_op_div) + avmMini_sel_op_mul)) * - (avmMini_pc_shift - (avmMini_pc + FF(1)))); + auto tmp = (avmMini_sel_internal_return * (avmMini_pc_shift - avmMini_ia)); tmp *= scaling_factor; std::get<35>(evals) += tmp; } @@ -384,12 +385,38 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(36); + auto tmp = (avmMini_sel_internal_return * avmMini_rwa); + tmp *= scaling_factor; + std::get<36>(evals) += tmp; + } + // Contribution 37 + { + AvmMini_DECLARE_VIEWS(37); + + auto tmp = (avmMini_sel_internal_return * (avmMini_mem_op_a - FF(1))); + tmp *= scaling_factor; + std::get<37>(evals) += tmp; + } + // Contribution 38 + { + AvmMini_DECLARE_VIEWS(38); + + auto tmp = ((((-avmMini_first + FF(1)) * (-avmMini_sel_halt + FF(1))) * + (((avmMini_sel_op_add + avmMini_sel_op_sub) + avmMini_sel_op_div) + avmMini_sel_op_mul)) * + (avmMini_pc_shift - (avmMini_pc + FF(1)))); + tmp *= scaling_factor; + std::get<38>(evals) += tmp; + } + // Contribution 39 + { + AvmMini_DECLARE_VIEWS(39); + auto tmp = ((-(((avmMini_first + avmMini_sel_internal_call) + avmMini_sel_internal_return) + avmMini_sel_halt) + FF(1)) * (avmMini_internal_return_ptr_shift - avmMini_internal_return_ptr)); tmp *= scaling_factor; - std::get<36>(evals) += tmp; + std::get<39>(evals) += tmp; } } }; diff --git a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp index 0c711d834290..2e660fd773ab 100644 --- a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp +++ b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp @@ -19,6 +19,7 @@ [[maybe_unused]] auto avmMini_internal_return_ptr = View(new_term.avmMini_internal_return_ptr); \ [[maybe_unused]] auto avmMini_sel_internal_call = View(new_term.avmMini_sel_internal_call); \ [[maybe_unused]] auto avmMini_sel_internal_return = View(new_term.avmMini_sel_internal_return); \ + [[maybe_unused]] auto avmMini_sel_jump = View(new_term.avmMini_sel_jump); \ [[maybe_unused]] auto avmMini_sel_halt = View(new_term.avmMini_sel_halt); \ [[maybe_unused]] auto avmMini_sel_op_add = View(new_term.avmMini_sel_op_add); \ [[maybe_unused]] auto avmMini_sel_op_sub = View(new_term.avmMini_sel_op_sub); \ @@ -41,9 +42,9 @@ [[maybe_unused]] auto avmMini_mem_idx_b = View(new_term.avmMini_mem_idx_b); \ [[maybe_unused]] auto avmMini_mem_idx_c = View(new_term.avmMini_mem_idx_c); \ [[maybe_unused]] auto avmMini_last = View(new_term.avmMini_last); \ - [[maybe_unused]] auto avmMini_internal_return_ptr_shift = View(new_term.avmMini_internal_return_ptr_shift); \ [[maybe_unused]] auto avmMini_pc_shift = View(new_term.avmMini_pc_shift); \ - [[maybe_unused]] auto memTrace_m_tag_shift = View(new_term.memTrace_m_tag_shift); \ + [[maybe_unused]] auto avmMini_internal_return_ptr_shift = View(new_term.avmMini_internal_return_ptr_shift); \ [[maybe_unused]] auto memTrace_m_val_shift = View(new_term.memTrace_m_val_shift); \ [[maybe_unused]] auto memTrace_m_rw_shift = View(new_term.memTrace_m_rw_shift); \ - [[maybe_unused]] auto memTrace_m_addr_shift = View(new_term.memTrace_m_addr_shift); + [[maybe_unused]] auto memTrace_m_addr_shift = View(new_term.memTrace_m_addr_shift); \ + [[maybe_unused]] auto memTrace_m_tag_shift = View(new_term.memTrace_m_tag_shift); diff --git a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp index 2adc17baf9fb..08fdba79b36d 100644 --- a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp +++ b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp @@ -7,41 +7,41 @@ namespace proof_system::AvmMini_vm { template struct Mem_traceRow { - FF memTrace_m_tag_shift{}; - FF memTrace_m_tag{}; - FF memTrace_m_rw{}; - FF memTrace_m_lastAccess{}; FF memTrace_m_last{}; - FF memTrace_m_tag_err{}; - FF memTrace_m_val{}; - FF memTrace_m_one_min_inv{}; FF memTrace_m_val_shift{}; + FF memTrace_m_tag_err{}; FF memTrace_m_addr{}; + FF memTrace_m_rw{}; + FF memTrace_m_val{}; FF memTrace_m_rw_shift{}; FF memTrace_m_addr_shift{}; + FF memTrace_m_tag{}; + FF memTrace_m_tag_shift{}; + FF memTrace_m_lastAccess{}; FF memTrace_m_in_tag{}; + FF memTrace_m_one_min_inv{}; }; inline std::string get_relation_label_mem_trace(int index) { switch (index) { - case 5: - return "MEM_READ_WRITE_VAL_CONSISTENCY"; - - case 7: - return "MEM_ZERO_INIT"; - case 9: return "MEM_IN_TAG_CONSISTENCY_2"; - case 8: - return "MEM_IN_TAG_CONSISTENCY_1"; - case 4: return "MEM_LAST_ACCESS_DELIMITER"; + case 5: + return "MEM_READ_WRITE_VAL_CONSISTENCY"; + case 6: return "MEM_READ_WRITE_TAG_CONSISTENCY"; + + case 7: + return "MEM_ZERO_INIT"; + + case 8: + return "MEM_IN_TAG_CONSISTENCY_1"; } return std::to_string(index); } diff --git a/barretenberg/cpp/src/barretenberg/vm/generated/AvmMini_verifier.cpp b/barretenberg/cpp/src/barretenberg/vm/generated/AvmMini_verifier.cpp index 5673710fa24b..f0b102ede71b 100644 --- a/barretenberg/cpp/src/barretenberg/vm/generated/AvmMini_verifier.cpp +++ b/barretenberg/cpp/src/barretenberg/vm/generated/AvmMini_verifier.cpp @@ -80,6 +80,8 @@ bool AvmMiniVerifier::verify_proof(const plonk::proof& proof) transcript->template receive_from_prover(commitment_labels.avmMini_sel_internal_call); commitments.avmMini_sel_internal_return = transcript->template receive_from_prover(commitment_labels.avmMini_sel_internal_return); + commitments.avmMini_sel_jump = + transcript->template receive_from_prover(commitment_labels.avmMini_sel_jump); commitments.avmMini_sel_halt = transcript->template receive_from_prover(commitment_labels.avmMini_sel_halt); commitments.avmMini_sel_op_add = diff --git a/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp b/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp index 376f7ed1e5fc..a3b4cc82fba6 100644 --- a/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp +++ b/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp @@ -37,6 +37,7 @@ class AvmMiniControlFlowTests : public ::testing::Test { * *****************************************************************************/ +// TODO: add jump selector checks in here! TEST_F(AvmMiniControlFlowTests, simpleCall) { uint32_t const CALL_ADDRESS = 4; @@ -57,8 +58,8 @@ TEST_F(AvmMiniControlFlowTests, simpleCall) EXPECT_TRUE(call_row != trace.end()); EXPECT_EQ(call_row->avmMini_pc, FF(0)); EXPECT_EQ(call_row->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET)); - EXPECT_EQ(call_row->avmMini_ia, FF(1)); - EXPECT_EQ(call_row->avmMini_mem_idx_a, + EXPECT_EQ(call_row->avmMini_ib, FF(1)); + EXPECT_EQ(call_row->avmMini_mem_idx_b, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET)); // Store the return address (0) in memory } @@ -75,6 +76,40 @@ TEST_F(AvmMiniControlFlowTests, simpleCall) validateTraceProof(std::move(trace)); } +TEST_F(AvmMiniControlFlowTests, simpleJump) +{ + uint32_t const CALL_ADDRESS = 4; + + // trace_builder for the following operation + // pc opcode + // 0 INTERNAL_CALL(pc=4) + // 4 HALT + trace_builder.jump(CALL_ADDRESS); + trace_builder.halt(); + + auto trace = trace_builder.finalize(); + + // Check call + { + auto call_row = + std::ranges::find_if(trace.begin(), trace.end(), [](Row r) { return r.avmMini_sel_jump == FF(1); }); + EXPECT_TRUE(call_row != trace.end()); + EXPECT_EQ(call_row->avmMini_pc, FF(0)); + EXPECT_EQ(call_row->avmMini_ia, FF(CALL_ADDRESS)); + } + + // Check halt + { + auto halt_row = + std::ranges::find_if(trace.begin(), trace.end(), [](Row r) { return r.avmMini_sel_halt == FF(1); }); + + // Check that the correct result is stored at the expected memory location. + EXPECT_TRUE(halt_row != trace.end()); + EXPECT_EQ(halt_row->avmMini_pc, FF(CALL_ADDRESS)); + } + validateTraceProof(std::move(trace)); +} + TEST_F(AvmMiniControlFlowTests, simpleCallAndReturn) { uint32_t const CALL_ADDRESS = 20; @@ -97,8 +132,8 @@ TEST_F(AvmMiniControlFlowTests, simpleCallAndReturn) EXPECT_TRUE(call_row != trace.end()); EXPECT_EQ(call_row->avmMini_pc, FF(0)); EXPECT_EQ(call_row->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET)); - EXPECT_EQ(call_row->avmMini_ia, FF(1)); - EXPECT_EQ(call_row->avmMini_mem_idx_a, + EXPECT_EQ(call_row->avmMini_ib, FF(1)); + EXPECT_EQ(call_row->avmMini_mem_idx_b, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET)); // Store the return address (0) in memory } @@ -132,6 +167,8 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) uint32_t const CALL_ADDRESS_3 = 1337; uint32_t const CALL_ADDRESS_4 = 4; + uint32_t const JUMP_ADDRESS_1 = 22; + // trace_builder for the following operation // pc opcode // 0 INTERNAL_CALL(pc=420) @@ -140,7 +177,8 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) // 1337 INTERNAL_RETURN // 70 INTERNAL_CALL(pc=4) // 4 INTERNAL_RETURN - // 71 INTERNAL_RETURN + // 71 JUMP(pc=22) + // 22 INTERNAL_RETURN // 421 INTERNAL_RETURN // 1 HALT trace_builder.internal_call(CALL_ADDRESS_1); @@ -149,6 +187,7 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) trace_builder.internal_return(); trace_builder.internal_call(CALL_ADDRESS_4); trace_builder.internal_return(); + trace_builder.jump(JUMP_ADDRESS_1); trace_builder.internal_return(); trace_builder.internal_return(); trace_builder.halt(); @@ -158,12 +197,14 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) // Check call 1 { auto call_1 = std::ranges::find_if(trace.begin(), trace.end(), [](Row r) { - return r.avmMini_sel_internal_call == FF(1) && r.avmMini_ia == FF(1); + return r.avmMini_sel_internal_call == FF(1) && r.avmMini_ib == FF(1); }); EXPECT_TRUE(call_1 != trace.end()); EXPECT_EQ(call_1->avmMini_pc, FF(0)); + EXPECT_EQ(call_1->avmMini_sel_jump, FF(1)); + EXPECT_EQ(call_1->avmMini_ia, FF(CALL_ADDRESS_1)); EXPECT_EQ(call_1->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET)); - EXPECT_EQ(call_1->avmMini_mem_idx_a, + EXPECT_EQ(call_1->avmMini_mem_idx_b, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET)); // Store the return address (0) in memory } @@ -173,9 +214,11 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) return r.avmMini_sel_internal_call == FF(1) && r.avmMini_pc == FF(CALL_ADDRESS_1); }); EXPECT_TRUE(call_2 != trace.end()); - EXPECT_EQ(call_2->avmMini_ia, FF(CALL_ADDRESS_1 + 1)); + EXPECT_EQ(call_2->avmMini_ib, FF(CALL_ADDRESS_1 + 1)); + EXPECT_EQ(call_2->avmMini_sel_jump, FF(1)); + EXPECT_EQ(call_2->avmMini_ia, FF(CALL_ADDRESS_2)); EXPECT_EQ(call_2->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 1)); - EXPECT_EQ(call_2->avmMini_mem_idx_a, + EXPECT_EQ(call_2->avmMini_mem_idx_b, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 1)); // Store the return address (0) in memory } @@ -185,9 +228,10 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) return r.avmMini_sel_internal_call == FF(1) && r.avmMini_pc == FF(CALL_ADDRESS_2); }); EXPECT_TRUE(call_3 != trace.end()); - EXPECT_EQ(call_3->avmMini_ia, FF(CALL_ADDRESS_2 + 1)); + EXPECT_EQ(call_3->avmMini_ib, FF(CALL_ADDRESS_2 + 1)); + EXPECT_EQ(call_3->avmMini_sel_jump, FF(1)); EXPECT_EQ(call_3->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 2)); - EXPECT_EQ(call_3->avmMini_mem_idx_a, + EXPECT_EQ(call_3->avmMini_mem_idx_b, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 2)); // Store the return address (0) in memory } @@ -206,9 +250,10 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) return r.avmMini_sel_internal_call == FF(1) && r.avmMini_pc == FF(CALL_ADDRESS_2 + 1); }); EXPECT_TRUE(call_4 != trace.end()); - EXPECT_EQ(call_4->avmMini_ia, FF(CALL_ADDRESS_2 + 2)); + EXPECT_EQ(call_4->avmMini_ib, FF(CALL_ADDRESS_2 + 2)); + EXPECT_EQ(call_4->avmMini_sel_jump, FF(1)); EXPECT_EQ(call_4->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 2)); - EXPECT_EQ(call_4->avmMini_mem_idx_a, + EXPECT_EQ(call_4->avmMini_mem_idx_b, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 2)); // Store the return address (0) in memory } @@ -222,10 +267,20 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) EXPECT_EQ(return_2->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 3)); } + // Jump 1 + { + auto jump_1 = std::ranges::find_if(trace.begin(), trace.end(), [](Row r) { + return r.avmMini_sel_jump == FF(1) && r.avmMini_pc == FF(CALL_ADDRESS_2 + 2); + }); + EXPECT_TRUE(jump_1 != trace.end()); + EXPECT_EQ(jump_1->avmMini_ia, FF(JUMP_ADDRESS_1)); + EXPECT_EQ(jump_1->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 2)); + } + // Return 3 { auto return_3 = std::ranges::find_if(trace.begin(), trace.end(), [](Row r) { - return r.avmMini_sel_internal_return == FF(1) && r.avmMini_pc == FF(CALL_ADDRESS_2 + 2); + return r.avmMini_sel_internal_return == FF(1) && r.avmMini_pc == FF(JUMP_ADDRESS_1); }); EXPECT_TRUE(return_3 != trace.end()); EXPECT_EQ(return_3->avmMini_ia, FF(CALL_ADDRESS_1 + 1)); From 9be787095fe1777cd55eeb0eb9ff672af60db24c Mon Sep 17 00:00:00 2001 From: Maddiaa0 <47148561+Maddiaa0@users.noreply.github.com> Date: Tue, 2 Jan 2024 12:09:15 +0000 Subject: [PATCH 2/4] fix: pair internal call / jump relations selector --- barretenberg/cpp/pil/avm/avm_mini.pil | 2 +- .../flavor/generated/AvmMini_flavor.hpp | 31 ++++---- .../generated/AvmMini_circuit_builder.hpp | 16 ++-- .../relations/generated/AvmMini/avm_mini.hpp | 74 +++++++++---------- .../generated/AvmMini/declare_views.hpp | 6 +- .../relations/generated/AvmMini/mem_trace.hpp | 26 +++---- 6 files changed, 79 insertions(+), 76 deletions(-) diff --git a/barretenberg/cpp/pil/avm/avm_mini.pil b/barretenberg/cpp/pil/avm/avm_mini.pil index 483dda98de6b..3e98c3db6b5c 100644 --- a/barretenberg/cpp/pil/avm/avm_mini.pil +++ b/barretenberg/cpp/pil/avm/avm_mini.pil @@ -165,7 +165,7 @@ namespace avmMini(256); sel_internal_call * (internal_return_ptr - mem_idx_b) = 0; sel_internal_call * ((pc + 1) - ib) = 0; - sel_internal_call - (sel_jump * sel_internal_call) = 0; + sel_internal_call * (sel_internal_call - sel_jump) = 0; // TODO(md): Below relations may be removed through sub-op table lookup sel_internal_call * (rwb - 1) = 0; diff --git a/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp b/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp index 7907a1238c29..90018578a107 100644 --- a/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp +++ b/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp @@ -42,7 +42,7 @@ class AvmMiniFlavor { // the unshifted and one for the shifted static constexpr size_t NUM_ALL_ENTITIES = 46; - using Relations = std::tuple, AvmMini_vm::mem_trace>; + using Relations = std::tuple, AvmMini_vm::avm_mini>; static constexpr size_t MAX_PARTIAL_RELATION_LENGTH = compute_max_partial_relation_length(); @@ -202,12 +202,12 @@ class AvmMiniFlavor { avmMini_mem_idx_b, avmMini_mem_idx_c, avmMini_last, - avmMini_pc_shift, - avmMini_internal_return_ptr_shift, memTrace_m_val_shift, memTrace_m_rw_shift, memTrace_m_addr_shift, - memTrace_m_tag_shift) + memTrace_m_tag_shift, + avmMini_internal_return_ptr_shift, + avmMini_pc_shift) RefVector get_wires() { @@ -251,12 +251,12 @@ class AvmMiniFlavor { avmMini_mem_idx_b, avmMini_mem_idx_c, avmMini_last, - avmMini_pc_shift, - avmMini_internal_return_ptr_shift, memTrace_m_val_shift, memTrace_m_rw_shift, memTrace_m_addr_shift, - memTrace_m_tag_shift }; + memTrace_m_tag_shift, + avmMini_internal_return_ptr_shift, + avmMini_pc_shift }; }; RefVector get_unshifted() { @@ -303,14 +303,17 @@ class AvmMiniFlavor { }; RefVector get_to_be_shifted() { - return { avmMini_pc, avmMini_internal_return_ptr, memTrace_m_val, memTrace_m_rw, memTrace_m_addr, - memTrace_m_tag }; + return { memTrace_m_val, memTrace_m_rw, memTrace_m_addr, memTrace_m_tag, avmMini_internal_return_ptr, + avmMini_pc }; }; RefVector get_shifted() { - return { avmMini_pc_shift, avmMini_internal_return_ptr_shift, - memTrace_m_val_shift, memTrace_m_rw_shift, - memTrace_m_addr_shift, memTrace_m_tag_shift }; + return { memTrace_m_val_shift, + memTrace_m_rw_shift, + memTrace_m_addr_shift, + memTrace_m_tag_shift, + avmMini_internal_return_ptr_shift, + avmMini_pc_shift }; }; }; @@ -323,8 +326,8 @@ class AvmMiniFlavor { RefVector get_to_be_shifted() { - return { avmMini_pc, avmMini_internal_return_ptr, memTrace_m_val, memTrace_m_rw, memTrace_m_addr, - memTrace_m_tag }; + return { memTrace_m_val, memTrace_m_rw, memTrace_m_addr, memTrace_m_tag, avmMini_internal_return_ptr, + avmMini_pc }; }; // The plookup wires that store plookup read data. diff --git a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp index 041ff3c29c4d..1cb3977df040 100644 --- a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp +++ b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp @@ -59,12 +59,12 @@ template struct AvmMiniFullRow { FF avmMini_mem_idx_b{}; FF avmMini_mem_idx_c{}; FF avmMini_last{}; - FF avmMini_pc_shift{}; - FF avmMini_internal_return_ptr_shift{}; FF memTrace_m_val_shift{}; FF memTrace_m_rw_shift{}; FF memTrace_m_addr_shift{}; FF memTrace_m_tag_shift{}; + FF avmMini_internal_return_ptr_shift{}; + FF avmMini_pc_shift{}; }; class AvmMiniCircuitBuilder { @@ -136,12 +136,12 @@ class AvmMiniCircuitBuilder { polys.avmMini_last[i] = rows[i].avmMini_last; } - polys.avmMini_pc_shift = Polynomial(polys.avmMini_pc.shifted()); - polys.avmMini_internal_return_ptr_shift = Polynomial(polys.avmMini_internal_return_ptr.shifted()); polys.memTrace_m_val_shift = Polynomial(polys.memTrace_m_val.shifted()); polys.memTrace_m_rw_shift = Polynomial(polys.memTrace_m_rw.shifted()); polys.memTrace_m_addr_shift = Polynomial(polys.memTrace_m_addr.shifted()); polys.memTrace_m_tag_shift = Polynomial(polys.memTrace_m_tag.shifted()); + polys.avmMini_internal_return_ptr_shift = Polynomial(polys.avmMini_internal_return_ptr.shifted()); + polys.avmMini_pc_shift = Polynomial(polys.avmMini_pc.shifted()); return polys; } @@ -179,14 +179,14 @@ class AvmMiniCircuitBuilder { return true; }; - if (!evaluate_relation.template operator()>("avm_mini", - AvmMini_vm::get_relation_label_avm_mini)) { - return false; - } if (!evaluate_relation.template operator()>( "mem_trace", AvmMini_vm::get_relation_label_mem_trace)) { return false; } + if (!evaluate_relation.template operator()>("avm_mini", + AvmMini_vm::get_relation_label_avm_mini)) { + return false; + } return true; } diff --git a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp index bbf6a5d877a0..97ab4648746e 100644 --- a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp +++ b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp @@ -7,70 +7,70 @@ namespace proof_system::AvmMini_vm { template struct Avm_miniRow { - FF avmMini_mem_idx_b{}; - FF avmMini_sel_op_div{}; - FF avmMini_ic{}; - FF avmMini_sel_jump{}; - FF avmMini_pc{}; - FF avmMini_mem_idx_a{}; - FF avmMini_sel_op_sub{}; - FF avmMini_internal_return_ptr{}; FF avmMini_sel_op_add{}; - FF avmMini_ib{}; - FF avmMini_inv{}; - FF avmMini_pc_shift{}; - FF avmMini_tag_err{}; - FF avmMini_mem_op_b{}; - FF avmMini_sel_internal_return{}; - FF avmMini_op_err{}; - FF avmMini_rwb{}; FF avmMini_mem_op_c{}; - FF avmMini_rwc{}; FF avmMini_ia{}; - FF avmMini_internal_return_ptr_shift{}; FF avmMini_sel_op_mul{}; - FF avmMini_rwa{}; + FF avmMini_internal_return_ptr_shift{}; + FF avmMini_rwc{}; FF avmMini_mem_op_a{}; - FF avmMini_sel_halt{}; + FF avmMini_mem_idx_a{}; FF avmMini_first{}; FF avmMini_sel_internal_call{}; + FF avmMini_sel_internal_return{}; + FF avmMini_mem_op_b{}; + FF avmMini_ic{}; + FF avmMini_inv{}; + FF avmMini_ib{}; + FF avmMini_pc_shift{}; + FF avmMini_rwa{}; + FF avmMini_sel_jump{}; + FF avmMini_tag_err{}; + FF avmMini_rwb{}; + FF avmMini_internal_return_ptr{}; + FF avmMini_op_err{}; + FF avmMini_sel_op_sub{}; + FF avmMini_sel_halt{}; + FF avmMini_mem_idx_b{}; + FF avmMini_sel_op_div{}; + FF avmMini_pc{}; }; inline std::string get_relation_label_avm_mini(int index) { switch (index) { + case 20: + return "SUBOP_SUBTRACTION_FF"; + + case 21: + return "SUBOP_MULTIPLICATION_FF"; + case 24: return "SUBOP_DIVISION_ZERO_ERR2"; + case 33: + return "RETURN_POINTER_DECREMENT"; + case 19: return "SUBOP_ADDITION_FF"; - case 25: - return "SUBOP_ERROR_RELEVANT_OP"; - - case 22: - return "SUBOP_DIVISION_FF"; - - case 33: - return "RETURN_POINTER_DECREMENT"; + case 38: + return "PC_INCREMENT"; case 23: return "SUBOP_DIVISION_ZERO_ERR1"; - case 21: - return "SUBOP_MULTIPLICATION_FF"; + case 22: + return "SUBOP_DIVISION_FF"; case 27: return "RETURN_POINTER_INCREMENT"; - case 38: - return "PC_INCREMENT"; - - case 20: - return "SUBOP_SUBTRACTION_FF"; - case 39: return "INTERNAL_RETURN_POINTER_CONSISTENCY"; + + case 25: + return "SUBOP_ERROR_RELEVANT_OP"; } return std::to_string(index); } @@ -336,7 +336,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(30); - auto tmp = (avmMini_sel_internal_call - (avmMini_sel_jump * avmMini_sel_internal_call)); + auto tmp = (avmMini_sel_internal_call * (avmMini_sel_internal_call - avmMini_sel_jump)); tmp *= scaling_factor; std::get<30>(evals) += tmp; } diff --git a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp index 2e660fd773ab..c37a25009dda 100644 --- a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp +++ b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp @@ -42,9 +42,9 @@ [[maybe_unused]] auto avmMini_mem_idx_b = View(new_term.avmMini_mem_idx_b); \ [[maybe_unused]] auto avmMini_mem_idx_c = View(new_term.avmMini_mem_idx_c); \ [[maybe_unused]] auto avmMini_last = View(new_term.avmMini_last); \ - [[maybe_unused]] auto avmMini_pc_shift = View(new_term.avmMini_pc_shift); \ - [[maybe_unused]] auto avmMini_internal_return_ptr_shift = View(new_term.avmMini_internal_return_ptr_shift); \ [[maybe_unused]] auto memTrace_m_val_shift = View(new_term.memTrace_m_val_shift); \ [[maybe_unused]] auto memTrace_m_rw_shift = View(new_term.memTrace_m_rw_shift); \ [[maybe_unused]] auto memTrace_m_addr_shift = View(new_term.memTrace_m_addr_shift); \ - [[maybe_unused]] auto memTrace_m_tag_shift = View(new_term.memTrace_m_tag_shift); + [[maybe_unused]] auto memTrace_m_tag_shift = View(new_term.memTrace_m_tag_shift); \ + [[maybe_unused]] auto avmMini_internal_return_ptr_shift = View(new_term.avmMini_internal_return_ptr_shift); \ + [[maybe_unused]] auto avmMini_pc_shift = View(new_term.avmMini_pc_shift); diff --git a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp index 08fdba79b36d..843f93f8783b 100644 --- a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp +++ b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp @@ -7,39 +7,39 @@ namespace proof_system::AvmMini_vm { template struct Mem_traceRow { - FF memTrace_m_last{}; - FF memTrace_m_val_shift{}; - FF memTrace_m_tag_err{}; - FF memTrace_m_addr{}; + FF memTrace_m_lastAccess{}; FF memTrace_m_rw{}; + FF memTrace_m_tag_err{}; + FF memTrace_m_val_shift{}; FF memTrace_m_val{}; + FF memTrace_m_in_tag{}; + FF memTrace_m_addr{}; FF memTrace_m_rw_shift{}; FF memTrace_m_addr_shift{}; - FF memTrace_m_tag{}; FF memTrace_m_tag_shift{}; - FF memTrace_m_lastAccess{}; - FF memTrace_m_in_tag{}; FF memTrace_m_one_min_inv{}; + FF memTrace_m_last{}; + FF memTrace_m_tag{}; }; inline std::string get_relation_label_mem_trace(int index) { switch (index) { + case 5: + return "MEM_READ_WRITE_VAL_CONSISTENCY"; + + case 7: + return "MEM_ZERO_INIT"; + case 9: return "MEM_IN_TAG_CONSISTENCY_2"; case 4: return "MEM_LAST_ACCESS_DELIMITER"; - case 5: - return "MEM_READ_WRITE_VAL_CONSISTENCY"; - case 6: return "MEM_READ_WRITE_TAG_CONSISTENCY"; - case 7: - return "MEM_ZERO_INIT"; - case 8: return "MEM_IN_TAG_CONSISTENCY_1"; } From bf218c67b7e802df1ebedc213605235e148d4f49 Mon Sep 17 00:00:00 2001 From: Maddiaa0 <47148561+Maddiaa0@users.noreply.github.com> Date: Tue, 2 Jan 2024 15:18:55 +0000 Subject: [PATCH 3/4] fix: simplify --- barretenberg/cpp/pil/avm/avm_mini.pil | 20 +++--- .../flavor/generated/AvmMini_flavor.hpp | 10 +-- .../circuit_builder/AvmMini_trace.cpp | 1 - .../generated/AvmMini_circuit_builder.hpp | 4 +- .../relations/generated/AvmMini/avm_mini.hpp | 72 +++++++++---------- .../generated/AvmMini/declare_views.hpp | 2 +- .../relations/generated/AvmMini/mem_trace.hpp | 32 ++++----- .../vm/tests/AvmMini_control_flow.test.cpp | 17 ++--- 8 files changed, 77 insertions(+), 81 deletions(-) diff --git a/barretenberg/cpp/pil/avm/avm_mini.pil b/barretenberg/cpp/pil/avm/avm_mini.pil index 3e98c3db6b5c..cd3fb8f29e4c 100644 --- a/barretenberg/cpp/pil/avm/avm_mini.pil +++ b/barretenberg/cpp/pil/avm/avm_mini.pil @@ -149,29 +149,29 @@ namespace avmMini(256); // This works in combination with op_div_err * (sel_op_div - 1) = 0; // Drawback is the need to paralllelize the latter. + //===== CONTROL FLOW ======================================================= //===== JUMP =============================================================== - // TOOD: constrain that the jump location comes from the instruction's operands sel_jump * (pc' - ia) = 0; - //===== CALL_RETURN ======================================================== - // TODO: update this comment to be correct alongside the jump implementation - - // The program counter in the next row should be equal to the value loaded from the ia register - // This implies that a load from memory must occur at the same time - // Imply that we must load the return location into mem_idx_a + //===== INTERNAL_CALL ====================================================== + // - The program counter in the next row should be equal to the value loaded from the ia register + // - We then write the return location (pc + 1) into the call stack (in memory) #[RETURN_POINTER_INCREMENT] sel_internal_call * (internal_return_ptr' - (internal_return_ptr + 1)) = 0; sel_internal_call * (internal_return_ptr - mem_idx_b) = 0; + sel_internal_call * (pc' - ia) = 0; sel_internal_call * ((pc + 1) - ib) = 0; - sel_internal_call * (sel_internal_call - sel_jump) = 0; - // TODO(md): Below relations may be removed through sub-op table lookup sel_internal_call * (rwb - 1) = 0; sel_internal_call * (mem_op_b - 1) = 0; - // We must load the memory pointer to be the internal_return_ptr + //===== INTERNAL_RETURN =================================================== + // - We load the memory pointer to be the internal_return_ptr + // - Constrain then next program counter to be the loaded value + // - decrement the internal_return_ptr + #[RETURN_POINTER_DECREMENT] sel_internal_return * (internal_return_ptr' - (internal_return_ptr - 1)) = 0; sel_internal_return * ((internal_return_ptr - 1) - mem_idx_a) = 0; diff --git a/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp b/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp index 90018578a107..9240275729e1 100644 --- a/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp +++ b/barretenberg/cpp/src/barretenberg/flavor/generated/AvmMini_flavor.hpp @@ -203,9 +203,9 @@ class AvmMiniFlavor { avmMini_mem_idx_c, avmMini_last, memTrace_m_val_shift, - memTrace_m_rw_shift, memTrace_m_addr_shift, memTrace_m_tag_shift, + memTrace_m_rw_shift, avmMini_internal_return_ptr_shift, avmMini_pc_shift) @@ -252,9 +252,9 @@ class AvmMiniFlavor { avmMini_mem_idx_c, avmMini_last, memTrace_m_val_shift, - memTrace_m_rw_shift, memTrace_m_addr_shift, memTrace_m_tag_shift, + memTrace_m_rw_shift, avmMini_internal_return_ptr_shift, avmMini_pc_shift }; }; @@ -303,15 +303,15 @@ class AvmMiniFlavor { }; RefVector get_to_be_shifted() { - return { memTrace_m_val, memTrace_m_rw, memTrace_m_addr, memTrace_m_tag, avmMini_internal_return_ptr, + return { memTrace_m_val, memTrace_m_addr, memTrace_m_tag, memTrace_m_rw, avmMini_internal_return_ptr, avmMini_pc }; }; RefVector get_shifted() { return { memTrace_m_val_shift, - memTrace_m_rw_shift, memTrace_m_addr_shift, memTrace_m_tag_shift, + memTrace_m_rw_shift, avmMini_internal_return_ptr_shift, avmMini_pc_shift }; }; @@ -326,7 +326,7 @@ class AvmMiniFlavor { RefVector get_to_be_shifted() { - return { memTrace_m_val, memTrace_m_rw, memTrace_m_addr, memTrace_m_tag, avmMini_internal_return_ptr, + return { memTrace_m_val, memTrace_m_addr, memTrace_m_tag, memTrace_m_rw, avmMini_internal_return_ptr, avmMini_pc }; }; diff --git a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.cpp b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.cpp index db1a58cee3a2..308724f2e16a 100644 --- a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.cpp +++ b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/AvmMini_trace.cpp @@ -620,7 +620,6 @@ void AvmMiniTraceBuilder::internal_call(uint32_t jmpDest) .avmMini_pc = FF(pc), .avmMini_internal_return_ptr = FF(internal_return_ptr), .avmMini_sel_internal_call = FF(1), - .avmMini_sel_jump = FF(1), .avmMini_ia = FF(jmpDest), .avmMini_ib = stored_pc, .avmMini_mem_op_b = FF(1), diff --git a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp index 1cb3977df040..bd32d969d158 100644 --- a/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp +++ b/barretenberg/cpp/src/barretenberg/proof_system/circuit_builder/generated/AvmMini_circuit_builder.hpp @@ -60,9 +60,9 @@ template struct AvmMiniFullRow { FF avmMini_mem_idx_c{}; FF avmMini_last{}; FF memTrace_m_val_shift{}; - FF memTrace_m_rw_shift{}; FF memTrace_m_addr_shift{}; FF memTrace_m_tag_shift{}; + FF memTrace_m_rw_shift{}; FF avmMini_internal_return_ptr_shift{}; FF avmMini_pc_shift{}; }; @@ -137,9 +137,9 @@ class AvmMiniCircuitBuilder { } polys.memTrace_m_val_shift = Polynomial(polys.memTrace_m_val.shifted()); - polys.memTrace_m_rw_shift = Polynomial(polys.memTrace_m_rw.shifted()); polys.memTrace_m_addr_shift = Polynomial(polys.memTrace_m_addr.shifted()); polys.memTrace_m_tag_shift = Polynomial(polys.memTrace_m_tag.shifted()); + polys.memTrace_m_rw_shift = Polynomial(polys.memTrace_m_rw.shifted()); polys.avmMini_internal_return_ptr_shift = Polynomial(polys.avmMini_internal_return_ptr.shifted()); polys.avmMini_pc_shift = Polynomial(polys.avmMini_pc.shifted()); diff --git a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp index 97ab4648746e..7ad4452af56d 100644 --- a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp +++ b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/avm_mini.hpp @@ -7,70 +7,70 @@ namespace proof_system::AvmMini_vm { template struct Avm_miniRow { - FF avmMini_sel_op_add{}; - FF avmMini_mem_op_c{}; - FF avmMini_ia{}; - FF avmMini_sel_op_mul{}; - FF avmMini_internal_return_ptr_shift{}; - FF avmMini_rwc{}; - FF avmMini_mem_op_a{}; - FF avmMini_mem_idx_a{}; FF avmMini_first{}; - FF avmMini_sel_internal_call{}; - FF avmMini_sel_internal_return{}; - FF avmMini_mem_op_b{}; - FF avmMini_ic{}; - FF avmMini_inv{}; - FF avmMini_ib{}; - FF avmMini_pc_shift{}; - FF avmMini_rwa{}; FF avmMini_sel_jump{}; + FF avmMini_internal_return_ptr_shift{}; + FF avmMini_pc{}; FF avmMini_tag_err{}; + FF avmMini_mem_idx_a{}; + FF avmMini_sel_op_add{}; FF avmMini_rwb{}; - FF avmMini_internal_return_ptr{}; + FF avmMini_rwc{}; + FF avmMini_sel_internal_return{}; + FF avmMini_rwa{}; + FF avmMini_inv{}; + FF avmMini_sel_internal_call{}; FF avmMini_op_err{}; + FF avmMini_pc_shift{}; + FF avmMini_sel_op_mul{}; + FF avmMini_sel_op_div{}; FF avmMini_sel_op_sub{}; + FF avmMini_mem_op_b{}; FF avmMini_sel_halt{}; + FF avmMini_ia{}; + FF avmMini_mem_op_a{}; + FF avmMini_ic{}; + FF avmMini_ib{}; + FF avmMini_internal_return_ptr{}; + FF avmMini_mem_op_c{}; FF avmMini_mem_idx_b{}; - FF avmMini_sel_op_div{}; - FF avmMini_pc{}; }; inline std::string get_relation_label_avm_mini(int index) { switch (index) { - case 20: - return "SUBOP_SUBTRACTION_FF"; - - case 21: - return "SUBOP_MULTIPLICATION_FF"; - case 24: return "SUBOP_DIVISION_ZERO_ERR2"; - case 33: - return "RETURN_POINTER_DECREMENT"; - - case 19: - return "SUBOP_ADDITION_FF"; + case 20: + return "SUBOP_SUBTRACTION_FF"; case 38: return "PC_INCREMENT"; + case 22: + return "SUBOP_DIVISION_FF"; + case 23: return "SUBOP_DIVISION_ZERO_ERR1"; - case 22: - return "SUBOP_DIVISION_FF"; + case 21: + return "SUBOP_MULTIPLICATION_FF"; - case 27: - return "RETURN_POINTER_INCREMENT"; + case 19: + return "SUBOP_ADDITION_FF"; + + case 33: + return "RETURN_POINTER_DECREMENT"; case 39: return "INTERNAL_RETURN_POINTER_CONSISTENCY"; case 25: return "SUBOP_ERROR_RELEVANT_OP"; + + case 27: + return "RETURN_POINTER_INCREMENT"; } return std::to_string(index); } @@ -328,7 +328,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(29); - auto tmp = (avmMini_sel_internal_call * ((avmMini_pc + FF(1)) - avmMini_ib)); + auto tmp = (avmMini_sel_internal_call * (avmMini_pc_shift - avmMini_ia)); tmp *= scaling_factor; std::get<29>(evals) += tmp; } @@ -336,7 +336,7 @@ template class avm_miniImpl { { AvmMini_DECLARE_VIEWS(30); - auto tmp = (avmMini_sel_internal_call * (avmMini_sel_internal_call - avmMini_sel_jump)); + auto tmp = (avmMini_sel_internal_call * ((avmMini_pc + FF(1)) - avmMini_ib)); tmp *= scaling_factor; std::get<30>(evals) += tmp; } diff --git a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp index c37a25009dda..2bd134b62981 100644 --- a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp +++ b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/declare_views.hpp @@ -43,8 +43,8 @@ [[maybe_unused]] auto avmMini_mem_idx_c = View(new_term.avmMini_mem_idx_c); \ [[maybe_unused]] auto avmMini_last = View(new_term.avmMini_last); \ [[maybe_unused]] auto memTrace_m_val_shift = View(new_term.memTrace_m_val_shift); \ - [[maybe_unused]] auto memTrace_m_rw_shift = View(new_term.memTrace_m_rw_shift); \ [[maybe_unused]] auto memTrace_m_addr_shift = View(new_term.memTrace_m_addr_shift); \ [[maybe_unused]] auto memTrace_m_tag_shift = View(new_term.memTrace_m_tag_shift); \ + [[maybe_unused]] auto memTrace_m_rw_shift = View(new_term.memTrace_m_rw_shift); \ [[maybe_unused]] auto avmMini_internal_return_ptr_shift = View(new_term.avmMini_internal_return_ptr_shift); \ [[maybe_unused]] auto avmMini_pc_shift = View(new_term.avmMini_pc_shift); diff --git a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp index 843f93f8783b..ef96061a9ca3 100644 --- a/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp +++ b/barretenberg/cpp/src/barretenberg/relations/generated/AvmMini/mem_trace.hpp @@ -7,41 +7,41 @@ namespace proof_system::AvmMini_vm { template struct Mem_traceRow { - FF memTrace_m_lastAccess{}; + FF memTrace_m_last{}; + FF memTrace_m_val_shift{}; FF memTrace_m_rw{}; FF memTrace_m_tag_err{}; - FF memTrace_m_val_shift{}; + FF memTrace_m_addr_shift{}; + FF memTrace_m_lastAccess{}; + FF memTrace_m_tag_shift{}; + FF memTrace_m_tag{}; FF memTrace_m_val{}; + FF memTrace_m_rw_shift{}; FF memTrace_m_in_tag{}; FF memTrace_m_addr{}; - FF memTrace_m_rw_shift{}; - FF memTrace_m_addr_shift{}; - FF memTrace_m_tag_shift{}; FF memTrace_m_one_min_inv{}; - FF memTrace_m_last{}; - FF memTrace_m_tag{}; }; inline std::string get_relation_label_mem_trace(int index) { switch (index) { - case 5: - return "MEM_READ_WRITE_VAL_CONSISTENCY"; - case 7: return "MEM_ZERO_INIT"; - case 9: - return "MEM_IN_TAG_CONSISTENCY_2"; - - case 4: - return "MEM_LAST_ACCESS_DELIMITER"; - case 6: return "MEM_READ_WRITE_TAG_CONSISTENCY"; case 8: return "MEM_IN_TAG_CONSISTENCY_1"; + + case 4: + return "MEM_LAST_ACCESS_DELIMITER"; + + case 5: + return "MEM_READ_WRITE_VAL_CONSISTENCY"; + + case 9: + return "MEM_IN_TAG_CONSISTENCY_2"; } return std::to_string(index); } diff --git a/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp b/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp index a3b4cc82fba6..cabc5b8b01e0 100644 --- a/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp +++ b/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp @@ -57,6 +57,7 @@ TEST_F(AvmMiniControlFlowTests, simpleCall) trace.begin(), trace.end(), [](Row r) { return r.avmMini_sel_internal_call == FF(1); }); EXPECT_TRUE(call_row != trace.end()); EXPECT_EQ(call_row->avmMini_pc, FF(0)); + EXPECT_EQ(call_row->avmMini_ia, FF(CALL_ADDRESS)); EXPECT_EQ(call_row->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET)); EXPECT_EQ(call_row->avmMini_ib, FF(1)); EXPECT_EQ(call_row->avmMini_mem_idx_b, @@ -78,24 +79,24 @@ TEST_F(AvmMiniControlFlowTests, simpleCall) TEST_F(AvmMiniControlFlowTests, simpleJump) { - uint32_t const CALL_ADDRESS = 4; + uint32_t const JUMP_ADDRESS = 4; // trace_builder for the following operation // pc opcode - // 0 INTERNAL_CALL(pc=4) + // 0 JUMP(pc=4) // 4 HALT - trace_builder.jump(CALL_ADDRESS); + trace_builder.jump(JUMP_ADDRESS); trace_builder.halt(); auto trace = trace_builder.finalize(); - // Check call + // Check jump { auto call_row = std::ranges::find_if(trace.begin(), trace.end(), [](Row r) { return r.avmMini_sel_jump == FF(1); }); EXPECT_TRUE(call_row != trace.end()); EXPECT_EQ(call_row->avmMini_pc, FF(0)); - EXPECT_EQ(call_row->avmMini_ia, FF(CALL_ADDRESS)); + EXPECT_EQ(call_row->avmMini_ia, FF(JUMP_ADDRESS)); } // Check halt @@ -105,7 +106,7 @@ TEST_F(AvmMiniControlFlowTests, simpleJump) // Check that the correct result is stored at the expected memory location. EXPECT_TRUE(halt_row != trace.end()); - EXPECT_EQ(halt_row->avmMini_pc, FF(CALL_ADDRESS)); + EXPECT_EQ(halt_row->avmMini_pc, FF(JUMP_ADDRESS)); } validateTraceProof(std::move(trace)); } @@ -201,7 +202,6 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) }); EXPECT_TRUE(call_1 != trace.end()); EXPECT_EQ(call_1->avmMini_pc, FF(0)); - EXPECT_EQ(call_1->avmMini_sel_jump, FF(1)); EXPECT_EQ(call_1->avmMini_ia, FF(CALL_ADDRESS_1)); EXPECT_EQ(call_1->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET)); EXPECT_EQ(call_1->avmMini_mem_idx_b, @@ -215,7 +215,6 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) }); EXPECT_TRUE(call_2 != trace.end()); EXPECT_EQ(call_2->avmMini_ib, FF(CALL_ADDRESS_1 + 1)); - EXPECT_EQ(call_2->avmMini_sel_jump, FF(1)); EXPECT_EQ(call_2->avmMini_ia, FF(CALL_ADDRESS_2)); EXPECT_EQ(call_2->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 1)); EXPECT_EQ(call_2->avmMini_mem_idx_b, @@ -229,7 +228,6 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) }); EXPECT_TRUE(call_3 != trace.end()); EXPECT_EQ(call_3->avmMini_ib, FF(CALL_ADDRESS_2 + 1)); - EXPECT_EQ(call_3->avmMini_sel_jump, FF(1)); EXPECT_EQ(call_3->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 2)); EXPECT_EQ(call_3->avmMini_mem_idx_b, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 2)); // Store the return address (0) in memory @@ -251,7 +249,6 @@ TEST_F(AvmMiniControlFlowTests, multipleCallsAndReturns) }); EXPECT_TRUE(call_4 != trace.end()); EXPECT_EQ(call_4->avmMini_ib, FF(CALL_ADDRESS_2 + 2)); - EXPECT_EQ(call_4->avmMini_sel_jump, FF(1)); EXPECT_EQ(call_4->avmMini_internal_return_ptr, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 2)); EXPECT_EQ(call_4->avmMini_mem_idx_b, FF(AvmMiniTraceBuilder::CALLSTACK_OFFSET + 2)); // Store the return address (0) in memory From 20112cfb5c8313d17b26705ee37ec8c610f7c181 Mon Sep 17 00:00:00 2001 From: Maddiaa0 <47148561+Maddiaa0@users.noreply.github.com> Date: Tue, 2 Jan 2024 16:44:52 +0000 Subject: [PATCH 4/4] fix --- .../cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp b/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp index cabc5b8b01e0..c771ad6eaf6b 100644 --- a/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp +++ b/barretenberg/cpp/src/barretenberg/vm/tests/AvmMini_control_flow.test.cpp @@ -37,7 +37,6 @@ class AvmMiniControlFlowTests : public ::testing::Test { * *****************************************************************************/ -// TODO: add jump selector checks in here! TEST_F(AvmMiniControlFlowTests, simpleCall) { uint32_t const CALL_ADDRESS = 4; @@ -104,7 +103,6 @@ TEST_F(AvmMiniControlFlowTests, simpleJump) auto halt_row = std::ranges::find_if(trace.begin(), trace.end(), [](Row r) { return r.avmMini_sel_halt == FF(1); }); - // Check that the correct result is stored at the expected memory location. EXPECT_TRUE(halt_row != trace.end()); EXPECT_EQ(halt_row->avmMini_pc, FF(JUMP_ADDRESS)); }