-
Notifications
You must be signed in to change notification settings - Fork 1.8k
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
vm.roll() effect delayed when via_ir = true in solidity >=0.8.15 #4934
Comments
I believe this is a known issue. The problem is that according to Solidity, block.number is a constant across the transaction. So a new reference to it can just dup the value instead of calling the same opcode. Does that explain the issue? But there should be a way to fix these issues without creating further restrictions in the compiler. I'll make an issue in solidity on it |
hmm. so it's technically not a bug in neither forge nor solc and yet my code reverts. I think the best move would be if forge test could somehow detect vm.roll + via_ir (assuming that only happens in via_ir?) if that's possible. probably for timestamp and the likes as well. but I understand if that's not trivially achievable and just wallow in my misery and that some poor soul will encounter this in the future. edit: come to think about it, I think it could make most sense to create a cheatcode such as vm.blockhash. just the call to this contract would be enough to workaround this stack dup thing. |
Just linking some relevant issues here since this has come up before around block timestamp:
|
Initially I thought the compiler was contract Test {
function f() external {
}
}
contract C {
bytes32 x;
bytes32 y;
Test immutable test = new Test();
function f() external {
x = blockhash(block.number - 1);
test.f();
y = blockhash(block.number - 1);
}
} If you look at the optimized IR for this, If you change this to contract Test {
function f() external {
}
}
contract C {
uint x;
uint y;
Test immutable test = new Test();
function f() external {
x = block.number;
test.f();
y = block.number;
}
} You'll see that there are no |
that's right. thanks for the info. for now I just workaround it with the external call, but I think foundry should consider adding this to Cheatcodes.sol and the docs to warn people. |
Component
Forge
Have you ensured that all of these are up to date?
What version of Foundry are you on?
Windows: forge 0.2.0 (bb62e3c 2023-03-15T09:18:40.7502879Z), Linux: forge 0.2.0 (f3c20d5 2023-05-12T00:06:03.466532062Z)
What command(s) is the bug in?
forge test
Operating System
Windows
Describe the bug
vm.roll() is expected to set the block number such that subsequent reads of block.number are immediately updated.
however, strangely only with via_ir = true AND only for solidity >=0.8.15, the effect takes place only after calling a contract.
PoC:
Output:
notice block 6 returns two different hashes in different contexts.
Expected output:
I have tested this on Windows and on Linux with fresh forge install.
very strange bug indeed.
The text was updated successfully, but these errors were encountered: