10813 commits in all time Jan 20, 2026 05:36 – Apr 20, 2026 05:36 UTC
achidlow puya
test: add coverage test case for StaticallyFailingOpValidator
Exercises every warning-emitting branch in statically_failing_op.py (both the top-level `_check` match arms and the three helpers' immediate-form / stack-form / None-fallthrough paths). Hits 100% line coverage of the validator via a single test case:

  coverage run -m pytest tests/test_compile.py -k statically_failing_ops -o addopts=""
  coverage report -m --include="src/puya/ir/validation/statically_failing_op.py"

Overlaps deliberately with a handful of the existing regression_tests cases since this is targeted at coverage completeness rather than regression pinning.
Git Commit e4396587 Branch feat/statically-failing-op-validator Document 55/7,680 ++ 0 --
achidlow puya
minor refactor
Git Commit 42ec51a9 Branch feat/statically-failing-op-validator Document 1/57 ++ 34 --
achidlow puya
chore: compile all
Git Commit 6c134dd0 Branch feat/statically-failing-op-validator Document 3/39 ++ 0 --
achidlow puya
add StaticallyFailingOpValidator
Post-destructuring IR pass that emits a compile-time warning when an AVM op is statically known to fail at runtime given its constant arguments. Mirrors the guard conditions that `intrinsic_simplification` uses to bail out of folding.

Covers:
- arithmetic: +, -, *, /, %, exp (overflow / underflow / div-by-zero / 0**0)
- shifts: shl, shr (amount >= 64)
- conversion: btoi (len > 8), bzero (len > 4096)
- extract / extract3 / extract_uint{16,32,64}
- substring / substring3
- replace2 / replace3
- getbit / setbit (uint64 and bytes variants)
- getbyte / setbyte

Handles both immediate-form and stack-arg form where the AVM op has both (e.g. extract vs extract3).
Git Commit cbd32a20 Branch feat/statically-failing-op-validator Document 2/178 ++ 0 --
renovate[bot] use-wallet
Merge 6f7c6259a5bbd81f2288d2f5c967c3a19cde723c into 5073ca134b7c4c5721fcfbe976d5c364a5cc777a
Git Commit 8e184705 Branch pull/436/merge Document 1/1 ++ 1 --
renovate[bot] use-wallet
chore(deps): update actions/setup-node action to v5
Git Commit 6f7c6259 Branch renovate/actions-setup-node-5.x Document 1/1 ++ 1 --
achidlow puya
Merge 24cfcbe0a4ffd1832dec21757018574964ac30fa into ac3f3fa69648dabbdbe542599a1f4024567c6979
Git Commit 77167b5b Branch pull/707/merge Document 163/9,054 ++ 3,023 --
achidlow puya
chore: compile all
Git Commit 24cfcbe0 Branch fix/logical-fold-non-bool Document 53/3,424 ++ 3,018 --
achidlow puya
test: add coverage for || identity folding in a boolean context
Git Commit ebd2f7a0 Branch fix/logical-fold-non-bool Document 1/12 ++ 0 --
achidlow puya
chore: compile all
Git Commit e5f57dcb Branch fix/logical-fold-non-bool Document 22/319 ++ 105 --
achidlow puya
fix: only fold `0 || b` / `b || 0` to `b` in a bool context
The identity fold is only valid when `b` is boolean (0 or 1), since AVM `||` always returns 0 or 1. Guard with `bool_context` so the fold still applies where we know `b` is bool-typed.
Git Commit b8ffe5c1 Branch fix/logical-fold-non-bool Document 1/6 ++ 2 --
achidlow puya
test: add regression test for || identity fold with non-bool operand
The intrinsic simplifier folds `0 || b` and `b || 0` to `b` unconditionally, but this is only valid when `b` is boolean (0 or 1) — AVM `||` always returns 0 or 1. For non-bool `b`, the fold produces the wrong value.

This is only reachable from AWST (not Algorand Python source), so the test uses an LLM generated AWST JSON test case.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Git Commit d6010965 Branch fix/logical-fold-non-bool Document 54/2,779 ++ 0 --
achidlow puya
Merge 3dc154e78fc7b6aa6603904040f14b6daf74196e into ac3f3fa69648dabbdbe542599a1f4024567c6979
Git Commit fe9d329e Branch pull/707/merge Document 56/2,619 ++ 3 --
achidlow puya
chore: compile all
Git Commit 3dc154e7 Branch fix/logical-fold-non-bool Document 23/54 ++ 100 --
achidlow puya
fix: proactive fix to fold && and || to 0/1 instead of operand values
Currently, neither Algorand Python nor puya-ts emit non-boolean operands for these ops.
Git Commit d67e2f68 Branch fix/logical-fold-non-bool Document 1/2 ++ 2 --
achidlow puya
test: add regression test for && and || non-boolean constant folding
The intrinsic simplifier uses Python's `and`/`or` to fold AVM `&&`/`||`, which returns operand values instead of 0/1 for non-boolean constants. For example, `int(5 and 3)` returns 3, but AVM `&&` returns 1.

This is only reachable from AWST (not Algorand Python source), so the test uses an LLM generated AWST JSON test case.
Git Commit 3effaef5 Branch fix/logical-fold-non-bool Document 55/2,663 ++ 1 --
achidlow puya
Merge 13950bd6a22861d897027ec5c9dc70b6896601ac into ac3f3fa69648dabbdbe542599a1f4024567c6979
Git Commit 49015c80 Branch pull/707/merge Document 56/2,692 ++ 3 --
achidlow puya
chore: compile all
Git Commit 13950bd6 Branch fix/logical-fold-non-bool Document 23/54 ++ 100 --
achidlow puya
fix: proactive fix to fold && and || to 0/1 instead of operand values
Currently, neither Algorand Python nor puya-ts emit non-boolean operands for these ops.
Git Commit bba1f8ad Branch fix/logical-fold-non-bool Document 1/2 ++ 2 --
achidlow puya
test: add regression test for && and || non-boolean constant folding
The intrinsic simplifier uses Python's `and`/`or` to fold AVM `&&`/`||`, which returns operand values instead of 0/1 for non-boolean constants. For example, `int(5 and 3)` returns 3, but AVM `&&` returns 1.

This is only reachable from AWST (not Algorand Python source), so the test uses a hand-crafted AWST JSON test case.
Git Commit f222dcfd Branch fix/logical-fold-non-bool Document 55/2,736 ++ 1 --
Merge 2f70bdccc1b4caeabfad5d4ceadf1bc71faf32a8 into 5523fbf696623f4b6976a538563b4b95cdf659fb
Git Commit 848b41cd Branch pull/825/merge Document 1/1 ++ 1 --
build(deps-dev): update eslint requirement from ^10.2.0 to ^10.2.1
Updates the requirements on [eslint](https://github.com/eslint/eslint) to permit the latest version.
- [Release notes](https://github.com/eslint/eslint/releases)
- [Commits](https://github.com/eslint/eslint/compare/v10.2.0...v10.2.1)

---
updated-dependencies:
- dependency-name: eslint
  dependency-version: 10.2.1
  dependency-type: direct:development
...

Signed-off-by: dependabot[bot] <support@github.com>
Git Commit 2f70bdcc Branch dependabot/npm_and_yarn/eslint-tw-10.2.1 Document 1/1 ++ 1 --
achidlow puya
fix: guard extract/substring constant fold against OOB indices
Three related fixes:

1. Extract folding now checks len(source) < S+L before slicing,
   preventing Python's silent truncation from masking the AVM panic.

2. Substring folding now checks S <= E <= len(source) using a chained
   comparison, adding the missing upper bound check.

3. _get_bytes_length_safe now inductively verifies the source length
   before trusting an extract instruction's immediate length. Without
   this, a secondary optimization path could fold using an incorrect
   length even after the direct fold guard fires.
Git Commit 32abcc2c Branch main Document 2/52 ++ 3 --
achidlow puya
test: add regression test for OOB extract/substring constant folding
The intrinsic simplifier folds extract and substring even when the indices are out of bounds, silently truncating the result. The AVM panics in these cases.

Three separate contracts (ExtractLengthOOB, ExtractStartOOB, SubstringEndOOB) allow the on-chain tests to verify each error message independently.
Git Commit 05c02161 Branch main Document 153/1,435 ++ 0 --
achidlow puya
chore: compile all
Git Commit ac3f3fa6 Branch main Document 143/8,125 ++ 5,856 --