Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
N
nebula
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
exchain
nebula
Commits
8ce02ede
Unverified
Commit
8ce02ede
authored
Jan 23, 2023
by
mergify[bot]
Committed by
GitHub
Jan 23, 2023
Browse files
Options
Browse Files
Download
Plain Diff
Merge pull request #4714 from ethereum-optimism/refcell/missing-events
contracts-bedrock: Missing Event Tests
parents
64c8b4bb
e0232dbf
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
546 additions
and
43 deletions
+546
-43
.gas-snapshot
packages/contracts-bedrock/.gas-snapshot
+12
-10
L1StandardBridge.t.sol
...s/contracts-bedrock/contracts/test/L1StandardBridge.t.sol
+271
-23
L2StandardBridge.t.sol
...s/contracts-bedrock/contracts/test/L2StandardBridge.t.sol
+263
-10
No files found.
packages/contracts-bedrock/.gas-snapshot
View file @
8ce02ede
...
@@ -92,16 +92,17 @@ L1ERC721Bridge_Test:test_finalizeBridgeERC721_notFromRemoteMessenger_reverts() (
...
@@ -92,16 +92,17 @@ L1ERC721Bridge_Test:test_finalizeBridgeERC721_notFromRemoteMessenger_reverts() (
L1ERC721Bridge_Test:test_finalizeBridgeERC721_notViaLocalMessenger_reverts() (gas: 16093)
L1ERC721Bridge_Test:test_finalizeBridgeERC721_notViaLocalMessenger_reverts() (gas: 16093)
L1ERC721Bridge_Test:test_finalizeBridgeERC721_selfToken_reverts() (gas: 17593)
L1ERC721Bridge_Test:test_finalizeBridgeERC721_selfToken_reverts() (gas: 17593)
L1ERC721Bridge_Test:test_finalizeBridgeERC721_succeeds() (gas: 323814)
L1ERC721Bridge_Test:test_finalizeBridgeERC721_succeeds() (gas: 323814)
L1StandardBridge_DepositERC20To_Test:test_depositERC20To_succeeds() (gas:
576276
)
L1StandardBridge_DepositERC20To_Test:test_depositERC20To_succeeds() (gas:
624279
)
L1StandardBridge_DepositERC20_Test:test_depositERC20_succeeds() (gas:
574103
)
L1StandardBridge_DepositERC20_Test:test_depositERC20_succeeds() (gas:
621958
)
L1StandardBridge_DepositERC20_TestFail:test_depositERC20_notEoa_reverts() (gas: 22320)
L1StandardBridge_DepositERC20_TestFail:test_depositERC20_notEoa_reverts() (gas: 22320)
L1StandardBridge_DepositETHTo_Test:test_depositETHTo_succeeds() (gas: 3
24839
)
L1StandardBridge_DepositETHTo_Test:test_depositETHTo_succeeds() (gas: 3
58590
)
L1StandardBridge_DepositETH_Test:test_depositETH_succeeds() (gas:
367666
)
L1StandardBridge_DepositETH_Test:test_depositETH_succeeds() (gas:
401413
)
L1StandardBridge_DepositETH_TestFail:test_depositETH_notEoa_reverts() (gas: 40780)
L1StandardBridge_DepositETH_TestFail:test_depositETH_notEoa_reverts() (gas: 40780)
L1StandardBridge_FinalizeBridgeETH_Test:test_finalizeBridgeETH_succeeds() (gas: 48661)
L1StandardBridge_FinalizeBridgeETH_TestFail:test_finalizeBridgeETH_incorrectValue_reverts() (gas: 34207)
L1StandardBridge_FinalizeBridgeETH_TestFail:test_finalizeBridgeETH_incorrectValue_reverts() (gas: 34207)
L1StandardBridge_FinalizeBridgeETH_TestFail:test_finalizeBridgeETH_sendToMessenger_reverts() (gas: 34288)
L1StandardBridge_FinalizeBridgeETH_TestFail:test_finalizeBridgeETH_sendToMessenger_reverts() (gas: 34288)
L1StandardBridge_FinalizeBridgeETH_TestFail:test_finalizeBridgeETH_sendToSelf_reverts() (gas: 34257)
L1StandardBridge_FinalizeBridgeETH_TestFail:test_finalizeBridgeETH_sendToSelf_reverts() (gas: 34257)
L1StandardBridge_FinalizeERC20Withdrawal_Test:test_finalizeERC20Withdrawal_succeeds() (gas: 49
2896
)
L1StandardBridge_FinalizeERC20Withdrawal_Test:test_finalizeERC20Withdrawal_succeeds() (gas: 49
5885
)
L1StandardBridge_FinalizeERC20Withdrawal_TestFail:test_finalizeERC20Withdrawal_notMessenger_reverts() (gas: 31148)
L1StandardBridge_FinalizeERC20Withdrawal_TestFail:test_finalizeERC20Withdrawal_notMessenger_reverts() (gas: 31148)
L1StandardBridge_FinalizeERC20Withdrawal_TestFail:test_finalizeERC20Withdrawal_notOtherBridge_reverts() (gas: 31504)
L1StandardBridge_FinalizeERC20Withdrawal_TestFail:test_finalizeERC20Withdrawal_notOtherBridge_reverts() (gas: 31504)
L1StandardBridge_FinalizeETHWithdrawal_Test:test_finalizeETHWithdrawal_succeeds() (gas: 58686)
L1StandardBridge_FinalizeETHWithdrawal_Test:test_finalizeETHWithdrawal_succeeds() (gas: 58686)
...
@@ -163,16 +164,17 @@ L2OutputOracleUpgradeable_Test:test_initValuesOnProxy_succeeds() (gas: 26093)
...
@@ -163,16 +164,17 @@ L2OutputOracleUpgradeable_Test:test_initValuesOnProxy_succeeds() (gas: 26093)
L2OutputOracleUpgradeable_Test:test_initializeImpl_alreadyInitialized_reverts() (gas: 15149)
L2OutputOracleUpgradeable_Test:test_initializeImpl_alreadyInitialized_reverts() (gas: 15149)
L2OutputOracleUpgradeable_Test:test_initializeProxy_alreadyInitialized_reverts() (gas: 20131)
L2OutputOracleUpgradeable_Test:test_initializeProxy_alreadyInitialized_reverts() (gas: 20131)
L2OutputOracleUpgradeable_Test:test_upgrading_succeeds() (gas: 180413)
L2OutputOracleUpgradeable_Test:test_upgrading_succeeds() (gas: 180413)
L2StandardBridge_FinalizeBridgeETH_Test:test_finalizeBridgeETH_succeeds() (gas: 36076)
L2StandardBridge_Test:test_finalizeBridgeETH_incorrectValue_reverts() (gas: 23843)
L2StandardBridge_Test:test_finalizeBridgeETH_incorrectValue_reverts() (gas: 23843)
L2StandardBridge_Test:test_finalizeBridgeETH_sendToMessenger_reverts() (gas: 23982)
L2StandardBridge_Test:test_finalizeBridgeETH_sendToMessenger_reverts() (gas: 23982)
L2StandardBridge_Test:test_finalizeBridgeETH_sendToSelf_reverts() (gas: 23893)
L2StandardBridge_Test:test_finalizeBridgeETH_sendToSelf_reverts() (gas: 23893)
L2StandardBridge_Test:test_finalizeDeposit_succeeds() (gas:
89473
)
L2StandardBridge_Test:test_finalizeDeposit_succeeds() (gas:
90641
)
L2StandardBridge_Test:test_initialize_succeeds() (gas: 24270)
L2StandardBridge_Test:test_initialize_succeeds() (gas: 24270)
L2StandardBridge_Test:test_receive_succeeds() (gas: 1
41940
)
L2StandardBridge_Test:test_receive_succeeds() (gas: 1
76698
)
L2StandardBridge_Test:test_withdrawTo_succeeds() (gas: 3
44914
)
L2StandardBridge_Test:test_withdrawTo_succeeds() (gas: 3
84552
)
L2StandardBridge_Test:test_withdraw_insufficientValue_reverts() (gas: 19627)
L2StandardBridge_Test:test_withdraw_insufficientValue_reverts() (gas: 19627)
L2StandardBridge_Test:test_withdraw_notEOA_reverts() (gas: 251
798
)
L2StandardBridge_Test:test_withdraw_notEOA_reverts() (gas: 251
836
)
L2StandardBridge_Test:test_withdraw_succeeds() (gas: 3
44228
)
L2StandardBridge_Test:test_withdraw_succeeds() (gas: 3
82649
)
L2ToL1MessagePasserTest:test_burn_succeeds() (gas: 112572)
L2ToL1MessagePasserTest:test_burn_succeeds() (gas: 112572)
L2ToL1MessagePasserTest:test_initiateWithdrawal_fromContract_succeeds() (gas: 70423)
L2ToL1MessagePasserTest:test_initiateWithdrawal_fromContract_succeeds() (gas: 70423)
L2ToL1MessagePasserTest:test_initiateWithdrawal_fromEOA_succeeds() (gas: 75874)
L2ToL1MessagePasserTest:test_initiateWithdrawal_fromEOA_succeeds() (gas: 75874)
...
...
packages/contracts-bedrock/contracts/test/L1StandardBridge.t.sol
View file @
8ce02ede
...
@@ -3,6 +3,7 @@ pragma solidity 0.8.15;
...
@@ -3,6 +3,7 @@ pragma solidity 0.8.15;
import { Bridge_Initializer } from "./CommonTest.t.sol";
import { Bridge_Initializer } from "./CommonTest.t.sol";
import { StandardBridge } from "../universal/StandardBridge.sol";
import { StandardBridge } from "../universal/StandardBridge.sol";
import { OptimismPortal } from "../L1/OptimismPortal.sol";
import { L2StandardBridge } from "../L2/L2StandardBridge.sol";
import { L2StandardBridge } from "../L2/L2StandardBridge.sol";
import { CrossDomainMessenger } from "../universal/CrossDomainMessenger.sol";
import { CrossDomainMessenger } from "../universal/CrossDomainMessenger.sol";
import { Predeploys } from "../libraries/Predeploys.sol";
import { Predeploys } from "../libraries/Predeploys.sol";
...
@@ -78,26 +79,74 @@ contract L1StandardBridge_DepositETH_Test is Bridge_Initializer {
...
@@ -78,26 +79,74 @@ contract L1StandardBridge_DepositETH_Test is Bridge_Initializer {
// - ETH ends up in the optimismPortal
// - ETH ends up in the optimismPortal
function test_depositETH_succeeds() external {
function test_depositETH_succeeds() external {
assertEq(address(op).balance, 0);
assertEq(address(op).balance, 0);
uint256 nonce = L1Messenger.messageNonce();
uint256 version = 0; // Internal constant in the OptimismPortal: DEPOSIT_VERSION
address l1MessengerAliased = AddressAliasHelper.applyL1ToL2Alias(address(L1Messenger));
vm.expectEmit(true, true, true, true);
vm.expectEmit(true, true, true, true);
emit ETHBridgeInitiated(alice, alice, 500, hex"ff");
emit ETHBridgeInitiated(alice, alice, 500, hex"ff");
bytes memory message = abi.encodeWithSelector(
StandardBridge.finalizeBridgeETH.selector,
alice,
alice,
500,
hex"ff"
);
vm.expectCall(
vm.expectCall(
address(L1Messenger),
address(L1Messenger),
abi.encodeWithSelector(
abi.encodeWithSelector(
CrossDomainMessenger.sendMessage.selector,
CrossDomainMessenger.sendMessage.selector,
address(L2Bridge),
address(L2Bridge),
abi.encodeWithSelector(
message,
StandardBridge.finalizeBridgeETH.selector,
alice,
alice,
500,
hex"ff"
),
50000
50000
)
)
);
);
bytes memory innerMessage = abi.encodeWithSelector(
CrossDomainMessenger.relayMessage.selector,
nonce,
address(L1Bridge),
address(L2Bridge),
500,
50000,
message
);
uint64 baseGas = L1Messenger.baseGas(message, 50000);
vm.expectCall(
address(op),
abi.encodeWithSelector(
OptimismPortal.depositTransaction.selector,
address(L2Messenger),
500,
baseGas,
false,
innerMessage
)
);
bytes memory opaqueData = abi.encodePacked(
uint256(500),
uint256(500),
baseGas,
false,
innerMessage
);
// OptimismPortal emits a TransactionDeposited event on `depositTransaction` call
vm.expectEmit(true, true, true, true);
emit TransactionDeposited(l1MessengerAliased, address(L2Messenger), version, opaqueData);
// SentMessage event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessage(address(L2Bridge), address(L1Bridge), message, nonce, 50000);
// SentMessageExtension1 event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessageExtension1(address(L1Bridge), 500);
vm.prank(alice, alice);
vm.prank(alice, alice);
L1Bridge.depositETH{ value: 500 }(50000, hex"ff");
L1Bridge.depositETH{ value: 500 }(50000, hex"ff");
assertEq(address(op).balance, 500);
assertEq(address(op).balance, 500);
...
@@ -123,6 +172,9 @@ contract L1StandardBridge_DepositETHTo_Test is Bridge_Initializer {
...
@@ -123,6 +172,9 @@ contract L1StandardBridge_DepositETHTo_Test is Bridge_Initializer {
// - ETH ends up in the optimismPortal
// - ETH ends up in the optimismPortal
function test_depositETHTo_succeeds() external {
function test_depositETHTo_succeeds() external {
assertEq(address(op).balance, 0);
assertEq(address(op).balance, 0);
uint256 nonce = L1Messenger.messageNonce();
uint256 version = 0; // Internal constant in the OptimismPortal: DEPOSIT_VERSION
address l1MessengerAliased = AddressAliasHelper.applyL1ToL2Alias(address(L1Messenger));
vm.expectEmit(true, true, true, true);
vm.expectEmit(true, true, true, true);
emit ETHDepositInitiated(alice, bob, 600, hex"dead");
emit ETHDepositInitiated(alice, bob, 600, hex"dead");
...
@@ -136,6 +188,14 @@ contract L1StandardBridge_DepositETHTo_Test is Bridge_Initializer {
...
@@ -136,6 +188,14 @@ contract L1StandardBridge_DepositETHTo_Test is Bridge_Initializer {
abi.encodeWithSelector(L1Bridge.depositETHTo.selector, bob, 1000, hex"dead")
abi.encodeWithSelector(L1Bridge.depositETHTo.selector, bob, 1000, hex"dead")
);
);
bytes memory message = abi.encodeWithSelector(
StandardBridge.finalizeBridgeETH.selector,
alice,
bob,
600,
hex"dead"
);
// the L1 bridge should call
// the L1 bridge should call
// L1CrossDomainMessenger.sendMessage
// L1CrossDomainMessenger.sendMessage
vm.expectCall(
vm.expectCall(
...
@@ -143,19 +203,53 @@ contract L1StandardBridge_DepositETHTo_Test is Bridge_Initializer {
...
@@ -143,19 +203,53 @@ contract L1StandardBridge_DepositETHTo_Test is Bridge_Initializer {
abi.encodeWithSelector(
abi.encodeWithSelector(
CrossDomainMessenger.sendMessage.selector,
CrossDomainMessenger.sendMessage.selector,
address(L2Bridge),
address(L2Bridge),
abi.encodeWithSelector(
message,
StandardBridge.finalizeBridgeETH.selector,
alice,
bob,
600,
hex"dead"
),
1000
1000
)
)
);
);
// TODO: assert on OptimismPortal being called
bytes memory innerMessage = abi.encodeWithSelector(
// and the event being emitted correctly
CrossDomainMessenger.relayMessage.selector,
nonce,
address(L1Bridge),
address(L2Bridge),
600,
1000,
message
);
uint64 baseGas = L1Messenger.baseGas(message, 1000);
vm.expectCall(
address(op),
abi.encodeWithSelector(
OptimismPortal.depositTransaction.selector,
address(L2Messenger),
600,
baseGas,
false,
innerMessage
)
);
bytes memory opaqueData = abi.encodePacked(
uint256(600),
uint256(600),
baseGas,
false,
innerMessage
);
// OptimismPortal emits a TransactionDeposited event on `depositTransaction` call
vm.expectEmit(true, true, true, true);
emit TransactionDeposited(l1MessengerAliased, address(L2Messenger), version, opaqueData);
// SentMessage event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessage(address(L2Bridge), address(L1Bridge), message, nonce, 1000);
// SentMessageExtension1 event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessageExtension1(address(L1Bridge), 600);
// deposit eth to bob
// deposit eth to bob
vm.prank(alice, alice);
vm.prank(alice, alice);
...
@@ -174,26 +268,94 @@ contract L1StandardBridge_DepositERC20_Test is Bridge_Initializer {
...
@@ -174,26 +268,94 @@ contract L1StandardBridge_DepositERC20_Test is Bridge_Initializer {
// - calls optimismPortal.depositTransaction
// - calls optimismPortal.depositTransaction
// - only callable by EOA
// - only callable by EOA
function test_depositERC20_succeeds() external {
function test_depositERC20_succeeds() external {
uint256 nonce = L1Messenger.messageNonce();
uint256 version = 0; // Internal constant in the OptimismPortal: DEPOSIT_VERSION
address l1MessengerAliased = AddressAliasHelper.applyL1ToL2Alias(address(L1Messenger));
vm.expectEmit(true, true, true, true);
vm.expectEmit(true, true, true, true);
emit ERC20DepositInitiated(address(L1Token), address(L2Token), alice, alice, 100, hex"");
emit ERC20DepositInitiated(address(L1Token), address(L2Token), alice, alice, 100, hex"");
// Deal Alice's ERC20 State
deal(address(L1Token), alice, 100000, true);
deal(address(L1Token), alice, 100000, true);
vm.prank(alice);
vm.prank(alice);
L1Token.approve(address(L1Bridge), type(uint256).max);
L1Token.approve(address(L1Bridge), type(uint256).max);
// The L1Bridge should transfer alice's tokens
// The L1Bridge should transfer alice's tokens to itself
// to itself
vm.expectCall(
vm.expectCall(
address(L1Token),
address(L1Token),
abi.encodeWithSelector(ERC20.transferFrom.selector, alice, address(L1Bridge), 100)
abi.encodeWithSelector(ERC20.transferFrom.selector, alice, address(L1Bridge), 100)
);
);
// TODO: optimismPortal.depositTransaction call + event
bytes memory message = abi.encodeWithSelector(
StandardBridge.finalizeBridgeERC20.selector,
address(L2Token),
address(L1Token),
alice,
alice,
100,
hex""
);
// the L1 bridge should call L1CrossDomainMessenger.sendMessage
vm.expectCall(
address(L1Messenger),
abi.encodeWithSelector(
CrossDomainMessenger.sendMessage.selector,
address(L2Bridge),
message,
10000
)
);
bytes memory innerMessage = abi.encodeWithSelector(
CrossDomainMessenger.relayMessage.selector,
nonce,
address(L1Bridge),
address(L2Bridge),
0,
10000,
message
);
uint64 baseGas = L1Messenger.baseGas(message, 10000);
vm.expectCall(
address(op),
abi.encodeWithSelector(
OptimismPortal.depositTransaction.selector,
address(L2Messenger),
0,
baseGas,
false,
innerMessage
)
);
bytes memory opaqueData = abi.encodePacked(
uint256(0),
uint256(0),
baseGas,
false,
innerMessage
);
// ERC20 Deposit Initiated event emitted by the StandardBridge Contract
vm.expectEmit(true, true, true, true);
emit ERC20BridgeInitiated(address(L1Token), address(L2Token), alice, alice, 100, hex"");
// OptimismPortal emits a TransactionDeposited event on `depositTransaction` call
vm.expectEmit(true, true, true, true);
emit TransactionDeposited(l1MessengerAliased, address(L2Messenger), version, opaqueData);
// SentMessage event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessage(address(L2Bridge), address(L1Bridge), message, nonce, 10000);
// SentMessageExtension1 event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessageExtension1(address(L1Bridge), 0);
vm.prank(alice);
vm.prank(alice);
L1Bridge.depositERC20(address(L1Token), address(L2Token), 100, 10000, hex"");
L1Bridge.depositERC20(address(L1Token), address(L2Token), 100, 10000, hex"");
assertEq(L1Bridge.deposits(address(L1Token), address(L2Token)), 100);
assertEq(L1Bridge.deposits(address(L1Token), address(L2Token)), 100);
}
}
}
}
...
@@ -216,9 +378,80 @@ contract L1StandardBridge_DepositERC20To_Test is Bridge_Initializer {
...
@@ -216,9 +378,80 @@ contract L1StandardBridge_DepositERC20To_Test is Bridge_Initializer {
// - calls optimismPortal.depositTransaction
// - calls optimismPortal.depositTransaction
// - callable by a contract
// - callable by a contract
function test_depositERC20To_succeeds() external {
function test_depositERC20To_succeeds() external {
uint256 nonce = L1Messenger.messageNonce();
uint256 version = 0; // Internal constant in the OptimismPortal: DEPOSIT_VERSION
address l1MessengerAliased = AddressAliasHelper.applyL1ToL2Alias(address(L1Messenger));
bytes memory message = abi.encodeWithSelector(
StandardBridge.finalizeBridgeERC20.selector,
address(L2Token),
address(L1Token),
alice,
bob,
1000,
hex""
);
// the L1 bridge should call L1CrossDomainMessenger.sendMessage
vm.expectCall(
address(L1Messenger),
abi.encodeWithSelector(
CrossDomainMessenger.sendMessage.selector,
address(L2Bridge),
message,
10000
)
);
bytes memory innerMessage = abi.encodeWithSelector(
CrossDomainMessenger.relayMessage.selector,
nonce,
address(L1Bridge),
address(L2Bridge),
0,
10000,
message
);
uint64 baseGas = L1Messenger.baseGas(message, 10000);
vm.expectCall(
address(op),
abi.encodeWithSelector(
OptimismPortal.depositTransaction.selector,
address(L2Messenger),
0,
baseGas,
false,
innerMessage
)
);
bytes memory opaqueData = abi.encodePacked(
uint256(0),
uint256(0),
baseGas,
false,
innerMessage
);
vm.expectEmit(true, true, true, true);
vm.expectEmit(true, true, true, true);
emit ERC20DepositInitiated(address(L1Token), address(L2Token), alice, bob, 1000, hex"");
emit ERC20DepositInitiated(address(L1Token), address(L2Token), alice, bob, 1000, hex"");
vm.expectEmit(true, true, true, true);
emit ERC20BridgeInitiated(address(L1Token), address(L2Token), alice, bob, 1000, hex"");
// OptimismPortal emits a TransactionDeposited event on `depositTransaction` call
vm.expectEmit(true, true, true, true);
emit TransactionDeposited(l1MessengerAliased, address(L2Messenger), version, opaqueData);
// SentMessage event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessage(address(L2Bridge), address(L1Bridge), message, nonce, 10000);
// SentMessageExtension1 event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessageExtension1(address(L1Bridge), 0);
deal(address(L1Token), alice, 100000, true);
deal(address(L1Token), alice, 100000, true);
vm.prank(alice);
vm.prank(alice);
...
@@ -291,6 +524,9 @@ contract L1StandardBridge_FinalizeERC20Withdrawal_Test is Bridge_Initializer {
...
@@ -291,6 +524,9 @@ contract L1StandardBridge_FinalizeERC20Withdrawal_Test is Bridge_Initializer {
vm.expectEmit(true, true, true, true);
vm.expectEmit(true, true, true, true);
emit ERC20WithdrawalFinalized(address(L1Token), address(L2Token), alice, alice, 100, hex"");
emit ERC20WithdrawalFinalized(address(L1Token), address(L2Token), alice, alice, 100, hex"");
vm.expectEmit(true, true, true, true);
emit ERC20BridgeFinalized(address(L1Token), address(L2Token), alice, alice, 100, hex"");
vm.expectCall(
vm.expectCall(
address(L1Token),
address(L1Token),
abi.encodeWithSelector(ERC20.transfer.selector, alice, 100)
abi.encodeWithSelector(ERC20.transfer.selector, alice, 100)
...
@@ -354,10 +590,22 @@ contract L1StandardBridge_FinalizeERC20Withdrawal_TestFail is Bridge_Initializer
...
@@ -354,10 +590,22 @@ contract L1StandardBridge_FinalizeERC20Withdrawal_TestFail is Bridge_Initializer
}
}
}
}
// Todo: move these next two contracts into a test file specific to the direction agnostic
// StandardBridge interface
contract L1StandardBridge_FinalizeBridgeETH_Test is Bridge_Initializer {
contract L1StandardBridge_FinalizeBridgeETH_Test is Bridge_Initializer {
function test_finalizeBridgeETH_succeeds() external {
address messenger = address(L1Bridge.messenger());
vm.mockCall(
messenger,
abi.encodeWithSelector(CrossDomainMessenger.xDomainMessageSender.selector),
abi.encode(address(L1Bridge.OTHER_BRIDGE()))
);
vm.deal(messenger, 100);
vm.prank(messenger);
vm.expectEmit(true, true, true, true);
emit ETHBridgeFinalized(alice, alice, 100, hex"");
L1Bridge.finalizeBridgeETH{ value: 100 }(alice, alice, 100, hex"");
}
}
}
contract L1StandardBridge_FinalizeBridgeETH_TestFail is Bridge_Initializer {
contract L1StandardBridge_FinalizeBridgeETH_TestFail is Bridge_Initializer {
...
...
packages/contracts-bedrock/contracts/test/L2StandardBridge.t.sol
View file @
8ce02ede
...
@@ -6,6 +6,12 @@ import { stdStorage, StdStorage } from "forge-std/Test.sol";
...
@@ -6,6 +6,12 @@ import { stdStorage, StdStorage } from "forge-std/Test.sol";
import { CrossDomainMessenger } from "../universal/CrossDomainMessenger.sol";
import { CrossDomainMessenger } from "../universal/CrossDomainMessenger.sol";
import { Predeploys } from "../libraries/Predeploys.sol";
import { Predeploys } from "../libraries/Predeploys.sol";
import { console } from "forge-std/console.sol";
import { console } from "forge-std/console.sol";
import { StandardBridge } from "../universal/StandardBridge.sol";
import { L2ToL1MessagePasser } from "../L2/L2ToL1MessagePasser.sol";
import { Hashing } from "../libraries/Hashing.sol";
import { Types } from "../libraries/Types.sol";
import { ERC20 } from "@openzeppelin/contracts/token/ERC20/ERC20.sol";
import { OptimismMintableERC20 } from "../universal/OptimismMintableERC20.sol";
contract L2StandardBridge_Test is Bridge_Initializer {
contract L2StandardBridge_Test is Bridge_Initializer {
using stdStorage for StdStorage;
using stdStorage for StdStorage;
...
@@ -24,14 +30,78 @@ contract L2StandardBridge_Test is Bridge_Initializer {
...
@@ -24,14 +30,78 @@ contract L2StandardBridge_Test is Bridge_Initializer {
// - can accept ETH
// - can accept ETH
function test_receive_succeeds() external {
function test_receive_succeeds() external {
assertEq(address(messagePasser).balance, 0);
assertEq(address(messagePasser).balance, 0);
uint256 nonce = L2Messenger.messageNonce();
bytes memory message = abi.encodeWithSelector(
StandardBridge.finalizeBridgeETH.selector,
alice,
alice,
100,
hex""
);
uint64 baseGas = L2Messenger.baseGas(message, 200_000);
bytes memory withdrawalData = abi.encodeWithSelector(
CrossDomainMessenger.relayMessage.selector,
nonce,
address(L2Bridge),
address(L1Bridge),
100,
200_000,
message
);
bytes32 withdrawalHash = Hashing.hashWithdrawal(
Types.WithdrawalTransaction({
nonce: nonce,
sender: address(L2Messenger),
target: address(L1Messenger),
value: 100,
gasLimit: baseGas,
data: withdrawalData
})
);
vm.expectEmit(true, true, true, true);
vm.expectEmit(true, true, true, true);
emit ETHBridgeInitiated(alice, alice, 100, hex"");
emit ETHBridgeInitiated(alice, alice, 100, hex"");
// TODO: L2Messenger should be called
// L2ToL1MessagePasser will emit a MessagePassed event
// TODO: L2ToL1MessagePasser should be called
vm.expectEmit(true, true, true, true);
// TODO: withdrawal hash should be computed correctly
emit MessagePassed(
// TODO: events from each contract
nonce,
address(L2Messenger),
address(L1Messenger),
100,
baseGas,
withdrawalData,
withdrawalHash
);
// SentMessage event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessage(address(L1Bridge), address(L2Bridge), message, nonce, 200_000);
// SentMessageExtension1 event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessageExtension1(address(L2Bridge), 100);
vm.expectCall(
address(L2Messenger),
abi.encodeWithSelector(
CrossDomainMessenger.sendMessage.selector,
address(L1Bridge),
message,
200_000 // StandardBridge's RECEIVE_DEFAULT_GAS_LIMIT
)
);
vm.expectCall(
Predeploys.L2_TO_L1_MESSAGE_PASSER,
abi.encodeWithSelector(
L2ToL1MessagePasser.initiateWithdrawal.selector,
address(L1Messenger),
baseGas,
withdrawalData
)
);
vm.expectEmit(true, true, true, true);
vm.expectEmit(true, true, true, true);
emit WithdrawalInitiated(address(0), Predeploys.LEGACY_ERC20_ETH, alice, alice, 100, hex"");
emit WithdrawalInitiated(address(0), Predeploys.LEGACY_ERC20_ETH, alice, alice, 100, hex"");
...
@@ -60,12 +130,91 @@ contract L2StandardBridge_Test is Bridge_Initializer {
...
@@ -60,12 +130,91 @@ contract L2StandardBridge_Test is Bridge_Initializer {
// Alice has 100 L2Token
// Alice has 100 L2Token
deal(address(L2Token), alice, 100, true);
deal(address(L2Token), alice, 100, true);
assertEq(L2Token.balanceOf(alice), 100);
assertEq(L2Token.balanceOf(alice), 100);
uint256 nonce = L2Messenger.messageNonce();
bytes memory message = abi.encodeWithSelector(
StandardBridge.finalizeBridgeERC20.selector,
address(L1Token),
address(L2Token),
alice,
alice,
100,
hex""
);
uint64 baseGas = L2Messenger.baseGas(message, 1000);
bytes memory withdrawalData = abi.encodeWithSelector(
CrossDomainMessenger.relayMessage.selector,
nonce,
address(L2Bridge),
address(L1Bridge),
0,
1000,
message
);
bytes32 withdrawalHash = Hashing.hashWithdrawal(
Types.WithdrawalTransaction({
nonce: nonce,
sender: address(L2Messenger),
target: address(L1Messenger),
value: 0,
gasLimit: baseGas,
data: withdrawalData
})
);
vm.expectEmit(true, true, true, true);
emit ERC20BridgeInitiated(address(L2Token), address(L1Token), alice, alice, 100, hex"");
vm.expectEmit(true, true, true, true);
emit MessagePassed(
nonce,
address(L2Messenger),
address(L1Messenger),
0,
baseGas,
withdrawalData,
withdrawalHash
);
// SentMessage event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessage(address(L1Bridge), address(L2Bridge), message, nonce, 1000);
// SentMessageExtension1 event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessageExtension1(address(L2Bridge), 0);
vm.expectEmit(true, true, true, true);
emit WithdrawalInitiated(address(L1Token), address(L2Token), alice, alice, 100, hex"");
vm.expectCall(
address(L2Messenger),
abi.encodeWithSelector(
CrossDomainMessenger.sendMessage.selector,
address(L1Bridge),
message,
1000
)
);
vm.expectCall(
Predeploys.L2_TO_L1_MESSAGE_PASSER,
abi.encodeWithSelector(
L2ToL1MessagePasser.initiateWithdrawal.selector,
address(L1Messenger),
baseGas,
withdrawalData
)
);
// The L2Bridge should burn the tokens
vm.expectCall(
address(L2Token),
abi.encodeWithSelector(OptimismMintableERC20.burn.selector, alice, 100)
);
vm.prank(alice, alice);
vm.prank(alice, alice);
L2Bridge.withdraw(address(L2Token), 100, 1000, hex"");
L2Bridge.withdraw(address(L2Token), 100, 1000, hex"");
// TODO: events and calls
assertEq(L2Token.balanceOf(alice), 0);
assertEq(L2Token.balanceOf(alice), 0);
}
}
...
@@ -83,12 +232,92 @@ contract L2StandardBridge_Test is Bridge_Initializer {
...
@@ -83,12 +232,92 @@ contract L2StandardBridge_Test is Bridge_Initializer {
// - calls Withdrawer.initiateWithdrawal
// - calls Withdrawer.initiateWithdrawal
function test_withdrawTo_succeeds() external {
function test_withdrawTo_succeeds() external {
deal(address(L2Token), alice, 100, true);
deal(address(L2Token), alice, 100, true);
assertEq(L2Token.balanceOf(alice), 100);
uint256 nonce = L2Messenger.messageNonce();
bytes memory message = abi.encodeWithSelector(
StandardBridge.finalizeBridgeERC20.selector,
address(L1Token),
address(L2Token),
alice,
bob,
100,
hex""
);
uint64 baseGas = L2Messenger.baseGas(message, 1000);
bytes memory withdrawalData = abi.encodeWithSelector(
CrossDomainMessenger.relayMessage.selector,
nonce,
address(L2Bridge),
address(L1Bridge),
0,
1000,
message
);
bytes32 withdrawalHash = Hashing.hashWithdrawal(
Types.WithdrawalTransaction({
nonce: nonce,
sender: address(L2Messenger),
target: address(L1Messenger),
value: 0,
gasLimit: baseGas,
data: withdrawalData
})
);
vm.expectEmit(true, true, true, true);
emit ERC20BridgeInitiated(address(L2Token), address(L1Token), alice, bob, 100, hex"");
vm.expectEmit(true, true, true, true);
emit MessagePassed(
nonce,
address(L2Messenger),
address(L1Messenger),
0,
baseGas,
withdrawalData,
withdrawalHash
);
// SentMessage event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessage(address(L1Bridge), address(L2Bridge), message, nonce, 1000);
// SentMessageExtension1 event emitted by the CrossDomainMessenger
vm.expectEmit(true, true, true, true);
emit SentMessageExtension1(address(L2Bridge), 0);
vm.expectEmit(true, true, true, true);
emit WithdrawalInitiated(address(L1Token), address(L2Token), alice, bob, 100, hex"");
vm.expectCall(
address(L2Messenger),
abi.encodeWithSelector(
CrossDomainMessenger.sendMessage.selector,
address(L1Bridge),
message,
1000
)
);
vm.expectCall(
Predeploys.L2_TO_L1_MESSAGE_PASSER,
abi.encodeWithSelector(
L2ToL1MessagePasser.initiateWithdrawal.selector,
address(L1Messenger),
baseGas,
withdrawalData
)
);
// The L2Bridge should burn the tokens
vm.expectCall(
address(L2Token),
abi.encodeWithSelector(OptimismMintableERC20.burn.selector, alice, 100)
);
vm.prank(alice, alice);
vm.prank(alice, alice);
L2Bridge.withdrawTo(address(L2Token), bob, 100, 1000, hex"");
L2Bridge.withdrawTo(address(L2Token), bob, 100, 1000, hex"");
// TODO: events and calls
assertEq(L2Token.balanceOf(alice), 0);
assertEq(L2Token.balanceOf(alice), 0);
}
}
...
@@ -97,13 +326,17 @@ contract L2StandardBridge_Test is Bridge_Initializer {
...
@@ -97,13 +326,17 @@ contract L2StandardBridge_Test is Bridge_Initializer {
// - supported token pair emits DepositFinalized
// - supported token pair emits DepositFinalized
// - invalid deposit calls Withdrawer.initiateWithdrawal
// - invalid deposit calls Withdrawer.initiateWithdrawal
function test_finalizeDeposit_succeeds() external {
function test_finalizeDeposit_succeeds() external {
// TODO: events and calls
vm.mockCall(
vm.mockCall(
address(L2Bridge.messenger()),
address(L2Bridge.messenger()),
abi.encodeWithSelector(CrossDomainMessenger.xDomainMessageSender.selector),
abi.encodeWithSelector(CrossDomainMessenger.xDomainMessageSender.selector),
abi.encode(address(L2Bridge.OTHER_BRIDGE()))
abi.encode(address(L2Bridge.OTHER_BRIDGE()))
);
);
vm.expectCall(
address(L2Token),
abi.encodeWithSelector(OptimismMintableERC20.mint.selector, alice, 100)
);
vm.expectEmit(true, true, true, true, address(L2Bridge));
vm.expectEmit(true, true, true, true, address(L2Bridge));
emit ERC20BridgeFinalized(
emit ERC20BridgeFinalized(
address(L2Token), // localToken
address(L2Token), // localToken
...
@@ -113,8 +346,10 @@ contract L2StandardBridge_Test is Bridge_Initializer {
...
@@ -113,8 +346,10 @@ contract L2StandardBridge_Test is Bridge_Initializer {
100,
100,
hex""
hex""
);
);
vm.expectEmit(true, true, true, true, address(L2Bridge));
vm.expectEmit(true, true, true, true, address(L2Bridge));
emit DepositFinalized(address(L1Token), address(L2Token), alice, alice, 100, hex"");
emit DepositFinalized(address(L1Token), address(L2Token), alice, alice, 100, hex"");
vm.prank(address(L2Messenger));
vm.prank(address(L2Messenger));
L2Bridge.finalizeDeposit(address(L1Token), address(L2Token), alice, alice, 100, hex"");
L2Bridge.finalizeDeposit(address(L1Token), address(L2Token), alice, alice, 100, hex"");
}
}
...
@@ -155,3 +390,21 @@ contract L2StandardBridge_Test is Bridge_Initializer {
...
@@ -155,3 +390,21 @@ contract L2StandardBridge_Test is Bridge_Initializer {
L2Bridge.finalizeBridgeETH{ value: 100 }(alice, address(L2Messenger), 100, hex"");
L2Bridge.finalizeBridgeETH{ value: 100 }(alice, address(L2Messenger), 100, hex"");
}
}
}
}
contract L2StandardBridge_FinalizeBridgeETH_Test is Bridge_Initializer {
function test_finalizeBridgeETH_succeeds() external {
address messenger = address(L2Bridge.messenger());
vm.mockCall(
messenger,
abi.encodeWithSelector(CrossDomainMessenger.xDomainMessageSender.selector),
abi.encode(address(L2Bridge.OTHER_BRIDGE()))
);
vm.deal(messenger, 100);
vm.prank(messenger);
vm.expectEmit(true, true, true, true);
emit ETHBridgeFinalized(alice, alice, 100, hex"");
L2Bridge.finalizeBridgeETH{ value: 100 }(alice, alice, 100, hex"");
}
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment