For the governance representation, the token and the bridge admin has been set to the Lido DAO agent contract as a final result of deployment
The governance executor has been deployed from the following repo:
https://github.com/lidofinance/governance-crosschain-bridges/tree/master, the contracts correspond to master
branch.
Deployment instructions: https://github.com/lidofinance/governance-crosschain-bridges#deploying-the-optimismbridgeexecutor, deployment script: https://github.com/lidofinance/governance-crosschain-bridges/blob/master/deploy/gov-bridge-optimism.ts
npm run deploy:optimism:mainnet
getEthereumGovernanceExecutor()
== 0x3e40D73EB977Dc6a537aF587D48316feE66E9C8c (Lido DAO Agent)getDelay() == 0
getGracePeriod() == 86400
getMinimumDelay() == 0
getMaximumDelay() == 1
getGuardian() == 0x0000000000000000000000000000000000000000
getActionsSetCount() == 0
OPT_CONTRACT_ADDRESS
variable in the validate-deployment.ts
filenpx hardhat run scripts/validate-deployment.ts
GitHub repo: https://github.com/lidofinance/lido-l2, main
branch.
the deployment happened on the pre-bedrock OP version
The list of the deployed artifacts together with a governance executor module:
https://docs.lido.fi/deployed-contracts/#optimism
One can use the deployment instructions described in the following sections:
https://github.com/lidofinance/lido-l2#bridge-deployment (general env setup)
https://github.com/lidofinance/lido-l2#deploying-optimism-bridge (Optimism case)
0x3e40D73EB977Dc6a537aF587D48316feE66E9C8c
(Aragon Agent)0x3cd9F71F80AB08ea5a7Dca348B5e94BC595f26A0
(Lido’s DEV multisig)0x73b047fe6337183A454c5217241D780a932777bD
(Lido’s Ethereum Emergency multi-sig)0x4Cf8fE0A4c2539F7EFDD2047d8A5D46F14613088
(Lido’s Optimism Emergency multisig).env
file using deployment config as a seed and fill the rest variablesnpm run optimism:deploy
forking
variable in the .env
file to false
npm run optimism:deploy
Deployed Contract Addresses:
L1ERC20TokenBridge
Impl : 0x29C5c51A031165CE62F964966A6399b81165EFA4
L1ERC20TokenBridge
Proxy: 0x76943C0D61395d8F2edF9060e1533529cAe05dE6
ERC20Bridged
Impl: 0x92834c37dF982A13bb0f8C3F6608E26F0546538e
ERC20Bridged
Proxy: 0x1F32b1c2345538c0c6f582fCB022739c4A194Ebb
L2ERC20TokenBridge
Impl: 0x23B96aDD54c479C6784Dd504670B5376B808f4C7
L2ERC20TokenBridge
Proxy: 0x8E01013243a96601a86eb3153F0d9Fa4fbFb6957
Verify the deployed contracts on Etherscan using the commands generated by the deploy script
Run tests for deployed contracts:
.env
fileTESTING_OPT_L2_TOKEN=
TESTING_OPT_L1_ERC20_TOKEN_BRIDGE=
TESTING_OPT_L2_ERC20_TOKEN_BRIDGE=
TESTING_L1_TOKENS_HOLDER=
npm run fork:eth:mainnet
npm run fork:opt:mainnet
npm run optimism:test:acceptance
npm run optimism:test:integration
Manually validate the state of the contracts:
OssifiableProxy
for L1ERC20TokenBridge
(0x76943C0D61395d8F2edF9060e1533529cAe05dE6
)
proxy__getAdmin
- 0x3e40D73EB977Dc6a537aF587D48316feE66E9C8c
proxy__getImplementation
- 0x29C5c51A031165CE62F964966A6399b81165EFA4
proxy__getIsOssified == false
isDepositsEnabled == false
isWithdrawalsEnabled == true
isInitialized == true
hasRole(DEFAULT_ADMIN_ROLE, 0x3e40D73EB977Dc6a537aF587D48316feE66E9C8c) == true
hasRole(DEFAULT_ADMIN_ROLE, 0x2a61d3ba5030Ef471C74f612962c7367ECa3a62d) == false
hasRole(DEPOSITS_ENABLER_ROLE, 0x2a61d3ba5030Ef471C74f612962c7367ECa3a62d) == false
hasRole(DEPOSITS_ENABLER_ROLE, 0x3cd9F71F80AB08ea5a7Dca348B5e94BC595f26A0) == true
hasRole(DEPOSITS_ENABLER_ROLE, 0x3e40D73EB977Dc6a537aF587D48316feE66E9C8c) == true
hasRole(DEPOSITS_DISABLER_ROLE, 0x3e40D73EB977Dc6a537aF587D48316feE66E9C8c) == true
hasRole(DEPOSITS_DISABLER_ROLE, 0x2a61d3ba5030Ef471C74f612962c7367ECa3a62d) == false
hasRole(DEPOSITS_DISABLER_ROLE, 0x73b047fe6337183A454c5217241D780a932777bD) == true
hasRole(WITHDRAWALS_ENABLER_ROLE, 0x3e40D73EB977Dc6a537aF587D48316feE66E9C8c) == true
hasRole(WITHDRAWALS_ENABLER_ROLE, 0x2a61d3ba5030Ef471C74f612962c7367ECa3a62d) == false
hasRole(WITHDRAWALS_DISABLER_ROLE, 0x2a61d3ba5030Ef471C74f612962c7367ECa3a62d) == false
hasRole(WITHDRAWALS_DISABLER_ROLE, 0x3e40D73EB977Dc6a537aF587D48316feE66E9C8c) == true
hasRole(WITHDRAWALS_DISABLER_ROLE, 0x73b047fe6337183A454c5217241D780a932777bD) == true
L1ERC20TokenBridge
implementation (0x29C5c51A031165CE62F964966A6399b81165EFA4
)
l1Token == 0x7f39C581F595B53c5cb19bD0b3f8dA6c935E2Ca0
l2Token
- 0x1F32b1c2345538c0c6f582fCB022739c4A194Ebb
l2TokenBridge
- 0x8E01013243a96601a86eb3153F0d9Fa4fbFb6957
messenger == 0x25ace71c97B33Cc4729CF772ae268934F7ab5fA1
OssifiableProxy
for L2ERC20TokenBridge
(0x8E01013243a96601a86eb3153F0d9Fa4fbFb6957
)
proxy__getAdmin
- 0xEfa0dB536d2c8089685630fafe88CF7805966FC3
(Lido’s Optimism Governance Bridge)proxy__getImplementation
- 0x23B96aDD54c479C6784Dd504670B5376B808f4C7
proxy__getIsOssified == false
isDepositsEnabled == true
isWithdrawalsEnabled == true
isInitialized == true
hasRole(DEFAULT_ADMIN_ROLE, 0xEfa0dB536d2c8089685630fafe88CF7805966FC3) == true
hasRole(DEFAULT_ADMIN_ROLE, 0x2C01F405e3C525C0cB867789AAf077f3553ccbB7) == false
hasRole(DEPOSITS_ENABLER_ROLE, 0x2C01F405e3C525C0cB867789AAf077f3553ccbB7) == false
hasRole(DEPOSITS_ENABLER_ROLE, 0xEfa0dB536d2c8089685630fafe88CF7805966FC3) == true
hasRole(DEPOSITS_DISABLER_ROLE, 0xEfa0dB536d2c8089685630fafe88CF7805966FC3) == true
hasRole(DEPOSITS_DISABLER_ROLE, 0x4Cf8fE0A4c2539F7EFDD2047d8A5D46F14613088) == true
hasRole(DEPOSITS_DISABLER_ROLE, 0x2C01F405e3C525C0cB867789AAf077f3553ccbB7) == false
hasRole(WITHDRAWALS_ENABLER_ROLE, 0x2C01F405e3C525C0cB867789AAf077f3553ccbB7) == false
hasRole(WITHDRAWALS_ENABLER_ROLE, 0xEfa0dB536d2c8089685630fafe88CF7805966FC3) == true
hasRole(WITHDRAWALS_DISABLER_ROLE, 0xEfa0dB536d2c8089685630fafe88CF7805966FC3) == true
hasRole(WITHDRAWALS_DISABLER_ROLE, 0x4Cf8fE0A4c2539F7EFDD2047d8A5D46F14613088) == true
hasRole(WITHDRAWALS_DISABLER_ROLE, 0x2C01F405e3C525C0cB867789AAf077f3553ccbB7) == false
L2ERC20TokenBridge
implementation (0x23B96aDD54c479C6784Dd504670B5376B808f4C7
)
l1Token == 0x7f39C581F595B53c5cb19bD0b3f8dA6c935E2Ca0
l2Token
- 0x1F32b1c2345538c0c6f582fCB022739c4A194Ebb
l1TokenBridge
- 0x76943C0D61395d8F2edF9060e1533529cAe05dE6
messenger == 0x4200000000000000000000000000000000000007
OssifiableProxy
for L2ERC20Bridged
(0x1F32b1c2345538c0c6f582fCB022739c4A194Ebb
)
proxy__getAdmin == 0xEfa0dB536d2c8089685630fafe88CF7805966FC3
(Lido’s AAVE Governance Bridge)proxy__getImplementation == 0x92834c37dF982A13bb0f8C3F6608E26F0546538e
proxy__getIsOssified == false
name == Wrapped liquid staked Ether 2.0
symbol == wstETH
totalSupply == 0
L2ERC20Bridged
(0x92834c37dF982A13bb0f8C3F6608E26F0546538e
)
decimals == 18
bridge == 0x8E01013243a96601a86eb3153F0d9Fa4fbFb6957
L1ERC20TokenBridge
Impl :0x7E1dBD017973871abcFac9e4B830018812056c17
0x29C5c51A031165CE62F964966A6399b81165EFA4
L2ERC20TokenBridge
Impl:
0x69d02FedAE5E289F467280bC25316D2E835C5864
0x23B96aDD54c479C6784Dd504670B5376B808f4C7
ERC20Bridged
Impl:
0x75ff3dd673Ef9fC459A52E1054db5dF2A1101212
0x92834c37dF982A13bb0f8C3F6608E26F0546538e
ERC20Bridged
Proxy:
0xbADcCcf4156967783fA818Bc4a8c93b5575A07B0
0x1F32b1c2345538c0c6f582fCB022739c4A194Ebb
L1ERC20TokenBridge
Proxy:
0x89057C7E4c5cD283afF5907B816F61e326047C29
0x76943C0D61395d8F2edF9060e1533529cAe05dE6
L2ERC20TokenBridge
Proxy:
0x0fc3De4B1bbcB315880d328e3f9C81d742D73d01
0x8E01013243a96601a86eb3153F0d9Fa4fbFb6957
Wrapped liquid staked Ether 2.0
wstETH
18
0x76943C0D61395d8F2edF9060e1533529cAe05dE6
0x8E01013243a96601a86eb3153F0d9Fa4fbFb6957
npm run fork:eth:mainnet
npm run fork:opt:mainnet
.env
variablesTESTING_OPT_NETWORK=mainnet
TESTING_OPT_L1_TOKEN=0x7f39C581F595B53c5cb19bD0b3f8dA6c935E2Ca0
TESTING_OPT_L2_TOKEN=0x1F32b1c2345538c0c6f582fCB022739c4A194Ebb
TESTING_OPT_L1_ERC20_TOKEN_BRIDGE=0x76943C0D61395d8F2edF9060e1533529cAe05dE6
TESTING_OPT_L2_ERC20_TOKEN_BRIDGE=0x8E01013243a96601a86eb3153F0d9Fa4fbFb6957
TESTING_OPT_GOV_BRIDGE_EXECUTOR=0xefa0db536d2c8089685630fafe88cf7805966fc3
TESTING_USE_DEPLOYED_CONTRACTS=true
L1_DEV_MULTISIG=0x3cd9F71F80AB08ea5a7Dca348B5e94BC595f26A0
TESTING_L1_TOKENS_HOLDER=0x23237b849d0e6f392573ee6ae9e3b1256f058143
npm run optimism:test:executor
npm run optimism:test:launch
OssifiableProxy
implementation slot:
keccak256("eip1967.proxy.implementation") - 1
0x360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc
OssifiableProxy
admin slot:
keccak256("eip1967.proxy.admin") - 1
0xb53127684a568b3173ae13b9f8a6016e243e63b6e8ee1178d6a717850b5d6103
BridgingManager
state slot:
keccak256("BridgingManager.bridgingState")
0x013e929b381f2fbbac854bd18fb8231dc73c4a2eab0d4cbb4db9436b6ff9b2ba
ERC20Metadata
state slot:
keccak256("ERC20Metdata.dynamicMetadata")
0x3470f8373d566de7ab61e14a030ae865a1f164b610b931eb8aa08ad044e2e68e
L1ERC20TokenBridge
Impl : 0x29C5c51A031165CE62F964966A6399b81165EFA4
L1ERC20TokenBridge.sol
IL1ERC20Bridge.sol
IL2ERC20Bridge.sol
BridgingManager.sol
BridgeableTokens.sol
CrossDomainEnabled.sol
ICrossDomainMessenger.sol
L2ERC20TokenBridge
Impl: 0x23B96aDD54c479C6784Dd504670B5376B808f4C7
L2ERC20TokenBridge.sol
IL1ERC20Bridge.sol
IL2ERC20Bridge.sol
IERC20Bridged.sol
BridgingManager.sol
BridgeableTokens.sol
CrossDomainEnabled.sol
ICrossDomainMessenger.sol
ERC20Bridged
Impl: 0x92834c37dF982A13bb0f8C3F6608E26F0546538e
ERC20Bridged.sol
IERC20Bridged.sol
ERC20Core.sol
ERC20Metadata.sol
IERC20Metadata.sol
ERC20Bridged
Proxy: 0x1F32b1c2345538c0c6f582fCB022739c4A194Ebb
OssifiableProxy.sol
L1ERC20TokenBridge
Proxy: 0x76943C0D61395d8F2edF9060e1533529cAe05dE6
OssifiableProxy.sol
L2ERC20TokenBridge
Proxy: 0x8E01013243a96601a86eb3153F0d9Fa4fbFb6957
OssifiableProxy.sol
Run launch scenario test
Activate deposits on L1 via dev multisig
0x76943C0D61395d8F2edF9060e1533529cAe05dE6
(L1ERC20TokenBridge
Proxy)enableDeposits()
Renounce role DEPOSITS_ENABLER_ROLE
from the dev multisig:
0x76943C0D61395d8F2edF9060e1533529cAe05dE6
(L1ERC20TokenBridge
Proxy)renounceRole(bytes32 role, address account)
role
- 0x4b43b36766bde12c5e9cbbc37d15f8d1f769f08f54720ab370faeb4ce893753a
address
- 0x3cd9F71F80AB08ea5a7Dca348B5e94BC595f26A0
Validate state of the contract on Etherescan
Re-run launch scenario test
Run the e2e test for optimism bridging after activation of deposits with addresses of deployed contracts:
.env
fileTESTING_OPT_NETWORK=mainnet
TESTING_OPT_L1_TOKEN=0x7f39C581F595B53c5cb19bD0b3f8dA6c935E2Ca0
TESTING_OPT_L2_TOKEN=0x1F32b1c2345538c0c6f582fCB022739c4A194Ebb
TESTING_OPT_L1_ERC20_TOKEN_BRIDGE=0x76943C0D61395d8F2edF9060e1533529cAe05dE6
TESTING_OPT_L2_ERC20_TOKEN_BRIDGE=0x8E01013243a96601a86eb3153F0d9Fa4fbFb6957
TESTING_PRIVATE_KEY=
npx hardhat test ./test/optimism/bridging.e2e.test.ts ```
Reach out to Optimism team that bridging was enabled and PR might be merged
Test the wstETH bridging via Optimism UI to test that bridging is working
Notify dev teams that bridge is enabled
chainId
retrieving: https://github.com/lidofinance/lido-l2/blob/471993c23f3f8c378b9ef4598e703381e9462189/utils/network.ts#L118)LDO
is bridged as a default token with the default OP bridgestETH
can't be bridged from the get-go because of rebasable mechanics that doesn't propagate cross-bridges (the Lido on Ethereum core protocol doesn't support this yet)