diff --git a/src/doc/simulate-l2-deposit-transactions.md b/src/doc/simulate-l2-deposit-transactions.md index 2280e9e0b..75d804218 100644 --- a/src/doc/simulate-l2-deposit-transactions.md +++ b/src/doc/simulate-l2-deposit-transactions.md @@ -29,14 +29,15 @@ https://github.com/ethereum-optimism/supersim Start supersim with forked chains for multiple L2s: ```bash -supersim fork --chains=op,ink +supersim fork --chains=op,ink,soneium ``` -**Note:** You can specify any L2 chains supported by supersim (e.g., `op`, `base`, `mode`, `ink`, etc.). The default ports are: +**Note:** You can specify any L2 chains supported by supersim (e.g., `op`, `base`, `mode`, `ink`, `soneium`, etc.). The default ports are: - L1 (Ethereum): `http://127.0.0.1:8545` - L2 (OP Mainnet): `http://127.0.0.1:9545` - L2 (Ink Mainnet): `http://127.0.0.1:9546` -- Additional L2s will increment the port (9547, 9548, etc.) +- L2 (Soneium Mainnet): `http://127.0.0.1:9547` +- Additional L2s will increment the port (9548, 9549, etc.) For different L2 chains, adjust the RPC URLs and network IDs accordingly. diff --git a/test/integration/IntegrationBase.t.sol b/test/integration/IntegrationBase.t.sol index 641e485ec..9e6757659 100644 --- a/test/integration/IntegrationBase.t.sol +++ b/test/integration/IntegrationBase.t.sol @@ -5,6 +5,9 @@ import {Test} from "forge-std/Test.sol"; import {Vm} from "forge-std/Vm.sol"; import {console2} from "forge-std/console2.sol"; import {AddressAliasHelper} from "@eth-optimism-bedrock/src/vendor/AddressAliasHelper.sol"; +import {FeeSplitterSetup} from "src/libraries/FeeSplitterSetup.sol"; +import {RevShareCommon} from "src/libraries/RevShareCommon.sol"; +import {Utils} from "src/libraries/Utils.sol"; import {RevShareContractsUpgrader} from "src/RevShareContractsUpgrader.sol"; import {Predeploys} from "@eth-optimism-bedrock/src/libraries/Predeploys.sol"; import {IFeeSplitter} from "src/interfaces/IFeeSplitter.sol"; @@ -22,6 +25,7 @@ abstract contract IntegrationBase is Test { uint256 internal _mainnetForkId; uint256 internal _opMainnetForkId; uint256 internal _inkMainnetForkId; + uint256 internal _soneiumMainnetForkId; // Shared upgrader contract RevShareContractsUpgrader public revShareUpgrader; @@ -30,6 +34,7 @@ abstract contract IntegrationBase is Test { address internal constant PROXY_ADMIN_OWNER = 0x5a0Aae59D09fccBdDb6C6CcEB07B7279367C3d2A; address internal constant OP_MAINNET_PORTAL = 0xbEb5Fc579115071764c7423A4f12eDde41f106Ed; address internal constant INK_MAINNET_PORTAL = 0x5d66C1782664115999C47c9fA5cd031f495D3e4F; + address internal constant SONEIUM_MAINNET_PORTAL = 0x88e529A6ccd302c948689Cd5156C83D4614FAE92; address internal constant REV_SHARE_UPGRADER_ADDRESS = 0x0000000000000000000000000000000000001337; // L2 predeploys (same across all OP Stack chains) @@ -39,13 +44,6 @@ abstract contract IntegrationBase is Test { address internal constant L1_FEE_VAULT = 0x420000000000000000000000000000000000001A; address internal constant FEE_SPLITTER = 0x420000000000000000000000000000000000002B; - // Expected deployed contracts (deterministic CREATE2 addresses) - address internal constant OP_L1_WITHDRAWER = 0xB3AeB34b88D73Fb4832f65BEa5Bd865017fB5daC; - address internal constant OP_REV_SHARE_CALCULATOR = 0x3E806Fd8592366E850197FEC8D80608b5526Bba2; - - address internal constant INK_L1_WITHDRAWER = 0x70e26B12a578176BccCD3b7e7f58f605871c5eF7; - address internal constant INK_REV_SHARE_CALCULATOR = 0xd7a5307B4Ce92B0269903191007b95dF42552Dfa; - // Test configuration - OP Mainnet uint256 internal constant OP_MIN_WITHDRAWAL_AMOUNT = 350000; address internal constant OP_L1_WITHDRAWAL_RECIPIENT = 0x0000000000000000000000000000000000000001; @@ -55,9 +53,15 @@ abstract contract IntegrationBase is Test { // Test configuration - Ink Mainnet uint256 internal constant INK_MIN_WITHDRAWAL_AMOUNT = 500000; address internal constant INK_L1_WITHDRAWAL_RECIPIENT = 0x0000000000000000000000000000000000000002; - uint32 internal constant INK_WITHDRAWAL_GAS_LIMIT = 1000000; + uint32 internal constant INK_WITHDRAWAL_GAS_LIMIT = 800000; address internal constant INK_CHAIN_FEES_RECIPIENT = 0x0000000000000000000000000000000000000002; + // Test configuration - Soneium Mainnet + uint256 internal constant SONEIUM_MIN_WITHDRAWAL_AMOUNT = 500000; + address internal constant SONEIUM_L1_WITHDRAWAL_RECIPIENT = 0x0000000000000000000000000000000000000003; + uint32 internal constant SONEIUM_WITHDRAWAL_GAS_LIMIT = 800000; + address internal constant SONEIUM_CHAIN_FEES_RECIPIENT = 0x0000000000000000000000000000000000000003; + bool internal constant IS_SIMULATE = true; /// @notice Relay all deposit transactions from L1 to multiple L2s /// @param _forkIds Array of fork IDs for each L2 chain @@ -175,9 +179,35 @@ abstract contract IntegrationBase is Test { return _result; } + /// @notice Compute deterministic L1Withdrawer address using CREATE2 + function _computeL1WithdrawerAddress(uint256 _minWithdrawalAmount, address _recipient, uint32 _gasLimit) + internal + pure + returns (address) + { + bytes memory _initCode = bytes.concat( + FeeSplitterSetup.l1WithdrawerCreationCode, abi.encode(_minWithdrawalAmount, _recipient, _gasLimit) + ); + bytes32 _salt = RevShareCommon.getSalt("L1Withdrawer"); + return Utils.getCreate2Address(_salt, _initCode, RevShareCommon.CREATE2_DEPLOYER); + } + + /// @notice Compute deterministic RevShareCalculator address using CREATE2 + function _computeRevShareCalculatorAddress(address _l1Withdrawer, address _chainFeesRecipient) + internal + pure + returns (address) + { + bytes memory _initCode = bytes.concat( + FeeSplitterSetup.scRevShareCalculatorCreationCode, abi.encode(_l1Withdrawer, _chainFeesRecipient) + ); + bytes32 _salt = RevShareCommon.getSalt("SCRevShareCalculator"); + return Utils.getCreate2Address(_salt, _initCode, RevShareCommon.CREATE2_DEPLOYER); + } /// @notice Fund all fee vaults with specified amount /// @param _amount Amount to fund each vault with /// @param _forkId Fork ID to execute on + function _fundVaults(uint256 _amount, uint256 _forkId) internal { vm.selectFork(_forkId); vm.deal(SEQUENCER_FEE_VAULT, _amount); diff --git a/test/integration/RevShareContractsUpgraderIntegration.t.sol b/test/integration/RevShareContractsUpgraderIntegration.t.sol index 8ef016548..904ee507f 100644 --- a/test/integration/RevShareContractsUpgraderIntegration.t.sol +++ b/test/integration/RevShareContractsUpgraderIntegration.t.sol @@ -9,10 +9,11 @@ contract RevShareContractsUpgraderIntegrationTest is IntegrationBase { RevShareUpgradeAndSetup public revShareTask; function setUp() public { - // Create forks for L1 (mainnet) and L2 (OP Mainnet) + // Create forks for L1 (mainnet) and L2s _mainnetForkId = vm.createFork("http://127.0.0.1:8545"); _opMainnetForkId = vm.createFork("http://127.0.0.1:9545"); _inkMainnetForkId = vm.createFork("http://127.0.0.1:9546"); + _soneiumMainnetForkId = vm.createFork("http://127.0.0.1:9547"); // Deploy contracts on L1 vm.selectFork(_mainnetForkId); @@ -35,21 +36,26 @@ contract RevShareContractsUpgraderIntegrationTest is IntegrationBase { revShareTask.simulate("test/tasks/example/eth/016-revshare-upgrade-and-setup/config.toml"); // Step 3: Relay deposit transactions from L1 to all L2s - uint256[] memory forkIds = new uint256[](2); + uint256[] memory forkIds = new uint256[](3); forkIds[0] = _opMainnetForkId; forkIds[1] = _inkMainnetForkId; + forkIds[2] = _soneiumMainnetForkId; - address[] memory portals = new address[](2); + address[] memory portals = new address[](3); portals[0] = OP_MAINNET_PORTAL; portals[1] = INK_MAINNET_PORTAL; + portals[2] = SONEIUM_MAINNET_PORTAL; _relayAllMessages(forkIds, IS_SIMULATE, portals); // Step 4: Assert the state of the OP Mainnet contracts vm.selectFork(_opMainnetForkId); + address opL1Withdrawer = + _computeL1WithdrawerAddress(OP_MIN_WITHDRAWAL_AMOUNT, OP_L1_WITHDRAWAL_RECIPIENT, OP_WITHDRAWAL_GAS_LIMIT); + address opRevShareCalculator = _computeRevShareCalculatorAddress(opL1Withdrawer, OP_CHAIN_FEES_RECIPIENT); _assertL2State( - OP_L1_WITHDRAWER, - OP_REV_SHARE_CALCULATOR, + opL1Withdrawer, + opRevShareCalculator, OP_MIN_WITHDRAWAL_AMOUNT, OP_L1_WITHDRAWAL_RECIPIENT, OP_WITHDRAWAL_GAS_LIMIT, @@ -58,22 +64,43 @@ contract RevShareContractsUpgraderIntegrationTest is IntegrationBase { // Step 5: Assert the state of the Ink Mainnet contracts vm.selectFork(_inkMainnetForkId); + address inkL1Withdrawer = _computeL1WithdrawerAddress( + INK_MIN_WITHDRAWAL_AMOUNT, INK_L1_WITHDRAWAL_RECIPIENT, INK_WITHDRAWAL_GAS_LIMIT + ); + address inkRevShareCalculator = _computeRevShareCalculatorAddress(inkL1Withdrawer, INK_CHAIN_FEES_RECIPIENT); _assertL2State( - INK_L1_WITHDRAWER, - INK_REV_SHARE_CALCULATOR, + inkL1Withdrawer, + inkRevShareCalculator, INK_MIN_WITHDRAWAL_AMOUNT, INK_L1_WITHDRAWAL_RECIPIENT, INK_WITHDRAWAL_GAS_LIMIT, INK_CHAIN_FEES_RECIPIENT ); - // Step 6: Do a withdrawal flow + // Step 6: Assert the state of the Soneium Mainnet contracts + vm.selectFork(_soneiumMainnetForkId); + address soneiumL1Withdrawer = _computeL1WithdrawerAddress( + SONEIUM_MIN_WITHDRAWAL_AMOUNT, SONEIUM_L1_WITHDRAWAL_RECIPIENT, SONEIUM_WITHDRAWAL_GAS_LIMIT + ); + address soneiumRevShareCalculator = + _computeRevShareCalculatorAddress(soneiumL1Withdrawer, SONEIUM_CHAIN_FEES_RECIPIENT); + _assertL2State( + soneiumL1Withdrawer, + soneiumRevShareCalculator, + SONEIUM_MIN_WITHDRAWAL_AMOUNT, + SONEIUM_L1_WITHDRAWAL_RECIPIENT, + SONEIUM_WITHDRAWAL_GAS_LIMIT, + SONEIUM_CHAIN_FEES_RECIPIENT + ); + + // Step 7: Do a withdrawal flow // Fund vaults with amount > minWithdrawalAmount _fundVaults(1 ether, _opMainnetForkId); _fundVaults(1 ether, _inkMainnetForkId); + _fundVaults(1 ether, _soneiumMainnetForkId); - // Disburse fees in both chains and expect the L1Withdrawer to trigger the withdrawal + // Disburse fees in all chains and expect the L1Withdrawer to trigger the withdrawal // Expected L1Withdrawer share = 3 ether * 15% = 0.45 ether // It is 3 ether instead of 4 because net revenue doesn't count L1FeeVault's balance // For details on the rev share calculation, check the SuperchainRevSharesCalculator contract. @@ -82,5 +109,8 @@ contract RevShareContractsUpgraderIntegrationTest is IntegrationBase { _executeDisburseAndAssertWithdrawal(_opMainnetForkId, OP_L1_WITHDRAWAL_RECIPIENT, expectedWithdrawalAmount); _executeDisburseAndAssertWithdrawal(_inkMainnetForkId, INK_L1_WITHDRAWAL_RECIPIENT, expectedWithdrawalAmount); + _executeDisburseAndAssertWithdrawal( + _soneiumMainnetForkId, SONEIUM_L1_WITHDRAWAL_RECIPIENT, expectedWithdrawalAmount + ); } } diff --git a/test/integration/RevShareSetupIntegration.t.sol b/test/integration/RevShareSetupIntegration.t.sol index 207df093d..13f10477a 100644 --- a/test/integration/RevShareSetupIntegration.t.sol +++ b/test/integration/RevShareSetupIntegration.t.sol @@ -23,11 +23,18 @@ contract RevShareSetupIntegrationTest is IntegrationBase { bytes internal DEFAULT_FEE_VAULT_CREATION_CODE = FeeVaultUpgrader.defaultFeeVaultCreationCode; bytes internal FEE_SPLITTER_CREATION_CODE = FeeSplitterSetup.feeSplitterCreationCode; + // Implementation addresses (deployed and etched in setUp) + address internal _operatorFeeVaultImpl; + address internal _sequencerFeeVaultImpl; + address internal _defaultFeeVaultImpl; + address internal _feeSplitterImpl; + function setUp() public { - // Create forks for L1 (mainnet) and L2 (OP Mainnet) + // Create forks for L1 (mainnet) and L2s (OP Mainnet, Ink, Soneium) _mainnetForkId = vm.createFork("http://127.0.0.1:8545"); _opMainnetForkId = vm.createFork("http://127.0.0.1:9545"); _inkMainnetForkId = vm.createFork("http://127.0.0.1:9546"); + _soneiumMainnetForkId = vm.createFork("http://127.0.0.1:9547"); // Deploy contracts on L1 vm.selectFork(_mainnetForkId); @@ -41,16 +48,16 @@ contract RevShareSetupIntegrationTest is IntegrationBase { revShareTask = new RevShareSetup(); // Deploy implementations once to get their addresses and bytecode - address operatorFeeVaultImpl = _deployFromCreationCode(OPERATOR_FEE_VAULT_CREATION_CODE); - address sequencerFeeVaultImpl = _deployFromCreationCode(SEQUENCER_FEE_VAULT_CREATION_CODE); - address defaultFeeVaultImpl = _deployFromCreationCode(DEFAULT_FEE_VAULT_CREATION_CODE); - address feeSplitterImpl = _deployFromCreationCode(FEE_SPLITTER_CREATION_CODE); + _operatorFeeVaultImpl = _deployFromCreationCode(OPERATOR_FEE_VAULT_CREATION_CODE); + _sequencerFeeVaultImpl = _deployFromCreationCode(SEQUENCER_FEE_VAULT_CREATION_CODE); + _defaultFeeVaultImpl = _deployFromCreationCode(DEFAULT_FEE_VAULT_CREATION_CODE); + _feeSplitterImpl = _deployFromCreationCode(FEE_SPLITTER_CREATION_CODE); // Get implementation bytecodes - bytes memory operatorFeeVaultImplCode = operatorFeeVaultImpl.code; - bytes memory sequencerFeeVaultImplCode = sequencerFeeVaultImpl.code; - bytes memory defaultFeeVaultImplCode = defaultFeeVaultImpl.code; - bytes memory feeSplitterImplCode = feeSplitterImpl.code; + bytes memory operatorFeeVaultImplCode = _operatorFeeVaultImpl.code; + bytes memory sequencerFeeVaultImplCode = _sequencerFeeVaultImpl.code; + bytes memory defaultFeeVaultImplCode = _defaultFeeVaultImpl.code; + bytes memory feeSplitterImplCode = _feeSplitterImpl.code; // Deploy a proxy to get its bytecode Proxy proxyTemplate = new Proxy(address(this)); @@ -59,33 +66,49 @@ contract RevShareSetupIntegrationTest is IntegrationBase { // Etch predeploys on OP Mainnet fork vm.selectFork(_opMainnetForkId); _etchImplementations( - operatorFeeVaultImpl, - sequencerFeeVaultImpl, - defaultFeeVaultImpl, - feeSplitterImpl, + _operatorFeeVaultImpl, + _sequencerFeeVaultImpl, + _defaultFeeVaultImpl, + _feeSplitterImpl, operatorFeeVaultImplCode, sequencerFeeVaultImplCode, defaultFeeVaultImplCode, feeSplitterImplCode ); _setupProxyPredeploys( - proxyCode, operatorFeeVaultImpl, sequencerFeeVaultImpl, defaultFeeVaultImpl, feeSplitterImpl + proxyCode, _operatorFeeVaultImpl, _sequencerFeeVaultImpl, _defaultFeeVaultImpl, _feeSplitterImpl ); // Etch predeploys on Ink Mainnet fork vm.selectFork(_inkMainnetForkId); _etchImplementations( - operatorFeeVaultImpl, - sequencerFeeVaultImpl, - defaultFeeVaultImpl, - feeSplitterImpl, + _operatorFeeVaultImpl, + _sequencerFeeVaultImpl, + _defaultFeeVaultImpl, + _feeSplitterImpl, + operatorFeeVaultImplCode, + sequencerFeeVaultImplCode, + defaultFeeVaultImplCode, + feeSplitterImplCode + ); + _setupProxyPredeploys( + proxyCode, _operatorFeeVaultImpl, _sequencerFeeVaultImpl, _defaultFeeVaultImpl, _feeSplitterImpl + ); + + // Etch predeploys on Soneium Mainnet fork + vm.selectFork(_soneiumMainnetForkId); + _etchImplementations( + _operatorFeeVaultImpl, + _sequencerFeeVaultImpl, + _defaultFeeVaultImpl, + _feeSplitterImpl, operatorFeeVaultImplCode, sequencerFeeVaultImplCode, defaultFeeVaultImplCode, feeSplitterImplCode ); _setupProxyPredeploys( - proxyCode, operatorFeeVaultImpl, sequencerFeeVaultImpl, defaultFeeVaultImpl, feeSplitterImpl + proxyCode, _operatorFeeVaultImpl, _sequencerFeeVaultImpl, _defaultFeeVaultImpl, _feeSplitterImpl ); // Switch back to mainnet fork after setup @@ -103,66 +126,66 @@ contract RevShareSetupIntegrationTest is IntegrationBase { } /// @notice Etch implementation bytecode at addresses on the current fork - /// @param _operatorFeeVaultImpl OperatorFeeVault implementation address - /// @param _sequencerFeeVaultImpl SequencerFeeVault implementation address - /// @param _defaultFeeVaultImpl Default FeeVault implementation address - /// @param _feeSplitterImpl FeeSplitter implementation address - /// @param _operatorFeeVaultImplCode OperatorFeeVault implementation bytecode - /// @param _sequencerFeeVaultImplCode SequencerFeeVault implementation bytecode - /// @param _defaultFeeVaultImplCode Default FeeVault implementation bytecode - /// @param _feeSplitterImplCode FeeSplitter implementation bytecode + /// @param operatorFeeVaultImplAddr OperatorFeeVault implementation address + /// @param sequencerFeeVaultImplAddr SequencerFeeVault implementation address + /// @param defaultFeeVaultImplAddr Default FeeVault implementation address + /// @param feeSplitterImplAddr FeeSplitter implementation address + /// @param operatorFeeVaultImplCode OperatorFeeVault implementation bytecode + /// @param sequencerFeeVaultImplCode SequencerFeeVault implementation bytecode + /// @param defaultFeeVaultImplCode Default FeeVault implementation bytecode + /// @param feeSplitterImplCode FeeSplitter implementation bytecode function _etchImplementations( - address _operatorFeeVaultImpl, - address _sequencerFeeVaultImpl, - address _defaultFeeVaultImpl, - address _feeSplitterImpl, - bytes memory _operatorFeeVaultImplCode, - bytes memory _sequencerFeeVaultImplCode, - bytes memory _defaultFeeVaultImplCode, - bytes memory _feeSplitterImplCode + address operatorFeeVaultImplAddr, + address sequencerFeeVaultImplAddr, + address defaultFeeVaultImplAddr, + address feeSplitterImplAddr, + bytes memory operatorFeeVaultImplCode, + bytes memory sequencerFeeVaultImplCode, + bytes memory defaultFeeVaultImplCode, + bytes memory feeSplitterImplCode ) internal { - vm.etch(_operatorFeeVaultImpl, _operatorFeeVaultImplCode); - vm.etch(_sequencerFeeVaultImpl, _sequencerFeeVaultImplCode); - vm.etch(_defaultFeeVaultImpl, _defaultFeeVaultImplCode); - vm.etch(_feeSplitterImpl, _feeSplitterImplCode); + vm.etch(operatorFeeVaultImplAddr, operatorFeeVaultImplCode); + vm.etch(sequencerFeeVaultImplAddr, sequencerFeeVaultImplCode); + vm.etch(defaultFeeVaultImplAddr, defaultFeeVaultImplCode); + vm.etch(feeSplitterImplAddr, feeSplitterImplCode); } /// @notice Setup proxy predeploys pointing to implementations - /// @param _proxyCode Proxy runtime bytecode - /// @param _operatorFeeVaultImpl OperatorFeeVault implementation address - /// @param _sequencerFeeVaultImpl SequencerFeeVault implementation address - /// @param _defaultFeeVaultImpl Default FeeVault implementation address (for Base and L1) - /// @param _feeSplitterImpl FeeSplitter implementation address + /// @param proxyCode Proxy runtime bytecode + /// @param operatorFeeVaultImplAddr OperatorFeeVault implementation address + /// @param sequencerFeeVaultImplAddr SequencerFeeVault implementation address + /// @param defaultFeeVaultImplAddr Default FeeVault implementation address (for Base and L1) + /// @param feeSplitterImplAddr FeeSplitter implementation address function _setupProxyPredeploys( - bytes memory _proxyCode, - address _operatorFeeVaultImpl, - address _sequencerFeeVaultImpl, - address _defaultFeeVaultImpl, - address _feeSplitterImpl + bytes memory proxyCode, + address operatorFeeVaultImplAddr, + address sequencerFeeVaultImplAddr, + address defaultFeeVaultImplAddr, + address feeSplitterImplAddr ) internal { // Setup OperatorFeeVault proxy - vm.etch(OPERATOR_FEE_VAULT, _proxyCode); - vm.store(OPERATOR_FEE_VAULT, PROXY_IMPLEMENTATION_SLOT, bytes32(uint256(uint160(_operatorFeeVaultImpl)))); + vm.etch(OPERATOR_FEE_VAULT, proxyCode); + vm.store(OPERATOR_FEE_VAULT, PROXY_IMPLEMENTATION_SLOT, bytes32(uint256(uint160(operatorFeeVaultImplAddr)))); vm.store(OPERATOR_FEE_VAULT, PROXY_OWNER_SLOT, bytes32(uint256(uint160(RevShareCommon.PROXY_ADMIN)))); // Setup SequencerFeeVault proxy - vm.etch(SEQUENCER_FEE_VAULT, _proxyCode); - vm.store(SEQUENCER_FEE_VAULT, PROXY_IMPLEMENTATION_SLOT, bytes32(uint256(uint160(_sequencerFeeVaultImpl)))); + vm.etch(SEQUENCER_FEE_VAULT, proxyCode); + vm.store(SEQUENCER_FEE_VAULT, PROXY_IMPLEMENTATION_SLOT, bytes32(uint256(uint160(sequencerFeeVaultImplAddr)))); vm.store(SEQUENCER_FEE_VAULT, PROXY_OWNER_SLOT, bytes32(uint256(uint160(RevShareCommon.PROXY_ADMIN)))); // Setup BaseFeeVault proxy - vm.etch(BASE_FEE_VAULT, _proxyCode); - vm.store(BASE_FEE_VAULT, PROXY_IMPLEMENTATION_SLOT, bytes32(uint256(uint160(_defaultFeeVaultImpl)))); + vm.etch(BASE_FEE_VAULT, proxyCode); + vm.store(BASE_FEE_VAULT, PROXY_IMPLEMENTATION_SLOT, bytes32(uint256(uint160(defaultFeeVaultImplAddr)))); vm.store(BASE_FEE_VAULT, PROXY_OWNER_SLOT, bytes32(uint256(uint160(RevShareCommon.PROXY_ADMIN)))); // Setup L1FeeVault proxy - vm.etch(L1_FEE_VAULT, _proxyCode); - vm.store(L1_FEE_VAULT, PROXY_IMPLEMENTATION_SLOT, bytes32(uint256(uint160(_defaultFeeVaultImpl)))); + vm.etch(L1_FEE_VAULT, proxyCode); + vm.store(L1_FEE_VAULT, PROXY_IMPLEMENTATION_SLOT, bytes32(uint256(uint160(defaultFeeVaultImplAddr)))); vm.store(L1_FEE_VAULT, PROXY_OWNER_SLOT, bytes32(uint256(uint160(RevShareCommon.PROXY_ADMIN)))); // Setup FeeSplitter proxy - vm.etch(FEE_SPLITTER, _proxyCode); - vm.store(FEE_SPLITTER, PROXY_IMPLEMENTATION_SLOT, bytes32(uint256(uint160(_feeSplitterImpl)))); + vm.etch(FEE_SPLITTER, proxyCode); + vm.store(FEE_SPLITTER, PROXY_IMPLEMENTATION_SLOT, bytes32(uint256(uint160(feeSplitterImplAddr)))); vm.store(FEE_SPLITTER, PROXY_OWNER_SLOT, bytes32(uint256(uint160(RevShareCommon.PROXY_ADMIN)))); } @@ -175,21 +198,26 @@ contract RevShareSetupIntegrationTest is IntegrationBase { revShareTask.simulate("test/tasks/example/eth/017-revshare-setup/config.toml"); // Step 3: Relay deposit transactions from L1 to all L2s - uint256[] memory forkIds = new uint256[](2); + uint256[] memory forkIds = new uint256[](3); forkIds[0] = _opMainnetForkId; forkIds[1] = _inkMainnetForkId; + forkIds[2] = _soneiumMainnetForkId; - address[] memory portals = new address[](2); + address[] memory portals = new address[](3); portals[0] = OP_MAINNET_PORTAL; portals[1] = INK_MAINNET_PORTAL; + portals[2] = SONEIUM_MAINNET_PORTAL; _relayAllMessages(forkIds, IS_SIMULATE, portals); // Step 4: Assert the state of the OP Mainnet contracts vm.selectFork(_opMainnetForkId); + address opL1Withdrawer = + _computeL1WithdrawerAddress(OP_MIN_WITHDRAWAL_AMOUNT, OP_L1_WITHDRAWAL_RECIPIENT, OP_WITHDRAWAL_GAS_LIMIT); + address opRevShareCalculator = _computeRevShareCalculatorAddress(opL1Withdrawer, OP_CHAIN_FEES_RECIPIENT); _assertL2State( - OP_L1_WITHDRAWER, - OP_REV_SHARE_CALCULATOR, + opL1Withdrawer, + opRevShareCalculator, OP_MIN_WITHDRAWAL_AMOUNT, OP_L1_WITHDRAWAL_RECIPIENT, OP_WITHDRAWAL_GAS_LIMIT, @@ -198,22 +226,43 @@ contract RevShareSetupIntegrationTest is IntegrationBase { // Step 5: Assert the state of the Ink Mainnet contracts vm.selectFork(_inkMainnetForkId); + address inkL1Withdrawer = _computeL1WithdrawerAddress( + INK_MIN_WITHDRAWAL_AMOUNT, INK_L1_WITHDRAWAL_RECIPIENT, INK_WITHDRAWAL_GAS_LIMIT + ); + address inkRevShareCalculator = _computeRevShareCalculatorAddress(inkL1Withdrawer, INK_CHAIN_FEES_RECIPIENT); _assertL2State( - INK_L1_WITHDRAWER, - INK_REV_SHARE_CALCULATOR, + inkL1Withdrawer, + inkRevShareCalculator, INK_MIN_WITHDRAWAL_AMOUNT, INK_L1_WITHDRAWAL_RECIPIENT, INK_WITHDRAWAL_GAS_LIMIT, INK_CHAIN_FEES_RECIPIENT ); - // Step 6: Do a withdrawal flow + // Step 6: Assert the state of the Soneium Mainnet contracts + vm.selectFork(_soneiumMainnetForkId); + address soneiumL1Withdrawer = _computeL1WithdrawerAddress( + SONEIUM_MIN_WITHDRAWAL_AMOUNT, SONEIUM_L1_WITHDRAWAL_RECIPIENT, SONEIUM_WITHDRAWAL_GAS_LIMIT + ); + address soneiumRevShareCalculator = + _computeRevShareCalculatorAddress(soneiumL1Withdrawer, SONEIUM_CHAIN_FEES_RECIPIENT); + _assertL2State( + soneiumL1Withdrawer, + soneiumRevShareCalculator, + SONEIUM_MIN_WITHDRAWAL_AMOUNT, + SONEIUM_L1_WITHDRAWAL_RECIPIENT, + SONEIUM_WITHDRAWAL_GAS_LIMIT, + SONEIUM_CHAIN_FEES_RECIPIENT + ); + + // Step 7: Do a withdrawal flow // Fund vaults with amount > minWithdrawalAmount _fundVaults(1 ether, _opMainnetForkId); _fundVaults(1 ether, _inkMainnetForkId); + _fundVaults(1 ether, _soneiumMainnetForkId); - // Disburse fees in both chains and expect the L1Withdrawer to trigger the withdrawal + // Disburse fees in all chains and expect the L1Withdrawer to trigger the withdrawal // Expected L1Withdrawer share = 3 ether * 15% = 0.45 ether // It is 3 ether instead of 4 because net revenue doesn't count L1FeeVault's balance // For details on the rev share calculation, check the SuperchainRevSharesCalculator contract. @@ -222,5 +271,8 @@ contract RevShareSetupIntegrationTest is IntegrationBase { _executeDisburseAndAssertWithdrawal(_opMainnetForkId, OP_L1_WITHDRAWAL_RECIPIENT, expectedWithdrawalAmount); _executeDisburseAndAssertWithdrawal(_inkMainnetForkId, INK_L1_WITHDRAWAL_RECIPIENT, expectedWithdrawalAmount); + _executeDisburseAndAssertWithdrawal( + _soneiumMainnetForkId, SONEIUM_L1_WITHDRAWAL_RECIPIENT, expectedWithdrawalAmount + ); } } diff --git a/test/tasks/Regression.t.sol b/test/tasks/Regression.t.sol index 6683bf0c1..ce08bbb96 100644 --- a/test/tasks/Regression.t.sol +++ b/test/tasks/Regression.t.sol @@ -990,7 +990,7 @@ contract RegressionTest is Test { function testRegressionCallDataMatches_RevShareSetup() public { string memory taskConfigFilePath = "test/tasks/example/eth/017-revshare-setup/config.toml"; string memory expectedCallData = - "0x82ad56cb0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000200000000000000000000000006fee65a372d63295e8eb12574652f0bfeb913149000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000184cdab407800000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000002000000000000000000000000beb5fc579115071764c7423a4f12edde41f106ed0000000000000000000000000000000000000000000000000000000000055730000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000c350000000000000000000000000000000000000000000000000000000000000000010000000000000000000000005d66c1782664115999c47c9fa5cd031f495d3e4f000000000000000000000000000000000000000000000000000000000007a120000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000f4240000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000"; + "0x82ad56cb0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000200000000000000000000000006fee65a372d63295e8eb12574652f0bfeb913149000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000224cdab407800000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000003000000000000000000000000beb5fc579115071764c7423a4f12edde41f106ed0000000000000000000000000000000000000000000000000000000000055730000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000c350000000000000000000000000000000000000000000000000000000000000000010000000000000000000000005d66c1782664115999c47c9fa5cd031f495d3e4f000000000000000000000000000000000000000000000000000000000007a120000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000c3500000000000000000000000000000000000000000000000000000000000000000200000000000000000000000088e529a6ccd302c948689cd5156c83d4614fae92000000000000000000000000000000000000000000000000000000000007a120000000000000000000000000000000000000000000000000000000000000000300000000000000000000000000000000000000000000000000000000000c3500000000000000000000000000000000000000000000000000000000000000000300000000000000000000000000000000000000000000000000000000"; MultisigTask multisigTask = new RevShareSetup(); address rootSafe = address(0x5a0Aae59D09fccBdDb6C6CcEB07B7279367C3d2A); address foundationChildMultisig = 0x847B5c174615B1B7fDF770882256e2D3E95b9D92; @@ -1005,10 +1005,10 @@ contract RegressionTest is Test { // Foundation expectedDataToSign[0] = - "0x1901a4a9c312badf3fcaa05eafe5dc9bee8bd9316c78ee8b0bebe3115bb21b732672babdaa6c60c018aea833417700ce7e0a97768f0941586fcba368f0a8a874c277"; + "0x1901a4a9c312badf3fcaa05eafe5dc9bee8bd9316c78ee8b0bebe3115bb21b7326725ee24803aca0a6af16bc1c33df420238c2447291f5ab417a1a6fe8375a17d5c0"; // Security council expectedDataToSign[1] = - "0x1901df53d510b56e539b90b369ef08fce3631020fbf921e3136ea5f8747c20bce96715194e3147a0c8a32ef87e4beed5390c7d4abea66d51a9863c04959bc09f4765"; + "0x1901df53d510b56e539b90b369ef08fce3631020fbf921e3136ea5f8747c20bce9678d870bb68459395de3d3ba0b1a21834e6c6802a206a8797c4442d74f8a96cecb"; _assertDataToSignNestedMultisig(multisigTask, actions, expectedDataToSign, MULTICALL3_ADDRESS, rootSafe); } @@ -1047,7 +1047,7 @@ contract RegressionTest is Test { function testRegressionCallDataMatches_RevShareUpgradeAndSetup() public { string memory taskConfigFilePath = "test/tasks/example/eth/016-revshare-upgrade-and-setup/config.toml"; string memory expectedCallData = - "0x82ad56cb0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000200000000000000000000000006fee65a372d63295e8eb12574652f0bfeb9131490000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000006000000000000000000000000000000000000000000000000000000000000001841a80dc3800000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000002000000000000000000000000beb5fc579115071764c7423a4f12edde41f106ed0000000000000000000000000000000000000000000000000000000000055730000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000c350000000000000000000000000000000000000000000000000000000000000000010000000000000000000000005d66c1782664115999c47c9fa5cd031f495d3e4f000000000000000000000000000000000000000000000000000000000007a120000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000f4240000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000"; + "0x82ad56cb0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000200000000000000000000000006fee65a372d63295e8eb12574652f0bfeb9131490000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000006000000000000000000000000000000000000000000000000000000000000002241a80dc3800000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000003000000000000000000000000beb5fc579115071764c7423a4f12edde41f106ed0000000000000000000000000000000000000000000000000000000000055730000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000c350000000000000000000000000000000000000000000000000000000000000000010000000000000000000000005d66c1782664115999c47c9fa5cd031f495d3e4f000000000000000000000000000000000000000000000000000000000007a120000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000c3500000000000000000000000000000000000000000000000000000000000000000200000000000000000000000088e529a6ccd302c948689cd5156c83d4614fae92000000000000000000000000000000000000000000000000000000000007a120000000000000000000000000000000000000000000000000000000000000000300000000000000000000000000000000000000000000000000000000000c3500000000000000000000000000000000000000000000000000000000000000000300000000000000000000000000000000000000000000000000000000"; MultisigTask multisigTask = new RevShareUpgradeAndSetup(); address rootSafe = address(0x5a0Aae59D09fccBdDb6C6CcEB07B7279367C3d2A); address foundationChildMultisig = 0x847B5c174615B1B7fDF770882256e2D3E95b9D92; @@ -1062,19 +1062,19 @@ contract RegressionTest is Test { // Foundation expectedDataToSign[0] = - "0x1901a4a9c312badf3fcaa05eafe5dc9bee8bd9316c78ee8b0bebe3115bb21b732672c961ba462b2a42c1fb200d0b4913ed0d6a3b2cc16038d315bd371d8ba7f047ad"; + "0x1901a4a9c312badf3fcaa05eafe5dc9bee8bd9316c78ee8b0bebe3115bb21b732672569b3a00909d6ad42875c28e2c90907c62c499ce07f5c2dacdb7a87254d21912"; // Security council expectedDataToSign[1] = - "0x1901df53d510b56e539b90b369ef08fce3631020fbf921e3136ea5f8747c20bce967b1995e96a0709bb32b54ce9157c14c44a3ceffc8840b4e6ede4c68f954bc3712"; + "0x1901df53d510b56e539b90b369ef08fce3631020fbf921e3136ea5f8747c20bce96739b6686709d121f08dcfd80a4755692c5571d9c561a666d4cb5b16467f69a32e"; _assertDataToSignNestedMultisig(multisigTask, actions, expectedDataToSign, MULTICALL3_ADDRESS, rootSafe); } /// @notice Expected call data and data to sign generated by manually running the RevShareUpgradeAndSetup template at block 9628956 on Sepolia. - /// Simulate from task directory (test/tasks/example/sep/030-revshare-upgrade-and-setup) with: + /// Simulate from task directory (test/tasks/example/sep/032-revshare-upgrade-and-setup) with: /// SIMULATE_WITHOUT_LEDGER=1 just --dotenv-path $(pwd)/.env --justfile ../../../../../src/improvements/single.just simulate function testRegressionCallDataMatches_RevShareUpgradeAndSetupSepolia() public { - string memory taskConfigFilePath = "test/tasks/example/sep/030-revshare-upgrade-and-setup/config.toml"; + string memory taskConfigFilePath = "test/tasks/example/sep/032-revshare-upgrade-and-setup/config.toml"; string memory expectedCallData = "0x82ad56cb000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000020000000000000000000000000890c61c7f3f40b851ebcaacfa879c6075426419d0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000006000000000000000000000000000000000000000000000000000000000000000e41a80dc380000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000100000000000000000000000016fc5058f25648194471939df75cf27a2fdc48bc0000000000000000000000000000000000000000000000000000000000055730000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000c3500000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000"; MultisigTask multisigTask = new RevShareUpgradeAndSetup(); diff --git a/test/tasks/example/eth/016-revshare-upgrade-and-setup/.env b/test/tasks/example/eth/016-revshare-upgrade-and-setup/.env index 861095467..ea5dd7ac8 100644 --- a/test/tasks/example/eth/016-revshare-upgrade-and-setup/.env +++ b/test/tasks/example/eth/016-revshare-upgrade-and-setup/.env @@ -1,3 +1,3 @@ -TENDERLY_GAS=16000000 +TENDERLY_GAS=24000000 NESTED_SAFE_NAME_DEPTH_1=foundation -FORK_BLOCK_NUMBER=23820274 \ No newline at end of file +FORK_BLOCK_NUMBER=23872150 \ No newline at end of file diff --git a/test/tasks/example/eth/016-revshare-upgrade-and-setup/config.toml b/test/tasks/example/eth/016-revshare-upgrade-and-setup/config.toml index a97c00efc..d86d88efe 100644 --- a/test/tasks/example/eth/016-revshare-upgrade-and-setup/config.toml +++ b/test/tasks/example/eth/016-revshare-upgrade-and-setup/config.toml @@ -3,7 +3,7 @@ templateName = "RevShareUpgradeAndSetup" # L2 chains to target -l2chains = [{name = "OP Mainnet", chainId = 10}, {name = "Ink", chainId = 57073}] +l2chains = [{name = "OP Mainnet", chainId = 10}, {name = "Ink", chainId = 57073}, {name = "Soneium", chainId = 1868}] safeAddress = "ProxyAdminOwner" @@ -14,21 +14,25 @@ revShareUpgrader = "0x6fee65A372d63295E8EB12574652F0BfEb913149" # RevShare configurations (one per chain) - flattened arrays portals = [ "0xbEb5Fc579115071764c7423A4f12eDde41f106Ed", # OP Mainnet Portal - "0x5d66C1782664115999C47c9fA5cd031f495D3e4F" # Ink Mainnet Portal + "0x5d66C1782664115999C47c9fA5cd031f495D3e4F", # Ink Mainnet Portal + "0x88e529A6ccd302c948689Cd5156C83D4614FAE92" # Soneium Mainnet Portal ] chainFeesRecipients = [ - "0x0000000000000000000000000000000000000001", # Update to the corresponding address once defined - "0x0000000000000000000000000000000000000002" # Update to the corresponding address once defined + "0x0000000000000000000000000000000000000001", # TODO: Update to the corresponding address once defined + "0x0000000000000000000000000000000000000002", # TODO: Update to the corresponding address once defined + "0x0000000000000000000000000000000000000003" # TODO: Update to the corresponding address once defined ] -l1WithdrawerMinWithdrawalAmounts = [350000, 500000] +l1WithdrawerMinWithdrawalAmounts = [350000, 500000, 500000] l1WithdrawerRecipients = [ - # TODO(17505): Update to the corresponding (e.g. FeesDepositor) address once defined - "0x0000000000000000000000000000000000000001", - # TODO(17505): Update to the corresponding (e.g. FeesDepositor) address once defined - "0x0000000000000000000000000000000000000002" + # TODO: Update to the corresponding (e.g. FeesDepositor) address once defined + "0x0000000000000000000000000000000000000001", + # TODO: Update to the corresponding (e.g. FeesDepositor) address once defined + "0x0000000000000000000000000000000000000002", + # TODO: Update to the corresponding (e.g. FeesDepositor) address once defined + "0x0000000000000000000000000000000000000003" ] -l1WithdrawerGasLimits = [800000, 1000000] +l1WithdrawerGasLimits = [800000, 800000, 800000] [addresses] ProxyAdminOwner = "0x5a0Aae59D09fccBdDb6C6CcEB07B7279367C3d2A" diff --git a/test/tasks/example/eth/017-revshare-setup/config.toml b/test/tasks/example/eth/017-revshare-setup/config.toml index a90b6664f..61daeb357 100644 --- a/test/tasks/example/eth/017-revshare-setup/config.toml +++ b/test/tasks/example/eth/017-revshare-setup/config.toml @@ -3,32 +3,36 @@ templateName = "RevShareSetup" # L2 chains to target -l2chains = [{name = "OP Mainnet", chainId = 10}, {name = "Ink", chainId = 57073}] +l2chains = [{name = "OP Mainnet", chainId = 10}, {name = "Ink", chainId = 57073}, {name = "Soneium", chainId = 1868}] safeAddress = "ProxyAdminOwner" # RevShareContractsUpgrader address # TODO: Update to the corresponding address after audit -revShareUpgrader = "0x6fee65A372d63295E8EB12574652F0BfEb913149" +revShareUpgrader = "0x6fee65A372d63295E8EB12574652F0BfEb913149" # RevShare configurations (one per chain) - flattened arrays portals = [ "0xbEb5Fc579115071764c7423A4f12eDde41f106Ed", # OP Mainnet Portal - "0x5d66C1782664115999C47c9fA5cd031f495D3e4F" # Ink Mainnet Portal + "0x5d66C1782664115999C47c9fA5cd031f495D3e4F", # Ink Mainnet Portal + "0x88e529A6ccd302c948689Cd5156C83D4614FAE92" # Soneium Mainnet Portal ] chainFeesRecipients = [ - "0x0000000000000000000000000000000000000001", # Update to the corresponding address once defined - "0x0000000000000000000000000000000000000002" # Update to the corresponding address once defined + "0x0000000000000000000000000000000000000001", # TODO: Update to the corresponding address once defined + "0x0000000000000000000000000000000000000002", # TODO: Update to the corresponding address once defined + "0x0000000000000000000000000000000000000003" # TODO: Update to the corresponding address once defined ] -l1WithdrawerMinWithdrawalAmounts = [350000, 500000] +l1WithdrawerMinWithdrawalAmounts = [350000, 500000, 500000] l1WithdrawerRecipients = [ - # TODO(17505): Update to the corresponding (e.g. FeesDepositor) address once defined - "0x0000000000000000000000000000000000000001", - # TODO(17505): Update to the corresponding (e.g. FeesDepositor) address once defined - "0x0000000000000000000000000000000000000002" + # TODO: Update to the corresponding (e.g. FeesDepositor) address once defined + "0x0000000000000000000000000000000000000001", + # TODO: Update to the corresponding (e.g. FeesDepositor) address once defined + "0x0000000000000000000000000000000000000002", + # TODO: Update to the corresponding (e.g. FeesDepositor) address once defined + "0x0000000000000000000000000000000000000003" ] -l1WithdrawerGasLimits = [800000, 1000000] +l1WithdrawerGasLimits = [800000, 800000, 800000] [addresses] ProxyAdminOwner = "0x5a0Aae59D09fccBdDb6C6CcEB07B7279367C3d2A" diff --git a/test/tasks/example/sep/030-revshare-upgrade-and-setup/.env b/test/tasks/example/sep/032-revshare-upgrade-and-setup/.env similarity index 100% rename from test/tasks/example/sep/030-revshare-upgrade-and-setup/.env rename to test/tasks/example/sep/032-revshare-upgrade-and-setup/.env diff --git a/test/tasks/example/sep/030-revshare-upgrade-and-setup/config.toml b/test/tasks/example/sep/032-revshare-upgrade-and-setup/config.toml similarity index 100% rename from test/tasks/example/sep/030-revshare-upgrade-and-setup/config.toml rename to test/tasks/example/sep/032-revshare-upgrade-and-setup/config.toml