Skip to content

Commit ab86cf9

Browse files
authored
chore(test): Moved transaction validator tests to foundry (#151)
1 parent 9ddf15d commit ab86cf9

File tree

5 files changed

+209
-232
lines changed

5 files changed

+209
-232
lines changed

l1-contracts/contracts/dev-contracts/test/TransactionValidatorTest.sol

-19
This file was deleted.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
pragma solidity 0.8.20;
2+
3+
import {TransactionValidatorSharedTest} from "./_TransactionValidator_Shared.t.sol";
4+
import {IMailbox} from "solpp/zksync/interfaces/IMailbox.sol";
5+
import {TransactionValidator} from "solpp/zksync/libraries/TransactionValidator.sol";
6+
7+
contract ValidateL1L2TxTest is TransactionValidatorSharedTest {
8+
function test_BasicRequestL1L2() public pure {
9+
IMailbox.L2CanonicalTransaction memory testTx = createTestTransaction();
10+
testTx.gasLimit = 500000;
11+
validateL1ToL2Transaction(testTx, 500000);
12+
}
13+
14+
function test_RevertWhen_GasLimitDoesntCoverOverhead() public {
15+
IMailbox.L2CanonicalTransaction memory testTx = createTestTransaction();
16+
// The limit is so low, that it doesn't even cover the overhead
17+
testTx.gasLimit = 0;
18+
vm.expectRevert(bytes("my"));
19+
validateL1ToL2Transaction(testTx, 500000);
20+
}
21+
22+
function test_RevertWhen_GasLimitHigherThanMax() public {
23+
IMailbox.L2CanonicalTransaction memory testTx = createTestTransaction();
24+
// We should fail, if user asks for too much gas.
25+
// Notice, that we subtract the transaction overhead costs from the user's gas limit
26+
// before checking that it is below the max gas limit.
27+
uint256 priorityTxMaxGasLimit = 500000;
28+
testTx.gasLimit = priorityTxMaxGasLimit + 1000000;
29+
vm.expectRevert(bytes("ui"));
30+
validateL1ToL2Transaction(testTx, priorityTxMaxGasLimit);
31+
}
32+
33+
function test_RevertWhen_TooMuchPubdata() public {
34+
IMailbox.L2CanonicalTransaction memory testTx = createTestTransaction();
35+
// We should fail, if user's transaction could output too much pubdata.
36+
// We can allow only 99k of pubdata (otherwise we'd exceed the ethereum calldata limits).
37+
38+
uint256 priorityTxMaxGasLimit = 500000;
39+
testTx.gasLimit = priorityTxMaxGasLimit;
40+
// So if the pubdata costs per byte is 1 - then this transaction could produce 500k of pubdata.
41+
// (hypothetically, assuming all the gas was spent on writing).
42+
testTx.gasPerPubdataByteLimit = 1;
43+
vm.expectRevert(bytes("uk"));
44+
validateL1ToL2Transaction(testTx, priorityTxMaxGasLimit);
45+
}
46+
47+
function test_RevertWhen_BelowMinimumCost() public {
48+
IMailbox.L2CanonicalTransaction memory testTx = createTestTransaction();
49+
uint256 priorityTxMaxGasLimit = 500000;
50+
testTx.gasLimit = 200000;
51+
vm.expectRevert(bytes("up"));
52+
validateL1ToL2Transaction(testTx, priorityTxMaxGasLimit);
53+
}
54+
55+
function test_RevertWhen_HugePubdata() public {
56+
IMailbox.L2CanonicalTransaction memory testTx = createTestTransaction();
57+
uint256 priorityTxMaxGasLimit = 500000;
58+
testTx.gasLimit = 400000;
59+
// Setting huge pubdata limit should cause the panic.
60+
testTx.gasPerPubdataByteLimit = type(uint256).max;
61+
vm.expectRevert();
62+
validateL1ToL2Transaction(testTx, priorityTxMaxGasLimit);
63+
}
64+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,100 @@
1+
pragma solidity 0.8.20;
2+
3+
import {TransactionValidatorSharedTest} from "./_TransactionValidator_Shared.t.sol";
4+
import {IMailbox} from "solpp/zksync/interfaces/IMailbox.sol";
5+
import {TransactionValidator} from "solpp/zksync/libraries/TransactionValidator.sol";
6+
7+
contract ValidateUpgradeTxTest is TransactionValidatorSharedTest {
8+
function test_BasicRequest() public pure {
9+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
10+
TransactionValidator.validateUpgradeTransaction(testTx);
11+
}
12+
13+
function test_RevertWhen_RequestNotFromSystemContract() public {
14+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
15+
// only system contracts (address < 2^16) are allowed to send upgrade transactions.
16+
testTx.from = uint256(1000000000);
17+
vm.expectRevert(bytes("ua"));
18+
TransactionValidator.validateUpgradeTransaction(testTx);
19+
}
20+
21+
function test_RevertWhen_RequestNotToSystemContract() public {
22+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
23+
// Now the 'to' address it too large.
24+
testTx.to = uint256(type(uint160).max) + 100;
25+
vm.expectRevert(bytes("ub"));
26+
TransactionValidator.validateUpgradeTransaction(testTx);
27+
}
28+
29+
function test_RevertWhen_PaymasterIsNotZero() public {
30+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
31+
// Paymaster must be 0 - otherwise we revert.
32+
testTx.paymaster = 1;
33+
vm.expectRevert(bytes("uc"));
34+
TransactionValidator.validateUpgradeTransaction(testTx);
35+
}
36+
37+
function test_RevertWhen_ValueIsNotZero() public {
38+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
39+
// Value must be 0 - otherwise we revert.
40+
testTx.value = 1;
41+
vm.expectRevert(bytes("ud"));
42+
TransactionValidator.validateUpgradeTransaction(testTx);
43+
}
44+
45+
function test_RevertWhen_Reserved0IsNonZero() public {
46+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
47+
// reserved 0 must be 0 - otherwise we revert.
48+
testTx.reserved[0] = 1;
49+
vm.expectRevert(bytes("ue"));
50+
TransactionValidator.validateUpgradeTransaction(testTx);
51+
}
52+
53+
function test_RevertWhen_Reserved1IsTooLarge() public {
54+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
55+
// reserved 1 must be a valid address
56+
testTx.reserved[1] = uint256(type(uint160).max) + 100;
57+
vm.expectRevert(bytes("uf"));
58+
TransactionValidator.validateUpgradeTransaction(testTx);
59+
}
60+
61+
function test_RevertWhen_Reserved2IsNonZero() public {
62+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
63+
// reserved 2 must be 0 - otherwise we revert.
64+
testTx.reserved[2] = 1;
65+
vm.expectRevert(bytes("ug"));
66+
TransactionValidator.validateUpgradeTransaction(testTx);
67+
}
68+
69+
function test_RevertWhen_Reserved3IsNonZero() public {
70+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
71+
// reserved 3 be 0 - otherwise we revert.
72+
testTx.reserved[3] = 1;
73+
vm.expectRevert(bytes("uo"));
74+
TransactionValidator.validateUpgradeTransaction(testTx);
75+
}
76+
77+
function test_RevertWhen_NonZeroSignature() public {
78+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
79+
// Signature must be 0 - otherwise we revert.
80+
testTx.signature = bytes("hello");
81+
vm.expectRevert(bytes("uh"));
82+
TransactionValidator.validateUpgradeTransaction(testTx);
83+
}
84+
85+
function test_RevertWhen_PaymasterInputNonZero() public {
86+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
87+
// PaymasterInput must be 0 - otherwise we revert.
88+
testTx.paymasterInput = bytes("hi");
89+
vm.expectRevert(bytes("ul"));
90+
TransactionValidator.validateUpgradeTransaction(testTx);
91+
}
92+
93+
function test_RevertWhen_ReservedDynamicIsNonZero() public {
94+
IMailbox.L2CanonicalTransaction memory testTx = createUpgradeTransaction();
95+
// ReservedDynamic must be 0 - otherwise we revert.
96+
testTx.reservedDynamic = bytes("something");
97+
vm.expectRevert(bytes("um"));
98+
TransactionValidator.validateUpgradeTransaction(testTx);
99+
}
100+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
// SPDX-License-Identifier: MIT
2+
pragma solidity 0.8.20;
3+
4+
import {Test} from "forge-std/Test.sol";
5+
import {IMailbox} from "solpp/zksync/interfaces/IMailbox.sol";
6+
//import {TransactionValidator} from "solpp/zksync/libraries/TransactionValidator.sol";
7+
import {TransactionValidator} from "cache/solpp-generated-contracts/zksync/libraries/TransactionValidator.sol";
8+
9+
contract TransactionValidatorSharedTest is Test {
10+
constructor() {}
11+
12+
function createTestTransaction() public pure returns (IMailbox.L2CanonicalTransaction memory testTx) {
13+
testTx = IMailbox.L2CanonicalTransaction({
14+
txType: 0,
15+
from: uint256(uint160(1_000_000_000)),
16+
to: uint256(uint160(0)),
17+
gasLimit: 500000,
18+
gasPerPubdataByteLimit: 800,
19+
maxFeePerGas: uint256(0),
20+
maxPriorityFeePerGas: uint256(0),
21+
paymaster: uint256(0),
22+
nonce: uint256(0),
23+
value: 0,
24+
reserved: [uint256(0), uint256(0), uint256(0), uint256(0)],
25+
data: new bytes(0),
26+
signature: new bytes(0),
27+
factoryDeps: new uint256[](0),
28+
paymasterInput: new bytes(0),
29+
reservedDynamic: new bytes(0)
30+
});
31+
}
32+
33+
function createUpgradeTransaction() public pure returns (IMailbox.L2CanonicalTransaction memory testTx) {
34+
testTx = createTestTransaction();
35+
testTx.from = uint256(0x8001);
36+
testTx.to = uint256(0x8007);
37+
}
38+
39+
function validateL1ToL2Transaction(
40+
IMailbox.L2CanonicalTransaction memory _transaction,
41+
uint256 _priorityTxMaxGasLimit
42+
) public pure {
43+
TransactionValidator.validateL1ToL2Transaction(_transaction, abi.encode(_transaction), _priorityTxMaxGasLimit);
44+
}
45+
}

0 commit comments

Comments
 (0)