-
Notifications
You must be signed in to change notification settings - Fork 318
fix(acir_gen): Keep range checks before side effects #9340
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
⚠️ Performance Alert ⚠️
Possible performance regression was detected for benchmark 'Execution Time'.
Benchmark result of this commit is worse than the previous benchmark result exceeding threshold 1.20
.
Benchmark suite | Current: 48468a5 | Previous: 1748cbe | Ratio |
---|---|---|---|
sha512-100-bytes |
0.14 s |
0.11 s |
1.27 |
This comment was automatically generated by workflow using github-action-benchmark.
CC: @TomAFrench
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
⚠️ Performance Alert ⚠️
Possible performance regression was detected for benchmark 'Opcode count'.
Benchmark result of this commit is worse than the previous benchmark result exceeding threshold 1.10
.
Benchmark suite | Current: 752d323 | Previous: 18b01b3 | Ratio |
---|---|---|---|
sha512-100-bytes |
22229 opcodes |
13173 opcodes |
1.69 |
This comment was automatically generated by workflow using github-action-benchmark.
CC: @TomAFrench
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
⚠️ Performance Alert ⚠️
Possible performance regression was detected for benchmark 'Test Suite Duration'.
Benchmark result of this commit is worse than the previous benchmark result exceeding threshold 1.20
.
Benchmark suite | Current: 53f0187 | Previous: 8d78909 | Ratio |
---|---|---|---|
test_report_zkpassport_noir-ecdsa_ |
3 s |
2 s |
1.50 |
This comment was automatically generated by workflow using github-action-benchmark.
CC: @TomAFrench
ce9056f
to
752d323
Compare
Changes to circuit sizes
🧾 Summary (10% most significant diffs)
Full diff report 👇
|
For the fn main(message: pub str<11>, y: Field, hex_as_string: str<4>, hex_as_field: Field) {
...
std::println(10);
...
assert(hex_as_string == "0x41");
...
} They range constraints to restrict all 4 characters in
I moved the assertion to the top of the program to let it remove the range checks. |
…ng/noir into af/9335-fix-acir-redundant-range
I investigated the regression on We had for example this code: fn main(x: u32) {
lambdas_in_array_literal(x - 1);
}
fn lambdas_in_array_literal(x: u32) {
let xs = [|| println("hi"), || println("bye"), || println("wow"), || println("big")];
(xs[x])();
} Resulting in this ACIR:
So the array has 4 elements and we got a RANGE constraint to limit
I changed this so MEM is allowed to take precedence over RANGE, and by limiting the number of bits to what is required to represent the maximum index value, rather than the array size. (In the original code |
Review the following changes in direct dependencies. Learn more about Socket for GitHub.
|
Will be taking a look today. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks good! I would like to get the ACIR parser working in other crates but we can do that in follow-up work. One of the main reasons for the ACIR parser was being able to test the ACVM compiler as well as the ACIR gen which both live in different crates.
Automated pull of nightly from the [noir](https://github.com/noir-lang/noir) programming language, a dependency of Aztec. BEGIN_COMMIT_OVERRIDE chore: some mem2reg refactors regarding expressions and aliases (noir-lang/noir#9610) feat: keep last loads from predecessors in mem2reg (noir-lang/noir#9492) chore: Update flattening docs (noir-lang/noir#9588) chore: remove redundant globals creation (noir-lang/noir#9606) chore: simplify Expression in mem2reg (noir-lang/noir#9599) chore: remove duplicate `contains_reference` in mem2reg (noir-lang/noir#9602) chore!: remove `verify_signature_slice` methods from stdlib (noir-lang/noir#9597) fix(expand): correctly handle nested dereferences (noir-lang/noir#9598) fix(ssa): Do not simplify on lhs being zero for shifts (noir-lang/noir#9596) chore: store last loads in `HashSet` instead of `HashMap` in mem2reg (noir-lang/noir#9498) chore: `--no-ssa-locations` for `nargo interpret` and show negative values when printing SSA (noir-lang/noir#9586) fix: `assert_constant` refactors and fixes from audit (noir-lang/noir#9547) fix(ssa): Consider `shl` and `shr` to have side effects (noir-lang/noir#9580) fix: avoid invalid cast in `remove_bit_shifts` (noir-lang/noir#9570) fix(mem2reg): Consider aliases of a loaded address to be loaded from as well (noir-lang/noir#9567) fix: Consume correct number of fields when printing references (noir-lang/noir#9579) chore: Add a section for numeric type aliases (noir-lang/noir#9589) chore(remove_paired_rc): Add various unit tests (noir-lang/noir#9425) fix: incorrect max bit size in `remove_bit_shifts` (noir-lang/noir#9585) chore(ssa): Simplify shl/shr identity operations (noir-lang/noir#9587) chore: greenlight `brillig_array_get_and_set` for audits (noir-lang/noir#9540) chore(ssa): Update comments on `loop_invariant` for audit and some missing unit tests (noir-lang/noir#9574) chore: Switch to node v22.15.0 (noir-lang/noir#9582) chore: Update unrolling docs for audit (noir-lang/noir#9572) chore: greenlight `array_set_optimization` (noir-lang/noir#9560) fix(acir_gen): Keep range checks before side effects (noir-lang/noir#9340) END_COMMIT_OVERRIDE
Automated pull of nightly from the [noir](https://github.com/noir-lang/noir) programming language, a dependency of Aztec. BEGIN_COMMIT_OVERRIDE chore: some mem2reg refactors regarding expressions and aliases (noir-lang/noir#9610) feat: keep last loads from predecessors in mem2reg (noir-lang/noir#9492) chore: Update flattening docs (noir-lang/noir#9588) chore: remove redundant globals creation (noir-lang/noir#9606) chore: simplify Expression in mem2reg (noir-lang/noir#9599) chore: remove duplicate `contains_reference` in mem2reg (noir-lang/noir#9602) chore!: remove `verify_signature_slice` methods from stdlib (noir-lang/noir#9597) fix(expand): correctly handle nested dereferences (noir-lang/noir#9598) fix(ssa): Do not simplify on lhs being zero for shifts (noir-lang/noir#9596) chore: store last loads in `HashSet` instead of `HashMap` in mem2reg (noir-lang/noir#9498) chore: `--no-ssa-locations` for `nargo interpret` and show negative values when printing SSA (noir-lang/noir#9586) fix: `assert_constant` refactors and fixes from audit (noir-lang/noir#9547) fix(ssa): Consider `shl` and `shr` to have side effects (noir-lang/noir#9580) fix: avoid invalid cast in `remove_bit_shifts` (noir-lang/noir#9570) fix(mem2reg): Consider aliases of a loaded address to be loaded from as well (noir-lang/noir#9567) fix: Consume correct number of fields when printing references (noir-lang/noir#9579) chore: Add a section for numeric type aliases (noir-lang/noir#9589) chore(remove_paired_rc): Add various unit tests (noir-lang/noir#9425) fix: incorrect max bit size in `remove_bit_shifts` (noir-lang/noir#9585) chore(ssa): Simplify shl/shr identity operations (noir-lang/noir#9587) chore: greenlight `brillig_array_get_and_set` for audits (noir-lang/noir#9540) chore(ssa): Update comments on `loop_invariant` for audit and some missing unit tests (noir-lang/noir#9574) chore: Switch to node v22.15.0 (noir-lang/noir#9582) chore: Update unrolling docs for audit (noir-lang/noir#9572) chore: greenlight `array_set_optimization` (noir-lang/noir#9560) fix(acir_gen): Keep range checks before side effects (noir-lang/noir#9340) END_COMMIT_OVERRIDE
Automated pull of nightly from the [noir](https://github.com/noir-lang/noir) programming language, a dependency of Aztec. BEGIN_COMMIT_OVERRIDE chore: some mem2reg refactors regarding expressions and aliases (noir-lang/noir#9610) feat: keep last loads from predecessors in mem2reg (noir-lang/noir#9492) chore: Update flattening docs (noir-lang/noir#9588) chore: remove redundant globals creation (noir-lang/noir#9606) chore: simplify Expression in mem2reg (noir-lang/noir#9599) chore: remove duplicate `contains_reference` in mem2reg (noir-lang/noir#9602) chore!: remove `verify_signature_slice` methods from stdlib (noir-lang/noir#9597) fix(expand): correctly handle nested dereferences (noir-lang/noir#9598) fix(ssa): Do not simplify on lhs being zero for shifts (noir-lang/noir#9596) chore: store last loads in `HashSet` instead of `HashMap` in mem2reg (noir-lang/noir#9498) chore: `--no-ssa-locations` for `nargo interpret` and show negative values when printing SSA (noir-lang/noir#9586) fix: `assert_constant` refactors and fixes from audit (noir-lang/noir#9547) fix(ssa): Consider `shl` and `shr` to have side effects (noir-lang/noir#9580) fix: avoid invalid cast in `remove_bit_shifts` (noir-lang/noir#9570) fix(mem2reg): Consider aliases of a loaded address to be loaded from as well (noir-lang/noir#9567) fix: Consume correct number of fields when printing references (noir-lang/noir#9579) chore: Add a section for numeric type aliases (noir-lang/noir#9589) chore(remove_paired_rc): Add various unit tests (noir-lang/noir#9425) fix: incorrect max bit size in `remove_bit_shifts` (noir-lang/noir#9585) chore(ssa): Simplify shl/shr identity operations (noir-lang/noir#9587) chore: greenlight `brillig_array_get_and_set` for audits (noir-lang/noir#9540) chore(ssa): Update comments on `loop_invariant` for audit and some missing unit tests (noir-lang/noir#9574) chore: Switch to node v22.15.0 (noir-lang/noir#9582) chore: Update unrolling docs for audit (noir-lang/noir#9572) chore: greenlight `array_set_optimization` (noir-lang/noir#9560) fix(acir_gen): Keep range checks before side effects (noir-lang/noir#9340) END_COMMIT_OVERRIDE
Description
Problem*
Resolves #9335
Summary*
Changes the
redundant_range
optimisation to keep range constraints which are stricter than the previously known constraint, unless there is an even stricter constraint further down the line and before the next potential side effect.To minimise the increase in opcodes, I'm passing some information about Brillig functions to the ACIR optimisers, which should indicate whether they might have visible side effects, currently defined as calling oracle functions.
The new version also treats MEM operations like it used to handle assertions in that it is considered to replace an equivalent strength RANGE constraint.
Additional Context
Take this code, where the multiplication can result in an overflow:
This resulted in the following ACIR:
So
a
is_0
,b
is_2
, and_2
is range constrained to fit into 64 bits, which catches any overflow before we pass_2
to the Brillig call.With the
assert
uncomment the ACIR changes into this:_2
is now constrained to equal -2288862572, which implies 32 bits; this results in the removal of the 64 bit range constraint, because the optimisation pass knows it can save this opcode because there will be a stricter one. However, this allows the circuit to execute the Brillig call, which has a visible side effect.With the changes in this PR, the new ACIR looks like this:
We keep the range constraint on
_2
, with the 64 bits it used originally (see discussion below for why using 32 bits would be incorrect).A different example is the following (notice that we don't print
b
, just something completely unrelated):If we delay the constraint on
b
until theassert
, we see the effect ofprintln
; for this reason we keep any range constraint that straddles a side effect, not just constraints on the inputs/outputs of Brillig calls.To illustrate in a different way:
Documentation*
Check one:
PR Checklist*
cargo fmt
on default settings.