From 36e740dcb6173b9606b0c928638131628045aa28 Mon Sep 17 00:00:00 2001 From: Pablo Maldonado Date: Wed, 27 Mar 2024 11:49:44 +0000 Subject: [PATCH] feat: add base deployments (#4729) Signed-off-by: Pablo Maldonado --- packages/common/src/HardhatConfig.ts | 16 +++++- packages/common/src/ProviderUtils.ts | 1 + packages/common/src/TimeUtils.ts | 2 + .../src/hardhat/tasks/collateralWhitelist.ts | 18 ++++++ .../common/src/hardhat/tasks/xchainSetup.ts | 57 +++++++++++++++++-- .../contracts/cross-chain-oracle/README.md | 51 +++++++++++------ .../core/deploy/038_deploy_oracle_spoke.js | 9 ++- packages/core/deploy/039_deploy_oracle_hub.js | 2 +- .../core/deploy/040_deploy_governor_spoke.js | 9 ++- .../core/deploy/041_deploy_governor_hub.js | 2 +- .../deploy/057_deploy_optimistic_oracle_V3.js | 1 + .../062_deploy_base_parent_messenger.js | 19 +++++++ .../deploy/063_deploy_base_child_messenger.js | 25 ++++++++ packages/core/networks/1.json | 5 ++ packages/core/networks/8453.json | 47 +++++++++++++++ yarn.lock | 7 ++- 16 files changed, 242 insertions(+), 29 deletions(-) create mode 100644 packages/core/deploy/062_deploy_base_parent_messenger.js create mode 100644 packages/core/deploy/063_deploy_base_child_messenger.js create mode 100644 packages/core/networks/8453.json diff --git a/packages/common/src/HardhatConfig.ts b/packages/common/src/HardhatConfig.ts index 1f50255237..06dfac5c17 100644 --- a/packages/common/src/HardhatConfig.ts +++ b/packages/common/src/HardhatConfig.ts @@ -107,7 +107,7 @@ export function getHardhatConfig( chainId: 1, url: getNodeUrl("mainnet", true, 1), accounts: { mnemonic }, - companionNetworks: { arbitrum: "arbitrum", optimism: "optimism", boba: "boba", xdai: "xdai" }, + companionNetworks: { arbitrum: "arbitrum", optimism: "optimism", boba: "boba", xdai: "xdai", base: "base" }, }, rinkeby: { chainId: 4, url: getNodeUrl("rinkeby", true, 4), accounts: { mnemonic } }, goerli: { chainId: 5, url: getNodeUrl("goerli", true, 5), accounts: { mnemonic } }, @@ -118,6 +118,12 @@ export function getHardhatConfig( url: getNodeUrl("blast-sepolia", true, 168587773), accounts: { mnemonic }, }, + base: { + chainId: 8453, + url: getNodeUrl("base", true, 8453), + accounts: { mnemonic }, + companionNetworks: { mainnet: "mainnet" }, + }, kovan: { chainId: 42, url: getNodeUrl("kovan", true, 42), accounts: { mnemonic } }, optimism: { chainId: 10, @@ -213,6 +219,14 @@ export function getHardhatConfig( browserURL: "https://goerli.basescan.org", }, }, + { + network: "base", + chainId: 8453, + urls: { + apiURL: "https://api.basescan.org/api", + browserURL: "https://basescan.org", + }, + }, { network: "blast-sepolia", chainId: 168587773, diff --git a/packages/common/src/ProviderUtils.ts b/packages/common/src/ProviderUtils.ts index 7fe9103cf7..7b26d2f6dc 100644 --- a/packages/common/src/ProviderUtils.ts +++ b/packages/common/src/ProviderUtils.ts @@ -52,6 +52,7 @@ export function getNodeUrl(networkName: string, useHttps = false, chainId: numbe if (name === "blast-sepolia") return overrideUrl || "https://sepolia.blast.io"; if (name === "core") return overrideUrl || "https://rpc.coredao.org/"; if (name === "base-goerli") return overrideUrl || "https://goerli.base.org"; + if (name === "base") return overrideUrl || "https://mainnet.base.org"; return ( overrideUrl || (useHttps ? `https://${name}.infura.io/v3/${infuraApiKey}` : `wss://${name}.infura.io/ws/v3/${infuraApiKey}`) diff --git a/packages/common/src/TimeUtils.ts b/packages/common/src/TimeUtils.ts index e852445c94..992cb69d6b 100644 --- a/packages/common/src/TimeUtils.ts +++ b/packages/common/src/TimeUtils.ts @@ -30,6 +30,8 @@ export async function averageBlockTimeSeconds(chainId?: number): Promise return 3; case 1116: return 3; + case 8453: + return 2; case 1: return defaultBlockTimeSeconds; default: diff --git a/packages/common/src/hardhat/tasks/collateralWhitelist.ts b/packages/common/src/hardhat/tasks/collateralWhitelist.ts index 1d10f741af..9552b02f83 100644 --- a/packages/common/src/hardhat/tasks/collateralWhitelist.ts +++ b/packages/common/src/hardhat/tasks/collateralWhitelist.ts @@ -260,6 +260,12 @@ async function findL2TokenForL1Token(l1Web3: Web3, l2Web3: Web3, l2chainid: numb return await _findL2TokenForOvmChain(l2Web3, l1TokenAddress); } + if (l2chainid == 8453) { + const foundOnChain = await _findL2TokenForOvmChain(l2Web3, l1TokenAddress); + if (foundOnChain != ZERO_ADDRESS) return foundOnChain; + else return await _findL2TokenFromTokenList(l1Web3, l2chainid, l1TokenAddress); + } + if (l2chainid == 42161) { return await _findL2TokenFromTokenList(l1Web3, l2chainid, l1TokenAddress); } @@ -283,6 +289,18 @@ async function _findL2TokenFromTokenList(l1Web3: Web3, l2chainid: number, l1Toke if (!searchSymbol) return ZERO_ADDRESS; return tokenList.find((element: any) => element.chainId == 10 && element.symbol == searchSymbol).address; } + if (l2chainid == 8453) { + // See https://docs.base.org/tokens/list/ for more information + const response = await fetch("https://static.optimism.io/optimism.tokenlist.json"); + const body = await response.text(); + const tokenList = JSON.parse(body).tokens; + const searchSymbol = tokenList.find( + (element: any) => element.chainId == 1 && element.address.toLowerCase() == l1TokenAddress.toLowerCase() + )?.symbol; + if (!searchSymbol) return ZERO_ADDRESS; + const found = tokenList.find((element: any) => element.chainId == 8453 && element.symbol == searchSymbol); + return found?.address ?? ZERO_ADDRESS; + } if (l2chainid == 42161) { const response = await fetch("https://bridge.arbitrum.io/token-list-42161.json"); const body = await response.text(); diff --git a/packages/common/src/hardhat/tasks/xchainSetup.ts b/packages/common/src/hardhat/tasks/xchainSetup.ts index d354a1bafc..65e4c3a595 100644 --- a/packages/common/src/hardhat/tasks/xchainSetup.ts +++ b/packages/common/src/hardhat/tasks/xchainSetup.ts @@ -8,7 +8,7 @@ import Web3 from "web3"; const { utf8ToHex, toBN } = Web3.utils; const assert = require("assert"); -const L2_CHAIN_NAMES = ["arbitrum", "optimism", "boba"]; +const L2_CHAIN_NAMES = ["arbitrum", "optimism", "boba", "base"]; L2_CHAIN_NAMES.forEach((chainName) => assert(isPublicNetwork(chainName), "L2_CHAIN_NAMES contains invalid public network name") ); @@ -156,9 +156,11 @@ async function setupOvmBasedL1Chain(hre_: any, chainId: number) { console.log(`Found OracleHub @ ${oracleHub.options.address}`); console.log(`Found GovernorHub @ ${governorHub.options.address}`); - const OracleSpoke = await companionNetworks.optimism.deployments.get("OracleSpoke"); - const ChildMessenger = await companionNetworks.optimism.deployments.get(`${chainName}_ChildMessenger`); - const GovernorSpoke = await companionNetworks.optimism.deployments.get("GovernorSpoke"); + const OracleSpoke = await companionNetworks[chainName.toLowerCase()].deployments.get("OracleSpoke"); + const ChildMessenger = await companionNetworks[chainName.toLowerCase()].deployments.get( + `${chainName}_ChildMessenger` + ); + const GovernorSpoke = await companionNetworks[chainName.toLowerCase()].deployments.get("GovernorSpoke"); await setupParentMessenger(messenger, deployer, ChildMessenger, OracleHub, GovernorHub, OracleSpoke, GovernorSpoke); @@ -277,6 +279,13 @@ task("setup-l1-boba-xchain", "Configures L1 cross chain smart contracts for Boba await setupOvmBasedL1Chain(hre_, 288); }); +task("setup-l1-base-xchain", "Configures L1 cross chain smart contracts for Base bridge").setAction(async function ( + _, + hre_ +) { + await setupOvmBasedL1Chain(hre_, 8453); +}); + task("setup-l1-optimism-xchain", "Configures L1 cross chain smart contracts for Optimism bridge").setAction( async function (_, hre_) { await setupOvmBasedL1Chain(hre_, 10); @@ -353,11 +362,13 @@ task("verify-xchain", "Checks ownership state of cross chain smart contracts") l2IdentifierWhitelist, l2AddressWhitelist, l2OptimisticOracle, + l2OptimisticOracleV2, + l2OptimisticOracleV3, l2Finder, ] = await Promise.all([ deployments.get("GovernorHub"), deployments.get("OracleHub"), - deployments.get("Governor"), + deployments.get("GovernorV2"), deployments.get(`${l2ChainName}_ParentMessenger`), companionNetworkGet(`${l2ChainName}_ChildMessenger`), companionNetworkGet(`OracleSpoke`), @@ -368,6 +379,8 @@ task("verify-xchain", "Checks ownership state of cross chain smart contracts") companionNetworkGet(`IdentifierWhitelist`), companionNetworkGet(`AddressWhitelist`), companionNetworkGet(`OptimisticOracle`), + companionNetworkGet(`OptimisticOracleV2`), + companionNetworkGet(`OptimisticOracleV3`), companionNetworkGet(`Finder`), ]); @@ -456,11 +469,20 @@ task("verify-xchain", "Checks ownership state of cross chain smart contracts") console.group("Registry"); const l2RegistryContract = new l2Web3.eth.Contract(l2Registry.abi, l2Registry.address); - const [optimisticOracleRegistered, l2RegistryOwner] = await Promise.all([ + const [ + optimisticOracleRegistered, + optimisticOracleV2Registered, + optimisticOracleV3Registered, + l2RegistryOwner, + ] = await Promise.all([ l2RegistryContract.methods.isContractRegistered(l2OptimisticOracle.address).call(), + l2RegistryContract.methods.isContractRegistered(l2OptimisticOracleV2.address).call(), + l2RegistryContract.methods.isContractRegistered(l2OptimisticOracleV3.address).call(), l2RegistryContract.methods.getMember(0).call(), ]); console.log(`- OptimisticOracle registered: ${optimisticOracleRegistered ? "✅" : "❌"}`); + console.log(`- OptimisticOracleV2 registered: ${optimisticOracleV2Registered ? "✅" : "❌"}`); + console.log(`- OptimisticOracleV3 registered: ${optimisticOracleV3Registered ? "✅" : "❌"}`); console.log(`- Owned by GovernorSpoke: ${l2RegistryOwner === governorSpoke.address ? "✅" : "❌"}`); console.groupEnd(); @@ -479,6 +501,15 @@ task("verify-xchain", "Checks ownership state of cross chain smart contracts") console.log(`- Owned by GovernorSpoke: ${l2IdentifierWhitelistOwner === governorSpoke.address ? "✅" : "❌"}`); console.groupEnd(); + console.group("OptimisticOracleV3"); + const l2OptimisticOracleV3Contract = new l2Web3.eth.Contract( + l2OptimisticOracleV3.abi, + l2OptimisticOracleV3.address + ); + const [l2OptimisticOracleV3Owner] = await Promise.all([l2OptimisticOracleV3Contract.methods.owner().call()]); + console.log(`- Owned by GovernorSpoke: ${l2OptimisticOracleV3Owner === governorSpoke.address ? "✅" : "❌"}`); + console.groupEnd(); + console.group("AddressWhitelist"); const l2AddressWhitelistContract = new l2Web3.eth.Contract(l2AddressWhitelist.abi, l2AddressWhitelist.address); const [l2AddressWhitelistOwner] = await Promise.all([l2AddressWhitelistContract.methods.owner().call()]); @@ -504,6 +535,8 @@ task("verify-xchain", "Checks ownership state of cross chain smart contracts") l2FinderAddressWhitelist, l2FinderOracle, l2FinderOptimisticOracle, + l2FinderOptimisticOracleV2, + l2FinderOptimisticOracleV3, l2FinderChildMessenger, ] = await Promise.all([ l2FinderContract.methods.owner().call(), @@ -512,6 +545,8 @@ task("verify-xchain", "Checks ownership state of cross chain smart contracts") l2FinderContract.methods.interfacesImplemented(utf8ToHex(interfaceName.CollateralWhitelist)).call(), l2FinderContract.methods.interfacesImplemented(utf8ToHex(interfaceName.Oracle)).call(), l2FinderContract.methods.interfacesImplemented(utf8ToHex(interfaceName.OptimisticOracle)).call(), + l2FinderContract.methods.interfacesImplemented(utf8ToHex(interfaceName.OptimisticOracleV2)).call(), + l2FinderContract.methods.interfacesImplemented(utf8ToHex(interfaceName.OptimisticOracleV3)).call(), l2FinderContract.methods.interfacesImplemented(utf8ToHex(interfaceName.ChildMessenger)).call(), ]); console.log(`- Owned by GovernorSpoke: ${l2FinderOwner === governorSpoke.address ? "✅" : "❌"}`); @@ -536,6 +571,16 @@ task("verify-xchain", "Checks ownership state of cross chain smart contracts") l2FinderOptimisticOracle === l2OptimisticOracle.address ? "✅" : "❌" }` ); + console.log( + `- Set "${interfaceName.OptimisticOracleV2}" in Finder: ${ + l2FinderOptimisticOracleV2 === l2OptimisticOracleV2.address ? "✅" : "❌" + }` + ); + console.log( + `- Set "${interfaceName.OptimisticOracleV3}" in Finder: ${ + l2FinderOptimisticOracleV3 === l2OptimisticOracleV3.address ? "✅" : "❌" + }` + ); console.log( `- Set "${interfaceName.ChildMessenger}" in Finder: ${ l2FinderChildMessenger === childMessenger.address ? "✅" : "❌" diff --git a/packages/core/contracts/cross-chain-oracle/README.md b/packages/core/contracts/cross-chain-oracle/README.md index 159fbcee09..f59dc2d893 100644 --- a/packages/core/contracts/cross-chain-oracle/README.md +++ b/packages/core/contracts/cross-chain-oracle/README.md @@ -26,7 +26,7 @@ Note: in the commands below, you'll need to set the relevant `NODE_URL_X` enviro If you're having trouble redeploying contracts because `hardhat` wants to "reuse" contracts, then run `yarn clean && yarn` in the `core` package to reset `deployments`. -## Step-by-step guide to deployments on rollups: Arbitrum, Boba and Optimism +## Step-by-step guide to deployments on rollups: Arbitrum, Boba, Optimism and Base The steps below explain how to deploy the cross-chain oracle onto supported rollups. @@ -39,25 +39,26 @@ export NODE_URL_1= export NODE_URL_42161= export NODE_URL_288= export NODE_URL_10= +export NODE_URL_8453= export MNEMONIC="Your 12-word mnemonic here" ``` 2. Deploy mainnet contracts. Note that the following commands are slightly different based on which L2 you're deploying to. ```sh -yarn hardhat deploy --network mainnet --tags [l1-arbitrum-xchain/l1-boba-xchain/l1-optimism-xchain] +yarn hardhat deploy --network mainnet --tags [l1-arbitrum-xchain/l1-boba-xchain/l1-optimism-xchain/l1-base-xchain] ``` -Add the deployed [Arbitrum/Boba/Optimism]\_ParentMessenger contract to the associated networks file. +Add the deployed [Arbitrum/Boba/Optimism/Base]\_ParentMessenger contract to the associated networks file. 3. Deploy l2 contracts: ```sh -yarn hardhat deploy --network [arbitrum/boba/optimism] --tags [l2-arbitrum-xchain/l2-boba-xchain/l2-optimism-xchain],Registry +yarn hardhat deploy --network [arbitrum/boba/optimism/base] --tags [l2-arbitrum-xchain/l2-boba-xchain/l2-optimism-xchain/l2-base-xchain],Registry ``` -Add the deployed [Arbitrum/Boba/Optimism] Registry, finder, OracleSpoke, GovernorSpoke and x_ChildMessenger contracts to the associated networks file. +Add the deployed [Arbitrum/Boba/Optimism/Base] Registry, finder, OracleSpoke, GovernorSpoke and x_ChildMessenger contracts to the associated networks file. 4. Verify contracts: @@ -70,24 +71,26 @@ yarn hardhat --network arbitrum etherscan-verify --api-key --lic yarn hardhat --network boba sourcify # Optimism (etherscan-verify does not work on Optimism so we use hardhat verify) yarn hardhat --network optimism verify +# Base +yarn hardhat --network base verify ``` 5. Setup mainnet contracts ```sh -yarn hardhat [setup-l1-arbitrum-xchain/setup-l1-boba-xchain/setup-l1-optimism-xchain] --network mainnet +yarn hardhat [setup-l1-arbitrum-xchain/setup-l1-boba-xchain/setup-l1-optimism-xchain/setup-l1-base-xchain] --network mainnet ``` 6. Setup l2 contracts ```sh -yarn hardhat setup-l2-xchain --network [arbitrum/boba/optimism] +yarn hardhat setup-l2-xchain --network [arbitrum/boba/optimism/base] ``` -7. At this point, the cross chain contract suite setup is complete. We will now deploy the `OptimisticOracle` and required contracts to the L2. +7. At this point, the cross chain contract suite setup is complete. We will now deploy the `OptimisticOracle,OptimisticOracleV2` and required contracts to the L2, the `OptimisticOracleV3` contract is deployed in a later step. ```sh -yarn hardhat deploy --network [arbitrum/boba/optimism] --tags OptimisticOracle,IdentifierWhitelist,AddressWhitelist,Store +yarn hardhat deploy --network [arbitrum/boba/optimism/base] --tags OptimisticOracle,OptimisticOracleV2,OptimisticOracleV3,IdentifierWhitelist,AddressWhitelist,Store ``` 8. Verify contracts: @@ -99,27 +102,39 @@ yarn hardhat --network arbitrum etherscan-verify --api-key --lic yarn hardhat --network boba sourcify # Optimism (etherscan-verify does not work on Optimism so we use hardhat verify) yarn hardhat --network optimism verify +# Base +yarn hardhat --network base verify ``` 9. Setup l2 optimistic oracle: ```sh # Seed IdentifierWhitelist with all identifiers already approved on mainnet. Note the --from address is the IdentifierWhitelist deployed on mainnet. -CROSS_CHAIN_NODE_URL= yarn hardhat migrate-identifiers --network [arbitrum/boba/optimism] --from 0xcF649d9Da4D1362C4DAEa67573430Bd6f945e570 --crosschain true +CROSS_CHAIN_NODE_URL= yarn hardhat migrate-identifiers --network [arbitrum/boba/optimism/base] --from 0xcF649d9Da4D1362C4DAEa67573430Bd6f945e570 --crosschain true # Seed Collateral whitelist with all collaterals already approved on Mainnet. This will also pull the final fee from the L1 store and set it in the L2 Store. -yarn hardhat --network [arbitrum/boba/optimism] migrate-collateral-whitelist --l1chainid 1 --l2chainid [42161/288/10] +yarn hardhat --network [arbitrum/boba/optimism/base] migrate-collateral-whitelist --l1chainid 1 --l2chainid [42161/288/10/8453] # Point L2 Finder to remaining Optimistic Oracle system contracts. -yarn hardhat setup-finder --oraclespoke --identifierwhitelist --addresswhitelist --optimisticoracle --store --network [arbitrum/boba/optimism] -# Register OptimisticOracle as registered contract. -yarn hardhat register-accounts --network [arbitrum/boba/optimism] --account +yarn hardhat setup-finder --oraclespoke --identifierwhitelist --addresswhitelist --optimisticoracle --optimisticoraclev2 --store --network [arbitrum/boba/optimism/base] +# Register OptimisticOracles as registered contract. +yarn hardhat register-accounts --network [arbitrum/boba/optimism/base] --account +yarn hardhat register-accounts --network [arbitrum/boba/optimism/base] --account +yarn hardhat register-accounts --network [arbitrum/boba/optimism/base] --account ``` -10. Perform other set up when appropriate such as transferring ownership to the Governor and Governor spokes. Run the following script to check all required steps: +10. At this point we can deploy the `OptimisticOracleV3` contract to the L2: + +- First deploy the `OptimisticOracleV3` contract with the required constructor arguments. +- Then run again the `setup-finder` script to point the L2 Finder to the `OptimisticOracleV3` contract. + - Run: `yarn hardhat setup-finder --optimisticoraclev3 --network [arbitrum/boba/optimism/base]` +- Finally, register the `OptimisticOracleV3` contract as a registered contract. + - Run: `yarn hardhat register-accounts --network [arbitrum/boba/optimism/base] --account ` + +11. Perform other set up when appropriate such as transferring ownership to the Governor and Governor spokes. Run the following script to check all required steps: ```sh -yarn hardhat verify-xchain --network mainnet --l2 [arbitrum/boba/optimism] +yarn hardhat verify-xchain --network mainnet --l2 [arbitrum/boba/optimism/base] ``` ## L2->L1 Message passing and finalization @@ -128,7 +143,9 @@ The cross-chain-oracle contracts send messages from L1<->L2 under different situ To finalize **Arbitrum** transactions see the docs [here](https://github.com/OffchainLabs/arbitrum-tutorials/tree/master/packages/outbox-execute) on how to do this. Alternatively, Arbiscan provides a list of L2->L1 transactions and a UI for finalizing those that have passed liveness. This can also be used if you don't want to run the `outbox-execute` script. The relevant page can be found [here](https://arbiscan.io/txsExit). -To finalize **Optimism** transactions see the equivalent script [here](https://github.com/ethereum-optimism/optimism/blob/develop/packages/message-relayer/src/exec/withdraw.ts). Optimism's Etherscan also provides a UI, similar to Arbitrum, which can be found [here](https://optimistic.etherscan.io/txsExit). +To finalize **Optimism** transactions see the equivalent script [here](https://github.com/ethereum-optimism/optimism/blob/34e7450873548f65bf3160ca58eed2328907310a/packages/sdk/tasks/finalize-withdrawal.ts#L14). Optimism's Etherscan also provides a UI, similar to Arbitrum, which can be found [here](https://optimistic.etherscan.io/txsExit). + +To finalize **Base** transactions see the equivalent script [here](https://github.com/ethereum-optimism/optimism/blob/develop/packages/message-relayer/src/exec/withdraw.ts). Base's Etherscan also provides a UI, similar to Optimism, which can be found [here](https://basescan.org/txsExit). **Boba** at present auto-finalizes all L2->L1 transactions without any required user intervention. diff --git a/packages/core/deploy/038_deploy_oracle_spoke.js b/packages/core/deploy/038_deploy_oracle_spoke.js index 39bcc7b5e9..3ce402fc6f 100644 --- a/packages/core/deploy/038_deploy_oracle_spoke.js +++ b/packages/core/deploy/038_deploy_oracle_spoke.js @@ -10,5 +10,12 @@ const func = async function (hre) { await deploy("OracleSpoke", { from: deployer, args: [finder.address], log: true, skipIfAlreadyDeployed: true }); }; module.exports = func; -func.tags = ["OracleSpoke", "l2-arbitrum-xchain", "l2-boba-xchain", "l2-optimism-xchain", "l2-admin-xchain"]; +func.tags = [ + "OracleSpoke", + "l2-arbitrum-xchain", + "l2-boba-xchain", + "l2-optimism-xchain", + "l2-admin-xchain", + "l2-base-xchain", +]; func.dependencies = ["Finder"]; diff --git a/packages/core/deploy/039_deploy_oracle_hub.js b/packages/core/deploy/039_deploy_oracle_hub.js index cc88d4a3c0..e69591f239 100644 --- a/packages/core/deploy/039_deploy_oracle_hub.js +++ b/packages/core/deploy/039_deploy_oracle_hub.js @@ -21,5 +21,5 @@ const func = async function (hre) { }); }; module.exports = func; -func.tags = ["OracleHub", "l1-arbitrum-xchain", "l1-boba-xchain", "l1-optimism-xchain"]; +func.tags = ["OracleHub", "l1-arbitrum-xchain", "l1-boba-xchain", "l1-optimism-xchain", "l1-base-xchain"]; func.dependencies = ["Finder", "VotingToken"]; diff --git a/packages/core/deploy/040_deploy_governor_spoke.js b/packages/core/deploy/040_deploy_governor_spoke.js index 8053d1c3d5..d5bf67ea52 100644 --- a/packages/core/deploy/040_deploy_governor_spoke.js +++ b/packages/core/deploy/040_deploy_governor_spoke.js @@ -10,5 +10,12 @@ const func = async function (hre) { await deploy("GovernorSpoke", { from: deployer, args: [finder.address], log: true, skipIfAlreadyDeployed: true }); }; module.exports = func; -func.tags = ["GovernorSpoke", "l2-arbitrum-xchain", "l2-boba-xchain", "l2-optimism-xchain", "l2-admin-xchain"]; +func.tags = [ + "GovernorSpoke", + "l2-arbitrum-xchain", + "l2-boba-xchain", + "l2-optimism-xchain", + "l2-admin-xchain", + "l2-base-xchain", +]; func.dependencies = ["Finder"]; diff --git a/packages/core/deploy/041_deploy_governor_hub.js b/packages/core/deploy/041_deploy_governor_hub.js index 9546af26cf..00037c71ec 100644 --- a/packages/core/deploy/041_deploy_governor_hub.js +++ b/packages/core/deploy/041_deploy_governor_hub.js @@ -7,4 +7,4 @@ const func = async function (hre) { await deploy("GovernorHub", { from: deployer, args: [], log: true, skipIfAlreadyDeployed: true }); }; module.exports = func; -func.tags = ["GovernorHub", "l1-arbitrum-xchain", "l1-boba-xchain", "l1-optimism-xchain"]; +func.tags = ["GovernorHub", "l1-arbitrum-xchain", "l1-boba-xchain", "l1-optimism-xchain", "l1-base-xchain"]; diff --git a/packages/core/deploy/057_deploy_optimistic_oracle_V3.js b/packages/core/deploy/057_deploy_optimistic_oracle_V3.js index acb01ccfd1..2562200c68 100644 --- a/packages/core/deploy/057_deploy_optimistic_oracle_V3.js +++ b/packages/core/deploy/057_deploy_optimistic_oracle_V3.js @@ -11,6 +11,7 @@ const ADDRESSES_FOR_NETWORK = { 288: { defaultCurrency: "0x66a2A913e447d6b4BF33EFbec43aAeF87890FBbc" }, 1116: { defaultCurrency: "0xa4151B2B3e269645181dCcF2D426cE75fcbDeca9" }, 9001: { defaultCurrency: "0x51e44FfaD5C2B122C8b635671FCC8139dc636E82" }, + 8453: { defaultCurrency: "0xd9aAEc86B65D86f6A7B5B1b0c42FFA531710b6CA" }, 42161: { defaultCurrency: "0xFF970A61A04b1cA14834A43f5dE4533eBDDB5CC8" }, 43114: { defaultCurrency: "0xB97EF9Ef8734C71904D8002F8b6Bc66Dd9c48a6E" }, 80001: { defaultCurrency: "0xe6b8a5CF854791412c1f6EFC7CAf629f5Df1c747" }, diff --git a/packages/core/deploy/062_deploy_base_parent_messenger.js b/packages/core/deploy/062_deploy_base_parent_messenger.js new file mode 100644 index 0000000000..f84b08e3c3 --- /dev/null +++ b/packages/core/deploy/062_deploy_base_parent_messenger.js @@ -0,0 +1,19 @@ +const func = async function (hre) { + const { deployments, getNamedAccounts } = hre; + const { deploy } = deployments; + + const { deployer } = await getNamedAccounts(); + + await deploy("Base_ParentMessenger", { + contract: "Optimism_ParentMessenger", + from: deployer, + args: [ + "0x866E82a600A1414e583f7F13623F1aC5d58b0Afa", // Base's OVM L1 Cross Domain Messenger + 8453, // Child network ID + ], + log: true, + skipIfAlreadyDeployed: true, + }); +}; +module.exports = func; +func.tags = ["Base_ParentMessenger", "l1-base-xchain"]; diff --git a/packages/core/deploy/063_deploy_base_child_messenger.js b/packages/core/deploy/063_deploy_base_child_messenger.js new file mode 100644 index 0000000000..a4363f8265 --- /dev/null +++ b/packages/core/deploy/063_deploy_base_child_messenger.js @@ -0,0 +1,25 @@ +const func = async function (hre) { + const { deployments, getNamedAccounts, companionNetworks } = hre; + const { deploy } = deployments; + const { deployer } = await getNamedAccounts(); + + // Grab parent messenger address: + // Default to pulling from this chain if the companion network doesn't exist. + if (!companionNetworks["mainnet"]) + console.error( + "WARNING: attempting to use same chain for mainnet and base contracts because mainnet companion network doesn't exist." + ); + const { deployments: l1Deployments } = companionNetworks["mainnet"] || hre; + const parentMessenger = await l1Deployments.get("Base_ParentMessenger"); + console.log(`Using l1 parent messenger @ ${parentMessenger.address}`); + + await deploy("Base_ChildMessenger", { + contract: "Optimism_ChildMessenger", + from: deployer, + args: [parentMessenger.address], + log: true, + skipIfAlreadyDeployed: true, + }); +}; +module.exports = func; +func.tags = ["Base_ChildMessenger", "l2-base-xchain"]; diff --git a/packages/core/networks/1.json b/packages/core/networks/1.json index ea0d284cf2..7d2dfcb67f 100644 --- a/packages/core/networks/1.json +++ b/packages/core/networks/1.json @@ -157,6 +157,11 @@ "deploymentName": "Optimism_ParentMessenger", "address": "0x6455D800D1Dbf9B1C3a63c67CcF22B9308728dC4" }, + { + "contractName": "Optimism_ParentMessenger", + "deploymentName": "Base_ParentMessenger", + "address": "0x721bA6f9A0a44657f008f3d68C6dBdDeDBDE831A" + }, { "contractName": "Proposer", "address": "0x226726Ac52e6e948D1B7eA9168F9Ff2E27DbcbB5" diff --git a/packages/core/networks/8453.json b/packages/core/networks/8453.json new file mode 100644 index 0000000000..30a11bc105 --- /dev/null +++ b/packages/core/networks/8453.json @@ -0,0 +1,47 @@ +[ + { + "contractName": "Finder", + "address": "0x7E6d9618Ba8a87421609352d6e711958A97e2512" + }, + { + "contractName": "OracleSpoke", + "address": "0x689FF0D2c17ECbB01477420aB18482A8DAd45186" + }, + { + "contractName": "GovernorSpoke", + "address": "0xd0Ce2F132d606A19B01C03f6c327F324aDD8FCd3" + }, + { + "contractName": "Optimism_ChildMessenger", + "deploymentName": "Base_ChildMessenger", + "address": "0x981A64547d2979510de5b409C7D107938Cc0885e" + }, + { + "contractName": "Registry", + "address": "0x10be62b7d5c02e122a0c32e3dff7e8bf5f9f7f20" + }, + { + "contractName": "OptimisticOracleV2", + "address": "0x880d041D67aaB3B062995d11d4aD9c1018A3b02f" + }, + { + "contractName": "IdentifierWhitelist", + "address": "0xAd517D72B9Cd31F578197D5e903d041B88c69795" + }, + { + "contractName": "AddressWhitelist", + "address": "0x0F7fC5E6482f096380db6158f978167b57388deE" + }, + { + "contractName": "OptimisticOracle", + "address": "0x1037A21a30aEfF90c269b01c3933eB9a5285d9b8" + }, + { + "contractName": "Store", + "address": "0xa799650614f84e0B7E7E99e12d5DFc241907cd85" + }, + { + "contractName": "OptimisticOracleV3", + "address": "0x2aBf1Bd76655de80eDB3086114315Eec75AF500c" + } +] diff --git a/yarn.lock b/yarn.lock index 9c28b01073..9d6fc23f35 100644 --- a/yarn.lock +++ b/yarn.lock @@ -4264,7 +4264,12 @@ resolved "https://registry.yarnpkg.com/@openzeppelin/contracts/-/contracts-4.1.0.tgz#baec89a7f5f73e3d8ea582a78f1980134b605375" integrity sha512-TihZitscnaHNcZgXGj9zDLDyCqjziytB4tMCwXq0XimfWkAjBYyk5/pOsDbbwcavhlc79HhpTEpQcrMnPVa1mw== -"@openzeppelin/contracts@4.9.3", "@openzeppelin/contracts@^4.2.0", "@openzeppelin/contracts@^4.8.1": +"@openzeppelin/contracts@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@openzeppelin/contracts/-/contracts-4.9.6.tgz#2a880a24eb19b4f8b25adc2a5095f2aa27f39677" + integrity sha512-xSmezSupL+y9VkHZJGDoCBpmnB2ogM13ccaYDWqJTfS3dbuHkgjuwDFUmaFauBCboQMGB/S5UqUl2y54X99BmA== + +"@openzeppelin/contracts@^4.2.0", "@openzeppelin/contracts@^4.8.1": version "4.9.3" resolved "https://registry.yarnpkg.com/@openzeppelin/contracts/-/contracts-4.9.3.tgz#00d7a8cf35a475b160b3f0293a6403c511099364" integrity sha512-He3LieZ1pP2TNt5JbkPA4PNT9WC3gOTOlDcFGJW4Le4QKqwmiNJCRt44APfxMxvq7OugU/cqYuPcSBzOw38DAg==