Skip to content

Commit

Permalink
Merge 26ec4fa into 8d7f1f9
Browse files Browse the repository at this point in the history
  • Loading branch information
TomAFrench authored Jan 8, 2025
2 parents 8d7f1f9 + 26ec4fa commit e0d9016
Showing 1 changed file with 33 additions and 12 deletions.
45 changes: 33 additions & 12 deletions compiler/noirc_evaluator/src/ssa/opt/flatten_cfg/value_merger.rs
Original file line number Diff line number Diff line change
Expand Up @@ -117,18 +117,39 @@ impl<'a> ValueMerger<'a> {
let then_condition =
dfg.insert_instruction_and_results(cast, block, None, call_stack).first();

let cast = Instruction::Cast(else_condition, else_type);
let else_condition =
dfg.insert_instruction_and_results(cast, block, None, call_stack).first();

let mul = Instruction::binary(BinaryOp::Mul, then_condition, then_value);
let then_value = dfg.insert_instruction_and_results(mul, block, None, call_stack).first();

let mul = Instruction::binary(BinaryOp::Mul, else_condition, else_value);
let else_value = dfg.insert_instruction_and_results(mul, block, None, call_stack).first();

let add = Instruction::binary(BinaryOp::Add, then_value, else_value);
dfg.insert_instruction_and_results(add, block, None, call_stack).first()
if then_type == NumericType::NativeField {
// We're merging two fields so we can do a more efficient value merger as by converting
// the expression `if c { a } else { b }` as `c * (a-b) + b`.
//
// This removes a multiplication compared to the standard `c*a + (!c)*b`.

let diff = Instruction::binary(BinaryOp::Sub, then_value, else_value);
let diff_value =
dfg.insert_instruction_and_results(diff, block, None, call_stack).first();

let conditional_diff = Instruction::binary(BinaryOp::Mul, then_condition, diff_value);
let conditional_diff_value = dfg
.insert_instruction_and_results(conditional_diff, block, None, call_stack)
.first();

let merged_field =
Instruction::binary(BinaryOp::Add, else_value, conditional_diff_value);
dfg.insert_instruction_and_results(merged_field, block, None, call_stack)
.first()
} else {
let cast = Instruction::Cast(else_condition, else_type);
let else_condition =
dfg.insert_instruction_and_results(cast, block, None, call_stack).first();

let mul = Instruction::binary(BinaryOp::Mul, then_condition, then_value);
let then_value = dfg.insert_instruction_and_results(mul, block, None, call_stack).first();

let mul = Instruction::binary(BinaryOp::Mul, else_condition, else_value);
let else_value = dfg.insert_instruction_and_results(mul, block, None, call_stack).first();

let add = Instruction::binary(BinaryOp::Add, then_value, else_value);
dfg.insert_instruction_and_results(add, block, None, call_stack).first()
}
}

/// Given an if expression that returns an array: `if c { array1 } else { array2 }`,
Expand Down

0 comments on commit e0d9016

Please sign in to comment.