Skip to content

Commit

Permalink
feat: Sync from aztec-packages (#6403)
Browse files Browse the repository at this point in the history
Co-authored-by: Tom French <[email protected]>
  • Loading branch information
AztecBot and TomAFrench authored Oct 30, 2024
1 parent 4e44e1f commit 321a493
Show file tree
Hide file tree
Showing 25 changed files with 200 additions and 116 deletions.
2 changes: 1 addition & 1 deletion .aztec-sync-commit
Original file line number Diff line number Diff line change
@@ -1 +1 @@
07d6dc29db2eb04154b8f0c66bd1efa74c0e8b9d
d9de430e4a01d6908a9b1fe5e6ede9309aa8a10d
2 changes: 1 addition & 1 deletion acvm-repo/acir/codegen/acir.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -694,7 +694,7 @@ namespace Program {
};

struct Trap {
Program::HeapArray revert_data;
Program::HeapVector revert_data;

friend bool operator==(const Trap&, const Trap&);
std::vector<uint8_t> bincodeSerialize() const;
Expand Down
18 changes: 14 additions & 4 deletions acvm-repo/acvm/tests/solver.rs
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
use std::collections::{BTreeMap, HashSet};
use std::sync::Arc;

use acir::brillig::{BitSize, IntegerBitSize};
use acir::brillig::{BitSize, HeapVector, IntegerBitSize};
use acir::{
acir_field::GenericFieldElement,
brillig::{BinaryFieldOp, HeapArray, MemoryAddress, Opcode as BrilligOpcode, ValueOrArray},
brillig::{BinaryFieldOp, MemoryAddress, Opcode as BrilligOpcode, ValueOrArray},
circuit::{
brillig::{BrilligBytecode, BrilligFunctionId, BrilligInputs, BrilligOutputs},
opcodes::{BlackBoxFuncCall, BlockId, BlockType, FunctionInput, MemOp},
Expand Down Expand Up @@ -667,7 +667,12 @@ fn unsatisfied_opcode_resolved_brillig() {
let jmp_if_opcode =
BrilligOpcode::JumpIf { condition: MemoryAddress::direct(2), location: location_of_stop };

let trap_opcode = BrilligOpcode::Trap { revert_data: HeapArray::default() };
let trap_opcode = BrilligOpcode::Trap {
revert_data: HeapVector {
pointer: MemoryAddress::direct(0),
size: MemoryAddress::direct(3),
},
};
let stop_opcode = BrilligOpcode::Stop { return_data_offset: 0, return_data_size: 0 };

let brillig_bytecode = BrilligBytecode {
Expand All @@ -682,6 +687,11 @@ fn unsatisfied_opcode_resolved_brillig() {
bit_size: BitSize::Integer(IntegerBitSize::U32),
value: FieldElement::from(0u64),
},
BrilligOpcode::Const {
destination: MemoryAddress::direct(3),
bit_size: BitSize::Integer(IntegerBitSize::U32),
value: FieldElement::from(0u64),
},
calldata_copy_opcode,
equal_opcode,
jmp_if_opcode,
Expand Down Expand Up @@ -739,7 +749,7 @@ fn unsatisfied_opcode_resolved_brillig() {
ACVMStatus::Failure(OpcodeResolutionError::BrilligFunctionFailed {
function_id: BrilligFunctionId(0),
payload: None,
call_stack: vec![OpcodeLocation::Brillig { acir_index: 0, brillig_index: 5 }]
call_stack: vec![OpcodeLocation::Brillig { acir_index: 0, brillig_index: 6 }]
}),
"The first opcode is not satisfiable, expected an error indicating this"
);
Expand Down
2 changes: 1 addition & 1 deletion acvm-repo/brillig/src/opcodes.rs
Original file line number Diff line number Diff line change
Expand Up @@ -305,7 +305,7 @@ pub enum BrilligOpcode<F> {
BlackBox(BlackBoxOp),
/// Used to denote execution failure, returning data after the offset
Trap {
revert_data: HeapArray,
revert_data: HeapVector,
},
/// Stop execution, returning data after the offset
Stop {
Expand Down
10 changes: 5 additions & 5 deletions acvm-repo/brillig_vm/src/black_box.rs
Original file line number Diff line number Diff line change
Expand Up @@ -330,18 +330,18 @@ pub(crate) fn evaluate_black_box<F: AcirField, Solver: BlackBoxFunctionSolver<F>
let mut input = BigUint::from_bytes_be(&input.to_be_bytes());
let radix = BigUint::from_bytes_be(&radix.to_be_bytes());

let mut limbs: Vec<MemoryValue<F>> = Vec::with_capacity(output.size);
let mut limbs: Vec<MemoryValue<F>> = vec![MemoryValue::default(); output.size];

for _ in 0..output.size {
for i in (0..output.size).rev() {
let limb = &input % &radix;
if *output_bits {
limbs.push(MemoryValue::new_integer(
limbs[i] = MemoryValue::new_integer(
if limb.is_zero() { 0 } else { 1 },
IntegerBitSize::U1,
));
);
} else {
let limb: u8 = limb.try_into().unwrap();
limbs.push(MemoryValue::new_integer(limb as u128, IntegerBitSize::U8));
limbs[i] = MemoryValue::new_integer(limb as u128, IntegerBitSize::U8);
};
input /= &radix;
}
Expand Down
23 changes: 18 additions & 5 deletions acvm-repo/brillig_vm/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -347,10 +347,11 @@ impl<'a, F: AcirField, B: BlackBoxFunctionSolver<F>> VM<'a, F, B> {
self.increment_program_counter()
}
Opcode::Trap { revert_data } => {
if revert_data.size > 0 {
let revert_data_size = self.memory.read(revert_data.size).to_usize();
if revert_data_size > 0 {
self.trap(
self.memory.read_ref(revert_data.pointer).unwrap_direct(),
revert_data.size,
revert_data_size,
)
} else {
self.trap(0, 0)
Expand Down Expand Up @@ -937,8 +938,18 @@ mod tests {
size_address: MemoryAddress::direct(0),
offset_address: MemoryAddress::direct(1),
},
Opcode::Jump { location: 5 },
Opcode::Trap { revert_data: HeapArray::default() },
Opcode::Jump { location: 6 },
Opcode::Const {
destination: MemoryAddress::direct(0),
bit_size: BitSize::Integer(IntegerBitSize::U32),
value: FieldElement::from(0u64),
},
Opcode::Trap {
revert_data: HeapVector {
pointer: MemoryAddress::direct(0),
size: MemoryAddress::direct(0),
},
},
Opcode::BinaryFieldOp {
op: BinaryFieldOp::Equals,
lhs: MemoryAddress::direct(0),
Expand Down Expand Up @@ -966,6 +977,8 @@ mod tests {
assert_eq!(status, VMStatus::InProgress);
let status = vm.process_opcode();
assert_eq!(status, VMStatus::InProgress);
let status = vm.process_opcode();
assert_eq!(status, VMStatus::InProgress);

let output_cmp_value = vm.memory.read(MemoryAddress::direct(2));
assert_eq!(output_cmp_value.to_field(), false.into());
Expand All @@ -978,7 +991,7 @@ mod tests {
status,
VMStatus::Failure {
reason: FailureReason::Trap { revert_data_offset: 0, revert_data_size: 0 },
call_stack: vec![4]
call_stack: vec![5]
}
);

Expand Down
2 changes: 1 addition & 1 deletion compiler/integration-tests/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
"lint": "NODE_NO_WARNINGS=1 eslint . --ext .ts --ignore-path ./.eslintignore --max-warnings 0"
},
"dependencies": {
"@aztec/bb.js": "0.60.0",
"@aztec/bb.js": "0.61.0",
"@noir-lang/noir_js": "workspace:*",
"@noir-lang/noir_wasm": "workspace:*",
"@nomicfoundation/hardhat-chai-matchers": "^2.0.0",
Expand Down
28 changes: 26 additions & 2 deletions compiler/noirc_evaluator/src/brillig/brillig_gen/brillig_block.rs
Original file line number Diff line number Diff line change
Expand Up @@ -548,7 +548,7 @@ impl<'block> BrilligBlock<'block> {
source,
target_array,
radix,
matches!(endianness, Endian::Big),
matches!(endianness, Endian::Little),
false,
);
}
Expand All @@ -573,7 +573,7 @@ impl<'block> BrilligBlock<'block> {
source,
target_array,
two,
matches!(endianness, Endian::Big),
matches!(endianness, Endian::Little),
true,
);

Expand All @@ -583,7 +583,31 @@ impl<'block> BrilligBlock<'block> {
// `Intrinsic::AsWitness` is used to provide hints to acir-gen on optimal expression splitting.
// It is then useless in the brillig runtime and so we can ignore it
Value::Intrinsic(Intrinsic::AsWitness) => (),
Value::Intrinsic(Intrinsic::FieldLessThan) => {
let lhs = self.convert_ssa_single_addr_value(arguments[0], dfg);
assert!(lhs.bit_size == FieldElement::max_num_bits());
let rhs = self.convert_ssa_single_addr_value(arguments[1], dfg);
assert!(rhs.bit_size == FieldElement::max_num_bits());

let results = dfg.instruction_results(instruction_id);
let destination = self
.variables
.define_variable(
self.function_context,
self.brillig_context,
results[0],
dfg,
)
.extract_single_addr();
assert!(destination.bit_size == 1);

self.brillig_context.binary_instruction(
lhs,
rhs,
destination,
BrilligBinaryOp::LessThan,
);
}
_ => {
unreachable!("unsupported function call type {:?}", dfg[*func])
}
Expand Down
18 changes: 14 additions & 4 deletions compiler/noirc_evaluator/src/brillig/brillig_ir.rs
Original file line number Diff line number Diff line change
Expand Up @@ -146,8 +146,8 @@ pub(crate) mod tests {
use std::vec;

use acvm::acir::brillig::{
BitSize, ForeignCallParam, ForeignCallResult, HeapArray, HeapVector, IntegerBitSize,
MemoryAddress, ValueOrArray,
BitSize, ForeignCallParam, ForeignCallResult, HeapVector, IntegerBitSize, MemoryAddress,
ValueOrArray,
};
use acvm::brillig_vm::brillig::HeapValueType;
use acvm::brillig_vm::{VMStatus, VM};
Expand Down Expand Up @@ -289,8 +289,18 @@ pub(crate) mod tests {
// We push a JumpIf and Trap opcode directly as the constrain instruction
// uses unresolved jumps which requires a block to be constructed in SSA and
// we don't need this for Brillig IR tests
context.push_opcode(BrilligOpcode::JumpIf { condition: r_equality, location: 8 });
context.push_opcode(BrilligOpcode::Trap { revert_data: HeapArray::default() });
context.push_opcode(BrilligOpcode::JumpIf { condition: r_equality, location: 9 });
context.push_opcode(BrilligOpcode::Const {
destination: MemoryAddress::direct(0),
bit_size: BitSize::Integer(IntegerBitSize::U32),
value: FieldElement::from(0u64),
});
context.push_opcode(BrilligOpcode::Trap {
revert_data: HeapVector {
pointer: MemoryAddress::direct(0),
size: MemoryAddress::direct(0),
},
});

context.stop_instruction();

Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
use acvm::{
acir::brillig::{HeapArray, MemoryAddress},
acir::brillig::{HeapVector, MemoryAddress},
AcirField,
};

Expand Down Expand Up @@ -192,12 +192,12 @@ impl<F: AcirField + DebugToString, Registers: RegisterAllocator> BrilligContext<
assert!(condition.bit_size == 1);

self.codegen_if_not(condition.address, |ctx| {
let revert_data = HeapArray {
pointer: ctx.allocate_register(),
// + 1 due to the revert data id being the first item returned
size: Self::flattened_tuple_size(&revert_data_types) + 1,
};
ctx.codegen_allocate_immediate_mem(revert_data.pointer, revert_data.size);
// + 1 due to the revert data id being the first item returned
let revert_data_size = Self::flattened_tuple_size(&revert_data_types) + 1;
let revert_data_size_var = ctx.make_usize_constant_instruction(revert_data_size.into());
let revert_data =
HeapVector { pointer: ctx.allocate_register(), size: revert_data_size_var.address };
ctx.codegen_allocate_immediate_mem(revert_data.pointer, revert_data_size);

let current_revert_data_pointer = ctx.allocate_register();
ctx.mov_instruction(current_revert_data_pointer, revert_data.pointer);
Expand Down Expand Up @@ -243,6 +243,7 @@ impl<F: AcirField + DebugToString, Registers: RegisterAllocator> BrilligContext<
);
}
ctx.trap_instruction(revert_data);
ctx.deallocate_single_addr(revert_data_size_var);
ctx.deallocate_register(revert_data.pointer);
ctx.deallocate_register(current_revert_data_pointer);
});
Expand All @@ -258,7 +259,12 @@ impl<F: AcirField + DebugToString, Registers: RegisterAllocator> BrilligContext<
assert!(condition.bit_size == 1);

self.codegen_if_not(condition.address, |ctx| {
ctx.trap_instruction(HeapArray::default());
let revert_data_size_var = ctx.make_usize_constant_instruction(F::zero());
ctx.trap_instruction(HeapVector {
pointer: MemoryAddress::direct(0),
size: revert_data_size_var.address,
});
ctx.deallocate_single_addr(revert_data_size_var);
if let Some(assert_message) = assert_message {
ctx.obj.add_assert_message_to_last_opcode(assert_message);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ impl<F: AcirField + DebugToString, Registers: RegisterAllocator> BrilligContext<
source_field: SingleAddrVariable,
target_array: BrilligArray,
radix: SingleAddrVariable,
big_endian: bool,
little_endian: bool,
output_bits: bool, // If true will generate bit limbs, if false will generate byte limbs
) {
assert!(source_field.bit_size == F::max_num_bits());
Expand All @@ -79,14 +79,15 @@ impl<F: AcirField + DebugToString, Registers: RegisterAllocator> BrilligContext<

let heap_array = self.codegen_brillig_array_to_heap_array(target_array);

// Perform big-endian ToRadix
self.black_box_op_instruction(BlackBoxOp::ToRadix {
input: source_field.address,
radix: radix.address,
output: heap_array,
output_bits,
});

if big_endian {
if little_endian {
let items_len = self.make_usize_constant_instruction(target_array.size.into());
self.codegen_array_reverse(heap_array.pointer, items_len.address);
self.deallocate_single_addr(items_len);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,7 @@ impl DebugShow {
}

/// Emits a `trap` instruction.
pub(crate) fn trap_instruction(&self, revert_data: HeapArray) {
pub(crate) fn trap_instruction(&self, revert_data: HeapVector) {
debug_println!(self.enable_debug_trace, " TRAP {}", revert_data);
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
use acvm::{
acir::{
brillig::{
BinaryFieldOp, BinaryIntOp, BitSize, BlackBoxOp, HeapArray, HeapValueType,
BinaryFieldOp, BinaryIntOp, BitSize, BlackBoxOp, HeapValueType, HeapVector,
MemoryAddress, Opcode as BrilligOpcode, ValueOrArray,
},
AcirField,
Expand Down Expand Up @@ -425,7 +425,7 @@ impl<F: AcirField + DebugToString, Registers: RegisterAllocator> BrilligContext<
self.deallocate_single_addr(offset_var);
}

pub(super) fn trap_instruction(&mut self, revert_data: HeapArray) {
pub(super) fn trap_instruction(&mut self, revert_data: HeapVector) {
self.debug_show.trap_instruction(revert_data);

self.push_opcode(BrilligOpcode::Trap { revert_data });
Expand Down
3 changes: 3 additions & 0 deletions compiler/noirc_evaluator/src/ssa/acir_gen/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2789,6 +2789,9 @@ impl<'a> Context<'a> {
Intrinsic::DerivePedersenGenerators => {
unreachable!("DerivePedersenGenerators can only be called with constants")
}
Intrinsic::FieldLessThan => {
unreachable!("FieldLessThan can only be called in unconstrained")
}
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -218,7 +218,8 @@ impl Context {
| Intrinsic::StaticAssert
| Intrinsic::StrAsBytes
| Intrinsic::ToBits(..)
| Intrinsic::ToRadix(..) => {
| Intrinsic::ToRadix(..)
| Intrinsic::FieldLessThan => {
self.value_sets.push(instruction_arguments_and_results);
}
},
Expand Down
7 changes: 6 additions & 1 deletion compiler/noirc_evaluator/src/ssa/ir/instruction.rs
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@ pub(crate) enum Intrinsic {
AsWitness,
IsUnconstrained,
DerivePedersenGenerators,
FieldLessThan,
}

impl std::fmt::Display for Intrinsic {
Expand Down Expand Up @@ -100,6 +101,7 @@ impl std::fmt::Display for Intrinsic {
Intrinsic::AsWitness => write!(f, "as_witness"),
Intrinsic::IsUnconstrained => write!(f, "is_unconstrained"),
Intrinsic::DerivePedersenGenerators => write!(f, "derive_pedersen_generators"),
Intrinsic::FieldLessThan => write!(f, "field_less_than"),
}
}
}
Expand Down Expand Up @@ -131,7 +133,8 @@ impl Intrinsic {
| Intrinsic::FromField
| Intrinsic::AsField
| Intrinsic::IsUnconstrained
| Intrinsic::DerivePedersenGenerators => false,
| Intrinsic::DerivePedersenGenerators
| Intrinsic::FieldLessThan => false,

// Some black box functions have side-effects
Intrinsic::BlackBox(func) => matches!(
Expand Down Expand Up @@ -169,6 +172,8 @@ impl Intrinsic {
"as_witness" => Some(Intrinsic::AsWitness),
"is_unconstrained" => Some(Intrinsic::IsUnconstrained),
"derive_pedersen_generators" => Some(Intrinsic::DerivePedersenGenerators),
"field_less_than" => Some(Intrinsic::FieldLessThan),

other => BlackBoxFunc::lookup(other).map(Intrinsic::BlackBox),
}
}
Expand Down
Loading

0 comments on commit 321a493

Please sign in to comment.