How CVE-2025-27104 Works
This vulnerability in Vyper (EVM smart contract language) occurs when for-loop iterators containing conditional expressions (ifexp
) are evaluated multiple times. The iterator expression can consume side effects from the loop body, leading to unexpected behavior. For example, in for s: uint256 in (
if True else [])</code>, storage reads may interleave with writes from the loop body. While Vyper's codegen enforces constant context for iterable lists via <code>range_scope</code>, it fails to prevent side-effect consumption when using SArrays/DArrays. The `iter_list` for SArrays is instantiated within a `repeat` IR node, enabling multiple evaluations that can exploit storage state changes mid-loop. <h2 style="color: blue;">DailyCVE Form</h2> Platform: Vyper Version: <0.4.1 Vulnerability: Iterator side-effects Severity: Critical Date: 03/28/2025 <h2 style="color: blue;">What Undercode Say:</h2> <h2 style="color: blue;">Exploitation:</h2> <h2 style="color: blue;">1. Craft a for-loop with `ifexp` iterator:</h2> [bash] for i in ([bash] if condition else []): storage_write() Modifies state read by iterator
2. Deploy malicious contract targeting state-dependent logic (e.g., reentrancy guards).
Protection:
1. Upgrade to Vyper ≥0.4.1.
2. Audit loops with dynamic iterators.
Detection:
vyper --version | grep -q "0.4.1" || echo "Vulnerable"
Patch Analysis:
The fix enforces single evaluation of iterators by:
- Moving SArray/DArray `iter_list` outside `repeat` IR.
- Adding runtime checks for side-effects.
Affected Code Pattern:
@external def exploit(): for x in ([bash] if self.flag else []): self.storage_var += 1 Side-effect
Mitigation Workaround:
Temporary fix: Use range() for critical loops for i in range(static_len): ...
Debugging:
from vyper.compiler import compile_code compile_code(vulnerable_code, [bash]) Check for IR `repeat` nodes
References:
- Vyper GHSA-xxxx-xxxx
- EVM bytecode analyzer: `evm --analyze contract.bin`
References:
Reported By: https://nvd.nist.gov/vuln/detail/CVE-2025-27104
Extra Source Hub:
Undercode