diff --git a/.env.example b/.env.example index 73bbb8a4..83fd5f92 100644 --- a/.env.example +++ b/.env.example @@ -1,21 +1,21 @@ # anvil --port 8646 or via docker compose up in eth-pos-devnet CLIENT_CHAIN_RPC=http://localhost:8646 -EXOCORE_TESTNET_RPC=http://localhost:8545 -EXOCORE_LOCAL_RPC=http://localhost:8545 +IMUACHAIN_TESTNET_RPC=http://localhost:8545 +IMUACHAIN_LOCALNET_RPC=http://localhost:8545 # The following are default Anvil keys - not real keys! TEST_ACCOUNT_ONE_PRIVATE_KEY=0x59c6995e998f97a5a0044966f0945389dc9e86dae88c7a8412f4603b6b78690d TEST_ACCOUNT_THREE_PRIVATE_KEY=0xac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80 TEST_ACCOUNT_FOUR_PRIVATE_KEY=0x7c852118294e51e653712a81e05800f419141751be58f605c371e15141b007a6 -# Use 'exocored keys unsafe-export-eth-key "dev0" --home ~/.tmp-exocored' to get the privatekey -EXOCORE_GENESIS_PRIVATE_KEY=0x5de4111afa1a4b94908f83103eb1f1706367c2e68ca870fc3fb9a804cdab365a +# Use 'imuad keys unsafe-export-eth-key "dev0" --home ~/.tmp-imuad' to get the privatekey +IMUACHAIN_GENESIS_PRIVATE_KEY=0x5de4111afa1a4b94908f83103eb1f1706367c2e68ca870fc3fb9a804cdab365a USE_ENDPOINT_MOCK=false -USE_EXOCORE_PRECOMPILE_MOCK=false +USE_IMUACHAIN_PRECOMPILE_MOCK=false # For contract verification ETHERSCAN_API_KEY= -EXOCORE_TESTNET_EXPLORER= +IMUACHAIN_TESTNET_EXPLORER= # These are used for integration testing the Bootstrap contract, in addition to # CLIENT_CHAIN_RPC and BEACON_CHAIN_ENDPOINT above. diff --git a/.github/workflows/forge-ci.yml b/.github/workflows/forge-ci.yml index 5571841b..7f4e0d08 100644 --- a/.github/workflows/forge-ci.yml +++ b/.github/workflows/forge-ci.yml @@ -196,21 +196,25 @@ jobs: # however, we cannot do that in the PR context without leaking the # Etherscan API key. - # Note that the keys of the json dict below are case sensitive and - # must match the keys `x.deployed.json` defined in `compareLayouts.js` - # exactly. + # Note that + # (0) we use the logic addresses to match the comparison code: eg. Bootstrap is + # compared against BootstrapLogic instead of Bootstrap because Bootstrap is + # a proxy contract that points to the logic contract. + # (1) keys of the input json dict below are sourced from `deployedContracts.json` + # (2) keys of the output json dict below are case sensitive and must match the + # keys `x.deployed.json` defined in `compareLayouts.js` exactly. jq -n \ - --arg bootstrap "$bootstrap" \ - --arg clientGateway "$clientGateway" \ - --arg vault "$vault" \ - --arg rewardVault "$rewardVault" \ - --arg capsule "$capsule" \ + --arg bootstrap "$bootstrapLogic" \ + --arg clientGateway "$clientGatewayLogic" \ + --arg vault "$vaultImplementation" \ + --arg rewardVault "$rewardVaultImplementation" \ + --arg capsule "$capsuleImplementation" \ '{ Bootstrap: $bootstrap, ClientChainGateway: $clientGateway, Vault: $vault, RewardVault: $rewardVault, - ExoCapsule: $capsule + ImuaCapsule: $capsule }' > validatedContracts.json echo "Validation passed: All fields are non-empty and valid Ethereum checksum addresses" @@ -231,7 +235,7 @@ jobs: strategy: matrix: include: - - contract: ExocoreGateway + - contract: ImuachainGateway base: true - contract: Bootstrap base: false @@ -241,9 +245,9 @@ jobs: base: false - contract: Vault base: false - - contract: ExocoreGateway + - contract: ImuachainGateway base: false - - contract: ExoCapsule + - contract: ImuaCapsule base: false steps: - name: Restore cached Foundry toolchain diff --git a/.gitmodules b/.gitmodules index 9391723c..10983222 100644 --- a/.gitmodules +++ b/.gitmodules @@ -27,4 +27,4 @@ url = https://github.com/safe-global/safe-smart-account [submodule "lib/create3-factory"] path = lib/create3-factory - url = https://github.com/zeframlou/create3-factory + url = https://github.com/imua-xyz/create3-factory diff --git a/README.md b/README.md index 31c839d3..a8aa15ef 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ -# Exocore Contracts +# Imua Contracts -The Exocore contracts repository contains a set of smart contracts deployed on both Exocore and the target client chains, which facilitate assets deposit and withdrawal, cross-chain communication, and restaking operations for native assets and liquid staking tokens (LSTs), ensuring secure interactions and efficient management of restaked assets. +The imua-contracts repository contains a set of smart contracts deployed on both Imuachain and the target client chains, which facilitate assets deposit and withdrawal, cross-chain communication, and restaking operations for native assets and liquid staking tokens (LSTs), ensuring secure interactions and efficient management of restaked assets. ## Getting Started @@ -12,7 +12,7 @@ The Exocore contracts repository contains a set of smart contracts deployed on b ### Basics -Our docs site is [here](https://docs.exocore.network/components/smart-contracts). It contains tutorials, explainers, and smart contract documentation. If you'd like to view these docs on github instead, check out [the docs](/docs) repo: +Our docs site is [here](https://docs.imua.xyz/components/smart-contracts). It contains tutorials, explainers, and smart contract documentation. If you'd like to view these docs on github instead, check out [the docs](/docs) repo: - [Contracts summary](./docs/summary.md) - [Architecture diagrams](/docs/architecture.svg) @@ -31,7 +31,7 @@ This repository utilizes Foundry. For more information on installation and usage ``` foundryup -git clone --recurse-submodules git@github.com:ExocoreNetwork/exocore-contracts.git && cd exocore-contracts +git clone --recurse-submodules git@github.com:imua-xyz/imua-contracts.git && cd imua-contracts forge build @@ -69,14 +69,8 @@ Deposit & Withdraw e2e test: ### Current Testnet Deployment -The current main deployment is our v1.0.0 release. You can view the deployed contract addresses below, or check out the code itself on the [`main`](https://github.com/ExocoreNetwork/exocore-contracts/tree/main) branch. +You can view the deployed contract addresses below, or check out the code itself on the [`main`](https://github.com/imua-xyz/imua-contracts/tree/main) branch. -###### Core +#### Core -| Name | Proxy | Implementation | Notes | -| -------- | -------- | -------- | -------- | -| [`ClientChainGateway`](https://github.com/ExocoreNetwork/exocore-contracts/blob/main/src/contracts/core/ClientChainGateway.sol) | [`0xe9591d5b1ea9733ad36834cd0bde40ce0028ae33`](https://sepolia.etherscan.io/address/0xe9591d5b1ea9733ad36834cd0bde40ce0028ae33) | [`0xdC51F6d62ce78EfF7c98f3BD59227B4D0785C6ef`](https://sepolia.etherscan.io/address/0xdC51F6d62ce78EfF7c98f3BD59227B4D0785C6ef) | Proxy: [`TUP@4.7.1`](https://github.com/OpenZeppelin/openzeppelin-contracts/blob/v4.7.1/contracts/proxy/transparent/TransparentUpgradeableProxy.sol) | -| [`ExocoreGateway`](https://github.com/ExocoreNetwork/exocore-contracts/blob/main/src/contracts/core/ExocoreGateway.sol) | [`0xe13Ef2fE9B4bC1A3bBB62Df6bB19d6aD79525036`](https://exoscan.org/address/0xe13Ef2fE9B4bC1A3bBB62Df6bB19d6aD79525036) | [`0xe13Ef2fE9B4bC1A3bBB62Df6bB19d6aD79525036`](https://exoscan.org/address/0xe13Ef2fE9B4bC1A3bBB62Df6bB19d6aD79525036) | Proxy: - | -| [`TokenVault`](https://github.com/ExocoreNetwork/exocore-contracts/blob/main/src/contracts/core/Vault.sol) | [`0x0F4760CCab936a8fb0C9459dba2a739B22059b5f`](https://sepolia.etherscan.io/address/0x0F4760CCab936a8fb0C9459dba2a739B22059b5f) | [`0xF22097E6799DF7D8b25CCeF6E64DA3CB9133012D`](https://sepolia.etherscan.io/address/0xF22097E6799DF7D8b25CCeF6E64DA3CB9133012D) | Proxy: [`TUP@4.7.1`](https://github.com/OpenZeppelin/openzeppelin-contracts/blob/v4.7.1/contracts/proxy/transparent/TransparentUpgradeableProxy.sol) | -| [`Bootstrap`](https://github.com/ExocoreNetwork/exocore-contracts/blob/main/src/contracts/core/Bootstrap.sol) | [`0x53E91EB5105ec8C1c22055F790616cB8F82c664e`](https://sepolia.etherscan.io/address/0x53E91EB5105ec8C1c22055F790616cB8F82c664e) | [`0x417CaBa1E4a63D1202dCc6E19F7c3eC79b31EC45`](https://sepolia.etherscan.io/address/0x417CaBa1E4a63D1202dCc6E19F7c3eC79b31EC45) | Proxy: [`TUP@4.7.1`](https://github.com/OpenZeppelin/openzeppelin-contracts/blob/v4.7.1/contracts/proxy/transparent/TransparentUpgradeableProxy.sol) | -| [`LzEndpoint`](https://github.com/ExocoreNetwork/exocore-contracts/blob/main/src/contracts/core/Bootstrap.sol) | [`0x6EDCE65403992e310A62460808c4b910D972f10f`](https://sepolia.etherscan.io/address/0x6EDCE65403992e310A62460808c4b910D972f10f) | [`0x6EDCE65403992e310A62460808c4b910D972f10f`](https://sepolia.etherscan.io/address/0x6EDCE65403992e310A62460808c4b910D972f10f) | Proxy: [`TUP@4.7.1`](https://github.com/OpenZeppelin/openzeppelin-contracts/blob/v4.7.1/contracts/proxy/transparent/TransparentUpgradeableProxy.sol) | +For the latest deployment addresses, see [script/deployments/deployedContracts.json](./script/deployments/deployedContracts.json). diff --git a/docs/ClientChainGateway.md b/docs/ClientChainGateway.md index 054d0a6b..dff26e6b 100644 --- a/docs/ClientChainGateway.md +++ b/docs/ClientChainGateway.md @@ -1,6 +1,6 @@ # ClientChainGateway Documentation -The ClientChainGateway serves as the primary interface for stakers to interact with the Exocore network. It functions as a LayerZero application capable of cross-chain messaging and manages both Vault and Capsule contracts. +The ClientChainGateway serves as the primary interface for stakers to interact with Imua. It functions as a LayerZero application capable of cross-chain messaging and manages both Vault and Capsule contracts. ## Overview @@ -12,10 +12,10 @@ ClientChainGateway implements two types of restaking: ### Deposit Operations - `deposit(address token, uint256 amount)` - - Deposits whitelisted tokens into Exocore + - Deposits whitelisted tokens into Imua - Locks tokens in a Vault contract - - Sends cross-chain message to Exocore for accounting - - Always considered successful on Exocore side + - Sends cross-chain message to Imuachain for accounting + - Always considered successful on Imuachain - Requires relay fee in ETH for cross-chain message - `depositThenDelegateTo(address token, uint256 amount, string operator)` @@ -29,28 +29,28 @@ ClientChainGateway implements two types of restaking: - `delegateTo(string operator, address token, uint256 amount)` - Delegates previously deposited tokens to an operator - Requires prior deposit - - Sends cross-chain message to Exocore - - Updates delegation accounting on Exocore + - Sends cross-chain message to Imuachain + - Updates delegation accounting on Imuachain - Requires relay fee in ETH for cross-chain message - `undelegateFrom(string operator, address token, uint256 amount)` - Undelegates tokens from an operator - Requires prior delegation - - Sends cross-chain message to Exocore + - Sends cross-chain message to Imuachain - Initiates unbonding period - Requires relay fee in ETH for cross-chain message ### Withdrawal Operations -- `claimPrincipalFromExocore(address token, uint256 principalAmount)` - - Initiates withdrawal process from Exocore - - Sends cross-chain message to Exocore +- `claimPrincipalFromImuachain(address token, uint256 principalAmount)` + - Initiates withdrawal process from Imuachain + - Sends cross-chain message to Imuachain - Awaits response to unlock balance in Vault - Does not transfer tokens to user - Requires relay fee in ETH for cross-chain message - `withdrawPrincipal(address token, uint256 amount, address recipient)` - Transfers unlocked tokens from Vault to recipient - - Must be called after successful `claimPrincipalFromExocore` + - Must be called after successful `claimPrincipalFromImuachain` - No cross-chain message required - Direct transfer from Vault - No relay fee needed @@ -58,7 +58,7 @@ ClientChainGateway implements two types of restaking: ## NST Restaking Functions ### Setup Operations -- `createExoCapsule()` +- `createImuaCapsule()` - Creates Capsule contract for staker - Used as withdrawal credentials - Required before staking to beacon chain @@ -67,7 +67,7 @@ ClientChainGateway implements two types of restaking: - `stake(bytes pubkey, bytes signature, bytes32 depositDataRoot)` - Stakes ETH to Ethereum beacon chain - - Creates validator with ExoCapsule as withdrawal credentials + - Creates validator with ImuaCapsule as withdrawal credentials - Preparation step for NST restaking - Payable function accepting exactly 32 ETH for beacon chain staking - No relay fee needed @@ -75,8 +75,8 @@ ClientChainGateway implements two types of restaking: ### Deposit Operations - `verifyAndDepositNativeStake(bytes32[] validatorContainer, BeaconChainProofs.ValidatorContainerProof proof)` - Verifies beacon chain proof of withdrawal credentials - - Confirms validator is using correct ExoCapsule - - Sends message to Exocore to account for validator balance + - Confirms validator is using correct ImuaCapsule + - Sends message to Imuachain to account for validator balance - Required for NST restaking activation - Requires relay fee in ETH for cross-chain message @@ -84,8 +84,8 @@ ClientChainGateway implements two types of restaking: - `processBeaconChainWithdrawal(bytes32[] validatorContainer, BeaconChainProofs.ValidatorContainerProof validatorProof, bytes32[] withdrawalContainer, BeaconChainProofs.WithdrawalProof withdrawalProof)` - Processes beacon chain withdrawals - Verifies withdrawal proofs - - Sends message to Exocore to unlock ETH in Capsule - - Similar to `claimPrincipalFromExocore` for LSTs + - Sends message to Imuachain to unlock ETH in Capsule + - Similar to `claimPrincipalFromImuachain` for LSTs - Requires relay fee in ETH for cross-chain message - `withdrawNonBeaconChainETHFromCapsule(address payable recipient, uint256 amountToWithdraw)` @@ -100,18 +100,18 @@ ClientChainGateway implements two types of restaking: 1. Call `deposit` or `depositThenDelegateTo` 2. If using separate calls, wait for deposit confirmation 3. Call `delegateTo` if needed -4. Tokens are now staked and delegated on Exocore +4. Tokens are now staked and delegated on Imua ### LST Withdrawal -1. Call `claimPrincipalFromExocore` +1. Call `claimPrincipalFromImuachain` 2. Wait for cross-chain message confirmation 3. Call `withdrawPrincipal` to receive tokens ### NST Restaking -1. Call `createExoCapsule` +1. Call `createImuaCapsule` 2. Call `stake` to become validator 3. Call `verifyAndDepositNativeStake` with proofs -4. ETH is now restaked on Exocore +4. ETH is now restaked on Imua ### NST Withdrawal 1. Initiate withdrawal on beacon chain @@ -124,4 +124,4 @@ ClientChainGateway implements two types of restaking: - `stake` function requires exactly 32 ETH for beacon chain staking - Other payable functions only accept ETH for relay fees - NST operations require valid beacon chain proofs -- Delegation requires registered operators on Exocore +- Delegation requires registered operators on Imuachain diff --git a/docs/architecture.svg b/docs/architecture.svg index d0d9603f..38017f15 100644 --- a/docs/architecture.svg +++ b/docs/architecture.svg @@ -1 +1 @@ -IExocoreGatewayILSTRestakingControllerIVaultIExoCapsuleIBaseRestakingControllerILayerZeroReceiverIClientChainsIOAppReceiverIOAppCoreINativeRestakingControllerIBeaconChainOracleIETHPOSDepositITokenWhitelisterIValidatorRegistryPausableUpgradeableOwnableUpgradeableInitializableOAppUpgradeableOAppSenderUpgradeableOAppReceiverUpgradeableGatewayStorageBootstrapStorageClientChainGatewayStorageExocoreGatewayStorageExoCapsuleStorageBaseRestakingControllerclaim(address token, uint256 amount, address recipient)delegateTo(string calldata operator, address token, uint256 amount)undelegateFrom(string calldata operator, address token, uint256 amount)_processRequest(address token, address sender, uint256 amount, Action action, string memory operator)_sendMsgToExocore(Action action, bytes memory actionArgs)LSTRestakingControllerdeposit(address token, uint256 amount)withdrawPrincipleFromExocore(address token, uint256 principleAmount)withdrawRewardFromExocore(address token, uint256 rewardAmount)NativeRestakingControllernativeDeposit(uint256 amount)nativeWithdraw(uint256 amount)nativeDelegateTo(string calldata operator, uint256 amount)nativeUndelegateFrom(string calldata operator, uint256 amount)ExocoreGatewayinitialize(address payable exocoreValidatorSetAddress_)markBootstrap(uint32 chainId)pause()unpause()_lzReceive(Origin calldata _origin, bytes calldata payload)requestDeposit(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestWithdrawPrinciple(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestWithdrawReward(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestDelegateTo(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestUndelegateFrom(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)_sendInterchainMsg(uint32 srcChainId, Action act, bytes memory actionArgs)quote(uint32 srcChainid, bytes memory _message)nextNonce(uint32 srcEid, bytes32 sender)_verifyAndUpdateNonce(uint32 srcEid, bytes32 sender, uint64 nonce)ClientChainGatewayinitialize(address endpoint_)pause()unpause()deposit(address token, uint256 amount)withdraw(address token, uint256 amount)getBalance(address token)transfer(address token, address to, uint256 amount)nativeDeposit(uint256 amount)nativeWithdraw(uint256 amount)nativeDelegateTo(string calldata operator, uint256 amount)nativeUndelegateFrom(string calldata operator, uint256 amount)ClientGatewayLzReceiver_lzReceive(Origin calldata _origin, bytes calldata payload)nextNonce(uint32 srcEid, bytes32 sender)_verifyAndUpdateNonce(uint32 srcEid, bytes32 sender, uint64 nonce)afterReceiveDepositResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveWithdrawPrincipleResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveWithdrawRewardResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveDelegateResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveUndelegateResponse(bytes memory requestPayload, bytes calldata responsePayload)ExoCapsuleinitialize(address gateway_, address capsuleOwner_, address beaconOracle_)verifyDepositProof(bytes32[] calldata validatorContainer, ValidatorContainerProof calldata proof)verifyPartialWithdrawalProof(bytes32[] calldata validatorContainer, ValidatorContainerProof calldata validatorProof, bytes32[] calldata withdrawalContainer, WithdrawalContainerProof calldata withdrawalProof)verifyFullWithdrawalProof(bytes32[] calldata validatorContainer, ValidatorContainerProof calldata validatorProof, bytes32[] calldata withdrawalContainer, WithdrawalContainerProof calldata withdrawalProof)withdraw(uint256 amount, address recipient)updatePrincipleBalance(uint256 lastlyUpdatedPrincipleBalance)updateWithdrawableBalance(uint256 unlockPrincipleAmount)capsuleWithdrawalCredentials() : bytesgetBeaconBlockRoot(uint256 timestamp) : bytes32getRegisteredValidatorByPubkey(bytes32 pubkey) : ValidatorgetRegisteredValidatorByIndex(uint256 index) : Validator_verifyValidatorContainer(bytes32[] calldata validatorContainer, ValidatorContainerProof calldata proof)_verifyWithdrawalContainer(bytes32[] calldata withdrawalContainer, WithdrawalContainerProof calldata proof)_isActivatedAtEpoch(bytes32[] calldata validatorContainer, uint256 atTimestamp) : bool_isStaleProof(Validator storage validator, uint256 proofTimestamp) : bool_hasFullyWithdrawn(bytes32[] calldata validatorContainer) : bool_timestampToEpoch(uint256 timestamp) : uint64Bootstrapinitialize(address owner, uint256 spawnTime_, uint256 offsetDuration_, address payable exocoreValidatorSetAddress_, address[] calldata whitelistTokens_, address customProxyAdmin_)pause()unpause()setSpawnTime(uint256 _spawnTime)setOffsetDuration(uint256 _offsetDuration)addWhitelistToken(address _token)removeWhitelistToken(address _token)registerOperator(string calldata operatorExocoreAddress, string calldata name, Commission memory commission, bytes32 consensusPublicKey)replaceKey(bytes32 newKey)updateRate(uint256 newRate)deposit(address token, uint256 amount)withdrawPrincipleFromExocore(address token, uint256 amount)withdrawRewardFromExocore(address token, uint256 amount)claim(address token, uint256 amount, address recipient)delegateTo(string calldata operator, address token, uint256 amount)undelegateFrom(string calldata operator, address token, uint256 amount)setClientChainGatewayLogic(address _clientChainGatewayLogic, bytes calldata _clientChainInitializationData)getOperatorsCount()getDepositorsCount()getWhitelistedTokensCount()getWhitelistedTokenAtIndex(uint256 index)IClientChainGatewayBootstrapLzReceiver \ No newline at end of file +IImuachainGatewayILSTRestakingControllerIVaultIImuaCapsuleIBaseRestakingControllerILayerZeroReceiverIClientChainsIOAppReceiverIOAppCoreINativeRestakingControllerIBeaconChainOracleIETHPOSDepositITokenWhitelisterIValidatorRegistryPausableUpgradeableOwnableUpgradeableInitializableOAppUpgradeableOAppSenderUpgradeableOAppReceiverUpgradeableGatewayStorageBootstrapStorageClientChainGatewayStorageImuachainGatewayStorageImuaCapsuleStorageBaseRestakingControllerclaim(address token, uint256 amount, address recipient)delegateTo(string calldata operator, address token, uint256 amount)undelegateFrom(string calldata operator, address token, uint256 amount)_processRequest(address token, address sender, uint256 amount, Action action, string memory operator)_sendMsgToImuachain(Action action, bytes memory actionArgs)LSTRestakingControllerdeposit(address token, uint256 amount)withdrawPrincipleFromImuachain(address token, uint256 principleAmount)withdrawRewardFromImuachain(address token, uint256 rewardAmount)NativeRestakingControllernativeDeposit(uint256 amount)nativeWithdraw(uint256 amount)nativeDelegateTo(string calldata operator, uint256 amount)nativeUndelegateFrom(string calldata operator, uint256 amount)ImuachainGatewayinitialize(address payable ownerAddress)markBootstrap(uint32 chainId)pause()unpause()_lzReceive(Origin calldata _origin, bytes calldata payload)requestDeposit(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestWithdrawPrinciple(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestWithdrawReward(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestDelegateTo(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestUndelegateFrom(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)_sendInterchainMsg(uint32 srcChainId, Action act, bytes memory actionArgs)quote(uint32 srcChainid, bytes memory _message)nextNonce(uint32 srcEid, bytes32 sender)_verifyAndUpdateNonce(uint32 srcEid, bytes32 sender, uint64 nonce)ClientChainGatewayinitialize(address endpoint_)pause()unpause()deposit(address token, uint256 amount)withdraw(address token, uint256 amount)getBalance(address token)transfer(address token, address to, uint256 amount)nativeDeposit(uint256 amount)nativeWithdraw(uint256 amount)nativeDelegateTo(string calldata operator, uint256 amount)nativeUndelegateFrom(string calldata operator, uint256 amount)ClientGatewayLzReceiver_lzReceive(Origin calldata _origin, bytes calldata payload)nextNonce(uint32 srcEid, bytes32 sender)_verifyAndUpdateNonce(uint32 srcEid, bytes32 sender, uint64 nonce)afterReceiveDepositResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveWithdrawPrincipleResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveWithdrawRewardResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveDelegateResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveUndelegateResponse(bytes memory requestPayload, bytes calldata responsePayload)ImuaCapsuleinitialize(address gateway_, address capsuleOwner_, address beaconOracle_)verifyDepositProof(bytes32[] calldata validatorContainer, ValidatorContainerProof calldata proof)verifyPartialWithdrawalProof(bytes32[] calldata validatorContainer, ValidatorContainerProof calldata validatorProof, bytes32[] calldata withdrawalContainer, WithdrawalContainerProof calldata withdrawalProof)verifyFullWithdrawalProof(bytes32[] calldata validatorContainer, ValidatorContainerProof calldata validatorProof, bytes32[] calldata withdrawalContainer, WithdrawalContainerProof calldata withdrawalProof)withdraw(uint256 amount, address recipient)updatePrincipleBalance(uint256 lastlyUpdatedPrincipleBalance)updateWithdrawableBalance(uint256 unlockPrincipleAmount)capsuleWithdrawalCredentials() : bytesgetBeaconBlockRoot(uint256 timestamp) : bytes32getRegisteredValidatorByPubkey(bytes32 pubkey) : ValidatorgetRegisteredValidatorByIndex(uint256 index) : Validator_verifyValidatorContainer(bytes32[] calldata validatorContainer, ValidatorContainerProof calldata proof)_verifyWithdrawalContainer(bytes32[] calldata withdrawalContainer, WithdrawalContainerProof calldata proof)_isActivatedAtEpoch(bytes32[] calldata validatorContainer, uint256 atTimestamp) : bool_isStaleProof(Validator storage validator, uint256 proofTimestamp) : bool_hasFullyWithdrawn(bytes32[] calldata validatorContainer) : bool_timestampToEpoch(uint256 timestamp) : uint64Bootstrapinitialize(address owner, uint256 spawnTime_, uint256 offsetDuration_, address payable owner_, address[] calldata whitelistTokens_, address customProxyAdmin_)pause()unpause()setSpawnTime(uint256 _spawnTime)setOffsetDuration(uint256 _offsetDuration)addWhitelistToken(address _token)removeWhitelistToken(address _token)registerOperator(string calldata operatorImuachainAddress, string calldata name, Commission memory commission, bytes32 consensusPublicKey)replaceKey(bytes32 newKey)updateRate(uint256 newRate)deposit(address token, uint256 amount)withdrawPrincipleFromImuachain(address token, uint256 amount)withdrawRewardFromImuachain(address token, uint256 amount)claim(address token, uint256 amount, address recipient)delegateTo(string calldata operator, address token, uint256 amount)undelegateFrom(string calldata operator, address token, uint256 amount)setClientChainGatewayLogic(address _clientChainGatewayLogic, bytes calldata _clientChainInitializationData)getOperatorsCount()getDepositorsCount()getWhitelistedTokensCount()getWhitelistedTokenAtIndex(uint256 index)IClientChainGatewayBootstrapLzReceiver \ No newline at end of file diff --git a/docs/btc-staking-e2e-testing.md b/docs/btc-staking-e2e-testing.md index 6d492c1b..e3c623b1 100644 --- a/docs/btc-staking-e2e-testing.md +++ b/docs/btc-staking-e2e-testing.md @@ -16,7 +16,7 @@ This guide walks through setting up and testing the BTC staking functionality in 1. First, clone and set up the Esplora explorer: ```bash -git clone https://github.com/ExocoreNetwork/esplora.git +git clone https://github.com/imua-xyz/esplora.git cd esplora ``` @@ -32,7 +32,7 @@ Arguments: amount_btc Amount of BTC to send to faucet (default: 100) mining_interval_seconds Block mining interval in seconds (default: 30) -Faucet Information(only for regtest): +Faucet Information (only for regtest): Private Key: 0xee01cfc3f08cdb020064f31ff1a993aa9ecc1d38e684665742faa705685532a6 Address: bcrt1qvj7e5av2eqrhhvle56f9aqtjpxgywwnt5tem5y @@ -42,14 +42,14 @@ Example: NOTICE: Some amount of test BTC would be sent to the faucet address with known private key -### Start Exocore Node +### Start Imuachain Node -1. Set up and start the Exocore node: +1. Set up and start the Imuachain node: ```bash # Clone the repository -git clone https://github.com/ExocoreNetwork/exocore.git -cd exocore +git clone https://github.com/imua-xyz/imuachain.git +cd imuachain # Switch to develop branch git checkout develop @@ -63,19 +63,19 @@ git checkout develop 1. Clone repo and set up the UTXO gateway contract: ```bash -git clone https://github.com/ExocoreNetwork/exocore-contracts.git -cd exocore-contracts +git clone https://github.com/imua-xyz/imua-contracts.git +cd imua-contracts npm run deploy:utxogateway ``` -Before running the deployment command, please replace the URL path of `exocore_localnet` in `hardhat.config.js` with the URL path of your set up Exocore node, and also set the private key of the Exocore account in `hardhat.config.js` in your local `.env` file. We need at least 3 accounts (`deployer` == `faucet`, `owner` and `witness1`) to execute the deployment script. +Before running the deployment command, please replace the URL path of `imuachain_localnet` in `hardhat.config.js` with the URL path of your set up Imuachain node, and also set the private key of the Imuachain account in `hardhat.config.js` in your local `.env` file. We need at least 3 accounts (`deployer` == `faucet`, `owner` and `witness1`) to execute the deployment script. ```javascript -exocore_localnet: { +imuachain_localnet: { url: "http://127.0.0.1:8545", chainId: 232, accounts: [ - process.env.LOCAL_EXOCORE_FUNDED_ACCOUNT_PRIVATE_KEY, // Deployer/Faucet: Requires minimum 3 eth balance + process.env.LOCAL_IMUACHAIN_FUNDED_ACCOUNT_PRIVATE_KEY, // Deployer/Faucet: Requires minimum 3 eth balance process.env.TEST_ACCOUNT_ONE_PRIVATE_KEY, // Owner: the owner of the UTXOGateway contract process.env.TEST_ACCOUNT_TWO_PRIVATE_KEY, // Witness1: the only witness for current implementation, also needed by bridge process.env.TEST_ACCOUNT_THREE_PRIVATE_KEY, @@ -86,7 +86,7 @@ exocore_localnet: { } ``` -This would deploy UTXOGateway contract on exocore node and setup it: +This would deploy UTXOGateway contract on Imuachain node and set it up: - set deployed contract as authorized gateway - set required proofs count @@ -101,7 +101,8 @@ The final output would be stored under `script/deployments/utxogateway.json` ```bash # Clone the repository -git clone https://github.com/ExocoreNetwork/utxo-restaking.git +# TODO: transfer out to imua-xyz after upgrading the org plan +git clone https://github.com/imua-xyz/utxo-restaking.git cd utxo-restaking git checkout btc-restaking-v2 ``` @@ -117,7 +118,7 @@ cp .env.example .env BITCOIN_RPC // URL of the esplora API VAULT_ADDRESS // Address of the BTC vault MIN_CONFIRMATIONS // Minimum number of confirmations for a Bitcoin transaction -EXOCORE_RPC // URL of the Exocore node +EXOCORE_RPC // URL of the Imuachain node CONTRACT_ADDRESS // Address of the UTXOGateway contract WITNESS_ADDRESS // Address of the witness WALLET_PRIV_KEY // Private key of the signing wallet, should be the same as the witness for current implementation @@ -134,7 +135,7 @@ docker-compose up ### Run E2E Tests -1. Go back to the exocore-contracts directory and run the BTC staking E2E test: +1. Go back to the imua-contracts directory and run the BTC staking E2E test: ```bash npx hardhat test test/integration/btc-staking-e2e.test.js @@ -150,4 +151,4 @@ BITCOIN_TX_FEE // Transaction fee for BTC deposit DUST_THRESHOLD // Dust threshold for BTC deposit ``` -This test would simulate the process of building a valid Bitcoin deposit transaction, broadcasting it to the Bitcoin network and waiting for it to be confirmed, and finally checking staker's balance on Exocore. +This test would simulate the process of building a valid Bitcoin deposit transaction, broadcasting it to the Bitcoin network and waiting for it to be confirmed, and finally checking staker's balance on Imuachain. diff --git a/docs/client-chain-contracts-design.md b/docs/client-chain-contracts-design.md index e159d48c..29ec455b 100644 --- a/docs/client-chain-contracts-design.md +++ b/docs/client-chain-contracts-design.md @@ -2,21 +2,21 @@ ## Overview -Exocore Client chain smart contracts refer to a set of smart contracts that are deployed on multiple chains (EVM-compatible chains for current version), and provided for Exocore users (mainly stakers) to interact with Exocore system from specific client chains. The administrative functionalities of these contracts are via their owner, which ideally should be a multi-sig. +Imua client chain smart contracts refer to a set of smart contracts that are deployed on multiple chains (EVM-compatible chains for current version), and provided for Imua users (mainly stakers) to interact with Imua system from specific client chains. The administrative functionalities of these contracts are via their owner, which ideally should be a multi-sig. The two main functionalities of client chain smart contracts include: -1. Take user funds into custody when users ask to enter Exocore system, update user balance periodically and deal with withdrawal request of user based on withdrawable balance. -2. Forward user request from client chain side to Exocore, as well as receive response from Exocore to update state or execute some operations. +1. Take user funds into custody when users ask to enter Imua system, update user balance periodically and deal with withdrawal request of user based on withdrawable balance. +2. Forward user request from client chain side to Imuachain, as well as receive response from Imuachain to update state or execute some operations. -We have these components included in Exocore client chain smart contracts architecture: +We have these components included in Imua client chain smart contracts architecture: -1. `Bootstrap`: The contract is used for bootstraping the Exocore system, including accepting registration of validators and delegations from client chain stakers, and generate the valid genesis that could be used to bootstrap the Exocore chain. -2. `ClientChainGateway`: This is the entry point where client chain users make requests to the Exocore validator set, as well as the endpoint that receives cross-chain messages from the Exocore validator set. -3. `Vault`: This is where user funds are taken into custody and managed. Within `Vault`, user balance is updated periodically by Exocore validator set through cross-chain message to reveal user’s real position (after slashing, rewarding and other impact). Users can withdraw from `Vault` based on grant from the gateway. Every specific asset should have a standalone `Vault`. +1. `Bootstrap`: The contract is used for bootstraping the Imua system, including accepting registration of validators and delegations from client chain stakers, and generate the valid genesis that could be used to bootstrap Imuachain. +2. `ClientChainGateway`: This is the entry point where client chain users make requests to Imuachain, as well as the endpoint that receives cross-chain messages from Imuachain. +3. `Vault`: This is where user funds are taken into custody and managed. Within `Vault`, user balance is updated on-demand by Imuachain validator set through cross-chain message to reveal user’s real position (after slashing, rewarding and other impact). Users can withdraw from `Vault` based on grant from the gateway. Every specific asset should have a standalone `Vault`. 4. `LSTRestakingController`: The controller is responsible for managing multiple `Vault`s. It should be the entry point for operations on `Vault`, as well as the entry point for user’s interactions with the gateway. It is inherited / implemented by the `Gateway`. -5. `ExoCapsule`: The contract is used as the withdrawal destination for Ethereum native restaking. The Ethereum stakers who want to restake their staked ETH into Exocore should create an owned `ExoCapsule` contract through `NativeRestakingController` and point the withdrawal credentials of beacon chain validator to the `ExoCapsule` contract. -6. `NativeRestakingController`: The controller is responsible for managing multiple `ExoCapsule`s. It provide functions for Ethereum native restaking, so that Ethereum beacon chain stakers could deposit their staked ETH into Exocore without relying on any derived LST. It is inherited / implemented by the `ClientChainGateway` on Ethereum. +5. `ImuaCapsule`: The contract is used as the withdrawal destination for Ethereum native restaking. The Ethereum stakers who want to restake their staked ETH into Imua should create an owned `ImuaCapsule` contract through `NativeRestakingController` and point the withdrawal credentials of beacon chain validator to the `ImuaCapsule` contract. +6. `NativeRestakingController`: The controller is responsible for managing multiple `ImuaCapsule` instances. It provide functions for Ethereum native restaking, so that Ethereum beacon chain stakers could deposit their staked ETH into Imua without relying on any derived LST. It is inherited / implemented by the `ClientChainGateway` on Ethereum. ## Upgrade @@ -106,35 +106,35 @@ For more details please refer to these docs: Similar to LayerZero `endpoint`, `ClientChainGateway` is mainly responsible for sending cross-chain messages and receiving cross-chain messages. The validity of cross-chain messages are guaranteed by LayerZero oracle and relayer if integrated with LayerZero protocol, otherwise `Gateway` itself should validate the cross-chain messages. -Eventually, the Exocore validator set should be the owner of `ClientChainGateway` so that it can update some state variables or even upgrade it in the future. In the early stages, a more controlled way to upgrade is needed, for example, a multi-sig. +Eventually, the governance system of Imuachain should be the owner of `ClientChainGateway` so that it can update some state variables or even upgrade it in the future. In the early stages, a more controlled way to upgrade is needed, for example, a multi-sig. We have made `ClientChainGateway` contract upgradeable so that the state can be retained while adding or removing some features in the future. ```solidity contract BaseRestakingController { - /// @dev Sends a message to Exocore. + /// @dev Sends a message to Imuachain. /// @param action The action to be performed. /// @param actionArgs The encodePacked arguments for the action. - function _sendMsgToExocore(Action action, bytes memory actionArgs); + function _sendMsgToImuachain(Action action, bytes memory actionArgs); /// @inheritdoc OAppReceiverUpgradeable function _lzReceive(Origin calldata _origin, bytes calldata payload); } ``` -### `_sendMsgToExocore` +### `_sendMsgToImuachain` -This internal function is used to send a message, over LayerZero, from the client chain to the Exocore chain. It encodes the action to perform, along with its payload, and forwards the packed data. The fees for this cross-chain message is provided by the calling address. +This internal function is used to send a message, over LayerZero, from the client chain to Imuachain. It encodes the action to perform, along with its payload, and forwards the packed data. The fees for this cross-chain message is provided by the calling address. ### `_lzReceive` -This internal function is called via LayerZero upon the receipt of a cross-chain message. In the context of the `ClientChainGateway`, it is used to handle the response provided by the Exocore chain against an outgoing message. For example, if a withdrawal request is initiated by a user, and sent by the `ClientChainGateway` to Exocore, a response is received indicating whether the withdrawal is valid. Based on this validity, `ClientChainGateway` marks the funds available for the user to claim. +This internal function is called via LayerZero upon the receipt of a cross-chain message. In the context of the `ClientChainGateway`, it is used to handle the response provided by Imuachain against an outgoing message. For example, if a withdrawal request is initiated by a user, and sent by the `ClientChainGateway` to Imuachain, a response is received indicating whether the withdrawal is valid. Based on this validity, `ClientChainGateway` marks the funds available for the user to claim. ## `Vault` -Every whitelisted native token on the client chain for Exocore has a standalone `Vault` used for user funds custody. Each `Vault` contract takes into custody the user's assets and stores them on their behalf. A user can enter the system by providing approval to the `Vault` contract and then depositing in it through the `ClientChainGateway`. Similarly, a user can exit the system by undelegating and withdrawing their assets and claiming them from the vault. +Every whitelisted native token on the client chain has a standalone `Vault` used for user funds custody. Each `Vault` contract takes into custody the user's assets and stores them on their behalf. A user can enter the system by providing approval to the `Vault` contract and then depositing in it through the `ClientChainGateway`. Similarly, a user can exit the system by undelegating and withdrawing their assets and claiming them from the vault. -The assets in a `Vault` include the principal deposited as well as any rewards that may have accrued to the staker and any reductions for slashing. While each `Vault` contract stores some data, Exocore is the single source of truth for the accurate withdrawable, deposited and staked balances. +The assets in a `Vault` include the principal deposited as well as any rewards that may have accrued to the staker and any reductions for slashing. While each `Vault` contract stores some data, Imuachain is the single source of truth for the accurate withdrawable, deposited and staked balances. ```solidity interface IVault { @@ -179,7 +179,7 @@ interface IVault { } ``` -`principalBalance` refers to the principal that the user deposits into the `ClientChainGateway`. It is separated from the rewards earned by the users, since such rewards could be distributed on the Exocore chain or on another client chain, while the user principal is taken in custody on this chain. Besides, we assume that the principal balance can only be influenced during slashing and that it is not transferable to any other address. In other words, the principal balance to be withdrawn can never be greater than the originally deposited principal balance. +`principalBalance` refers to the principal that the user deposits into the `ClientChainGateway`. It is separated from the rewards earned by the users, since such rewards could be distributed on Imuachain or on another client chain, while the user principal is taken in custody on this chain. Besides, we assume that the principal balance can only be influenced during slashing and that it is not transferable to any other address. In other words, the principal balance to be withdrawn can never be greater than the originally deposited principal balance. ### `deposit` @@ -187,17 +187,17 @@ The implementation of this function transfers user funds into `Vault` address an This function is only accessible for `ClientChainGateway` so that this function could only work as part of the process of the whole deposit workflow and ensure the whole workflow is controlled by `ClientChainGateway`. -Whenever a `deposit` request is received by the `ClientChainGateway`, it first deposits the amount into the `Vault`. Then, it forwards the transaction to Exocore, where it is appropriately processed, in line with the `checks-effects-interactions` pattern. +Whenever a `deposit` request is received by the `ClientChainGateway`, it first deposits the amount into the `Vault`. Then, it forwards the transaction to Imuachain, where it is appropriately processed, in line with the `checks-effects-interactions` pattern. ### `withdraw` -This function allows a user to claim their withdrawable assets. The quantity of the withdrawable assets is set by the `ClientChainGateway` in response to a withdrawal request, after receiving a response from Exocore. +This function allows a user to claim their withdrawable assets. The quantity of the withdrawable assets is set by the `ClientChainGateway` in response to a withdrawal request, after receiving a response from Imuachain. ## `LSTRestakingController` -`LSTRestakingController` is the manager of all `Vaults`, as well as the entry point where users call to interact with Exocore system. +`LSTRestakingController` is the manager of all `Vaults`, as well as the entry point where users call to interact with Imua. -Ideally, the Exocore validator set should own `LSTRestakingController` so that upgrades can be made trustlessly. +Ideally, the Imuachain validator set, via governance, should own `LSTRestakingController` so that upgrades can be made trustlessly. ```solidity interface IBaseRestakingController { @@ -216,7 +216,7 @@ interface IBaseRestakingController { /// @notice Client chain users call to withdraw their unlocked assets from the vault. /// @dev This function assumes that the withdrawable assets should have been unlocked before calling this. - /// @dev This function does not interact with Exocore. + /// @dev This function does not interact with Imuachain. /// @param token The address of specific token that the user wants to claim from the vault. /// @param amount The amount of @param token that the user wants to claim from the vault. /// @param recipient The destination address that the assets would be transfered to. @@ -227,10 +227,10 @@ interface IBaseRestakingController { /// @param rewardAmount The amount of reward tokens that the user wants to submit. function submitReward(address token, address avs, uint256 rewardAmount) external payable; - /// @notice Claims reward tokens from Exocore. + /// @notice Claims reward tokens from Imuachain. /// @param token The address of the specific token that the user wants to claim as a reward. /// @param rewardAmount The amount of reward tokens that the user wants to claim. - function claimRewardFromExocore(address token, uint256 rewardAmount) external payable; + function claimRewardFromImuachain(address token, uint256 rewardAmount) external payable; /// @notice Withdraws reward tokens from vault to the recipient. /// @param token The address of the specific token that the user wants to withdraw as a reward. @@ -245,28 +245,28 @@ interface IBaseRestakingController { See [`deposit`](#deposit). -Once the assets have been deposited into the `Vault`, the `ClientChainGateway` sends a cross-chain message to Exocore, which is obviously asynchronous. Upon receiving the message, Exocore will consider the deposit, and must respond that the message succeeded. This is because our design requires that deposits can never fail. +Once the assets have been deposited into the `Vault`, the `ClientChainGateway` sends a cross-chain message to Imuachain, which is obviously asynchronous. Upon receiving the message, Imuachain will consider the deposit, and must respond that the message succeeded. This is because our design requires that deposits can never fail. ### `delegateTo` This function controls the delegation workflow originating from the client chain. It requires that the caller has previously deposited enough tokens into the system, failing which, the transaction will fail. -The delegation workflow involves only one transaction from the user: call `ClientChainGateway.sendInterchainMsg` to send delegate request to Exocore chain. And there is no response from Exocore, since the event emitted by `ExocoreGateway` to tell whether the delegation is successful or not. +The delegation workflow involves only one transaction from the user: call `ClientChainGateway.sendInterchainMsg` to send delegate request to Imuachain. And there is no response from Imuachain, since the event emitted by `ImuachainGateway` to tell whether the delegation is successful or not. Since the `ClientChainGateway` by itself does not store enough information to check whether a delegation will be successful, this method must not make any state alterations to the balance. ### `undelegateFrom` -This function is the reverse of [`delegatTo`](#delegateto), except that it requires an unbonding period before the undelegation is released for withdrawal. The unbonding period is determined by Exocore based on all the AVSs in which the operator was participating at the time of undelegation. +This function is the reverse of [`delegateTo`](#delegateto), except that it requires an unbonding period before the undelegation is released for withdrawal. The unbonding period is determined by Imuachain based on all the AVSs in which the operator was participating at the time of undelegation. -### `claimPrincipalFromExocore` +### `claimPrincipalFromImuachain` -This function is aimed for user claiming principal from Exocore chain to client chain. This involves the correct accounting on Exocore chain as well as the correct update of user's `principalBalance` and claimable balance. If this process is successful, user should be able to withdraw the corresponding assets on client chain to destination address. +This function is aimed for user claiming principal from Imuachain to client chain. This involves the correct accounting on Imuachain as well as the correct update of user's `principalBalance` and claimable balance. If this process is successful, user should be able to withdraw the corresponding assets on client chain to destination address. The principal withdrawal workflow is separated into two transactions: -1. Transaction from the user: call `ClientChainGateway.sendInterchainMsg` to send principal withdrawal request to Exocore chain. -2. Response from Exocore: call `ClientChainGateway.receiveInterchainMsg` to receive the response from Exocore chain, and call `unlockPrincipal` to update user's `principalBalance` and claimable balance. If response indicates failure, no user balance should be modified. +1. Transaction from the user: call `ClientChainGateway.sendInterchainMsg` to send principal withdrawal request to Imuachain. +2. Response from Imuachain: call `ClientChainGateway.receiveInterchainMsg` to receive the response from Imuachain, and call `unlockPrincipal` to update user's `principalBalance` and claimable balance. If response indicates failure, no user balance should be modified. The claimable amount of principal is defined as follows: @@ -276,7 +276,7 @@ The claimable amount of principal is defined as follows: ### `withdrawPrincipal` -This function is aimed for user withdrawing the unlocked amount of principal. Before withdrawing, user must make sure that there is enough principal unlocked by calling `claimPrincipalFromExocore`. The implementation of this function should check against user's claimable balance and transfer tokens to the destination address that the user specified. +This function is aimed for user withdrawing the unlocked amount of principal. Before withdrawing, user must make sure that there is enough principal unlocked by calling `claimPrincipalFromImuachain`. The implementation of this function should check against user's claimable balance and transfer tokens to the destination address that the user specified. ### `depositThenDelegateTo` diff --git a/docs/contract-governance.md b/docs/contract-governance.md index 678b03b2..299ba6de 100644 --- a/docs/contract-governance.md +++ b/docs/contract-governance.md @@ -25,7 +25,7 @@ The contract owner is effectively the protocol's governor, with governance prima ## Safe Multisig -We use the Safe Multisig wallets as the proposer/canceler, executor, circuit breaker and even the admin of the `CustomTimelockController`. For chains like Ethereum, we create the Safe Multisig wallets from deployed Safe proxy factory contract, and set the implementation as the deployed Safe. And for Exocore specifically, we deploy the set of Safe contracts, especially for the `GnosisSafeProxyFactory` and the `GnosisSafe`, `GnosisSafeL2` singletons. The deployed Safe contracts address can be found in the [deployment json file](../script/safe_contracts_on_exocore.json). +We use the Safe Multisig wallets as the proposer/canceler, executor, circuit breaker and even the admin of the `CustomTimelockController`. For chains like Ethereum, we create the Safe Multisig wallets from deployed Safe proxy factory contract, and set the implementation as the deployed Safe. And for Imuachain specifically, we deploy the set of Safe contracts, especially for the `GnosisSafeProxyFactory` and the `GnosisSafe`, `GnosisSafeL2` singletons. The deployed Safe contracts address can be found in the [deployment json file](../script/deployments/safe_contracts_on_imuachain.json). ## Governance Test diff --git a/docs/contracts-owner-manual.md b/docs/contracts-owner-manual.md index 42e84ecf..474b27a2 100644 --- a/docs/contracts-owner-manual.md +++ b/docs/contracts-owner-manual.md @@ -1,26 +1,26 @@ # Contract Owner's Manual -Currently, almost all contracts are ownable contracts including `Bootstrap`, `ClientChainGateway`, `Vault`, `ExocoreGateway`. The owner of these contracts is a privileged account in many aspects including upgrading contract by changing implementation, registering some client chain to Exocore before enabling restaking from that client chain, adding token info to whitelist and even pausing/unpausing contracts in case of emergencies. +Currently, almost all contracts are ownable contracts including `Bootstrap`, `ClientChainGateway`, `Vault`, `ImuachainGateway`. The owner of these contracts is a privileged account in many aspects including upgrading contract by changing implementation, registering some client chain to Imuachain before enabling restaking from that client chain, adding token info to whitelist and even pausing/unpausing contracts in case of emergencies. ## Owner Only Functionalities ## `pause`/`unpause` -In case of emergencies where some unexpected errors happened to the protocol, contract owner could pause the contract to disable all user-facing functions and re-enable these functions after successfully recovering from emergencies. Currently, pauseable contracts include `Bootstrap`, `ClientChainGateway`, `ExocoreGateway`. For `Vault` and `ExoCapsule`, as all the functions are limited to be called by their management contract(`ClientChainGateway`, `Bootstrap`), their functionalities are also paused when their management contract get paused. +In case of emergencies where some unexpected errors happened to the protocol, contract owner could pause the contract to disable all user-facing functions and re-enable these functions after successfully recovering from emergencies. Currently, pauseable contracts include `Bootstrap`, `ClientChainGateway`, `ImuachainGateway`. For `Vault` and `ImuaCapsule`, as all the functions are limited to be called by their management contract(`ClientChainGateway`, `Bootstrap`), their functionalities are also paused when their management contract get paused. ## upgrade to new implementation -Most contracts including `Bootstrap`, `ClientChainGateway`, `ExocoreGateway`, `Vault` and `ExoCapsule` are upgradeable. For `Bootstrap`, `ClientChainGateway` and `ExocoreGateway`, they are upgradeable through `ProxyAdmin` contract, so the owner of `ProxyAdmin` could upgrade these contracts by changing implementation contract. -While for `Vault` and `ExoCapsule`, they are deployed with upgradeable beacon proxy, so only `upgradeableBeacon` could access the upgrading functionalities of these contracts, that is to say only the owner of `upgradeableBeacon` could upgrade these contracts by changing implementation contract. Notice as all `Vault`s are deployed with upgradeable beacon proxy and all these proxies point to the same `upgradeableBeacon` contract, when the owner change implementation contract stored in `upgradeableBeacon`, all `Vault`s get upgraded to the same new version of contract, and same case for `ExoCapsule`. +Most contracts including `Bootstrap`, `ClientChainGateway`, `ImuachainGateway`, `Vault` and `ImuaCapsule` are upgradeable. For `Bootstrap`, `ClientChainGateway` and `ImuachainGateway`, they are upgradeable through `ProxyAdmin` contract, so the owner of `ProxyAdmin` could upgrade these contracts by changing implementation contract. +While for `Vault` and `ImuaCapsule`, they are deployed with upgradeable beacon proxy, so only `upgradeableBeacon` could access the upgrading functionalities of these contracts, that is to say only the owner of `upgradeableBeacon` could upgrade these contracts by changing implementation contract. Notice as all `Vault`s are deployed with upgradeable beacon proxy and all these proxies point to the same `upgradeableBeacon` contract, when the owner change implementation contract stored in `upgradeableBeacon`, all `Vault`s get upgraded to the same new version of contract, and same case for `ImuaCapsule`. ## register client chain -After all contracts are deployed, before the protocol starts to work, there are a few works left to be done by contract owner to enable restaking. One of the most important tasks is to register the client chain id and meta info to Exocore to mark this client chain as valid. This is done by the contract caller calling `ExocoreGateway.registerOrUpdateClientChain` to write `clientChainId`, `addressLength`, `name`, `signatureType` and other meta data to Exocore native module to finish registration. This operation would also call `ExocoreGateway.setPeer` to enable LayerZero messaging by setting remote `ClientChainGateway` as trusted peer to send/receive messages. After finishing registration, contract owner could call `ExocoreGateway.registerOrUpdateClientChain` again to update the meta data and set new peer, or contract owner could solely call `ExocoreGateway.setPeer` to change the address of remote peer contract. +After all contracts are deployed, before the protocol starts to work, there are a few works left to be done by contract owner to enable restaking. One of the most important tasks is to register the client chain id and meta info to Imuachain to mark this client chain as valid. This is done by the contract caller calling `ImuachainGateway.registerOrUpdateClientChain` to write `clientChainId`, `addressLength`, `name`, `signatureType` and other meta data to Imuachain native module to finish registration. This operation would also call `ImuachainGateway.setPeer` to enable LayerZero messaging by setting remote `ClientChainGateway` as trusted peer to send/receive messages. After finishing registration, contract owner could call `ImuachainGateway.registerOrUpdateClientChain` again to update the meta data and set new peer, or contract owner could solely call `ImuachainGateway.setPeer` to change the address of remote peer contract. ## add or update tokens to whitelist -Another important task before restaking being activated is to add tokens to whitelist to mark them as stake-able on both Exocore and client chain. This is done by contract owner calling `ExocoreGateway.addOrUpdateWhitelistTokens` to write token addresses, decimals, TVL limits and other metadata to Exocore, as well as sending a cross-chain message through layerzero to client chain to add these token addresses to the whitelist of `ClientChainGateway`. +Another important task before restaking being activated is to add tokens to whitelist to mark them as stake-able on both Imuachain and client chain. This is done by contract owner calling `ImuachainGateway.addOrUpdateWhitelistTokens` to write token addresses, decimals, TVL limits and other metadata to Imuachain, as well as sending a cross-chain message through layerzero to client chain to add these token addresses to the whitelist of `ClientChainGateway`. Notice: contract owner must make sure the token data is correct like address, decimals and TVL limit, more importantly contract owner must ensure that for the same index, the data in different arrays like `tokens`, `decimals`, `tvlLimits` must point to the same token to be composed as complete token data. -After adding tokens to whitelist, contract owner could call `ExocoreGateway.addOrUpdateWhitelistTokens` to update the meta data of already whitelisted tokens, and this function would not send a cross-chain message to client chain since the whitelist of `ClientChainGateway` only stores the token addresses. \ No newline at end of file +After adding tokens to whitelist, contract owner could call `ImuachainGateway.addOrUpdateWhitelistTokens` to update the meta data of already whitelisted tokens, and this function would not send a cross-chain message to client chain since the whitelist of `ClientChainGateway` only stores the token addresses. \ No newline at end of file diff --git a/docs/cross-chain-communication-model.md b/docs/cross-chain-communication-model.md index 078163e1..cd1364fd 100644 --- a/docs/cross-chain-communication-model.md +++ b/docs/cross-chain-communication-model.md @@ -2,11 +2,11 @@ ## 1:N -While there could be multiple client chains and `ClientChainGateway`s, there is only one Exocore chain that serves as the source of truth. Similarly, there is only one `ExocoreGateway` contract that manages the communication between the client chains and the Exocore chain. This contract receives messages from the client chains and forwards them to the Exocore chain, or sends requests to the client chains. Therefore, the communication between `ExocoreGateway` and `ClientChainGateway`s is 1:N. +While there could be multiple client chains and `ClientChainGateway`s, there is only one Imuachain that serves as the source of truth. Similarly, there is only one `ImuachainGateway` contract that manages the communication between a client chains and Imuachain internals. This contract receives messages from the client chains and forwards them to Imuachain chain, or sends requests to the client chains. Therefore, the communication between `ImuachainGateway` and `ClientChainGateway`s is 1:N. ## Ordered Message Execution -Both `ClientChainGateway` and `ExocoreGateway` ensure ordered message execution for requests and responses using a message nonce mechanism: +Both `ClientChainGateway` and `ImuachainGateway` ensure ordered message execution for requests and responses using a message nonce mechanism: 1. The first message sent by the sender contract has a nonce of 1, and each subsequent message has a unique nonce. 2. After successfully sending a message, the sender contract increments the nonce by 1. @@ -19,7 +19,7 @@ This nonce management is specific to each client chain and `ClientChainGateway`, ## Blocking Message Execution -Both `ClientChainGateway` and `ExocoreGateway` handle messages in a blocking manner. This ensures that the receiver contract does not process the next message until the current one is successfully executed. Specifically, if the relayer forwards a message to the receiver contract and the contract fails to execute the message, the message is not stored and the nonce is not incremented, preventing the message with the next expected nonce from being received. +Both `ClientChainGateway` and `ImuachainGateway` handle messages in a blocking manner. This ensures that the receiver contract does not process the next message until the current one is successfully executed. Specifically, if the relayer forwards a message to the receiver contract and the contract fails to execute the message, the message is not stored and the nonce is not incremented, preventing the message with the next expected nonce from being received. ## Request-Response diff --git a/docs/delegate.drawio.svg b/docs/delegate.drawio.svg index e1ceda50..3f2eca2e 100644 --- a/docs/delegate.drawio.svg +++ b/docs/delegate.drawio.svg @@ -8,13 +8,13 @@
- ExocoreGateway + ImuachainGateway
- ExocoreGateway + ImuachainGateway @@ -78,13 +78,13 @@
- Exocore-Base + Imuachain-Base
- Exocore-Base + Imuachain-Base diff --git a/docs/delegate.svg b/docs/delegate.svg index e0d9f44f..64c01d70 100644 --- a/docs/delegate.svg +++ b/docs/delegate.svg @@ -1 +1 @@ -
ExocoreGateway
ExocoreGateway
2. handleDelegation
2. handleDelegation
Controller
Controller
3. emit DelegationRequest
3. emit DelegationRequest
Exocore-Base
Exocore-Base
1. delegateTo
1. delegateTo
Actor
Actor
Text is not SVG - cannot display
\ No newline at end of file +
ImuachainGateway
ImuachainGateway
2. handleDelegation
2. handleDelegation
Controller
Controller
3. emit DelegationRequest
3. emit DelegationRequest
Imuachain-Base
Imuachain-Base
1. delegateTo
1. delegateTo
Actor
Actor
Text is not SVG - cannot display
\ No newline at end of file diff --git a/docs/deposit.drawio.svg b/docs/deposit.drawio.svg index 4b3b7929..378cc2c8 100644 --- a/docs/deposit.drawio.svg +++ b/docs/deposit.drawio.svg @@ -8,13 +8,13 @@
- ExocoreGateway + ImuachainGateway
- ExocoreGateway + ImuachainGateway @@ -115,13 +115,13 @@
- Exocore-Base + Imuachain-Base
- Exocore-Base + Imuachain-Base diff --git a/docs/deposit.svg b/docs/deposit.svg index 3cdc9da5..202b1130 100644 --- a/docs/deposit.svg +++ b/docs/deposit.svg @@ -1 +1 @@ -
ExocoreGateway
ExocoreGateway
3. safeTransferFrom
3. safeTransferFrom
4. handleLSTTransfer
4. handleLSTTransfer
Controller
Controller
Vault
Vault
5. emit LSTTransfer
5. emit LSTTransfer
Exocore-Base
Exocore-Base
1. deposit
1. deposit
Actor
Actor
IERC20
IERC20
2. depositRequest
2. depositRequest
Text is not SVG - cannot display
\ No newline at end of file +
ImuachainGateway
ImuachainGateway
3. safeTransferFrom
3. safeTransferFrom
4. handleLSTTransfer
4. handleLSTTransfer
Controller
Controller
Vault
Vault
5. emit LSTTransfer
5. emit LSTTransfer
Imuachain-Base
Imuachain-Base
1. deposit
1. deposit
Actor
Actor
IERC20
IERC20
2. depositRequest
2. depositRequest
Text is not SVG - cannot display
\ No newline at end of file diff --git a/docs/lst-flow.svg b/docs/lst-flow.svg index 1bfb7ec3..8691546a 100644 --- a/docs/lst-flow.svg +++ b/docs/lst-flow.svg @@ -1 +1 @@ -UserUserLSTRestakingControllerLSTRestakingControllerBaseRestakingControllerBaseRestakingControllerExocoreGatewayExocoreGatewayClientChainGatewayClientChainGatewaydeposit(address token, uint256 amount)withdrawPrincipleFromExocore(address token, uint256 principleAmount)withdrawRewardFromExocore(address token, uint256 rewardAmount)_processRequest(token, msg.sender, amount, Action.REQUEST_DEPOSIT, "")_processRequest(token, msg.sender, principleAmount, Action.REQUEST_WITHDRAW_PRINCIPLE_FROM_EXOCORE, "")_processRequest(token, msg.sender, rewardAmount, Action.REQUEST_WITHDRAW_REWARD_FROM_EXOCORE, "")_sendMsgToExocore(action, actionArgs)_lzReceive(Origin calldata _origin, bytes calldata payload)requestDeposit(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestWithdrawPrinciple(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestWithdrawReward(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestDelegateTo(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestUndelegateFrom(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)_sendInterchainMsg(srcChainId, Action act, bytes memory actionArgs)_lzReceive(Origin calldata _origin, bytes calldata payload)nextNonce(uint32 srcEid, bytes32 sender)_verifyAndUpdateNonce(uint32 srcEid, bytes32 sender, uint64 nonce)afterReceiveDepositResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveWithdrawPrincipleResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveWithdrawRewardResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveDelegateResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveUndelegateResponse(bytes memory requestPayload, bytes calldata responsePayload) \ No newline at end of file +UserUserLSTRestakingControllerLSTRestakingControllerBaseRestakingControllerBaseRestakingControllerImuachainGatewayImuachainGatewayClientChainGatewayClientChainGatewaydeposit(address token, uint256 amount)withdrawPrincipleFromImuachain(address token, uint256 principleAmount)withdrawPrincipleFromImuachain(address token, uint256 rewardAmount)_processRequest(token, msg.sender, amount, Action.REQUEST_DEPOSIT, "")_processRequest(token, msg.sender, principleAmount, Action.REQUEST_WITHDRAW_PRINCIPLE_FROM_IMUACHAIN, "")_processRequest(token, msg.sender, rewardAmount, Action.REQUEST_WITHDRAW_REWARD_FROM_IMUACHAIN, "")_sendMsgToImuachain(action, actionArgs)_lzReceive(Origin calldata _origin, bytes calldata payload)requestDeposit(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestWithdrawPrinciple(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestWithdrawReward(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestDelegateTo(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)requestUndelegateFrom(uint32 srcChainId, uint64 lzNonce, bytes calldata payload)_sendInterchainMsg(srcChainId, Action act, bytes memory actionArgs)_lzReceive(Origin calldata _origin, bytes calldata payload)nextNonce(uint32 srcEid, bytes32 sender)_verifyAndUpdateNonce(uint32 srcEid, bytes32 sender, uint64 nonce)afterReceiveDepositResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveWithdrawPrincipleResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveWithdrawRewardResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveDelegateResponse(bytes memory requestPayload, bytes calldata responsePayload)afterReceiveUndelegateResponse(bytes memory requestPayload, bytes calldata responsePayload) \ No newline at end of file diff --git a/docs/native_deposit_workflow.wsd b/docs/native_deposit_workflow.wsd index 027bbebc..3fce96dc 100644 --- a/docs/native_deposit_workflow.wsd +++ b/docs/native_deposit_workflow.wsd @@ -5,10 +5,10 @@ actor User participant NativeStakingController participant ETHPOS participant ClientChainLzReceiver -participant ExoCapsule +participant ImuaCapsule participant ClientChainL0Endpoint -participant ExocoreL0Endpoint -participant ExocoreGateway +participant ImuachainL0Endpoint +participant ImuachainGateway participant DepositPrecompile participant DepositNativeModule @@ -22,31 +22,31 @@ deactivate NativeStakingController User -> NativeStakingController: 2.1:verifyAndDepositNativeStake(validatorContainer, proof) activate NativeStakingController -NativeStakingController -> ExoCapsule: 2.2:verifyDepositProof(validatorContainer, proof) -activate ExoCapsule -ExoCapsule -> NativeStakingController: 2.3:return (isValidValidatorContainer) -deactivate ExoCapsule +NativeStakingController -> ImuaCapsule: 2.2:verifyDepositProof(validatorContainer, proof) +activate ImuaCapsule +ImuaCapsule -> NativeStakingController: 2.3:return (isValidValidatorContainer) +deactivate ImuaCapsule NativeStakingController -> ClientChainL0Endpoint: 2.4:send(request) activate ClientChainL0Endpoint ClientChainL0Endpoint -> NativeStakingController: 2.5:emit (requestSent) deactivate ClientChainL0Endpoint deactivate NativeStakingController -ClientChainL0Endpoint -> ExocoreL0Endpoint: 3.1:lzReceive(request) -activate ExocoreL0Endpoint -ExocoreL0Endpoint -> ExocoreGateway: 3.2:lzReceive(request) -activate ExocoreGateway -ExocoreGateway -> ExocoreGateway: 3.3:handleNSTTransfer(payload) -ExocoreGateway -> DepositPrecompile: 3.4:depositNST(payload) +ClientChainL0Endpoint -> ImuachainL0Endpoint: 3.1:lzReceive(request) +activate ImuachainL0Endpoint +ImuachainL0Endpoint -> ImuachainGateway: 3.2:lzReceive(request) +activate ImuachainGateway +ImuachainGateway -> ImuachainGateway: 3.3:handleNSTTransfer(payload) +ImuachainGateway -> DepositPrecompile: 3.4:depositNST(payload) activate DepositPrecompile DepositPrecompile -> DepositNativeModule: 3.5:depositTo(payload) activate DepositNativeModule DepositNativeModule -> DepositPrecompile: 3.6:return (result, balance) deactivate DepositNativeModule -DepositPrecompile -> ExocoreGateway: 3.7:return (result, balance) +DepositPrecompile -> ImuachainGateway: 3.7:return (result, balance) deactivate DepositPrecompile -ExocoreGateway -> ExocoreGateway: 3.9:emit (NSTTransfer) -deactivate ExocoreGateway -deactivate ExocoreL0Endpoint +ImuachainGateway -> ImuachainGateway: 3.9:emit (NSTTransfer) +deactivate ImuachainGateway +deactivate ImuachainL0Endpoint @enduml @@ -66,7 +66,7 @@ endif fork :Check if caller is gateway; if (msg.sender != gateway) then (no) - :Revert with "ExoCapsule: only client chain gateway could call this function"; + :Revert with "ImuaCapsule: only client chain gateway could call this function"; stop endif @@ -107,7 +107,7 @@ fork again :Store the request details in registeredRequests and registeredRequestActions; :Encode the request action arguments; -:Send the request action to Exocore using _sendMsgToExocore(); +:Send the request action to Imuachain using _sendMsgToImuachain(); stop diff --git a/docs/reward-vault.md b/docs/reward-vault.md index 6d0177bb..27e06570 100644 --- a/docs/reward-vault.md +++ b/docs/reward-vault.md @@ -2,7 +2,7 @@ ## 1. Overview -The Reward Vault is a crucial component of the Exocore ecosystem, designed to securely custody reward tokens distributed by the Exocore chain. It supports permissionless reward token deposits on behalf of AVS (Actively Validated Service) providers and allows stakers to claim their rewards after verification by the Exocore chain. The Reward Vault is managed by the Gateway contract, which acts as an intermediary for all operations. +The Reward Vault is a crucial component of IMUA, designed to securely custody reward tokens distributed by Imuachain. It supports permissionless reward token deposits on behalf of AVS (Actively Validated Service) providers and allows stakers to claim their rewards after verification by Imuachain. The Reward Vault is managed by the Gateway contract, which acts as an intermediary for all operations. The Reward Vault is implemented using the beacon proxy pattern for upgradeability, and a single instance of the Reward Vault is deployed when the ClientChainGateway is initialized. @@ -12,7 +12,7 @@ The Reward Vault is implemented using the beacon proxy pattern for upgradeabilit - The Reward Vault should handle standard ERC20 tokens without requiring prior whitelisting or governance approval. - Depositors should be able to deposit rewards in any standard ERC20 token on behalf of AVS providers without restrictions. -2.2. Exocore Chain as Source of Truth: The Exocore chain maintains the record of reward balances and handles reward distribution/accounting for each staker. The Reward Vault only tracks withdrawable balances after claim approval. +2.2. Imuachain as Source of Truth: Imuachain maintains the record of reward balances and handles reward distribution/accounting for each staker. The Reward Vault only tracks withdrawable balances after claim approval. 2.3. Separation of Concerns: The Reward Vault is distinct from principal vaults, maintaining a clear separation between staked principals and earned rewards. @@ -28,7 +28,7 @@ The Reward Vault is implemented using the beacon proxy pattern for upgradeabilit Key Functions: - `deposit(address token, address avs, uint256 amount)`: Allows the Gateway to deposit reward tokens on behalf of an AVS. Increases the total deposited rewards for the specified token and AVS. -- `unlockReward(address token, address staker, uint256 amount)`: Allows the Gateway to unlock rewards for a staker after claim approval from the Exocore chain. +- `unlockReward(address token, address staker, uint256 amount)`: Allows the Gateway to unlock rewards for a staker after claim approval from Imuachain. - `withdraw(address token, address withdrawer, address recipient, uint256 amount)`: Allows the Gateway to withdraw claimed rewards for a staker. - `getWithdrawableBalance(address token, address staker)`: Returns the withdrawable balance of a specific reward token for a staker. - `getTotalDepositedRewards(address token, address avs)`: Returns the total deposited rewards of a specific token for an AVS. @@ -41,7 +41,7 @@ Implementation: New Functions: - `submitReward(address token, uint256 amount, address avs)`: Receives reward submissions and calls RewardVault's `deposit`. -- `claimRewardFromExocore(address token, uint256 amount)`: Initiates a claim request to the Exocore chain. +- `claimRewardFromImuachain(address token, uint256 amount)`: Initiates a claim request to Imuachain. - `withdrawReward(address token, address recipient, uint256 amount)`: Calls RewardVault's `withdraw` to transfer claimed rewards to the staker. Additional Responsibility: @@ -121,19 +121,19 @@ contract RewardVaultProxy { a. Transfers the specified amount of tokens from the depositor to itself. b. Increases the total deposited rewards for the specified token and AVS in the `totalDepositedRewards` mapping. c. Emits a `RewardDeposited` event. -3. Gateway sends a message to the Exocore chain to account for the deposited rewards. -4. Exocore chain processes the request and emits a `RewardOperationResult` event to indicate the result of the submission. +3. Gateway sends a message to Imuachain to account for the deposited rewards. +4. Imuachain processes the request and emits a `RewardOperationResult` event to indicate the result of the submission. ### 4.2. Reward Distribution and Accounting -1. Exocore chain handles the distribution and accounting of rewards to stakers based on their staking activities and the rewards submitted. -2. Exocore chain maintains the record of each staker's earned rewards. +1. Imuachain handles the distribution and accounting of rewards to stakers based on their staking activities and the rewards submitted. +2. Imuachain maintains the record of each staker's earned rewards. ### 4.3. Reward Claiming and Withdrawal -1. Staker calls `claimRewardFromExocore` on the Gateway. -2. Gateway sends a claim request to the Exocore chain. -3. Exocore chain verifies the request and sends a response back to the Gateway, emitting a `RewardOperation` event. +1. Staker calls `claimRewardFromImuachain` on the Gateway. +2. Gateway sends a claim request to Imuachain. +3. Imuachain verifies the request and sends a response back to the Gateway, emitting a `RewardOperation` event. 4. If the claim is approved, Gateway calls RewardVault's `unlockReward`, which: a. Increases the staker's withdrawable balance for the specified token. b. Emits a `RewardUnlocked` event. @@ -148,7 +148,7 @@ contract RewardVaultProxy { 5.1. Access Control: - Only the Gateway should be able to call RewardVault's functions. - Any address should be able to call `ClientChainGateway.submitReward`. -- Only stakers should be able to call `ClientChainGateway.claimRewardFromExocore` for their own rewards. +- Only stakers should be able to call `ClientChainGateway.claimRewardFromImuachain` for their own rewards. 5.2. Token Compatibility: While the system is permissionless, it is designed to work with standard ERC20 tokens to ensure consistent behavior and accounting. diff --git a/docs/summary.md b/docs/summary.md index 22ca9a55..4e560460 100644 --- a/docs/summary.md +++ b/docs/summary.md @@ -2,23 +2,23 @@ ### Bootstrap The Bootstrap smart contract is designed to manage token whitelisting, operator registration, deposits, and withdrawals. It ensures that operations are locked during specific periods (before mainnet/testnet launch) for security. This contract is independent and upgrades itself to ClientChainGateway after the mainnet/testnet launch. -### ExocoreGateway -The ExocoreGateway contract handles cross-chain messaging and interactions with the Exocore chain. This contract provides functionalities such as deposits, delegations, undelegations, and the withdrawal of principal and rewards. It facilitates cross-chain communication through the LayerZero protocol. +### ImuachainGateway +The ImuachainGateway contract handles cross-chain messaging and interactions with Imuachain. This contract provides functionalities such as deposits, delegations, undelegations, and the withdrawal of principal and rewards. It facilitates cross-chain communication through the LayerZero protocol. ### ClientChainGateway -The ClientChainGateway contract acts as a cross-chain gateway, transmitting information and commands between the Exocore core layer and the client chain. It verifies and executes signed commands such as deposits, withdrawals, and delegation, manages whitelisted assets and their Vault deployments, allows stakers to interact with the core layer through events, and provides emergency pause and resume functions to ensure system stability. +The ClientChainGateway contract acts as a cross-chain gateway, transmitting information and commands between Imuachain's core layer and the client chain. It verifies and executes signed commands such as deposits, withdrawals, and delegation, manages whitelisted assets and their Vault deployments, allows stakers to interact with the core layer through events, and provides emergency pause and resume functions to ensure system stability. ### BaseRestakingController -The BaseRestakingController contract is an abstract contract. It primarily handles the fundamental logic related to restaking, including declarations, delegations, undelegations, and messaging with the Exocore chain. +The BaseRestakingController contract is an abstract contract. It primarily handles the fundamental logic related to restaking, including declarations, delegations, undelegations, and messaging with Imuachain. ### LSTRestakingController -The LSTRestakingController contract an abstract contract, which provides functionalities for users to deposit tokens, withdraw principal from Exocore, and withdraw rewards from Exocore. It primarily handles operations related to Liquid Staking Tokens (LST). +The LSTRestakingController contract an abstract contract, which provides functionalities for users to deposit tokens, withdraw principal from Imuachain, and withdraw rewards from Imuachain. It primarily handles operations related to Liquid Staking Tokens (LST). ### NativeRestakingController -The NativeRestakingController contract is an abstract contract, which primarily handles the logic for native Ethereum restaking. It includes functionalities such as staking, creating ExoCapsule contracts, and managing deposits and partial/full withdrawals for Beacon Chain validators. +The NativeRestakingController contract is an abstract contract, which primarily handles the logic for native Ethereum restaking. It includes functionalities such as staking, creating Imuaapsule contracts, and managing deposits and partial/full withdrawals for Beacon Chain validators. ### Vault The Vault smart contract manages deposits, withdrawals, and balance updates for users interacting with the system. It ensures secure handling of ERC20 tokens and implements business logic to maintain accurate records of user balances, including principal and reward amounts. -### ExoCapsule -The ExoCapsule contract is designed to handle specific operations related to native Ethereum restaking tokens. It provides functionalities for depositing and withdrawing these tokens, ensuring secure and efficient management of virtual staked assets. +### ImuaCapsule +The ImuaCapsule contract is designed to handle specific operations related to native Ethereum restaking tokens. It provides functionalities for depositing and withdrawing these tokens, ensuring secure and efficient management of virtual staked assets. diff --git a/docs/withdraw.drawio.svg b/docs/withdraw.drawio.svg index c519e019..5f474219 100644 --- a/docs/withdraw.drawio.svg +++ b/docs/withdraw.drawio.svg @@ -115,13 +115,13 @@
- Exocore-Base + Imuachain-Base
- Exocore-Base + Imuachain-Base diff --git a/docs/withdraw.svg b/docs/withdraw.svg index c0a97c39..2c80592c 100644 --- a/docs/withdraw.svg +++ b/docs/withdraw.svg @@ -1 +1 @@ -
4.isSuccess
4.isSuccess
Gateway
Gateway
2. handleLSTTransfer
2. handleLSTTransfer
Controller
Controller
Vault
Vault
3. grantWithdraw
3. grantWithdraw
Exocore-Base
Exocore-Base
1. withdraw
1. withdraw
Actor
Actor
5. updateWithdrawableBalance
5. updateWithdrawableBalance
Text is not SVG - cannot display
\ No newline at end of file +
4.isSuccess
4.isSuccess
Gateway
Gateway
2. handleLSTTransfer
2. handleLSTTransfer
Controller
Controller
Vault
Vault
3. grantWithdraw
3. grantWithdraw
Imuachain-Base
Imuachain-Base
1. withdraw
1. withdraw
Actor
Actor
5. updateWithdrawableBalance
5. updateWithdrawableBalance
Text is not SVG - cannot display
\ No newline at end of file diff --git a/foundry.toml b/foundry.toml index 8340ac31..16df69d2 100644 --- a/foundry.toml +++ b/foundry.toml @@ -17,12 +17,15 @@ deny_warnings = true optimizer = true optimizer_runs = 200 solc = "0.8.28" +libraries = ["src/libraries/NetworkConstants.sol:NetworkConstants:0xf718DcEC914835d47a5e428A5397BF2F7276808b"] [profile.test] # for tests, use the Eth mainnet chain_id for NetworkConstants to work. # do not specify this in the default profile to pacify forge script # running on non-Eth mainnet chains. chain_id = 1 +# clear the libraries to avoid errors in tests +libraries = [] [fmt] number_underscore = "thousands" @@ -37,13 +40,13 @@ contract_new_lines = true # mechanism to specify the chain name via command line; for example: # cast balance $ADDRESS --rpc-url client client = "${CLIENT_CHAIN_RPC}" -exocore_local = "${EXOCORE_LOCAL_RPC}" -exocore_testnet = "${EXOCORE_TESTNET_RPC}" +imuachain_localnet = "${IMUACHAIN_LOCALNET_RPC}" +imuachain_testnet = "${IMUACHAIN_TESTNET_RPC}" [etherscan] # Similar shortcut as `rpc_endpoints` to verify contracts by name and not URL. # Example: -# forge verify-contract --etherscan-api-key exocore_testnet <...usual args...> +# forge verify-contract --etherscan-api-key imuachain_testnet <...usual args...> # However, defining this section with these env vars makes `forge test` complain # if they are missing. It is because it tries to fetch debugging context from # the block explorer. To avoid this, either ensure these vars are set, or comment @@ -51,6 +54,6 @@ exocore_testnet = "${EXOCORE_TESTNET_RPC}" mainnet = { key = "${ETHERSCAN_API_KEY}" } sepolia = { key = "${ETHERSCAN_API_KEY}" } holesky = { key = "${ETHERSCAN_API_KEY}" } -exocore_testnet = { key = "${ETHERSCAN_API_KEY}", chain = 233, url = "${EXOCORE_TESTNET_EXPLORER_API}" } +imuachain_testnet = { key = "${ETHERSCAN_API_KEY}", chain = 233, url = "${IMUACHAIN_TESTNET_EXPLORER_API}" } # See more config options https://github.com/foundry-rs/foundry/blob/master/crates/config/README.md#all-options diff --git a/hardhat.config.js b/hardhat.config.js index 39082785..4d0c7ea2 100644 --- a/hardhat.config.js +++ b/hardhat.config.js @@ -17,11 +17,11 @@ module.exports = { networks: { hardhat: { }, - exocore_localnet: { + imuachain_localnet: { url: "http://127.0.0.1:8545", chainId: 232, accounts: [ - process.env.LOCAL_EXOCORE_FUNDED_ACCOUNT_PRIVATE_KEY, + process.env.LOCAL_IMUACHAIN_FUNDED_ACCOUNT_PRIVATE_KEY, process.env.TEST_ACCOUNT_ONE_PRIVATE_KEY, process.env.TEST_ACCOUNT_TWO_PRIVATE_KEY, process.env.TEST_ACCOUNT_THREE_PRIVATE_KEY, diff --git a/lib/create3-factory b/lib/create3-factory index 6b834ad6..e359aacb 160000 --- a/lib/create3-factory +++ b/lib/create3-factory @@ -1 +1 @@ -Subproject commit 6b834ad617902314521684e40e2f1ad73eb7ed13 +Subproject commit e359aacbee68e9d66bfec274c868e9751ae08442 diff --git a/package-lock.json b/package-lock.json index 56ffbb86..bd4dfa98 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,11 +1,11 @@ { - "name": "exocore-contracts", + "name": "imua-contracts", "version": "1.0.0", "lockfileVersion": 3, "requires": true, "packages": { "": { - "name": "exocore-contracts", + "name": "imua-contracts", "version": "1.0.0", "license": "ISC", "dependencies": { diff --git a/package.json b/package.json index b0b1066f..2c1a917a 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { - "name": "exocore-contracts", + "name": "imua-contracts", "version": "1.0.0", - "description": "The Exocore contracts repository contains a set of smart contracts deployed on both Exocore and the target client chains, which facilitate assets deposit and withdrawal, cross-chain communication, and restaking operations for native assets and liquid staking tokens (LSTs), ensuring secure interactions and efficient management of restaked assets.", + "description": "The imua-contracts repository contains a set of smart contracts deployed on both Imuachain and the target client chains, which facilitate assets deposit and withdrawal, cross-chain communication, and restaking operations for native assets and liquid staking tokens (LSTs), ensuring secure interactions and efficient management of restaked assets.", "main": "hardhat.config.js", "directories": { "doc": "docs", @@ -10,7 +10,7 @@ }, "scripts": { "test": "hardhat test", - "deploy:utxogateway": "hardhat run script/hardhat/deploy-and-setup-utxogateway.script.js --network exocore_localnet" + "deploy:utxogateway": "hardhat run script/hardhat/deploy-and-setup-utxogateway.script.js --network imuachain_localnet" }, "keywords": [], "author": "", diff --git a/script/10_DeployExocoreGatewayOnly.s.sol b/script/10_DeployExocoreGatewayOnly.s.sol deleted file mode 100644 index cdd43fdd..00000000 --- a/script/10_DeployExocoreGatewayOnly.s.sol +++ /dev/null @@ -1,61 +0,0 @@ -pragma solidity ^0.8.19; - -import {ILayerZeroEndpointV2} from "@layerzerolabs/lz-evm-protocol-v2/contracts/interfaces/ILayerZeroEndpointV2.sol"; - -import {ProxyAdmin} from "@openzeppelin/contracts/proxy/transparent/ProxyAdmin.sol"; -import {TransparentUpgradeableProxy} from "@openzeppelin/contracts/proxy/transparent/TransparentUpgradeableProxy.sol"; - -import {ExocoreGateway} from "../src/core/ExocoreGateway.sol"; - -import {BaseScript} from "./BaseScript.sol"; -import "forge-std/Script.sol"; - -contract DeployExocoreGatewayOnly is BaseScript { - - function setUp() public virtual override { - // load keys - super.setUp(); - // load contracts - string memory prerequisites = vm.readFile("script/deployments/prerequisiteContracts.json"); - exocoreLzEndpoint = ILayerZeroEndpointV2(stdJson.readAddress(prerequisites, ".exocore.lzEndpoint")); - require(address(exocoreLzEndpoint) != address(0), "exocore l0 endpoint should not be empty"); - // fork - exocore = vm.createSelectFork(exocoreRPCURL); - } - - function run() public { - vm.selectFork(exocore); - vm.startBroadcast(deployer.privateKey); - - ProxyAdmin exocoreProxyAdmin = new ProxyAdmin(); - ExocoreGateway exocoreGatewayLogic = new ExocoreGateway(address(exocoreLzEndpoint)); - exocoreGateway = ExocoreGateway( - payable( - address( - new TransparentUpgradeableProxy( - address(exocoreGatewayLogic), - address(exocoreProxyAdmin), - abi.encodeWithSelector( - exocoreGatewayLogic.initialize.selector, payable(exocoreValidatorSet.addr) - ) - ) - ) - ) - ); - - vm.stopBroadcast(); - - string memory exocoreContracts = "exocoreContracts"; - vm.serializeAddress(exocoreContracts, "lzEndpoint", address(exocoreLzEndpoint)); - vm.serializeAddress(exocoreContracts, "exocoreGatewayLogic", address(exocoreGatewayLogic)); - vm.serializeAddress(exocoreContracts, "exocoreProxyAdmin", address(exocoreProxyAdmin)); - string memory exocoreContractsOutput = - vm.serializeAddress(exocoreContracts, "exocoreGateway", address(exocoreGateway)); - - string memory deployedContracts = "deployedContracts"; - string memory finalJson = vm.serializeString(deployedContracts, "exocore", exocoreContractsOutput); - - vm.writeJson(finalJson, "script/deployments/deployedExocoreGatewayOnly.json"); - } - -} diff --git a/script/10_DeployImuachainGatewayOnly.s.sol b/script/10_DeployImuachainGatewayOnly.s.sol new file mode 100644 index 00000000..a7005015 --- /dev/null +++ b/script/10_DeployImuachainGatewayOnly.s.sol @@ -0,0 +1,62 @@ +pragma solidity ^0.8.19; + +import {ILayerZeroEndpointV2} from "@layerzerolabs/lz-evm-protocol-v2/contracts/interfaces/ILayerZeroEndpointV2.sol"; + +import {ProxyAdmin} from "@openzeppelin/contracts/proxy/transparent/ProxyAdmin.sol"; +import {TransparentUpgradeableProxy} from "@openzeppelin/contracts/proxy/transparent/TransparentUpgradeableProxy.sol"; + +import {ImuachainGateway} from "../src/core/ImuachainGateway.sol"; + +import {BaseScript} from "./BaseScript.sol"; +import "forge-std/Script.sol"; + +import {CREATE3_FACTORY} from "../lib/create3-factory/src/ICREATE3Factory.sol"; + +contract DeployImuachainGatewayOnly is BaseScript { + + bytes32 salt; + + function setUp() public virtual override { + // load keys + super.setUp(); + // load contracts + string memory prerequisites = vm.readFile("script/deployments/prerequisiteContracts.json"); + imuachainLzEndpoint = ILayerZeroEndpointV2(stdJson.readAddress(prerequisites, ".imuachain.lzEndpoint")); + require(address(imuachainLzEndpoint) != address(0), "imuachain l0 endpoint should not be empty"); + // fork + imuachain = vm.createSelectFork(imuachainRPCURL); + salt = keccak256(abi.encodePacked("imuachaintestnet_233-8")); + } + + function run() public { + vm.selectFork(imuachain); + // use the owner so that it owns the ProxyAdmin + vm.startBroadcast(owner.privateKey); + ProxyAdmin imuachainProxyAdmin = new ProxyAdmin(); + ImuachainGateway imuachainGatewayLogic = new ImuachainGateway(address(imuachainLzEndpoint)); + + bytes memory initialization = + abi.encodeWithSelector(imuachainGatewayLogic.initialize.selector, payable(owner.addr)); + + bytes memory creationCode = abi.encodePacked( + type(TransparentUpgradeableProxy).creationCode, + abi.encode(address(imuachainGatewayLogic), address(imuachainProxyAdmin), initialization) + ); + ImuachainGateway imuachainGateway = ImuachainGateway(payable(CREATE3_FACTORY.deploy(salt, creationCode))); + + vm.stopBroadcast(); + + string memory imuachainContracts = "imuachainContracts"; + vm.serializeAddress(imuachainContracts, "lzEndpoint", address(imuachainLzEndpoint)); + vm.serializeAddress(imuachainContracts, "imuachainGatewayLogic", address(imuachainGatewayLogic)); + vm.serializeAddress(imuachainContracts, "imuachainProxyAdmin", address(imuachainProxyAdmin)); + string memory imuachainContractsOutput = + vm.serializeAddress(imuachainContracts, "imuachainGateway", address(imuachainGateway)); + + string memory deployedContracts = "deployedContracts"; + string memory finalJson = vm.serializeString(deployedContracts, "imuachain", imuachainContractsOutput); + + vm.writeJson(finalJson, "script/deployments/deployedImuachainGatewayOnly.json"); + } + +} diff --git a/script/11_SetPeers.s.sol b/script/11_SetPeers.s.sol index 0b25bbf9..7ae50fff 100644 --- a/script/11_SetPeers.s.sol +++ b/script/11_SetPeers.s.sol @@ -1,7 +1,7 @@ pragma solidity ^0.8.19; import {Bootstrap} from "../src/core/Bootstrap.sol"; -import {ExocoreGateway} from "../src/core/ExocoreGateway.sol"; +import {ImuachainGateway} from "../src/core/ImuachainGateway.sol"; import {Action, GatewayStorage} from "../src/storage/GatewayStorage.sol"; import {BaseScript} from "./BaseScript.sol"; @@ -14,7 +14,7 @@ contract SetPeersAndUpgrade is BaseScript { using AddressCast for address; address bootstrapAddr; - address exocoreGatewayAddr; + address imuachainGatewayAddr; function setUp() public virtual override { // load keys @@ -23,36 +23,36 @@ contract SetPeersAndUpgrade is BaseScript { string memory deployed = vm.readFile("script/deployments/deployedBootstrapOnly.json"); bootstrapAddr = stdJson.readAddress(deployed, ".clientChain.bootstrap"); require(address(bootstrapAddr) != address(0), "bootstrap address should not be empty"); - deployed = vm.readFile("script/deployedExocoreGatewayOnly.json"); - exocoreGatewayAddr = stdJson.readAddress(deployed, ".exocore.exocoreGateway"); - require(address(exocoreGatewayAddr) != address(0), "exocore gateway address should not be empty"); + deployed = vm.readFile("script/deployments/deployedImuachainGatewayOnly.json"); + imuachainGatewayAddr = stdJson.readAddress(deployed, ".imuachain.imuachainGateway"); + require(address(imuachainGatewayAddr) != address(0), "imuachain gateway address should not be empty"); // forks - exocore = vm.createSelectFork(exocoreRPCURL); + imuachain = vm.createSelectFork(imuachainRPCURL); clientChain = vm.createSelectFork(clientChainRPCURL); } function run() public { - ExocoreGateway gateway = ExocoreGateway(payable(exocoreGatewayAddr)); + ImuachainGateway gateway = ImuachainGateway(payable(imuachainGatewayAddr)); - vm.selectFork(exocore); - if (!useExocorePrecompileMock) { + vm.selectFork(imuachain); + if (!useImuachainPrecompileMock) { _bindPrecompileMocks(); } - vm.startBroadcast(exocoreValidatorSet.privateKey); + vm.startBroadcast(owner.privateKey); gateway.setPeer(clientChainId, bootstrapAddr.toBytes32()); vm.stopBroadcast(); Bootstrap bootstrap = Bootstrap(payable(bootstrapAddr)); vm.selectFork(clientChain); - vm.startBroadcast(exocoreValidatorSet.privateKey); - bootstrap.setPeer(exocoreChainId, address(exocoreGatewayAddr).toBytes32()); + vm.startBroadcast(owner.privateKey); + bootstrap.setPeer(imuachainChainId, address(imuachainGatewayAddr).toBytes32()); vm.stopBroadcast(); - vm.selectFork(exocore); - vm.startBroadcast(exocoreValidatorSet.privateKey); - uint256 nativeFee = exocoreGateway.quote(clientChainId, abi.encodePacked(Action.REQUEST_MARK_BOOTSTRAP, "")); - exocoreGateway.markBootstrap{value: nativeFee}(clientChainId); + vm.selectFork(imuachain); + vm.startBroadcast(owner.privateKey); + uint256 nativeFee = imuachainGateway.quote(clientChainId, abi.encodePacked(Action.REQUEST_MARK_BOOTSTRAP, "")); + imuachainGateway.markBootstrap{value: nativeFee}(clientChainId); } } diff --git a/script/12_RedeployClientChainGateway.s.sol b/script/12_RedeployClientChainGateway.s.sol index c6541382..2f0d2ade 100644 --- a/script/12_RedeployClientChainGateway.s.sol +++ b/script/12_RedeployClientChainGateway.s.sol @@ -8,7 +8,7 @@ import {Bootstrap} from "../src/core/Bootstrap.sol"; import {ClientChainGateway} from "../src/core/ClientChainGateway.sol"; import {BootstrapStorage} from "../src/storage/BootstrapStorage.sol"; -import "../src/core/ExoCapsule.sol"; +import {ImuaCapsule} from "../src/core/ImuaCapsule.sol"; import {RewardVault} from "../src/core/RewardVault.sol"; import {Vault} from "../src/core/Vault.sol"; @@ -56,14 +56,14 @@ contract RedeployClientChainGateway is BaseScript { function run() public { vm.selectFork(clientChain); - vm.startBroadcast(exocoreValidatorSet.privateKey); + vm.startBroadcast(owner.privateKey); // Create ImmutableConfig struct BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(beaconOracle), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -73,8 +73,7 @@ contract RedeployClientChainGateway is BaseScript { new ClientChainGateway(address(clientChainLzEndpoint), config, address(rewardVaultBeacon)); // then the client chain initialization - bytes memory initialization = - abi.encodeWithSelector(clientGatewayLogic.initialize.selector, exocoreValidatorSet.addr); + bytes memory initialization = abi.encodeWithSelector(clientGatewayLogic.initialize.selector, owner.addr); bootstrap.setClientChainGatewayLogic(address(clientGatewayLogic), initialization); vm.stopBroadcast(); diff --git a/script/13_DepositValidator.s.sol b/script/13_DepositValidator.s.sol index 9cfd35e2..bc8af019 100644 --- a/script/13_DepositValidator.s.sol +++ b/script/13_DepositValidator.s.sol @@ -1,9 +1,9 @@ pragma solidity ^0.8.19; -import "../src/core/ExoCapsule.sol"; -import "../src/interfaces/IClientChainGateway.sol"; -import "../src/interfaces/IExocoreGateway.sol"; -import "../src/interfaces/IVault.sol"; +import {ImuaCapsule} from "../src/core/ImuaCapsule.sol"; +import {IClientChainGateway} from "../src/interfaces/IClientChainGateway.sol"; +import {IImuachainGateway} from "../src/interfaces/IImuachainGateway.sol"; +import {IVault} from "../src/interfaces/IVault.sol"; import {Action, GatewayStorage} from "../src/storage/GatewayStorage.sol"; import "@beacon-oracle/contracts/src/EigenLayerBeaconOracle.sol"; @@ -49,14 +49,14 @@ contract DepositScript is BaseScript { _loadValidatorContainer(validatorInfo); _loadValidatorProof(validatorInfo); - // transfer some gas fee to depositor, relayer and exocore gateway + // transfer some gas fee to depositor, relayer and imuachain gateway clientChain = vm.createSelectFork(clientChainRPCURL); _topUpPlayer(clientChain, address(0), deployer, depositor.addr, 0.2 ether); - exocore = vm.createSelectFork(exocoreRPCURL); - _topUpPlayer(exocore, address(0), exocoreGenesis, address(exocoreGateway), 1 ether); + imuachain = vm.createSelectFork(imuachainRPCURL); + _topUpPlayer(imuachain, address(0), imuachainGenesis, address(imuachainGateway), 1 ether); - if (!useExocorePrecompileMock) { + if (!useImuachainPrecompileMock) { _bindPrecompileMocks(); } } diff --git a/script/14_CorrectBootstrapErrors.s.sol b/script/14_CorrectBootstrapErrors.s.sol index 1a8e3262..fc0ac171 100644 --- a/script/14_CorrectBootstrapErrors.s.sol +++ b/script/14_CorrectBootstrapErrors.s.sol @@ -10,7 +10,7 @@ import {Bootstrap} from "../src/core/Bootstrap.sol"; import {ClientChainGateway} from "../src/core/ClientChainGateway.sol"; import "../src/utils/BeaconProxyBytecode.sol"; -import "../src/core/ExoCapsule.sol"; +import {ImuaCapsule} from "../src/core/ImuaCapsule.sol"; import {Vault} from "../src/core/Vault.sol"; import {ICustomProxyAdmin} from "../src/interfaces/ICustomProxyAdmin.sol"; @@ -77,9 +77,9 @@ contract CorrectBootstrapErrors is BaseScript { require(address(beaconOracle) != address(0), "beacon oracle should not be empty"); capsuleBeacon = UpgradeableBeacon(stdJson.readAddress(deployed, ".clientChain.capsuleBeacon")); - require(address(capsuleBeacon) != address(0), "exo capsule beacon should not be empty"); + require(address(capsuleBeacon) != address(0), "imuacapsule beacon should not be empty"); - initialization = abi.encodeCall(ClientChainGateway.initialize, (payable(exocoreValidatorSet.addr))); + initialization = abi.encodeCall(ClientChainGateway.initialize, (payable(owner.addr))); } function run() public { @@ -87,15 +87,15 @@ contract CorrectBootstrapErrors is BaseScript { uint256[] memory emptyListUint; vm.selectFork(clientChain); - vm.startBroadcast(exocoreValidatorSet.privateKey); + vm.startBroadcast(owner.privateKey); ProxyAdmin proxyAdmin = ProxyAdmin(proxyAdmin); // Create ImmutableConfig struct BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(beaconOracle), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -105,7 +105,7 @@ contract CorrectBootstrapErrors is BaseScript { bytes memory data = abi.encodeCall( Bootstrap.initialize, ( - exocoreValidatorSet.addr, + owner.addr, // 1 week from now block.timestamp + 168 hours, 2 seconds, diff --git a/script/15_DeploySafeMulstisigWallet.s.sol b/script/15_DeploySafeMulstisigWallet.s.sol index e2127a17..f5f743c1 100644 --- a/script/15_DeploySafeMulstisigWallet.s.sol +++ b/script/15_DeploySafeMulstisigWallet.s.sol @@ -15,16 +15,16 @@ contract CreateMultisigScript is BaseScript { function setUp() public override { super.setUp(); - exocore = vm.createSelectFork(exocoreRPCURL); - _topUpPlayer(exocore, address(0), exocoreGenesis, deployer.addr, 2 ether); + imuachain = vm.createSelectFork(imuachainRPCURL); + _topUpPlayer(imuachain, address(0), imuachainGenesis, deployer.addr, 2 ether); } function run() public { - vm.selectFork(exocore); + vm.selectFork(imuachain); vm.startBroadcast(deployer.privateKey); // Read deployed Safe contracts from JSON file - string memory json = vm.readFile("script/deployments/safe_contracts_on_exocore.json"); + string memory json = vm.readFile("script/deployments/safe_contracts_on_imuachain.json"); address proxyFactoryAddress = json.readAddress(".GnosisSafeProxyFactory"); address safeSingletonAddress = json.readAddress(".GnosisSafeL2"); @@ -36,7 +36,7 @@ contract CreateMultisigScript is BaseScript { // Set up owners address[] memory owners = new address[](3); owners[0] = deployer.addr; - owners[1] = exocoreValidatorSet.addr; + owners[1] = owner.addr; owners[2] = relayer.addr; // Set up Safe parameters diff --git a/script/16_UpgradeExoCapsule.s.sol b/script/16_UpgradeImuaCapsule.s.sol similarity index 79% rename from script/16_UpgradeExoCapsule.s.sol rename to script/16_UpgradeImuaCapsule.s.sol index fe29c0fa..08cad08a 100644 --- a/script/16_UpgradeExoCapsule.s.sol +++ b/script/16_UpgradeImuaCapsule.s.sol @@ -1,11 +1,11 @@ pragma solidity ^0.8.19; -import "../src/core/ExoCapsule.sol"; +import {ImuaCapsule} from "../src/core/ImuaCapsule.sol"; import "./BaseScript.sol"; import {UpgradeableBeacon} from "@openzeppelin/contracts/proxy/beacon/UpgradeableBeacon.sol"; import "forge-std/Script.sol"; -contract UpgradeExoCapsuleScript is BaseScript { +contract UpgradeImuaCapsuleScript is BaseScript { UpgradeableBeacon capsuleBeaconContract; @@ -24,11 +24,11 @@ contract UpgradeExoCapsuleScript is BaseScript { vm.selectFork(clientChain); vm.startBroadcast(deployer.privateKey); console.log("owner", capsuleBeaconContract.owner()); - ExoCapsule capsule = new ExoCapsule(address(0)); + ImuaCapsule capsule = new ImuaCapsule(address(0)); capsuleBeaconContract.upgradeTo(address(capsule)); vm.stopBroadcast(); - console.log("new Exocapsule Implementation address: ", address(capsule)); + console.log("new ImuaCapsule Implementation address: ", address(capsule)); } } diff --git a/script/17_WithdrawalValidator.s.sol b/script/17_WithdrawalValidator.s.sol index a524c15e..e84cca29 100644 --- a/script/17_WithdrawalValidator.s.sol +++ b/script/17_WithdrawalValidator.s.sol @@ -1,11 +1,11 @@ pragma solidity ^0.8.19; -import "../src/core/ExoCapsule.sol"; -import "../src/interfaces/IClientChainGateway.sol"; +import {ImuaCapsule} from "../src/core/ImuaCapsule.sol"; +import {IClientChainGateway} from "../src/interfaces/IClientChainGateway.sol"; -import "../src/interfaces/IExoCapsule.sol"; -import "../src/interfaces/IExocoreGateway.sol"; -import "../src/interfaces/IVault.sol"; +import {IImuaCapsule} from "../src/interfaces/IImuaCapsule.sol"; +import {IImuachainGateway} from "../src/interfaces/IImuachainGateway.sol"; +import {IVault} from "../src/interfaces/IVault.sol"; import "../src/storage/GatewayStorage.sol"; import "@beacon-oracle/contracts/src/EigenLayerBeaconOracle.sol"; @@ -58,16 +58,16 @@ contract WithdrawalValidatorScript is BaseScript { _loadWithdrawalContainer(); _loadWithdrawalProof(); - if (!useExocorePrecompileMock) { + if (!useImuachainPrecompileMock) { _bindPrecompileMocks(); } - // transfer some gas fee to depositor, relayer and exocore gateway + // transfer some gas fee to depositor, relayer and imuachain gateway clientChain = vm.createSelectFork(clientChainRPCURL); _topUpPlayer(clientChain, address(0), deployer, depositor.addr, 0.2 ether); - exocore = vm.createSelectFork(exocoreRPCURL); - _topUpPlayer(exocore, address(0), exocoreGenesis, address(exocoreGateway), 1 ether); + imuachain = vm.createSelectFork(imuachainRPCURL); + _topUpPlayer(imuachain, address(0), imuachainGenesis, address(imuachainGateway), 1 ether); } function run() public { diff --git a/script/19_DeployFaucet.s.sol b/script/19_DeployFaucet.s.sol index 86e634e6..13698be2 100644 --- a/script/19_DeployFaucet.s.sol +++ b/script/19_DeployFaucet.s.sol @@ -10,7 +10,7 @@ import "forge-std/Script.sol"; contract DeployScript is BaseScript { address tokenAddr; - bool exoEthFaucet; + bool imEthFaucet; address faucetOwner; function setUp() public virtual override { @@ -22,22 +22,25 @@ contract DeployScript is BaseScript { require(tokenAddr != address(0), "token address should not be empty"); clientChain = vm.createSelectFork(clientChainRPCURL); - exocore = vm.createSelectFork(exocoreRPCURL); + imuachain = vm.createSelectFork(imuachainRPCURL); - exoEthFaucet = vm.envBool("EXO_ETH_FAUCET"); + // boolean to decide which item is being deployed on which chain + // true => client chain, imETH faucet + // false => imuachain, native token faucet + imEthFaucet = vm.envBool("IM_ETH_FAUCET"); // for native token, using a different owner is better since the private key is exposed on the backend faucetOwner = vm.envAddress("FAUCET_OWNER"); } function run() public { - vm.selectFork(exoEthFaucet ? clientChain : exocore); - vm.startBroadcast(exocoreValidatorSet.privateKey); + vm.selectFork(imEthFaucet ? clientChain : imuachain); + vm.startBroadcast(owner.privateKey); address proxyAdmin = address(new ProxyAdmin()); CombinedFaucet faucetLogic = new CombinedFaucet(); CombinedFaucet faucet = CombinedFaucet( payable(address(new TransparentUpgradeableProxy(address(faucetLogic), address(proxyAdmin), ""))) ); - faucet.initialize(exocoreValidatorSet.addr, exoEthFaucet ? tokenAddr : address(0), 1 ether); + faucet.initialize(owner.addr, imEthFaucet ? tokenAddr : address(0), 1 ether); vm.stopBroadcast(); // do not store them as JSON since the address is intentionally kept private console.log("faucet", address(faucet)); diff --git a/script/1_Prerequisites.s.sol b/script/1_Prerequisites.s.sol index c749be21..b6342ceb 100644 --- a/script/1_Prerequisites.s.sol +++ b/script/1_Prerequisites.s.sol @@ -20,8 +20,8 @@ contract PrerequisitesScript is BaseScript { clientChain = vm.createSelectFork(clientChainRPCURL); // transfer some eth to deployer address - exocore = vm.createSelectFork(exocoreRPCURL); - _topUpPlayer(exocore, address(0), exocoreGenesis, deployer.addr, 1 ether); + imuachain = vm.createSelectFork(imuachainRPCURL); + _topUpPlayer(imuachain, address(0), imuachainGenesis, deployer.addr, 1 ether); } function run() public { @@ -29,20 +29,20 @@ contract PrerequisitesScript is BaseScript { if (useEndpointMock) { vm.selectFork(clientChain); vm.startBroadcast(deployer.privateKey); - clientChainLzEndpoint = new NonShortCircuitEndpointV2Mock(clientChainId, exocoreValidatorSet.addr); + clientChainLzEndpoint = new NonShortCircuitEndpointV2Mock(clientChainId, owner.addr); vm.stopBroadcast(); - vm.selectFork(exocore); + vm.selectFork(imuachain); vm.startBroadcast(deployer.privateKey); - exocoreLzEndpoint = new NonShortCircuitEndpointV2Mock(exocoreChainId, exocoreValidatorSet.addr); + imuachainLzEndpoint = new NonShortCircuitEndpointV2Mock(imuachainChainId, owner.addr); vm.stopBroadcast(); } else { clientChainLzEndpoint = ILayerZeroEndpointV2(sepoliaEndpointV2); - exocoreLzEndpoint = ILayerZeroEndpointV2(exocoreEndpointV2); + imuachainLzEndpoint = ILayerZeroEndpointV2(imuachainEndpointV2); } - if (useExocorePrecompileMock) { - vm.selectFork(exocore); + if (useImuachainPrecompileMock) { + vm.selectFork(imuachain); vm.startBroadcast(deployer.privateKey); assetsMock = address(new AssetsMock(clientChainId)); delegationMock = address(new DelegationMock()); @@ -55,23 +55,23 @@ contract PrerequisitesScript is BaseScript { string memory deployedContracts = "deployedContracts"; string memory clientChainContracts = "clientChainContracts"; - string memory exocoreContracts = "exocoreContracts"; + string memory imuachainContracts = "imuachainContracts"; vm.serializeAddress(clientChainContracts, "lzEndpoint", address(clientChainLzEndpoint)); vm.serializeAddress(clientChainContracts, "beaconOracle", address(beaconOracle)); string memory clientChainContractsOutput = vm.serializeAddress(clientChainContracts, "erc20Token", address(restakeToken)); - if (useExocorePrecompileMock) { - vm.serializeAddress(exocoreContracts, "assetsPrecompileMock", assetsMock); - vm.serializeAddress(exocoreContracts, "delegationPrecompileMock", delegationMock); - vm.serializeAddress(exocoreContracts, "rewardPrecompileMock", rewardMock); + if (useImuachainPrecompileMock) { + vm.serializeAddress(imuachainContracts, "assetsPrecompileMock", assetsMock); + vm.serializeAddress(imuachainContracts, "delegationPrecompileMock", delegationMock); + vm.serializeAddress(imuachainContracts, "rewardPrecompileMock", rewardMock); } - string memory exocoreContractsOutput = - vm.serializeAddress(exocoreContracts, "lzEndpoint", address(exocoreLzEndpoint)); + string memory imuachainContractsOutput = + vm.serializeAddress(imuachainContracts, "lzEndpoint", address(imuachainLzEndpoint)); vm.serializeString(deployedContracts, "clientChain", clientChainContractsOutput); - string memory finalJson = vm.serializeString(deployedContracts, "exocore", exocoreContractsOutput); + string memory finalJson = vm.serializeString(deployedContracts, "imuachain", imuachainContractsOutput); vm.writeJson(finalJson, "script/deployments/prerequisiteContracts.json"); } diff --git a/script/20_DeployCreate3.s.sol b/script/20_DeployCreate3.s.sol index f85484e2..4feb7967 100644 --- a/script/20_DeployCreate3.s.sol +++ b/script/20_DeployCreate3.s.sol @@ -4,7 +4,7 @@ pragma solidity ^0.8.19; import "forge-std/Script.sol"; /// @title DeployCreate3 -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice This script is used to deploy the deterministic Create2 and Create3 factories to any network. /// The Create2 factory is deployed using a raw transaction and the Create3 factory is deployed using a Create2 call. /// @dev The advantage of using the Create3 factory over the Create2 factory for further deployments is that the diff --git a/script/21_UpgradeImuachainGateway.s.sol b/script/21_UpgradeImuachainGateway.s.sol new file mode 100644 index 00000000..ab439755 --- /dev/null +++ b/script/21_UpgradeImuachainGateway.s.sol @@ -0,0 +1,62 @@ +pragma solidity ^0.8.19; + +import {ILayerZeroEndpointV2} from "@layerzerolabs/lz-evm-protocol-v2/contracts/interfaces/ILayerZeroEndpointV2.sol"; +import {ProxyAdmin} from "@openzeppelin/contracts/proxy/transparent/ProxyAdmin.sol"; +import "forge-std/Script.sol"; + +import {ImuachainGateway} from "../src/core/ImuachainGateway.sol"; + +import {BaseScript} from "./BaseScript.sol"; +import "forge-std/Script.sol"; + +import {Action} from "../src/storage/GatewayStorage.sol"; +import {ITransparentUpgradeableProxy} from "@openzeppelin/contracts/proxy/transparent/TransparentUpgradeableProxy.sol"; + +contract UpgradeImuachainGatewayScript is BaseScript { + + address proxy; + address proxyAdmin; + address restoreLogic; + + function setUp() public virtual override { + super.setUp(); + string memory prerequisites = vm.readFile("script/deployedContracts.json"); + imuachainLzEndpoint = ILayerZeroEndpointV2(stdJson.readAddress(prerequisites, ".imuachain.lzEndpoint")); + require(address(imuachainLzEndpoint) != address(0), "imuachain l0 endpoint should not be empty"); + proxy = stdJson.readAddress(prerequisites, ".imuachain.imuachainGateway"); + require(proxy != address(0), "imuachain gateway should not be empty"); + proxyAdmin = stdJson.readAddress(prerequisites, ".imuachain.imuachainProxyAdmin"); + require(proxyAdmin != address(0), "imuachain proxy admin should not be empty"); + restoreLogic = stdJson.readAddress(prerequisites, ".imuachain.imuachainGatewayLogic"); + require(restoreLogic != address(0), "imuachain gateway logic should not be empty"); + imuachain = vm.createSelectFork(imuachainRPCURL); + } + + function run() public { + vm.startBroadcast(owner.privateKey); + // new deployment + ImuachainGateway imuachainGatewayLogic = new ImuachainGateway(address(imuachainLzEndpoint)); + // upgrade to new deployment such that the onlyCalledFromThis is removed + ProxyAdmin(proxyAdmin).upgrade(ITransparentUpgradeableProxy(proxy), address(imuachainGatewayLogic)); + // then do the edit + ImuachainGateway gateway = ImuachainGateway(payable(proxy)); + // gateway.fixReentrance(); + // gateway.fixNonce(); + // validate the result + bytes32 slotValue = vm.load(address(gateway), bytes32(uint256(151))); + require(uint256(slotValue) == 1, "Slot value is not 1"); + // validate the nonce + // uint256 nextNonce = gateway.nextNonce(40168, + // bytes32(0xe57dcdb0740d281469f5be39b44bf495f8ade7a1af889bae16252e7b9875dc92)); + // require(nextNonce == 21, "Next nonce is not 21"); + // then upgrade back to the old deployment + ProxyAdmin(proxyAdmin).upgrade(ITransparentUpgradeableProxy(proxy), restoreLogic); + vm.stopBroadcast(); + + console.log( + "next nonce", + gateway.nextNonce(40_168, bytes32(0xe57dcdb0740d281469f5be39b44bf495f8ade7a1af889bae16252e7b9875dc92)) + ); + } + +} diff --git a/script/22_DeployLibrary.s.sol b/script/22_DeployLibrary.s.sol new file mode 100644 index 00000000..1554c7a2 --- /dev/null +++ b/script/22_DeployLibrary.s.sol @@ -0,0 +1,35 @@ +pragma solidity ^0.8.19; + +import {CREATE3_FACTORY} from "../lib/create3-factory/src/ICREATE3Factory.sol"; +import {NetworkConstants} from "../src/libraries/NetworkConstants.sol"; +import {BaseScript} from "./BaseScript.sol"; + +contract DeployNetworkConstants is BaseScript { + + bytes32 salt; + + function setUp() public virtual override { + // load keys + super.setUp(); + salt = keccak256(abi.encodePacked("NetworkConstants")); + require(CREATE3_FACTORY.getDeployed(owner.addr, salt).code.length == 0, "Salt already taken"); + } + + function run() public { + vm.selectFork(clientChain); + vm.startBroadcast(owner.privateKey); + + bytes memory creationCode = type(NetworkConstants).creationCode; + + address libraryAddress = CREATE3_FACTORY.deploy(salt, creationCode); + + vm.stopBroadcast(); + + string memory subkey = vm.serializeAddress("sepolia", "networkConstants", libraryAddress); + + string memory finalJson = vm.serializeString("libraries", "sepolia", subkey); + + vm.writeJson(finalJson, "script/deployments/libraries.json"); + } + +} diff --git a/script/2_DeployBoth.s.sol b/script/2_DeployBoth.s.sol index ffab2714..8bfd1be6 100644 --- a/script/2_DeployBoth.s.sol +++ b/script/2_DeployBoth.s.sol @@ -1,15 +1,15 @@ pragma solidity ^0.8.19; import "../src/core/ClientChainGateway.sol"; -import "../src/core/ExoCapsule.sol"; -import "../src/core/ExocoreGateway.sol"; +import "../src/core/ImuaCapsule.sol"; +import "../src/core/ImuachainGateway.sol"; import {RewardVault} from "../src/core/RewardVault.sol"; import {Vault} from "../src/core/Vault.sol"; import {NetworkConstants} from "../src/libraries/NetworkConstants.sol"; import "../src/utils/BeaconProxyBytecode.sol"; import "../src/utils/CustomProxyAdmin.sol"; -import {ExocoreGatewayMock} from "../test/mocks/ExocoreGatewayMock.sol"; +import {ImuachainGatewayMock} from "../test/mocks/ImuachainGatewayMock.sol"; import {BootstrapStorage} from "../src/storage/BootstrapStorage.sol"; import {BaseScript} from "./BaseScript.sol"; @@ -33,24 +33,24 @@ contract DeployScript is BaseScript { restakeToken = ERC20PresetFixedSupply(stdJson.readAddress(prerequisites, ".clientChain.erc20Token")); require(address(restakeToken) != address(0), "restake token address should not be empty"); - exocoreLzEndpoint = ILayerZeroEndpointV2(stdJson.readAddress(prerequisites, ".exocore.lzEndpoint")); - require(address(exocoreLzEndpoint) != address(0), "exocore l0 endpoint should not be empty"); + imuachainLzEndpoint = ILayerZeroEndpointV2(stdJson.readAddress(prerequisites, ".imuachain.lzEndpoint")); + require(address(imuachainLzEndpoint) != address(0), "imuachain l0 endpoint should not be empty"); - if (useExocorePrecompileMock) { - assetsMock = stdJson.readAddress(prerequisites, ".exocore.assetsPrecompileMock"); + if (useImuachainPrecompileMock) { + assetsMock = stdJson.readAddress(prerequisites, ".imuachain.assetsPrecompileMock"); require(assetsMock != address(0), "assetsMock should not be empty"); - delegationMock = stdJson.readAddress(prerequisites, ".exocore.delegationPrecompileMock"); + delegationMock = stdJson.readAddress(prerequisites, ".imuachain.delegationPrecompileMock"); require(delegationMock != address(0), "delegationMock should not be empty"); - rewardMock = stdJson.readAddress(prerequisites, ".exocore.rewardPrecompileMock"); + rewardMock = stdJson.readAddress(prerequisites, ".imuachain.rewardPrecompileMock"); require(rewardMock != address(0), "rewardMock should not be empty"); } clientChain = vm.createSelectFork(clientChainRPCURL); - exocore = vm.createSelectFork(exocoreRPCURL); - _topUpPlayer(exocore, address(0), exocoreGenesis, deployer.addr, 1 ether); + imuachain = vm.createSelectFork(imuachainRPCURL); + _topUpPlayer(imuachain, address(0), imuachainGenesis, deployer.addr, 1 ether); } function run() public { @@ -63,7 +63,7 @@ contract DeployScript is BaseScript { /// deploy implementations and beacons vaultImplementation = new Vault(); - capsuleImplementation = new ExoCapsule(address(0)); + capsuleImplementation = new ImuaCapsule(address(0)); rewardVaultImplementation = new RewardVault(); vaultBeacon = new UpgradeableBeacon(address(vaultImplementation)); @@ -75,10 +75,10 @@ contract DeployScript is BaseScript { // Create ImmutableConfig struct BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(beaconOracle), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -93,9 +93,7 @@ contract DeployScript is BaseScript { new TransparentUpgradeableProxy( address(clientGatewayLogic), address(clientChainProxyAdmin), - abi.encodeWithSelector( - clientGatewayLogic.initialize.selector, payable(exocoreValidatorSet.addr) - ) + abi.encodeWithSelector(clientGatewayLogic.initialize.selector, payable(owner.addr)) ) ) ) @@ -111,40 +109,36 @@ contract DeployScript is BaseScript { vm.stopBroadcast(); - // deploy on Exocore via rpc - vm.selectFork(exocore); + // deploy on Imuachain via rpc + vm.selectFork(imuachain); vm.startBroadcast(deployer.privateKey); - // deploy Exocore network contracts - ProxyAdmin exocoreProxyAdmin = new ProxyAdmin(); + // deploy Imuachain network contracts + ProxyAdmin imuachainProxyAdmin = new ProxyAdmin(); - if (useExocorePrecompileMock) { - ExocoreGatewayMock exocoreGatewayLogic = - new ExocoreGatewayMock(address(exocoreLzEndpoint), assetsMock, rewardMock, delegationMock); - exocoreGateway = ExocoreGateway( + if (useImuachainPrecompileMock) { + ImuachainGatewayMock imuachainGatewayLogic = + new ImuachainGatewayMock(address(imuachainLzEndpoint), assetsMock, rewardMock, delegationMock); + imuachainGateway = ImuachainGateway( payable( address( new TransparentUpgradeableProxy( - address(exocoreGatewayLogic), - address(exocoreProxyAdmin), - abi.encodeWithSelector( - exocoreGatewayLogic.initialize.selector, payable(exocoreValidatorSet.addr) - ) + address(imuachainGatewayLogic), + address(imuachainProxyAdmin), + abi.encodeWithSelector(imuachainGatewayLogic.initialize.selector, payable(owner.addr)) ) ) ) ); } else { - ExocoreGateway exocoreGatewayLogic = new ExocoreGateway(address(exocoreLzEndpoint)); - exocoreGateway = ExocoreGateway( + ImuachainGateway imuachainGatewayLogic = new ImuachainGateway(address(imuachainLzEndpoint)); + imuachainGateway = ImuachainGateway( payable( address( new TransparentUpgradeableProxy( - address(exocoreGatewayLogic), - address(exocoreProxyAdmin), - abi.encodeWithSelector( - exocoreGatewayLogic.initialize.selector, payable(exocoreValidatorSet.addr) - ) + address(imuachainGatewayLogic), + address(imuachainProxyAdmin), + abi.encodeWithSelector(imuachainGatewayLogic.initialize.selector, payable(owner.addr)) ) ) ) @@ -155,7 +149,7 @@ contract DeployScript is BaseScript { string memory deployedContracts = "deployedContracts"; string memory clientChainContracts = "clientChainContracts"; - string memory exocoreContracts = "exocoreContracts"; + string memory imuachainContracts = "imuachainContracts"; vm.serializeAddress(clientChainContracts, "lzEndpoint", address(clientChainLzEndpoint)); vm.serializeAddress(clientChainContracts, "beaconOracle", address(beaconOracle)); vm.serializeAddress(clientChainContracts, "clientChainGateway", address(clientGateway)); @@ -169,20 +163,20 @@ contract DeployScript is BaseScript { string memory clientChainContractsOutput = vm.serializeAddress(clientChainContracts, "proxyAdmin", address(clientChainProxyAdmin)); - vm.serializeAddress(exocoreContracts, "lzEndpoint", address(exocoreLzEndpoint)); - vm.serializeAddress(exocoreContracts, "exocoreGateway", address(exocoreGateway)); + vm.serializeAddress(imuachainContracts, "lzEndpoint", address(imuachainLzEndpoint)); + vm.serializeAddress(imuachainContracts, "imuachainGateway", address(imuachainGateway)); - if (useExocorePrecompileMock) { - vm.serializeAddress(exocoreContracts, "assetsPrecompileMock", assetsMock); - vm.serializeAddress(exocoreContracts, "delegationPrecompileMock", delegationMock); - vm.serializeAddress(exocoreContracts, "rewardPrecompileMock", rewardMock); + if (useImuachainPrecompileMock) { + vm.serializeAddress(imuachainContracts, "assetsPrecompileMock", assetsMock); + vm.serializeAddress(imuachainContracts, "delegationPrecompileMock", delegationMock); + vm.serializeAddress(imuachainContracts, "rewardPrecompileMock", rewardMock); } - string memory exocoreContractsOutput = - vm.serializeAddress(exocoreContracts, "proxyAdmin", address(exocoreProxyAdmin)); + string memory imuachainContractsOutput = + vm.serializeAddress(imuachainContracts, "proxyAdmin", address(imuachainProxyAdmin)); vm.serializeString(deployedContracts, "clientChain", clientChainContractsOutput); - string memory finalJson = vm.serializeString(deployedContracts, "exocore", exocoreContractsOutput); + string memory finalJson = vm.serializeString(deployedContracts, "imuachain", imuachainContractsOutput); vm.writeJson(finalJson, "script/deployments/deployedContracts.json"); } diff --git a/script/3_Setup.s.sol b/script/3_Setup.s.sol index d6f4ceeb..8f6a43ce 100644 --- a/script/3_Setup.s.sol +++ b/script/3_Setup.s.sol @@ -3,7 +3,7 @@ pragma solidity ^0.8.19; import {Action, GatewayStorage} from "../src/storage/GatewayStorage.sol"; import "../src/interfaces/IClientChainGateway.sol"; -import "../src/interfaces/IExocoreGateway.sol"; +import "../src/interfaces/IImuachainGateway.sol"; import "../src/interfaces/IVault.sol"; import {NonShortCircuitEndpointV2Mock} from "../test/mocks/NonShortCircuitEndpointV2Mock.sol"; @@ -33,61 +33,63 @@ contract SetupScript is BaseScript { restakeToken = ERC20PresetFixedSupply(stdJson.readAddress(deployedContracts, ".clientChain.erc20Token")); require(address(restakeToken) != address(0), "restakeToken address should not be empty"); - exocoreGateway = IExocoreGateway(payable(stdJson.readAddress(deployedContracts, ".exocore.exocoreGateway"))); - require(address(exocoreGateway) != address(0), "exocoreGateway address should not be empty"); + imuachainGateway = + IImuachainGateway(payable(stdJson.readAddress(deployedContracts, ".imuachain.imuachainGateway"))); + require(address(imuachainGateway) != address(0), "imuachainGateway address should not be empty"); - exocoreLzEndpoint = ILayerZeroEndpointV2(stdJson.readAddress(deployedContracts, ".exocore.lzEndpoint")); - require(address(exocoreLzEndpoint) != address(0), "exocoreLzEndpoint address should not be empty"); + imuachainLzEndpoint = ILayerZeroEndpointV2(stdJson.readAddress(deployedContracts, ".imuachain.lzEndpoint")); + require(address(imuachainLzEndpoint) != address(0), "imuachainLzEndpoint address should not be empty"); // transfer some gas fee to contract owner clientChain = vm.createSelectFork(clientChainRPCURL); - _topUpPlayer(clientChain, address(0), deployer, exocoreValidatorSet.addr, 0.2 ether); + _topUpPlayer(clientChain, address(0), deployer, owner.addr, 0.2 ether); - exocore = vm.createSelectFork(exocoreRPCURL); - _topUpPlayer(exocore, address(0), exocoreGenesis, exocoreValidatorSet.addr, 0.2 ether); + imuachain = vm.createSelectFork(imuachainRPCURL); + _topUpPlayer(imuachain, address(0), imuachainGenesis, owner.addr, 0.2 ether); - if (!useExocorePrecompileMock) { + if (!useImuachainPrecompileMock) { _bindPrecompileMocks(); } } function run() public { - // 1. setup client chain contracts to make them ready for sending and receiving messages from exocore gateway + // 1. setup client chain contracts to make them ready for sending and receiving messages from imuachain gateway vm.selectFork(clientChain); // Set owner of these contracts and only owner could setup contracts state - vm.startBroadcast(exocoreValidatorSet.privateKey); + vm.startBroadcast(owner.privateKey); // set the destination endpoint for corresponding destinations in endpoint mock if USE_ENDPOINT_MOCK is true if (useEndpointMock) { NonShortCircuitEndpointV2Mock(address(clientChainLzEndpoint)).setDestLzEndpoint( - address(exocoreGateway), address(exocoreLzEndpoint) + address(imuachainGateway), address(imuachainLzEndpoint) ); } - // as LzReceivers, client chain gateway should set exocoreGateway as trusted remote to receive messages from it - clientGateway.setPeer(exocoreChainId, address(exocoreGateway).toBytes32()); + // as LzReceivers, client chain gateway should set imuachainGateway as trusted remote to receive messages from + // it + clientGateway.setPeer(imuachainChainId, address(imuachainGateway).toBytes32()); vm.stopBroadcast(); - // 2. setup Exocore contracts to make them ready for sending and receiving messages from client chain - // gateway, and register client chain meta data to Exocore native module + // 2. setup imuachain contracts to make them ready for sending and receiving messages from client chain + // gateway, and register client chain meta data to imuachain native module - vm.selectFork(exocore); + vm.selectFork(imuachain); // Set the owner of these contracts and only owner could setup contracts state - vm.startBroadcast(exocoreValidatorSet.privateKey); + vm.startBroadcast(owner.privateKey); // set the destination endpoint for corresponding destinations in endpoint mock if USE_ENDPOINT_MOCK is true if (useEndpointMock) { - NonShortCircuitEndpointV2Mock(address(exocoreLzEndpoint)).setDestLzEndpoint( + NonShortCircuitEndpointV2Mock(address(imuachainLzEndpoint)).setDestLzEndpoint( address(clientGateway), address(clientChainLzEndpoint) ); } - // register clientChainId to Exocore native module and set peer for client chain gateway to be ready for + // register clientChainId to imuachain native module and set peer for client chain gateway to be ready for // messaging - exocoreGateway.registerOrUpdateClientChain( + imuachainGateway.registerOrUpdateClientChain( clientChainId, address(clientGateway).toBytes32(), 20, "ClientChain", "EVM compatible network", "secp256k1" ); vm.stopBroadcast(); - // 3. adding tokens to the whtielist of both Exocore and client chain gateway to enable restaking + // 3. adding tokens to the whtielist of both imuachain and client chain gateway to enable restaking vm.selectFork(clientChain); // first we read decimals from client chain ERC20 token contract to prepare for token data bytes32[] memory whitelistTokensBytes32 = new bytes32[](2); @@ -113,19 +115,20 @@ contract SetupScript is BaseScript { oracleInfos[1] = "ETH,Ethereum,8"; //[tokenName],[chainName],[tokenDecimal](,[interval],[contract](,[ChainDesc:{...}],[TokenDesc:{...}])) tvlLimits[1] = 0; // irrelevant for native restaking - // second add whitelist tokens and their meta data on Exocore side to enable LST Restaking and Native Restaking, + // second add whitelist tokens and their meta data on imuachain side to enable LST Restaking and Native + // Restaking, // and this would also add token addresses to client chain gateway's whitelist - vm.selectFork(exocore); - vm.startBroadcast(exocoreValidatorSet.privateKey); + vm.selectFork(imuachain); + vm.startBroadcast(owner.privateKey); uint256 nativeFee; for (uint256 i = 0; i < whitelistTokensBytes32.length; i++) { - nativeFee = exocoreGateway.quote( + nativeFee = imuachainGateway.quote( clientChainId, abi.encodePacked( Action.REQUEST_ADD_WHITELIST_TOKEN, abi.encodePacked(whitelistTokensBytes32[i], tvlLimits[i]) ) ); - exocoreGateway.addWhitelistToken{value: nativeFee}( + imuachainGateway.addWhitelistToken{value: nativeFee}( clientChainId, whitelistTokensBytes32[i], decimals[i], diff --git a/script/4_Deposit.s.sol b/script/4_Deposit.s.sol index 3981b312..92b93d57 100644 --- a/script/4_Deposit.s.sol +++ b/script/4_Deposit.s.sol @@ -2,7 +2,7 @@ pragma solidity ^0.8.19; import "../src/interfaces/IClientChainGateway.sol"; -import "../src/interfaces/IExocoreGateway.sol"; +import "../src/interfaces/IImuachainGateway.sol"; import "../src/interfaces/IVault.sol"; import {Action, GatewayStorage} from "../src/storage/GatewayStorage.sol"; @@ -35,24 +35,25 @@ contract DepositScript is BaseScript { vault = IVault(stdJson.readAddress(deployedContracts, ".clientChain.resVault")); require(address(vault) != address(0), "vault address should not be empty"); - exocoreGateway = IExocoreGateway(payable(stdJson.readAddress(deployedContracts, ".exocore.exocoreGateway"))); - require(address(exocoreGateway) != address(0), "exocoreGateway address should not be empty"); + imuachainGateway = + IImuachainGateway(payable(stdJson.readAddress(deployedContracts, ".imuachain.imuachainGateway"))); + require(address(imuachainGateway) != address(0), "imuachainGateway address should not be empty"); - exocoreLzEndpoint = ILayerZeroEndpointV2(stdJson.readAddress(deployedContracts, ".exocore.lzEndpoint")); - require(address(exocoreLzEndpoint) != address(0), "exocoreLzEndpoint address should not be empty"); + imuachainLzEndpoint = ILayerZeroEndpointV2(stdJson.readAddress(deployedContracts, ".imuachain.lzEndpoint")); + require(address(imuachainLzEndpoint) != address(0), "imuachainLzEndpoint address should not be empty"); - if (!useExocorePrecompileMock) { + if (!useImuachainPrecompileMock) { _bindPrecompileMocks(); } - // transfer some gas fee to depositor, relayer and exocore gateway + // transfer some gas fee to depositor, relayer and imuachain gateway clientChain = vm.createSelectFork(clientChainRPCURL); _topUpPlayer(clientChain, address(0), deployer, depositor.addr, 0.2 ether); - _topUpPlayer(clientChain, address(restakeToken), exocoreValidatorSet, depositor.addr, 2 * DEPOSIT_AMOUNT); + _topUpPlayer(clientChain, address(restakeToken), owner, depositor.addr, 2 * DEPOSIT_AMOUNT); - exocore = vm.createSelectFork(exocoreRPCURL); - _topUpPlayer(exocore, address(0), exocoreGenesis, relayer.addr, 0.2 ether); - _topUpPlayer(exocore, address(0), exocoreGenesis, address(exocoreGateway), 2 ether); + imuachain = vm.createSelectFork(imuachainRPCURL); + _topUpPlayer(imuachain, address(0), imuachainGenesis, relayer.addr, 0.2 ether); + _topUpPlayer(imuachain, address(0), imuachainGenesis, address(imuachainGateway), 2 ether); } function run() public { @@ -76,14 +77,18 @@ contract DepositScript is BaseScript { vm.stopBroadcast(); if (useEndpointMock) { - vm.selectFork(exocore); + vm.selectFork(imuachain); vm.startBroadcast(relayer.privateKey); - uint64 nonce = exocoreGateway.nextNonce(clientChainId, address(clientGateway).toBytes32()); - exocoreLzEndpoint.lzReceive{gas: 500_000}( + uint64 nonce = imuachainGateway.nextNonce(clientChainId, address(clientGateway).toBytes32()); + imuachainLzEndpoint.lzReceive{gas: 500_000}( Origin(clientChainId, address(clientGateway).toBytes32(), nonce), - address(exocoreGateway), + address(imuachainGateway), GUID.generate( - nonce, clientChainId, address(clientGateway), exocoreChainId, address(exocoreGateway).toBytes32() + nonce, + clientChainId, + address(clientGateway), + imuachainChainId, + address(imuachainGateway).toBytes32() ), msg_, bytes("") diff --git a/script/5_Withdraw.s.sol b/script/5_Withdraw.s.sol index f7f2925d..3fef1383 100644 --- a/script/5_Withdraw.s.sol +++ b/script/5_Withdraw.s.sol @@ -2,7 +2,7 @@ pragma solidity ^0.8.19; import "../src/interfaces/IClientChainGateway.sol"; -import "../src/interfaces/IExocoreGateway.sol"; +import "../src/interfaces/IImuachainGateway.sol"; import "../src/interfaces/IVault.sol"; import {Action, GatewayStorage} from "../src/storage/GatewayStorage.sol"; @@ -36,23 +36,24 @@ contract DepositScript is BaseScript { vault = IVault(stdJson.readAddress(deployedContracts, ".clientChain.resVault")); require(address(vault) != address(0), "vault address should not be empty"); - exocoreGateway = IExocoreGateway(payable(stdJson.readAddress(deployedContracts, ".exocore.exocoreGateway"))); - require(address(exocoreGateway) != address(0), "exocoreGateway address should not be empty"); + imuachainGateway = + IImuachainGateway(payable(stdJson.readAddress(deployedContracts, ".imuachain.imuachainGateway"))); + require(address(imuachainGateway) != address(0), "imuachainGateway address should not be empty"); - exocoreLzEndpoint = ILayerZeroEndpointV2(stdJson.readAddress(deployedContracts, ".exocore.lzEndpoint")); - require(address(exocoreLzEndpoint) != address(0), "exocoreLzEndpoint address should not be empty"); + imuachainLzEndpoint = ILayerZeroEndpointV2(stdJson.readAddress(deployedContracts, ".imuachain.lzEndpoint")); + require(address(imuachainLzEndpoint) != address(0), "imuachainLzEndpoint address should not be empty"); - if (!useExocorePrecompileMock) { + if (!useImuachainPrecompileMock) { _bindPrecompileMocks(); } - // transfer some gas fee to depositor, relayer and exocore gateway + // transfer some gas fee to depositor, relayer and imuachain gateway clientChain = vm.createSelectFork(clientChainRPCURL); _topUpPlayer(clientChain, address(0), deployer, depositor.addr, 0.2 ether); - exocore = vm.createSelectFork(exocoreRPCURL); - _topUpPlayer(exocore, address(0), exocoreGenesis, relayer.addr, 0.2 ether); - _topUpPlayer(exocore, address(0), exocoreGenesis, address(exocoreGateway), 1 ether); + imuachain = vm.createSelectFork(imuachainRPCURL); + _topUpPlayer(imuachain, address(0), imuachainGenesis, relayer.addr, 0.2 ether); + _topUpPlayer(imuachain, address(0), imuachainGenesis, address(imuachainGateway), 1 ether); } function run() public { @@ -68,18 +69,22 @@ contract DepositScript is BaseScript { uint256 nativeFee = clientGateway.quote(msg_); console.log("l0 native fee:", nativeFee); - clientGateway.claimPrincipalFromExocore{value: nativeFee}(address(restakeToken), WITHDRAW_AMOUNT); + clientGateway.claimPrincipalFromImuachain{value: nativeFee}(address(restakeToken), WITHDRAW_AMOUNT); vm.stopBroadcast(); if (useEndpointMock) { - vm.selectFork(exocore); + vm.selectFork(imuachain); vm.startBroadcast(relayer.privateKey); - uint64 nonce = exocoreGateway.nextNonce(clientChainId, address(clientGateway).toBytes32()); - exocoreLzEndpoint.lzReceive{gas: 500_000}( + uint64 nonce = imuachainGateway.nextNonce(clientChainId, address(clientGateway).toBytes32()); + imuachainLzEndpoint.lzReceive{gas: 500_000}( Origin(clientChainId, address(clientGateway).toBytes32(), nonce), - address(exocoreGateway), + address(imuachainGateway), GUID.generate( - nonce, clientChainId, address(clientGateway), exocoreChainId, address(exocoreGateway).toBytes32() + nonce, + clientChainId, + address(clientGateway), + imuachainChainId, + address(imuachainGateway).toBytes32() ), msg_, bytes("") diff --git a/script/6_CreateExoCapsule.s.sol b/script/6_CreateImuaCapsule.s.sol similarity index 81% rename from script/6_CreateExoCapsule.s.sol rename to script/6_CreateImuaCapsule.s.sol index 4253efa7..25c176d7 100644 --- a/script/6_CreateExoCapsule.s.sol +++ b/script/6_CreateImuaCapsule.s.sol @@ -2,7 +2,7 @@ pragma solidity ^0.8.19; import "../src/interfaces/IClientChainGateway.sol"; -import "../src/interfaces/IExocoreGateway.sol"; +import "../src/interfaces/IImuachainGateway.sol"; import "../src/interfaces/IVault.sol"; import "../src/storage/GatewayStorage.sol"; @@ -29,23 +29,23 @@ contract DepositScript is BaseScript { IClientChainGateway(payable(stdJson.readAddress(deployedContracts, ".clientChain.clientChainGateway"))); require(address(clientGateway) != address(0), "clientGateway address should not be empty"); - if (!useExocorePrecompileMock) { + if (!useImuachainPrecompileMock) { _bindPrecompileMocks(); } - // transfer some gas fee to depositor, relayer and exocore gateway + // transfer some gas fee to depositor, relayer and imuachain gateway clientChain = vm.createSelectFork(clientChainRPCURL); _topUpPlayer(clientChain, address(0), deployer, depositor.addr, 0.2 ether); - exocore = vm.createSelectFork(exocoreRPCURL); - _topUpPlayer(exocore, address(0), exocoreGenesis, address(exocoreGateway), 1 ether); + imuachain = vm.createSelectFork(imuachainRPCURL); + _topUpPlayer(imuachain, address(0), imuachainGenesis, address(imuachainGateway), 1 ether); } function run() public { vm.selectFork(clientChain); vm.startBroadcast(depositor.privateKey); - address capsule = clientGateway.createExoCapsule(); + address capsule = clientGateway.createImuaCapsule(); vm.stopBroadcast(); diff --git a/script/7_DeployBootstrap.s.sol b/script/7_DeployBootstrap.s.sol index d63c0023..9e289486 100644 --- a/script/7_DeployBootstrap.s.sol +++ b/script/7_DeployBootstrap.s.sol @@ -6,7 +6,7 @@ import {TransparentUpgradeableProxy} from "@openzeppelin/contracts/proxy/transpa import {Bootstrap} from "../src/core/Bootstrap.sol"; import {ClientChainGateway} from "../src/core/ClientChainGateway.sol"; -import "../src/core/ExoCapsule.sol"; +import {ImuaCapsule} from "../src/core/ImuaCapsule.sol"; import {RewardVault} from "../src/core/RewardVault.sol"; import {Vault} from "../src/core/Vault.sol"; @@ -21,9 +21,12 @@ import "forge-std/Script.sol"; import {BootstrapStorage} from "../src/storage/BootstrapStorage.sol"; import "@beacon-oracle/contracts/src/EigenLayerBeaconOracle.sol"; +import {CREATE3_FACTORY} from "../lib/create3-factory/src/ICREATE3Factory.sol"; + contract DeployBootstrapOnly is BaseScript { address wstETH; + bytes32 salt; function setUp() public virtual override { // load keys @@ -47,11 +50,17 @@ contract DeployBootstrapOnly is BaseScript { // https://docs.lido.fi/deployed-contracts/sepolia/ wstETH = stdJson.readAddress(prerequisiteContracts, ".clientChain.wstETH"); require(wstETH != address(0), "wstETH not found"); + // salt is automatically scoped to the deployer address + salt = keccak256(abi.encodePacked("Bootstrap")); + // check that the salt is not already taken + address deployed = CREATE3_FACTORY.getDeployed(owner.addr, salt); + console.log("deployed", deployed); + // require(deployed.code.length == 0, "Salt already taken"); } function run() public { vm.selectFork(clientChain); - vm.startBroadcast(exocoreValidatorSet.privateKey); + vm.startBroadcast(owner.privateKey); whitelistTokens.push(address(restakeToken)); tvlLimits.push(restakeToken.totalSupply() / 20); whitelistTokens.push(wstETH); @@ -66,7 +75,7 @@ contract DeployBootstrapOnly is BaseScript { /// deploy vault implementation contract, capsule implementation contract, reward vault implementation contract /// that has logics called by proxy vaultImplementation = new Vault(); - capsuleImplementation = new ExoCapsule(address(0)); + capsuleImplementation = new ImuaCapsule(address(0)); /// deploy the vault beacon, capsule beacon, reward vault beacon that store the implementation contract address vaultBeacon = new UpgradeableBeacon(address(vaultImplementation)); @@ -74,10 +83,10 @@ contract DeployBootstrapOnly is BaseScript { // Create ImmutableConfig struct BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(beaconOracle), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -92,33 +101,27 @@ contract DeployBootstrapOnly is BaseScript { new ClientChainGateway(address(clientChainLzEndpoint), config, address(rewardVaultBeacon)); // then the client chain initialization - bytes memory initialization = - abi.encodeWithSelector(clientGatewayLogic.initialize.selector, exocoreValidatorSet.addr); - - // bootstrap implementation - Bootstrap bootstrap = Bootstrap( - payable( - address( - new TransparentUpgradeableProxy( - address(bootstrapLogic), - address(clientChainProxyAdmin), - abi.encodeCall( - Bootstrap.initialize, - ( - exocoreValidatorSet.addr, - block.timestamp + 168 hours, - 2 seconds, - whitelistTokens, - tvlLimits, - address(clientChainProxyAdmin), - address(clientGatewayLogic), - initialization - ) - ) - ) - ) + bytes memory initialization = abi.encodeWithSelector(clientGatewayLogic.initialize.selector, owner.addr); + + // bootstrap proxy, it should be deployed using CREATE3 + bytes memory bootstrapInit = abi.encodeCall( + Bootstrap.initialize, + ( + owner.addr, + block.timestamp + 168 hours, + 2 seconds, + whitelistTokens, + tvlLimits, + address(clientChainProxyAdmin), + address(clientGatewayLogic), + initialization ) ); + bytes memory creationCode = abi.encodePacked( + type(TransparentUpgradeableProxy).creationCode, + abi.encode(address(bootstrapLogic), address(clientChainProxyAdmin), bootstrapInit) + ); + Bootstrap bootstrap = Bootstrap(payable(CREATE3_FACTORY.deploy(salt, creationCode))); // initialize proxyAdmin with bootstrap address clientChainProxyAdmin.initialize(address(bootstrap)); diff --git a/script/8_RegisterValidatorsAndDelegate.s.sol b/script/8_RegisterValidatorsAndDelegate.s.sol index 4bea4e01..a976e890 100644 --- a/script/8_RegisterValidatorsAndDelegate.s.sol +++ b/script/8_RegisterValidatorsAndDelegate.s.sol @@ -15,7 +15,7 @@ contract RegisterValidatorsAndDelegate is Script { uint256 primaryKey; // registration data for validators uint256[] validatorKeys; - string[] exoAddresses; + string[] imAddresses; string[] names; bytes32[] consKeys; // rpc settings @@ -35,7 +35,7 @@ contract RegisterValidatorsAndDelegate is Script { function setUp() public { primaryKey = vm.envUint("TEST_ACCOUNT_THREE_PRIVATE_KEY"); validatorKeys = vm.envUint("VALIDATOR_KEYS", ","); - exoAddresses = vm.envString("EXO_ADDRESSES", ","); + imAddresses = vm.envString("IM_ADDRESSES", ","); names = vm.envString("NAMES", ","); consKeys = vm.envBytes32("CONS_KEYS", ","); @@ -43,7 +43,7 @@ contract RegisterValidatorsAndDelegate is Script { clientChain = vm.createSelectFork(clientChainRPCURL); require( - validatorKeys.length == exoAddresses.length && validatorKeys.length == names.length + validatorKeys.length == imAddresses.length && validatorKeys.length == names.length && validatorKeys.length == consKeys.length, "Validator registration data length mismatch" ); @@ -65,12 +65,12 @@ contract RegisterValidatorsAndDelegate is Script { uint256 pk = validatorKeys[i]; address addr = vm.addr(pk); console.log(i, addr); - string memory exoAddr = exoAddresses[i]; + string memory imAddr = imAddresses[i]; string memory name = names[i]; bytes32 consKey = consKeys[i]; vm.startBroadcast(pk); // register validator - bootstrap.registerValidator(exoAddr, name, commission, consKey); + bootstrap.registerValidator(imAddr, name, commission, consKey); vm.stopBroadcast(); // give them the balance vm.startBroadcast(primaryKey); @@ -98,8 +98,8 @@ contract RegisterValidatorsAndDelegate is Script { continue; } // i is the transaction sender and j is the validator - string memory exoAddr = exoAddresses[j]; - bootstrap.delegateTo(exoAddr, tokenAddr, amount); + string memory imAddr = imAddresses[j]; + bootstrap.delegateTo(imAddr, tokenAddr, amount); } vm.stopBroadcast(); } diff --git a/script/9_ExtendBootstrapTime.s.sol b/script/9_ExtendBootstrapTime.s.sol index ee122dd7..82b1ef0c 100644 --- a/script/9_ExtendBootstrapTime.s.sol +++ b/script/9_ExtendBootstrapTime.s.sol @@ -21,7 +21,7 @@ contract SetBootstrapTime is BaseScript { function run() public { vm.selectFork(clientChain); - vm.startBroadcast(exocoreValidatorSet.privateKey); + vm.startBroadcast(owner.privateKey); Bootstrap bootstrap = Bootstrap(bootstrapAddr); bootstrap.setSpawnTime(block.timestamp + 120 seconds); diff --git a/script/BaseScript.sol b/script/BaseScript.sol index 25bde367..246890ce 100644 --- a/script/BaseScript.sol +++ b/script/BaseScript.sol @@ -1,8 +1,8 @@ pragma solidity ^0.8.19; import "../src/interfaces/IClientChainGateway.sol"; -import "../src/interfaces/IExoCapsule.sol"; -import "../src/interfaces/IExocoreGateway.sol"; +import "../src/interfaces/IImuaCapsule.sol"; +import "../src/interfaces/IImuachainGateway.sol"; import "../src/interfaces/IRewardVault.sol"; import "../src/interfaces/IVault.sol"; import "../src/utils/BeaconProxyBytecode.sol"; @@ -33,15 +33,15 @@ contract BaseScript is Script, StdCheats { } Player deployer; - Player exocoreValidatorSet; - Player exocoreGenesis; + Player owner; + Player imuachainGenesis; Player depositor; Player relayer; string sepoliaRPCURL; string holeskyRPCURL; string clientChainRPCURL; - string exocoreRPCURL; + string imuachainRPCURL; address[] whitelistTokens; uint256[] tvlLimits; @@ -49,14 +49,14 @@ contract BaseScript is Script, StdCheats { IClientChainGateway clientGateway; IVault vault; IRewardVault rewardVault; - IExocoreGateway exocoreGateway; + IImuachainGateway imuachainGateway; ILayerZeroEndpointV2 clientChainLzEndpoint; - ILayerZeroEndpointV2 exocoreLzEndpoint; + ILayerZeroEndpointV2 imuachainLzEndpoint; EigenLayerBeaconOracle beaconOracle; ERC20PresetFixedSupply restakeToken; IVault vaultImplementation; IRewardVault rewardVaultImplementation; - IExoCapsule capsuleImplementation; + IImuaCapsule capsuleImplementation; IBeacon vaultBeacon; IBeacon rewardVaultBeacon; IBeacon capsuleBeacon; @@ -68,13 +68,13 @@ contract BaseScript is Script, StdCheats { address rewardMock; uint256 clientChain; - uint256 exocore; + uint256 imuachain; - uint16 constant exocoreChainId = 40_259; + uint16 constant imuachainChainId = 40_259; uint16 constant clientChainId = 40_161; address constant sepoliaEndpointV2 = 0x6EDCE65403992e310A62460808c4b910D972f10f; - address constant exocoreEndpointV2 = 0x6EDCE65403992e310A62460808c4b910D972f10f; + address constant imuachainEndpointV2 = 0x6EDCE65403992e310A62460808c4b910D972f10f; address erc20TokenAddress = 0x83E6850591425e3C1E263c054f4466838B9Bd9e4; uint256 constant DEPOSIT_AMOUNT = 1 ether; @@ -82,18 +82,18 @@ contract BaseScript is Script, StdCheats { address internal constant VIRTUAL_STAKED_ETH_ADDRESS = 0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE; uint256 internal constant TOKEN_ADDRESS_BYTES_LENGTH = 32; - bool useExocorePrecompileMock; + bool useImuachainPrecompileMock; bool useEndpointMock; function setUp() public virtual { deployer.privateKey = vm.envUint("TEST_ACCOUNT_ONE_PRIVATE_KEY"); deployer.addr = vm.addr(deployer.privateKey); - exocoreValidatorSet.privateKey = vm.envUint("TEST_ACCOUNT_THREE_PRIVATE_KEY"); - exocoreValidatorSet.addr = vm.addr(exocoreValidatorSet.privateKey); + owner.privateKey = vm.envUint("TEST_ACCOUNT_THREE_PRIVATE_KEY"); + owner.addr = vm.addr(owner.privateKey); - exocoreGenesis.privateKey = vm.envUint("EXOCORE_GENESIS_PRIVATE_KEY"); - exocoreGenesis.addr = vm.addr(exocoreGenesis.privateKey); + imuachainGenesis.privateKey = vm.envUint("IMUACHAIN_GENESIS_PRIVATE_KEY"); + imuachainGenesis.addr = vm.addr(imuachainGenesis.privateKey); depositor.privateKey = vm.envUint("TEST_ACCOUNT_FOUR_PRIVATE_KEY"); depositor.addr = vm.addr(depositor.privateKey); @@ -103,11 +103,11 @@ contract BaseScript is Script, StdCheats { useEndpointMock = vm.envBool("USE_ENDPOINT_MOCK"); console.log("NOTICE: using l0 endpoint mock", useEndpointMock); - useExocorePrecompileMock = vm.envBool("USE_EXOCORE_PRECOMPILE_MOCK"); - console.log("NOTICE: using exocore precompiles mock", useExocorePrecompileMock); + useImuachainPrecompileMock = vm.envBool("USE_IMUACHAIN_PRECOMPILE_MOCK"); + console.log("NOTICE: using imuachain precompiles mock", useImuachainPrecompileMock); clientChainRPCURL = vm.envString("CLIENT_CHAIN_RPC"); - exocoreRPCURL = vm.envString("EXOCORE_TESTNET_RPC"); + imuachainRPCURL = vm.envString("IMUACHAIN_TESTNET_RPC"); } function _bindPrecompileMocks() internal { @@ -118,7 +118,7 @@ contract BaseScript is Script, StdCheats { // ignore } // choose the fork to ensure no client chain simulation is impacted - vm.selectFork(exocore); + vm.selectFork(imuachain); // even with --skip-simulation, some transactions fail. this helps work around that limitation // but it isn't perfect. if you face too much trouble, try calling the function(s) directly // with cast or remix. diff --git a/script/compareLayouts.js b/script/compareLayouts.js index db527b73..ff6e3d15 100644 --- a/script/compareLayouts.js +++ b/script/compareLayouts.js @@ -7,8 +7,8 @@ const fileMappings = [ { before: 'ClientChainGateway.deployed.json', after: 'ClientChainGateway.compiled.json', mustExist: true }, { before: 'Vault.deployed.json', after: 'Vault.compiled.json', mustExist: true }, { before: 'RewardVault.deployed.json', after: 'RewardVault.compiled.json', mustExist: true }, - { before: 'ExoCapsule.deployed.json', after: 'ExoCapsule.compiled.json', mustExist: true }, - { before: 'ExocoreGateway.base.json', after: 'ExocoreGateway.compiled.json', mustExist: true }, + { before: 'ImuaCapsule.deployed.json', after: 'ImuaCapsule.compiled.json', mustExist: true }, + { before: 'ImuachainGateway.base.json', after: 'ImuachainGateway.compiled.json', mustExist: true }, { before: 'Bootstrap.compiled.json', after: 'ClientChainGateway.compiled.json', mustExist: true }, ]; diff --git a/script/deployments/deployedContracts.json b/script/deployments/deployedContracts.json index ad5a5b34..46604f0e 100644 --- a/script/deployments/deployedContracts.json +++ b/script/deployments/deployedContracts.json @@ -2,17 +2,17 @@ "clientChain": { "beaconOracle": "0xd3D285cd1516038dAED61B8BF7Ae2daD63662492", "beaconProxyBytecode": "0xA15Ce26ba8E50ac21ecDa1791BAa3bf22a95b575", - "bootstrap": "0xDf9caDCfb027d9f6264Ecd5eAEc839a8335d8520", - "bootstrapLogic": "0xB97A39004Ba6900FAE801Ac04F8ce4DA70689879", - "capsuleBeacon": "0xB8D032a30a3B950CBcc6c1689E2381ab4290D4BB", - "capsuleImplementation": "0x8638502De2001e0dF71BbB5dd503E2008b2Ae948", - "clientGatewayLogic": "0x591433Ba4bD17973bbD02F201D4256e42fed141B", + "bootstrap": "0x64B5B5A618072C1E4D137f91Af780e3B17A81f3f", + "bootstrapLogic": "0xaa8901063317BF66dfed363468b01A9FD08D1a79", + "capsuleBeacon": "0x1F91eD5F48E5Ad897E71Fa4559Be8fA1851F0696", + "capsuleImplementation": "0xE71771EeC8ba37c8383FaAe6F4D0de7521813442", + "clientGatewayLogic": "0xF1d902b81aEc0E4944FE6675c32FD21dfBe365ae", "lzEndpoint": "0x6EDCE65403992e310A62460808c4b910D972f10f", - "proxyAdmin": "0x4317A7f62dA871E4512424Df8CaE91A6Ccc2afEA", - "rewardVaultBeacon": "0xEe75FF2f3A6E49a7cfd0aa2F729563F8c0F7707b", - "rewardVaultImplementation": "0xAE4Aed8C1A66f89D7c19D7B1021BE027846A51e6", - "vaultBeacon": "0x737e311Bf34B838943A30110289C5a9b22eba2A8", - "vaultImplementation": "0xce7f4AC8D00f5e4aB3BEd9fDD1EDB9cD20516477", + "proxyAdmin": "0xDb8710Ba0A1F161747d9459947Fd3B23DbdaB4ED", + "rewardVaultBeacon": "0xB058fa6626Fcc56e44A1137a4CE2EFd8BD7f7711", + "rewardVaultImplementation": "0xcb6986a0ebF721e9a26C6F9427E58082e87E86F7", + "vaultBeacon": "0xa188242ec78894840E20979B6F5087FeB56a9f19", + "vaultImplementation": "0x8cdCC93823cCBed482cf20b22A78305CF0404DC4", "wstETH": "0xB82381A3fBD3FaFA77B3a7bE693342618240067b" }, "holesky": { @@ -31,10 +31,10 @@ "vaultBeacon": "0x9a7bc99d90D5B8D8a47Bd6F8DBb5407fE3b51668", "vaultImplementation": "0x9A6735c19f293500C24886cC829870cD725a98b6" }, - "exocore": { - "exocoreGateway": "0xEAf4E4D09b9CeB936492518A852026c914beb11E", - "exocoreGatewayLogic": "0x651a66c43F6A257a878F62BD124c668D5F3bd1AF", - "exocoreProxyAdmin": "0x9bBDDb68B47b88d3Dd2eF7E1682C1EFE4E2e2315", + "imuachain": { + "imuachainGateway": "0xdDf5218Dbff297ADdF17fB7977E2469D774545ED", + "imuachainGatewayLogic": "0x71C95911E9a5D330f4D621842EC243EE1343292e", + "imuachainProxyAdmin": "0x8464135c8F25Da09e49BC8782676a84730C318bC", "lzEndpoint": "0x6EDCE65403992e310A62460808c4b910D972f10f" } } \ No newline at end of file diff --git a/script/deployments/deployedExocoreGatewayOnly.json b/script/deployments/deployedExocoreGatewayOnly.json deleted file mode 100644 index 1f2507ba..00000000 --- a/script/deployments/deployedExocoreGatewayOnly.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "exocore": { - "exocoreGateway": "0xbf5497Deb7C409623Ad58D798E73a865a80873DD", - "exocoreGatewayLogic": "0xdd359906110Ae307eeCdE5d1179ab59461152348", - "exocoreProxyAdmin": "0xbf75076c383a8dede075faa250de4abdb6a15d76", - "lzEndpoint": "0x6EDCE65403992e310A62460808c4b910D972f10f" - } -} \ No newline at end of file diff --git a/script/deployments/deployedImuachainGatewayOnly.json b/script/deployments/deployedImuachainGatewayOnly.json new file mode 100644 index 00000000..59e3e856 --- /dev/null +++ b/script/deployments/deployedImuachainGatewayOnly.json @@ -0,0 +1,8 @@ +{ + "imuachain": { + "imuachainGateway": "0xbf5497Deb7C409623Ad58D798E73a865a80873DD", + "imuachainGatewayLogic": "0xdd359906110Ae307eeCdE5d1179ab59461152348", + "imuachainProxyAdmin": "0xbf75076c383a8dede075faa250de4abdb6a15d76", + "lzEndpoint": "0x6EDCE65403992e310A62460808c4b910D972f10f" + } +} \ No newline at end of file diff --git a/script/deployments/deployedMultisigWallets.json b/script/deployments/deployedMultisigWallets.json index 711dfd94..637f78d7 100644 --- a/script/deployments/deployedMultisigWallets.json +++ b/script/deployments/deployedMultisigWallets.json @@ -7,7 +7,7 @@ "0xA1dfab3234f49e02e04E6C56a021F1a497CD0f82" ] }, - "exocore": { + "imuachain": { "multisig": "0xF27865277D8Cc608F279B3C09719A9Ceaa25A58f", "signers": [ "0x481E020DB4709e6EdDbf8134D41b866c6Fc8555e", diff --git a/script/deployments/libraries.json b/script/deployments/libraries.json new file mode 100644 index 00000000..b839cf9c --- /dev/null +++ b/script/deployments/libraries.json @@ -0,0 +1,5 @@ +{ + "sepolia": { + "networkConstants": "0xf718DcEC914835d47a5e428A5397BF2F7276808b" + } +} \ No newline at end of file diff --git a/script/deployments/prerequisiteContracts.json b/script/deployments/prerequisiteContracts.json index 2f12a570..5552e712 100644 --- a/script/deployments/prerequisiteContracts.json +++ b/script/deployments/prerequisiteContracts.json @@ -6,7 +6,7 @@ "wstETH": "0xB82381A3fBD3FaFA77B3a7bE693342618240067b", "lzEndpoint": "0x6EDCE65403992e310A62460808c4b910D972f10f" }, - "exocore": { + "imuachain": { "lzEndpoint": "0x6EDCE65403992e310A62460808c4b910D972f10f" } } \ No newline at end of file diff --git a/script/deployments/safe_contracts_on_exocore.json b/script/deployments/safe_contracts_on_imuachain.json similarity index 100% rename from script/deployments/safe_contracts_on_exocore.json rename to script/deployments/safe_contracts_on_imuachain.json diff --git a/script/deployments/testContracts.json b/script/deployments/testContracts.json index 0f9f1c6c..2dad6733 100644 --- a/script/deployments/testContracts.json +++ b/script/deployments/testContracts.json @@ -1,6 +1,6 @@ { - "exocore": { - "exocoreGateway": "0xbBd770D6288d03DfB2b87b6f88A049EC120647b7", + "imuachain": { + "imuachainGateway": "0xbBd770D6288d03DfB2b87b6f88A049EC120647b7", "lzEndpoint": "0x43B57f4fA1E4445296c133B1C3814655E2d77c35" } } \ No newline at end of file diff --git a/script/generate.mjs b/script/generate.mjs index 6dfc9f03..a01ae2a4 100644 --- a/script/generate.mjs +++ b/script/generate.mjs @@ -11,7 +11,7 @@ const clientChainInfo = { }; // this must be in the same order as whitelistTokens const tokenMetaInfos = [ - 'Exocore Holesky ETH', + 'Imuachain Holesky ETH', // named as exoETH 'Staked ETH', ]; // this must be in the same order as whitelistTokens @@ -23,25 +23,25 @@ const tokenNamesForOracle = [ 'ETH', 'nstETH' // not case sensitive ] const nativeChain = { - "name": "Exocore", - "meta_info": "The (native) Exocore chain", + "name": "Imuachain", + "meta_info": "The (native) Imuachain chain", "finalization_blocks": 10, "layer_zero_chain_id": 0, // virtual chain "address_length": 20, } const nativeAsset = { "asset_basic_info": { - "name": "Native EXO token", - "symbol": "exo", + "name": "Native IMUA token", + "symbol": "IMUA", "address": "0x0000000000000000000000000000000000000000", "decimals": "18", "layer_zero_chain_id": nativeChain.layer_zero_chain_id, - "exocore_chain_index": "1", - "meta_info": "EXO native to the Exocore chain", + "imua_chain_index": "1", + "meta_info": "IMUA native to Imuachain", }, "staking_total_amount": "0" }; -const EXOCORE_BECH32_PREFIX = 'exo'; +const IMUACHAIN_BECH32_PREFIX = 'im'; const VIRTUAL_STAKED_ETH_ADDR = "0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE"; import dotenv from 'dotenv'; @@ -60,7 +60,7 @@ const isValidBech32 = (address) => { if (!prefix || !words.length) { return false; } - return prefix === EXOCORE_BECH32_PREFIX; + return prefix === IMUACHAIN_BECH32_PREFIX; } catch (error) { // If there's any error in decoding, return false return false; @@ -245,7 +245,7 @@ async function updateGenesisFile() { address: token.tokenAddress.toLowerCase(), decimals: token.decimals.toString(), layer_zero_chain_id: clientChainInfo.layer_zero_chain_id, - exocore_chain_index: i.toString(), // unused + imua_chain_index: i.toString(), // unused meta_info: tokenMetaInfos[i], }, staking_total_amount: deposit_amount.toString(), @@ -423,9 +423,9 @@ async function updateGenesisFile() { for(let k = 0; k < validatorStates.length; k++) { // we cannot drop validators even though they may be slashed. this is because // even after slashing, the validators will retain 16 ETH of total balance. - // this must be allowed to be withdrawn after Exocore is launched. since the - // withdrawal credentials point to the ExoCapsule, such a withdrawal will - // be permitted only via Exocore, which must, correspondingly, have this validator's + // this must be allowed to be withdrawn after Imuachain is launched. since the + // withdrawal credentials point to the ImuaCapsule, such a withdrawal will + // be permitted only via ImuachainGateway, which must, correspondingly, have this validator's // state recorded. const validator = validatorStates[k]; const effectiveBalance = new Decimal(web3.utils.toWei(validator.validator.effectiveBalance.toString(), "gwei")); @@ -524,7 +524,7 @@ async function updateGenesisFile() { // (3) lower effective balance means that the Ethereum validator was either downtime // penalised or slashed. we follow the logic enshrined in update_native_restaking_balance.go // store this value before making any adjustments to calculate the slash proportion accurately. - // An example case wherein not all the 32 ETH is staked to an Exocore validator. + // An example case wherein not all the 32 ETH is staked to an Imuachain validator. // Effective balance = 29 ETH // Deposited 32, of which 2 is free and 30 is delegated. So withdrawable is 2. // DepositValue = 32 @@ -644,21 +644,21 @@ async function updateGenesisFile() { const operator_assets = genesisJSON.app_state.assets.operator_assets; for (let i = 0; i < validatorCount; i++) { const validatorEthAddress = await myContract.methods.registeredValidators(i).call(); - const validatorExoAddress = await myContract.methods.ethToExocoreAddress(validatorEthAddress).call(); + const validatorImAddress = await myContract.methods.ethToImAddress(validatorEthAddress).call(); const assetsByOperator = []; for (let j = 0; j < supportedTokensCount; j++) { // do not reuse the older array since it has been sorted. const tokenAddress = (await myContract.methods.getWhitelistedTokenAtIndex(j).call()).tokenAddress; let matchingEntries = slashProportions.filter( - (element) => element.token === tokenAddress && element.impacted_validators.includes(validatorExoAddress) + (element) => element.token === tokenAddress && element.impacted_validators.includes(validatorImAddress) ); let totalSlashing = ZERO_DECIMAL; let selfSlashing = ZERO_DECIMAL; for(let k = 0; k < matchingEntries.length; k++) { let matchingEntry = matchingEntries[k]; let delegation = await myContract.methods.delegations( - matchingEntry.staker, validatorExoAddress, tokenAddress + matchingEntry.staker, validatorImAddress, tokenAddress ).call(); if (delegation > 0) { let slashing = new Decimal(delegation.toString()).mul(matchingEntry.proportion); @@ -669,10 +669,10 @@ async function updateGenesisFile() { } } const delegationValue = new Decimal((await myContract.methods.delegationsByValidator( - validatorExoAddress, tokenAddress + validatorImAddress, tokenAddress ).call()).toString()).minus(totalSlashing).truncated(); const selfDelegation = new Decimal((await myContract.methods.delegations( - validatorEthAddress, validatorExoAddress, tokenAddress + validatorEthAddress, validatorImAddress, tokenAddress ).call()).toString()).minus(selfSlashing).truncated(); const assetsByOperatorForAsset = { @@ -699,7 +699,7 @@ async function updateGenesisFile() { return 0; }); const assetsByOperatorWrapped = { - operator: validatorExoAddress, + operator: validatorImAddress, assets_state: assetsByOperator }; operator_assets.push(assetsByOperatorWrapped); @@ -756,16 +756,16 @@ async function updateGenesisFile() { for (let i = 0; i < operatorsCount; i++) { // operators const opAddressHex = await myContract.methods.registeredValidators(i).call(); - const opAddressExo = await myContract.methods.ethToExocoreAddress( + const opAddressIm = await myContract.methods.ethToImAddress( opAddressHex ).call(); - if (!isValidBech32(opAddressExo)) { - console.log(`Skipping operator with invalid bech32 address: ${opAddressExo}`); + if (!isValidBech32(opAddressIm)) { + console.log(`Skipping operator with invalid bech32 address: ${opAddressIm}`); continue; } - const operatorInfo = await myContract.methods.validators(opAddressExo).call(); + const operatorInfo = await myContract.methods.validators(opAddressIm).call(); const operator_info = { - earnings_addr: opAddressExo, + earnings_addr: opAddressIm, // approve_addr unset operator_meta_info: operatorInfo.name, client_chain_earnings_addr: { @@ -792,7 +792,7 @@ async function updateGenesisFile() { } } const operatorCleaned = { - operator_address: opAddressExo, + operator_address: opAddressIm, operator_info: operator_info } operators.push(operatorCleaned); @@ -813,17 +813,17 @@ async function updateGenesisFile() { const tokenAddress = (await myContract.methods.getWhitelistedTokenAtIndex(j).call()).tokenAddress; let selfDelegationAmount = new Decimal((await myContract.methods.delegations( - opAddressHex, opAddressExo, tokenAddress + opAddressHex, opAddressIm, tokenAddress ).call()).toString()); let matchingEntries = slashProportions.filter( - (element) => element.token === tokenAddress && element.impacted_validators.includes(opAddressExo) + (element) => element.token === tokenAddress && element.impacted_validators.includes(opAddressIm) ); let totalSlashing = ZERO_DECIMAL; let selfSlashing = ZERO_DECIMAL; for(let k = 0; k < matchingEntries.length; k++) { let matchingEntry = matchingEntries[k]; let delegation = await myContract.methods.delegations( - matchingEntry.staker, opAddressExo, tokenAddress + matchingEntry.staker, opAddressIm, tokenAddress ).call(); if (delegation > 0) { let slashing = new Decimal(delegation.toString()).mul(matchingEntry.proportion); @@ -840,7 +840,7 @@ async function updateGenesisFile() { mul(exchangeRates[j].toFixed()) ); const perTokenDelegation = new Decimal((await myContract.methods.delegationsByValidator( - opAddressExo, tokenAddress + opAddressIm, tokenAddress ).call()).toString()).minus(totalSlashing).truncated(); totalAmount = totalAmount.plus( perTokenDelegation. @@ -863,11 +863,11 @@ async function updateGenesisFile() { consensus_key: operatorInfo.consensusPublicKey, }); operator_records.push({ - operator_address: opAddressExo, + operator_address: opAddressIm, chains: chains }); // opted info - const key = getJoinedStoreKey(opAddressExo, dogfoodAddr); + const key = getJoinedStoreKey(opAddressIm, dogfoodAddr); const DefaultOptedOutHeight = BigInt("18446744073709551615"); opt_states.push({ key: key, @@ -877,7 +877,7 @@ async function updateGenesisFile() { } }); // USD value for the operators - const usdValuekey = getJoinedStoreKey(dogfoodAddr, opAddressExo); + const usdValuekey = getJoinedStoreKey(dogfoodAddr, opAddressIm); operator_usd_values.push({ key: usdValuekey, opted_usd_value: { @@ -888,12 +888,12 @@ async function updateGenesisFile() { }); dogfoodUSDValue = dogfoodUSDValue.plus(totalAmount); } else { - console.log(`Skipping operator ${opAddressExo} due to insufficient self delegation.`); + console.log(`Skipping operator ${opAddressIm} due to insufficient self delegation.`); } let stakerId = opAddressHex.toLowerCase() + clientChainSuffix; let association = { staker_id: stakerId, - operator: opAddressExo, + operator: opAddressIm, }; associations.push(association); } @@ -1011,7 +1011,7 @@ async function updateGenesisFile() { for (let k = 0; k < operatorsCount; k++) { const operatorEth = await myContract.methods.registeredValidators(k).call(); - const operator = await myContract.methods.ethToExocoreAddress(operatorEth).call(); + const operator = await myContract.methods.ethToImAddress(operatorEth).call(); if (!isValidBech32(operator)) { console.log(`Skipping operator with invalid bech32 address: ${operator}`); continue; diff --git a/script/hardhat/deploy-and-setup-utxogateway.script.js b/script/hardhat/deploy-and-setup-utxogateway.script.js index 7afd70d5..eb56a198 100644 --- a/script/hardhat/deploy-and-setup-utxogateway.script.js +++ b/script/hardhat/deploy-and-setup-utxogateway.script.js @@ -21,10 +21,10 @@ async function main() { } // Check if contracts are already deployed - if (deployedContracts.exocore.utxoGateway) { - const utxoGatewayCode = await ethers.provider.getCode(deployedContracts.exocore.utxoGateway); + if (deployedContracts.imuachain.utxoGateway) { + const utxoGatewayCode = await ethers.provider.getCode(deployedContracts.imuachain.utxoGateway); if (utxoGatewayCode !== "0x") { - console.log("Using existing UTXOGateway deployment:", deployedContracts.exocore.utxoGateway); + console.log("Using existing UTXOGateway deployment:", deployedContracts.imuachain.utxoGateway); return; } } @@ -54,21 +54,21 @@ async function main() { const create3Code = await ethers.provider.getCode(CREATE3_DESTINATION); if (create3Code === "0x") { console.log("Deploying CREATE3 factory..."); - + // Use low-level call to deploy CREATE3 factory const tx = await deployer.sendTransaction({ to: CREATE2_DESTINATION, data: ethers.concat([CREATE3_SALT, CREATE3_INIT_CODE]) }); - + await tx.wait(); - + // Verify deployment const newCode = await ethers.provider.getCode(CREATE3_DESTINATION); if (newCode === "0x") { throw new Error("Failed to deploy CREATE3 factory"); } - + console.log("CREATE3 factory deployed to:", CREATE3_DESTINATION); } @@ -81,10 +81,10 @@ async function main() { // Get or Deploy ProxyAdmin let proxyAdmin; - if (deployedContracts.exocore?.exocoreProxyAdmin) { - console.log("\nUsing existing ProxyAdmin at:", deployedContracts.exocore.exocoreProxyAdmin); + if (deployedContracts.imuachain?.imuachainProxyAdmin) { + console.log("\nUsing existing ProxyAdmin at:", deployedContracts.imuachain.imuachainProxyAdmin); const ProxyAdminFactory = await ethers.getContractFactory("ProxyAdmin"); - proxyAdmin = ProxyAdminFactory.attach(deployedContracts.exocore.exocoreProxyAdmin); + proxyAdmin = ProxyAdminFactory.attach(deployedContracts.imuachain.imuachainProxyAdmin); } else { console.log("\nDeploying new ProxyAdmin..."); const ProxyAdminFactory = await ethers.getContractFactory("ProxyAdmin"); @@ -95,7 +95,7 @@ async function main() { // Deploy Proxy using CREATE3 console.log("\nDeploying UTXOGateway Proxy via CREATE3..."); - + // Generate deterministic salt for UTXOGateway const PROXY_SALT = ethers.id("UTXOGateway_v1"); @@ -185,12 +185,12 @@ async function main() { ); // Update deployedContracts.json - if (!deployedContracts.exocore) { - deployedContracts.exocore = {}; + if (!deployedContracts.imuachain) { + deployedContracts.imuachain = {}; } - - deployedContracts.exocore.utxoGateway = await utxoGateway.getAddress(); - deployedContracts.exocore.utxoGatewayLogic = await utxoGatewayLogic.getAddress(); + + deployedContracts.imuachain.utxoGateway = await utxoGateway.getAddress(); + deployedContracts.imuachain.utxoGatewayLogic = await utxoGatewayLogic.getAddress(); fs.writeFileSync( DEPLOYED_CONTRACTS_PATH, diff --git a/script/integration/1_DeployBootstrap.s.sol b/script/integration/1_DeployBootstrap.s.sol index 094802db..a4c8cc6c 100644 --- a/script/integration/1_DeployBootstrap.s.sol +++ b/script/integration/1_DeployBootstrap.s.sol @@ -21,9 +21,9 @@ import {BootstrapStorage} from "../../src/storage/BootstrapStorage.sol"; import {BeaconOracle} from "./BeaconOracle.sol"; import {ALLOWED_CHAIN_ID, NetworkConfig} from "./NetworkConfig.sol"; -import {ExoCapsule} from "../../src/core/ExoCapsule.sol"; +import {ImuaCapsule} from "../../src/core/ImuaCapsule.sol"; import {Vault} from "../../src/core/Vault.sol"; -import {IExoCapsule} from "../../src/interfaces/IExoCapsule.sol"; +import {IImuaCapsule} from "../../src/interfaces/IImuaCapsule.sol"; import {IRewardVault} from "../../src/interfaces/IRewardVault.sol"; import {IValidatorRegistry} from "../../src/interfaces/IValidatorRegistry.sol"; @@ -35,7 +35,7 @@ import {MyToken} from "../../test/foundry/unit/MyToken.sol"; // Technically this is used for testing but it is marked as a script // because it is a script that is used to deploy the contracts on Anvil / Prysm PoS -// and setup the initial state of the Exocore chain. +// and setup the initial state of Imuachain. // The keys provided in the dot-env file are required to be already // initialized by Anvil by `anvil --accounts 20`. @@ -46,7 +46,7 @@ contract DeployContracts is Script { using stdJson for string; // no cross-chain communication is part of this test so these are not relevant - uint16 exocoreChainId = 1; + uint16 imuachainChainId = 1; uint16 clientChainId = 2; uint256[] validators; @@ -65,7 +65,7 @@ contract DeployContracts is Script { BeaconOracle beaconOracle; IVault vaultImplementation; IRewardVault rewardVaultImplementation; - IExoCapsule capsuleImplementation; + IImuaCapsule capsuleImplementation; IBeacon vaultBeacon; IBeacon capsuleBeacon; IBeacon rewardVaultBeacon; @@ -187,7 +187,7 @@ contract DeployContracts is Script { /// deploy vault implementation contract, capsule implementation contract vaultImplementation = new Vault(); - capsuleImplementation = new ExoCapsule(address(networkConfig)); + capsuleImplementation = new ImuaCapsule(address(networkConfig)); /// deploy the vault beacon and capsule beacon vaultBeacon = new UpgradeableBeacon(address(vaultImplementation)); @@ -201,10 +201,10 @@ contract DeployContracts is Script { // Create ImmutableConfig struct BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(beaconOracle), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(networkConfig) }); @@ -239,7 +239,7 @@ contract DeployContracts is Script { // to keep bootstrap address constant, we must keep its nonce unchanged. hence, further transactions are sent // after the bare minimum bootstrap and associated deployments. - // the default deposit params are created using exocapsule address 0x90618D1cDb01bF37c24FC012E70029DA20fCe971 + // the default deposit params are created using imuacapsule address 0x90618D1cDb01bF37c24FC012E70029DA20fCe971 // which is made using the default NST_DEPOSITOR + bootstrap address 0xF801fc13AA08876F343fEBf50dFfA52A78180811 // if you get a DepositDataRoot or related error, check these addresses first. // if these addresses match, check that the DepositDataRoot, the Signature and the Pubkey match the default @@ -292,26 +292,26 @@ contract DeployContracts is Script { vm.startBroadcast(nstDepositor); address myAddress = address(bootstrap.ownerToCapsule(vm.addr(nstDepositor))); if (myAddress == address(0)) { - myAddress = bootstrap.createExoCapsule(); + myAddress = bootstrap.createImuaCapsule(); } - console.log("ExoCapsule address", myAddress); + console.log("ImuaCapsule address", myAddress); bootstrap.stake{value: 32 ether}(pubkey, signature, depositDataRoot); vm.stopBroadcast(); } function registerValidators() private { - string[3] memory exos = [ + string[3] memory ims = [ // these addresses will accrue rewards but they are not needed to keep the chain // running. - "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", - "exo1wnw7zcl9fy04ax69uffumwkdxftfqsjyj37wt2", - "exo1rtg0cgw94ep744epyvanc0wdd5kedwql73vlmr" + "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", + "im1wnw7zcl9fy04ax69uffumwkdxftfqsjyz0akf0", + "im1rtg0cgw94ep744epyvanc0wdd5kedwqlw008ex" ]; string[3] memory names = ["validator1", "validator2", "validator3"]; // the mnemonics corresponding to the consensus public keys are given here. to recover, - // echo "${MNEMONIC}" | exocored init localnet --chain-id exocorelocal_233-1 --recover + // echo "${MNEMONIC}" | imuad init localnet --chain-id imuachainlocalnet_232-1 --recover // the value in this script is this one - // exocored keys consensus-pubkey-to-bytes --output json | jq -r .bytes + // imuad keys consensus-pubkey-to-bytes --output json | jq -r .bytes bytes32[3] memory pubKeys = [ // wonder quality resource ketchup occur stadium vicious output situate plug second // monkey harbor vanish then myself primary feed earth story real soccer shove like @@ -326,7 +326,7 @@ contract DeployContracts is Script { IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e18, 1e18); for (uint256 i = 0; i < validators.length; i++) { vm.startBroadcast(validators[i]); - bootstrap.registerValidator(exos[i], names[i], commission, pubKeys[i]); + bootstrap.registerValidator(ims[i], names[i], commission, pubKeys[i]); vm.stopBroadcast(); } } @@ -354,10 +354,10 @@ contract DeployContracts is Script { for (uint256 k = 0; k < validators.length; k++) { uint256 amount = validatorDelegations[i - 1][j][k]; address validator = vm.addr(validators[k]); - string memory validatorExo = bootstrap.ethToExocoreAddress(validator); + string memory validatorIm = bootstrap.ethToImAddress(validator); vm.startBroadcast(delegator); if (amount != 0) { - bootstrap.delegateTo(validatorExo, whitelistTokens[i], amount); + bootstrap.delegateTo(validatorIm, whitelistTokens[i], amount); } vm.stopBroadcast(); } @@ -382,9 +382,9 @@ contract DeployContracts is Script { amount = random(stakerDelegationToDo); } address validator = vm.addr(validators[k]); - string memory exo = bootstrap.ethToExocoreAddress(validator); + string memory im = bootstrap.ethToImAddress(validator); vm.startBroadcast(delegator); - bootstrap.delegateTo(exo, whitelistTokens[i], amount); + bootstrap.delegateTo(im, whitelistTokens[i], amount); stakerDelegationToDo -= amount; vm.stopBroadcast(); } diff --git a/script/integration/2_VerifyDepositNST.s.sol b/script/integration/2_VerifyDepositNST.s.sol index 9ec9c15f..9f1b0551 100644 --- a/script/integration/2_VerifyDepositNST.s.sol +++ b/script/integration/2_VerifyDepositNST.s.sol @@ -63,7 +63,7 @@ contract VerifyDepositNST is Script { bootstrap.verifyAndDepositNativeStake(validatorContainer, validatorProof); bootstrap.delegateTo( // a validator in 1_DeployBootstrap.s.sol - "exo1rtg0cgw94ep744epyvanc0wdd5kedwql73vlmr", + "im1rtg0cgw94ep744epyvanc0wdd5kedwqlw008ex", // the native token address address(0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE), // delegate only a small portion of the deposit for our test diff --git a/script/integration/BeaconOracle.sol b/script/integration/BeaconOracle.sol index 78a08555..bcd71ca2 100644 --- a/script/integration/BeaconOracle.sol +++ b/script/integration/BeaconOracle.sol @@ -7,7 +7,7 @@ import {NetworkConstants} from "src/libraries/NetworkConstants.sol"; import {IBeaconChainOracle} from "@beacon-oracle/contracts/src/IBeaconChainOracle.sol"; /// @title BeaconOracle -/// @author Succinct Labs and ExocoreNetwork +/// @author Succinct Labs and imua-xyz contract BeaconOracle is IBeaconChainOracle { /// @notice The address of the beacon roots precompile. diff --git a/script/integration/NetworkConfig.sol b/script/integration/NetworkConfig.sol index e6d052fa..44457f3e 100644 --- a/script/integration/NetworkConfig.sol +++ b/script/integration/NetworkConfig.sol @@ -7,7 +7,7 @@ import {INetworkConfig, NetworkParams} from "src/interfaces/INetworkConfig.sol"; uint256 constant ALLOWED_CHAIN_ID = 31_337; /// @title NetworkConfig -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice This contract provides an interface to expose the network configuration. /// @dev This contract is used for integration testing and is a substitute for the NetworkConstants library. Hence, it /// is located in the `integration` folder, and it is not used in the production environment. It needs to have the diff --git a/src/core/BaseRestakingController.sol b/src/core/BaseRestakingController.sol index 2b5c0270..fa198381 100644 --- a/src/core/BaseRestakingController.sol +++ b/src/core/BaseRestakingController.sol @@ -2,7 +2,7 @@ pragma solidity ^0.8.19; import {IBaseRestakingController} from "../interfaces/IBaseRestakingController.sol"; -import {IExoCapsule} from "../interfaces/IExoCapsule.sol"; +import {IImuaCapsule} from "../interfaces/IImuaCapsule.sol"; import {IVault} from "../interfaces/IVault.sol"; import {Errors} from "../libraries/Errors.sol"; @@ -17,7 +17,7 @@ import {PausableUpgradeable} from "@openzeppelin/contracts-upgradeable/security/ import {ReentrancyGuardUpgradeable} from "@openzeppelin/contracts-upgradeable/security/ReentrancyGuardUpgradeable.sol"; /// @title BaseRestakingController -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice The base contract for the restaking controller. It only controls ERC20 tokens. /// @dev This contract is abstract because it does not call the base contract's constructor. It is not used by /// Bootstrap. @@ -44,7 +44,7 @@ abstract contract BaseRestakingController is { require(recipient != address(0), "BaseRestakingController: recipient address cannot be empty or zero address"); if (token == VIRTUAL_NST_ADDRESS) { - IExoCapsule capsule = _getCapsule(msg.sender); + IImuaCapsule capsule = _getCapsule(msg.sender); capsule.withdraw(amount, payable(recipient)); } else { IVault vault = _getVault(token); @@ -90,7 +90,7 @@ abstract contract BaseRestakingController is /// @inheritdoc IBaseRestakingController /// @dev Reward functionalities are not yet activated - function claimRewardFromExocore(address, uint256) external payable { + function claimRewardFromImuachain(address, uint256) external payable { revert Errors.NotYetSupported(); } @@ -100,32 +100,32 @@ abstract contract BaseRestakingController is revert Errors.NotYetSupported(); } - /// @dev Processes the request by sending it to Exocore. + /// @dev Processes the request by sending it to Imuachain. /// @dev If the encodedRequest is not empty, it is regarded as a request that expects a response and the request /// would be cached /// @param action The action to be performed. /// @param actionArgs The encodePacked arguments for the action. /// @param encodedRequest The encoded request if the request expects a response. function _processRequest(Action action, bytes memory actionArgs, bytes memory encodedRequest) internal { - uint64 requestNonce = _sendMsgToExocore(action, actionArgs); + uint64 requestNonce = _sendMsgToImuachain(action, actionArgs); if (encodedRequest.length > 0) { _registeredRequests[requestNonce] = encodedRequest; _registeredRequestActions[requestNonce] = action; } } - /// @dev Sends a message to Exocore. + /// @dev Sends a message to Imuachain. /// @param action The action to be performed. /// @param actionArgs The encodePacked arguments for the action. - function _sendMsgToExocore(Action action, bytes memory actionArgs) internal returns (uint64) { + function _sendMsgToImuachain(Action action, bytes memory actionArgs) internal returns (uint64) { bytes memory payload = abi.encodePacked(action, actionArgs); bytes memory options = OptionsBuilder.newOptions().addExecutorLzReceiveOption( DESTINATION_GAS_LIMIT, DESTINATION_MSG_VALUE ).addExecutorOrderedExecutionOption(); - MessagingFee memory fee = _quote(EXOCORE_CHAIN_ID, payload, options, false); + MessagingFee memory fee = _quote(IMUACHAIN_CHAIN_ID, payload, options, false); MessagingReceipt memory receipt = - _lzSend(EXOCORE_CHAIN_ID, payload, options, MessagingFee(fee.nativeFee, 0), msg.sender, false); + _lzSend(IMUACHAIN_CHAIN_ID, payload, options, MessagingFee(fee.nativeFee, 0), msg.sender, false); emit MessageSent(action, receipt.guid, receipt.nonce, receipt.fee.nativeFee); return receipt.nonce; diff --git a/src/core/Bootstrap.sol b/src/core/Bootstrap.sol index b13057f1..b7dc819d 100644 --- a/src/core/Bootstrap.sol +++ b/src/core/Bootstrap.sol @@ -20,7 +20,7 @@ import {ILSTRestakingController} from "../interfaces/ILSTRestakingController.sol import {INativeRestakingController} from "../interfaces/INativeRestakingController.sol"; import {IValidatorRegistry} from "../interfaces/IValidatorRegistry.sol"; -import {IExoCapsule} from "../interfaces/IExoCapsule.sol"; +import {IImuaCapsule} from "../interfaces/IImuaCapsule.sol"; import {ITokenWhitelister} from "../interfaces/ITokenWhitelister.sol"; import {IVault} from "../interfaces/IVault.sol"; @@ -34,9 +34,8 @@ import {Action} from "../storage/GatewayStorage.sol"; import {BootstrapLzReceiver} from "./BootstrapLzReceiver.sol"; /// @title Bootstrap -/// @author ExocoreNetwork -/// @notice This contract is used to Bootstrap the Exocore network. It accepts validator registration, deposits and -/// delegations. +/// @author imua-xyz +/// @notice This contract is used to Bootstrap Imuachain. It accepts validator registration, deposits and delegations. contract Bootstrap is Initializable, PausableUpgradeable, @@ -52,7 +51,7 @@ contract Bootstrap is using ValidatorContainer for bytes32[]; /// @notice Constructor for the Bootstrap contract. - /// @param endpoint_ is the address of the layerzero endpoint on Exocore chain + /// @param endpoint_ is the address of the layerzero endpoint on Imuachain /// @param config is the struct containing the values for immutable state variables constructor(address endpoint_, ImmutableConfig memory config) OAppCoreUpgradeable(endpoint_) @@ -63,7 +62,7 @@ contract Bootstrap is /// @notice Initializes the Bootstrap contract. /// @param owner The address of the contract owner. - /// @param spawnTime_ The spawn time of the Exocore chain. + /// @param spawnTime_ The spawn time of Imuachain. /// @param offsetDuration_ The offset duration before the spawn time. /// @param whitelistTokens_ The list of whitelisted tokens. /// @param tvlLimits_ The list of TVL limits for the tokens, in the same order as the whitelist. @@ -99,7 +98,7 @@ contract Bootstrap is _setClientChainGatewayLogic(clientChainGatewayLogic_, clientChainInitializationData_); // msg.sender is not the proxy admin but the transparent proxy itself, and hence, - // cannot be used here. we must require a separate owner. since the Exocore validator + // cannot be used here. we must require a separate owner. since Imuachain validator // set can not sign without the chain, the owner is likely to be an EOA or a // contract controlled by one. _transferOwnership(owner); @@ -109,7 +108,7 @@ contract Bootstrap is } /// @notice Checks if the contract is locked, meaning it has passed the offset duration - /// before the Exocore spawn time. + /// before Imuachain's spawn time. /// @dev Returns true if the contract is locked, false otherwise. /// @return bool Returns `true` if the contract is locked, `false` otherwise. function isLocked() public view returns (bool) { @@ -117,7 +116,7 @@ contract Bootstrap is } /// @dev Modifier to restrict operations based on the contract's defined timeline, that is, - /// during the offset duration before the Exocore spawn time. + /// during the offset duration before Imuachain's spawn time. modifier beforeLocked() { if (isLocked()) { revert Errors.BootstrapBeforeLocked(); @@ -137,7 +136,7 @@ contract Bootstrap is _unpause(); } - /// @notice Allows the contract owner to modify the spawn time of the Exocore chain. + /// @notice Allows the contract owner to modify the spawn time of Imuachain. /// @dev This function can only be called by the contract owner and must /// be called before the currently set lock time has started. /// @param spawnTime_ The new spawn time in seconds. @@ -149,7 +148,7 @@ contract Bootstrap is } /// @notice Allows the contract owner to modify the offset duration that determines - /// the lock period before the Exocore spawn time. + /// the lock period before Imuachain's spawn time. /// @dev This function can only be called by the contract owner and must be called /// before the currently set lock time has started. /// @param offsetDuration_ The new offset duration in seconds. @@ -162,7 +161,7 @@ contract Bootstrap is /// @dev Validates the spawn time and offset duration. /// The spawn time must be in the future and greater than the offset duration. /// The difference of the two must be greater than the current time. - /// @param spawnTime_ The spawn time of the Exocore chain to validate. + /// @param spawnTime_ The spawn time of Imuachain to validate. /// @param offsetDuration_ The offset duration before the spawn time to validate. function _validateSpawnTimeAndOffsetDuration(uint256 spawnTime_, uint256 offsetDuration_) internal view { if (offsetDuration_ == 0) { @@ -199,7 +198,7 @@ contract Bootstrap is /// @param tokens The list of token addresses to be added to the whitelist. /// @param tvlLimits The list of TVL limits for the corresponding tokens. // Though `_deployVault` would make external call to newly created `Vault` contract and initialize it, - // `Vault` contract belongs to Exocore and we could make sure its implementation does not have dangerous behavior + // `Vault` contract belongs to Imuachain and we could make sure its implementation does not have dangerous behavior // like reentrancy. // slither-disable-next-line reentrancy-no-eth function _addWhitelistTokens(address[] calldata tokens, uint256[] calldata tvlLimits) internal { @@ -258,10 +257,10 @@ contract Bootstrap is bytes32 consensusPublicKey ) external beforeLocked whenNotPaused isValidBech32Address(validatorAddress) { // ensure that there is only one validator per ethereum address - if (bytes(ethToExocoreAddress[msg.sender]).length > 0) { + if (bytes(ethToImAddress[msg.sender]).length > 0) { revert Errors.BootstrapValidatorAlreadyHasAddress(msg.sender); } - // check if validator with the same exocore address already exists + // check if validator with the same Imuachain address already exists if (bytes(validators[validatorAddress].name).length > 0) { revert Errors.BootstrapValidatorAlreadyRegistered(); } @@ -277,7 +276,7 @@ contract Bootstrap is if (!isCommissionValid(commission)) { revert Errors.BootstrapInvalidCommission(); } - ethToExocoreAddress[msg.sender] = validatorAddress; + ethToImAddress[msg.sender] = validatorAddress; validators[validatorAddress] = IValidatorRegistry.Validator({name: name, commission: commission, consensusPublicKey: consensusPublicKey}); registeredValidators.push(msg.sender); @@ -301,20 +300,20 @@ contract Bootstrap is /// @inheritdoc IValidatorRegistry function replaceKey(bytes32 newKey) external beforeLocked whenNotPaused { - if (bytes(ethToExocoreAddress[msg.sender]).length == 0) { + if (bytes(ethToImAddress[msg.sender]).length == 0) { revert Errors.BootstrapValidatorNotExist(); } _validateConsensusKey(newKey); - bytes32 oldKey = validators[ethToExocoreAddress[msg.sender]].consensusPublicKey; + bytes32 oldKey = validators[ethToImAddress[msg.sender]].consensusPublicKey; consensusPublicKeyInUse[oldKey] = false; consensusPublicKeyInUse[newKey] = true; - validators[ethToExocoreAddress[msg.sender]].consensusPublicKey = newKey; - emit ValidatorKeyReplaced(ethToExocoreAddress[msg.sender], newKey); + validators[ethToImAddress[msg.sender]].consensusPublicKey = newKey; + emit ValidatorKeyReplaced(ethToImAddress[msg.sender], newKey); } /// @inheritdoc IValidatorRegistry function updateRate(uint256 newRate) external beforeLocked whenNotPaused { - string memory validatorAddress = ethToExocoreAddress[msg.sender]; + string memory validatorAddress = ethToImAddress[msg.sender]; if (bytes(validatorAddress).length == 0) { revert Errors.BootstrapValidatorNotExist(); } @@ -397,7 +396,7 @@ contract Bootstrap is } /// @inheritdoc ILSTRestakingController - function claimPrincipalFromExocore(address token, uint256 amount) + function claimPrincipalFromImuachain(address token, uint256 amount) external payable override @@ -448,7 +447,7 @@ contract Bootstrap is /// @inheritdoc IBaseRestakingController /// @dev This is not yet supported. - function claimRewardFromExocore(address, uint256) external payable beforeLocked whenNotPaused { + function claimRewardFromImuachain(address, uint256) external payable beforeLocked whenNotPaused { revert Errors.NotYetSupported(); } @@ -574,7 +573,7 @@ contract Bootstrap is /// @inheritdoc ILSTRestakingController // Though `_deposit` would make external call to `Vault` and some state variables would be written in the following // `_delegateTo`, - // `Vault` contract belongs to Exocore and we could make sure it's implementation does not have dangerous behavior + // `Vault` contract belongs to Imuachain and we could make sure it's implementation does not have dangerous behavior // like reentrancy. // slither-disable-next-line reentrancy-no-eth function depositThenDelegateTo(address token, uint256 amount, string calldata validator) @@ -597,12 +596,12 @@ contract Bootstrap is /// @notice Marks the contract as bootstrapped. /// @dev A contract can be marked as bootstrapped only when the current time is more than - /// the Exocore spawn time, since such a call must originate from the Exocore chain. To mark + /// Imuachain's spawn time, since such a call must originate from Imuachain. To mark /// a contract as bootstrapped, the address of the client chain gateway logic contract and its /// initialization data must be set. The contract must not have been bootstrapped before. /// Once it is marked bootstrapped, the implementation of the contract is upgraded to the /// client chain gateway logic contract. - /// @dev This call can never fail, since such failures are not handled by ExocoreGateway. + /// @dev This call can never fail, since such failures are not handled by ImuachainGateway. function markBootstrapped() public onlyCalledFromThis whenNotPaused { // whenNotPaused is applied so that the upgrade does not proceed without unpausing it. // LZ checks made so far include: @@ -734,31 +733,32 @@ contract Bootstrap is revert Errors.NativeRestakingControllerInvalidStakeValue(); } - IExoCapsule capsule = ownerToCapsule[msg.sender]; + IImuaCapsule capsule = ownerToCapsule[msg.sender]; if (address(capsule) == address(0)) { - capsule = IExoCapsule(createExoCapsule()); + capsule = IImuaCapsule(createImuaCapsule()); } ETH_POS.deposit{value: 32 ether}(pubkey, capsule.capsuleWithdrawalCredentials(), signature, depositDataRoot); emit StakedWithCapsule(msg.sender, address(capsule)); } - /// @notice Creates a new ExoCapsule contract for the message sender. + /// @notice Creates a new ImuaCapsule contract for the message sender. /// @notice The message sender must be payable - /// @return The address of the newly created ExoCapsule contract. - // The bytecode returned by `BEACON_PROXY_BYTECODE` and `EXO_CAPSULE_BEACON` address are actually fixed size of byte + /// @return The address of the newly created ImuaCapsule contract. + // The bytecode returned by `BEACON_PROXY_BYTECODE` and `IMUA_CAPSULE_BEACON` address are actually fixed size of + // byte // array, so it would not cause collision for encodePacked // slither-disable-next-line encode-packed-collision - function createExoCapsule() public whenNotPaused nativeRestakingEnabled returns (address) { + function createImuaCapsule() public whenNotPaused nativeRestakingEnabled returns (address) { if (address(ownerToCapsule[msg.sender]) != address(0)) { revert Errors.NativeRestakingControllerCapsuleAlreadyCreated(); } - IExoCapsule capsule = IExoCapsule( + IImuaCapsule capsule = IImuaCapsule( Create2.deploy( 0, bytes32(uint256(uint160(msg.sender))), // set the beacon address for beacon proxy - abi.encodePacked(BEACON_PROXY_BYTECODE.getBytecode(), abi.encode(address(EXO_CAPSULE_BEACON), "")) + abi.encodePacked(BEACON_PROXY_BYTECODE.getBytecode(), abi.encode(address(IMUA_CAPSULE_BEACON), "")) ) ); @@ -784,7 +784,7 @@ contract Bootstrap is revert Errors.NonZeroValue(); } - IExoCapsule capsule = _getCapsule(msg.sender); + IImuaCapsule capsule = _getCapsule(msg.sender); uint256 depositValue = capsule.verifyDepositProof(validatorContainer, proof); if (!isDepositor[msg.sender]) { @@ -803,7 +803,7 @@ contract Bootstrap is emit DepositResult(true, VIRTUAL_NST_ADDRESS, msg.sender, depositValue); } - /// @notice Verifies a withdrawal proof from the beacon chain and forwards the information to Exocore. + /// @notice Verifies a withdrawal proof from the beacon chain and forwards the information to Imuachain. /// @notice This function is not yet supported, but staker could call this function after bootstrapping to withdraw /// their stake. function processBeaconChainWithdrawal( @@ -815,7 +815,7 @@ contract Bootstrap is revert Errors.NotYetSupported(); } - /// @notice Withdraws the nonBeaconChainETHBalance from the ExoCapsule contract. + /// @notice Withdraws the nonBeaconChainETHBalance from the ImuaCapsule contract. /// @dev @param amountToWithdraw can not be greater than the available nonBeaconChainETHBalance. /// @param recipient The payable destination address to which the ETH are sent. /// @param amountToWithdraw The amount to withdraw. @@ -825,7 +825,7 @@ contract Bootstrap is nonReentrant nativeRestakingEnabled { - IExoCapsule capsule = _getCapsule(msg.sender); + IImuaCapsule capsule = _getCapsule(msg.sender); capsule.withdrawNonBeaconChainETHBalance(recipient, amountToWithdraw); } diff --git a/src/core/BootstrapLzReceiver.sol b/src/core/BootstrapLzReceiver.sol index 7e5ae528..32787f3e 100644 --- a/src/core/BootstrapLzReceiver.sol +++ b/src/core/BootstrapLzReceiver.sol @@ -9,8 +9,8 @@ import {Action} from "../storage/GatewayStorage.sol"; import {PausableUpgradeable} from "@openzeppelin/contracts-upgradeable/security/PausableUpgradeable.sol"; /// @title BootstrapLzReceiver -/// @author ExocoreNetwork -/// @notice The base contract for the BootstrapLzReceiver. It only receives messages from the Exocore chain and does not +/// @author imua-xyz +/// @notice The base contract for the BootstrapLzReceiver. It only receives messages from Imuachain and does not /// send any. /// @dev This contract is abstract because it does not call the base contract's constructor. abstract contract BootstrapLzReceiver is PausableUpgradeable, OAppReceiverUpgradeable, BootstrapStorage { @@ -25,7 +25,7 @@ abstract contract BootstrapLzReceiver is PausableUpgradeable, OAppReceiverUpgrad /// @inheritdoc OAppReceiverUpgradeable function _lzReceive(Origin calldata _origin, bytes calldata payload) internal virtual override { - if (_origin.srcEid != EXOCORE_CHAIN_ID) { + if (_origin.srcEid != IMUACHAIN_CHAIN_ID) { revert Errors.UnexpectedSourceChain(_origin.srcEid); } _verifyAndUpdateNonce(_origin.srcEid, _origin.sender, _origin.nonce); diff --git a/src/core/ClientChainGateway.sol b/src/core/ClientChainGateway.sol index 87bd93e9..b117f29d 100644 --- a/src/core/ClientChainGateway.sol +++ b/src/core/ClientChainGateway.sol @@ -25,8 +25,8 @@ import {PausableUpgradeable} from "@openzeppelin/contracts-upgradeable/security/ import {Create2} from "@openzeppelin/contracts/utils/Create2.sol"; /// @title ClientChainGateway -/// @author ExocoreNetwork -/// @notice The gateway contract deployed on client chains for Exocore operations. +/// @author imua-xyz +/// @notice The gateway contract deployed on client chains for Imuachain operations. contract ClientChainGateway is Initializable, PausableUpgradeable, @@ -107,7 +107,7 @@ contract ClientChainGateway is /// @inheritdoc ITokenWhitelister function addWhitelistTokens(address[] calldata, uint256[] calldata) external view onlyOwner whenNotPaused { - revert Errors.ClientChainGatewayTokenAdditionViaExocore(); + revert Errors.ClientChainGatewayTokenAdditionViaImuachain(); } /// @inheritdoc ITokenWhitelister @@ -129,7 +129,7 @@ contract ClientChainGateway is bytes memory options = OptionsBuilder.newOptions().addExecutorLzReceiveOption( DESTINATION_GAS_LIMIT, DESTINATION_MSG_VALUE ).addExecutorOrderedExecutionOption(); - MessagingFee memory fee = _quote(EXOCORE_CHAIN_ID, _message, options, false); + MessagingFee memory fee = _quote(IMUACHAIN_CHAIN_ID, _message, options, false); return fee.nativeFee; } diff --git a/src/core/ClientGatewayLzReceiver.sol b/src/core/ClientGatewayLzReceiver.sol index 93babf79..c496318e 100644 --- a/src/core/ClientGatewayLzReceiver.sol +++ b/src/core/ClientGatewayLzReceiver.sol @@ -1,7 +1,7 @@ // SPDX-License-Identifier: MIT pragma solidity ^0.8.19; -import {IExoCapsule} from "../interfaces/IExoCapsule.sol"; +import {IImuaCapsule} from "../interfaces/IImuaCapsule.sol"; import {IVault} from "../interfaces/IVault.sol"; import {ActionAttributes} from "../libraries/ActionAttributes.sol"; @@ -13,8 +13,8 @@ import {Errors} from "../libraries/Errors.sol"; import {PausableUpgradeable} from "@openzeppelin/contracts-upgradeable/security/PausableUpgradeable.sol"; /// @title ClientGatewayLzReceiver -/// @author ExocoreNetwork -/// @notice This contract receives messages over LayerZero from the Exocore Gateway. +/// @author imua-xyz +/// @notice This contract receives messages over LayerZero from the Imuachain Gateway. /// @dev It is abstract because it does not call the base contract's constructor. abstract contract ClientGatewayLzReceiver is PausableUpgradeable, OAppReceiverUpgradeable, ClientChainGatewayStorage { @@ -43,7 +43,7 @@ abstract contract ClientGatewayLzReceiver is PausableUpgradeable, OAppReceiverUp // This function would call other functions inside this contract through low-level-call // slither-disable-next-line reentrancy-no-eth function _lzReceive(Origin calldata _origin, bytes calldata message) internal virtual override whenNotPaused { - if (_origin.srcEid != EXOCORE_CHAIN_ID) { + if (_origin.srcEid != IMUACHAIN_CHAIN_ID) { revert Errors.UnexpectedSourceChain(_origin.srcEid); } @@ -67,11 +67,11 @@ abstract contract ClientGatewayLzReceiver is PausableUpgradeable, OAppReceiverUp emit MessageExecuted(act, _origin.nonce); } - /// @dev Called after a response is received from the Exocore Gateway. + /// @dev Called after a response is received from the Imuachain Gateway. /// @param response The response message. - // Though this function makes external calls to contract Vault or ExoCapsule, we just update their state variables + // Though this function makes external calls to contract Vault or ImuaCapsule, we just update their state variables // and don't make - // calls to other contracts that do not belong to Exocore. + // calls to other contracts that do not belong to Imuachain. // And (success, updatedBalance) would be updated according to response message. // slither-disable-next-line reentrancy-no-eth function _handleResponse(bytes calldata response) internal { @@ -151,7 +151,7 @@ abstract contract ClientGatewayLzReceiver is PausableUpgradeable, OAppReceiverUp */ function _unlockPrincipal(address token, address staker, uint256 amount) internal { if (token == VIRTUAL_NST_ADDRESS) { - IExoCapsule capsule = _getCapsule(staker); + IImuaCapsule capsule = _getCapsule(staker); capsule.unlockETHPrincipal(amount); } else { IVault vault = _getVault(token); @@ -172,7 +172,7 @@ abstract contract ClientGatewayLzReceiver is PausableUpgradeable, OAppReceiverUp /// @notice Called after an add-whitelist-token response is received. /// @param payload The request payload. /// @dev Though `_deployVault` would make external call to newly created `Vault` contract and initialize it, - /// `Vault` contract belongs to Exocore and we could make sure its implementation does not have dangerous behavior + /// `Vault` contract belongs to Imuachain and we could make sure its implementation does not have dangerous behavior /// like reentrancy. // slither-disable-next-line reentrancy-no-eth function afterReceiveAddWhitelistTokenRequest(bytes calldata payload) public onlyCalledFromThis whenNotPaused { diff --git a/src/core/CombinedFaucet.sol b/src/core/CombinedFaucet.sol index 18838d0f..e7e00b07 100644 --- a/src/core/CombinedFaucet.sol +++ b/src/core/CombinedFaucet.sol @@ -11,6 +11,9 @@ import {IERC20} from "@openzeppelin/contracts/token/ERC20/IERC20.sol"; import {IERC721Receiver} from "@openzeppelin/contracts/token/ERC721/IERC721Receiver.sol"; import {IERC165} from "@openzeppelin/contracts/utils/introspection/IERC165.sol"; +/// @title CombinedFaucet +/// @author imua-xyz +/// @notice This contract can support both ERC20 and the EVM native token. contract CombinedFaucet is IERC165, IERC1155Receiver, diff --git a/src/core/ExoCapsule.sol b/src/core/ImuaCapsule.sol similarity index 91% rename from src/core/ExoCapsule.sol rename to src/core/ImuaCapsule.sol index b1954c96..e1ddfb3c 100644 --- a/src/core/ExoCapsule.sol +++ b/src/core/ImuaCapsule.sol @@ -1,22 +1,22 @@ // SPDX-License-Identifier: MIT pragma solidity ^0.8.19; -import {IExoCapsule} from "../interfaces/IExoCapsule.sol"; +import {IImuaCapsule} from "../interfaces/IImuaCapsule.sol"; import {INativeRestakingController} from "../interfaces/INativeRestakingController.sol"; import {BeaconChainProofs} from "../libraries/BeaconChainProofs.sol"; import {Endian} from "../libraries/Endian.sol"; import {ValidatorContainer} from "../libraries/ValidatorContainer.sol"; import {WithdrawalContainer} from "../libraries/WithdrawalContainer.sol"; -import {ExoCapsuleStorage} from "../storage/ExoCapsuleStorage.sol"; +import {ImuaCapsuleStorage} from "../storage/ImuaCapsuleStorage.sol"; import {IBeaconChainOracle} from "@beacon-oracle/contracts/src/IBeaconChainOracle.sol"; import {ReentrancyGuardUpgradeable} from "@openzeppelin/contracts-upgradeable/security/ReentrancyGuardUpgradeable.sol"; -/// @title ExoCapsule -/// @author ExocoreNetwork -/// @notice The ExoCapsule contract is used to stake, deposit and withdraw from the Ethereum beacon chain. -contract ExoCapsule is ReentrancyGuardUpgradeable, ExoCapsuleStorage, IExoCapsule { +/// @title ImuaCapsule +/// @author imua-xyz +/// @notice The ImuaCapsule contract is used to stake, deposit and withdraw from the Imuachain beacon chain. +contract ImuaCapsule is ReentrancyGuardUpgradeable, ImuaCapsuleStorage, IImuaCapsule { using BeaconChainProofs for bytes32; using Endian for bytes32; @@ -131,9 +131,9 @@ contract ExoCapsule is ReentrancyGuardUpgradeable, ExoCapsuleStorage, IExoCapsul _; } - /// @notice Constructor to create the ExoCapsule contract. + /// @notice Constructor to create the ImuaCapsule contract. /// @param networkConfig_ network configuration contract address. - constructor(address networkConfig_) ExoCapsuleStorage(networkConfig_) { + constructor(address networkConfig_) ImuaCapsuleStorage(networkConfig_) { _disableInitializers(); } @@ -143,11 +143,11 @@ contract ExoCapsule is ReentrancyGuardUpgradeable, ExoCapsuleStorage, IExoCapsul emit NonBeaconChainETHReceived(msg.value); } - /// @inheritdoc IExoCapsule + /// @inheritdoc IImuaCapsule function initialize(address gateway_, address payable capsuleOwner_, address beaconOracle_) external initializer { - require(gateway_ != address(0), "ExoCapsule: gateway address can not be empty"); - require(capsuleOwner_ != address(0), "ExoCapsule: capsule owner address can not be empty"); - require(beaconOracle_ != address(0), "ExoCapsule: beacon chain oracle address should not be empty"); + require(gateway_ != address(0), "ImuaCapsule: gateway address can not be empty"); + require(capsuleOwner_ != address(0), "ImuaCapsule: capsule owner address can not be empty"); + require(beaconOracle_ != address(0), "ImuaCapsule: beacon chain oracle address should not be empty"); gateway = INativeRestakingController(gateway_); beaconOracle = IBeaconChainOracle(beaconOracle_); @@ -158,7 +158,7 @@ contract ExoCapsule is ReentrancyGuardUpgradeable, ExoCapsuleStorage, IExoCapsul emit RestakingActivated(capsuleOwner); } - /// @inheritdoc IExoCapsule + /// @inheritdoc IImuaCapsule function verifyDepositProof( bytes32[] calldata validatorContainer, BeaconChainProofs.ValidatorContainerProof calldata proof @@ -197,7 +197,7 @@ contract ExoCapsule is ReentrancyGuardUpgradeable, ExoCapsuleStorage, IExoCapsul _capsuleValidatorsByIndex[proof.validatorIndex] = validatorPubkeyHash; } - /// @inheritdoc IExoCapsule + /// @inheritdoc IImuaCapsule function verifyWithdrawalProof( bytes32[] calldata validatorContainer, BeaconChainProofs.ValidatorContainerProof calldata validatorProof, @@ -234,7 +234,7 @@ contract ExoCapsule is ReentrancyGuardUpgradeable, ExoCapsuleStorage, IExoCapsul uint64 withdrawalAmountGwei = withdrawalContainer.getAmount(); if (partialWithdrawal) { - // Immediately send ETH without sending request to Exocore side + // Immediately send ETH without sending request to Imuachain side emit PartialWithdrawalRedeemed(validatorPubkeyHash, withdrawalEpoch, capsuleOwner, withdrawalAmountGwei); _sendETH(capsuleOwner, withdrawalAmountGwei * GWEI_TO_WEI); } else { @@ -252,10 +252,10 @@ contract ExoCapsule is ReentrancyGuardUpgradeable, ExoCapsuleStorage, IExoCapsul } } - /// @inheritdoc IExoCapsule + /// @inheritdoc IImuaCapsule function withdraw(uint256 amount, address payable recipient) external onlyGateway { - require(recipient != address(0), "ExoCapsule: recipient address cannot be zero or empty"); - require(amount > 0 && amount <= withdrawableBalance, "ExoCapsule: invalid withdrawal amount"); + require(recipient != address(0), "ImuaCapsule: recipient address cannot be zero or empty"); + require(amount > 0 && amount <= withdrawableBalance, "ImuaCapsule: invalid withdrawal amount"); withdrawableBalance -= amount; _sendETH(recipient, amount); @@ -274,23 +274,23 @@ contract ExoCapsule is ReentrancyGuardUpgradeable, ExoCapsuleStorage, IExoCapsul { require( amountToWithdraw <= nonBeaconChainETHBalance, - "ExoCapsule.withdrawNonBeaconChainETHBalance: amountToWithdraw is greater than nonBeaconChainETHBalance" + "ImuaCapsule.withdrawNonBeaconChainETHBalance: amountToWithdraw is greater than nonBeaconChainETHBalance" ); - require(recipient != address(0), "ExoCapsule: recipient address cannot be zero or empty"); + require(recipient != address(0), "ImuaCapsule: recipient address cannot be zero or empty"); nonBeaconChainETHBalance -= amountToWithdraw; _sendETH(recipient, amountToWithdraw); emit NonBeaconChainETHWithdrawn(recipient, amountToWithdraw); } - /// @inheritdoc IExoCapsule + /// @inheritdoc IImuaCapsule function unlockETHPrincipal(uint256 unlockPrincipalAmount) external onlyGateway { withdrawableBalance += unlockPrincipalAmount; emit ETHPrincipalUnlocked(capsuleOwner, unlockPrincipalAmount); } - /// @inheritdoc IExoCapsule + /// @inheritdoc IImuaCapsule function capsuleWithdrawalCredentials() public view returns (bytes memory) { /** * The withdrawal_credentials field must be such that: @@ -316,7 +316,7 @@ contract ExoCapsule is ReentrancyGuardUpgradeable, ExoCapsuleStorage, IExoCapsul /// @notice Gets the registered validator by pubkeyHash. /// @dev The validator status must be registered. Reverts if not. /// @param pubkeyHash The validator's BLS12-381 public key hash. - /// @return The validator object, as defined in the `ExoCapsuleStorage`. + /// @return The validator object, as defined in the `ImuaCapsuleStorage`. function getRegisteredValidatorByPubkey(bytes32 pubkeyHash) public view returns (Validator memory) { Validator memory validator = _capsuleValidators[pubkeyHash]; if (validator.status == VALIDATOR_STATUS.UNREGISTERED) { @@ -329,7 +329,7 @@ contract ExoCapsule is ReentrancyGuardUpgradeable, ExoCapsuleStorage, IExoCapsul /// @notice Gets the registered validator by index. /// @dev The validator status must be registered. /// @param index The index of the validator. - /// @return The validator object, as defined in the `ExoCapsuleStorage`. + /// @return The validator object, as defined in the `ImuaCapsuleStorage`. function getRegisteredValidatorByIndex(uint256 index) public view returns (Validator memory) { Validator memory validator = _capsuleValidators[_capsuleValidatorsByIndex[index]]; if (validator.status == VALIDATOR_STATUS.UNREGISTERED) { diff --git a/src/core/ExocoreGateway.sol b/src/core/ImuachainGateway.sol similarity index 90% rename from src/core/ExocoreGateway.sol rename to src/core/ImuachainGateway.sol index c8d489f6..bc23e5b0 100644 --- a/src/core/ExocoreGateway.sol +++ b/src/core/ImuachainGateway.sol @@ -1,7 +1,7 @@ // SPDX-License-Identifier: MIT pragma solidity ^0.8.19; -import {IExocoreGateway} from "../interfaces/IExocoreGateway.sol"; +import {IImuachainGateway} from "../interfaces/IImuachainGateway.sol"; import {Action} from "../storage/GatewayStorage.sol"; @@ -17,7 +17,7 @@ import { OAppUpgradeable, Origin } from "../lzApp/OAppUpgradeable.sol"; -import {ExocoreGatewayStorage} from "../storage/ExocoreGatewayStorage.sol"; +import {ImuachainGatewayStorage} from "../storage/ImuachainGatewayStorage.sol"; import {Errors} from "../libraries/Errors.sol"; import {OAppCoreUpgradeable} from "../lzApp/OAppCoreUpgradeable.sol"; @@ -29,17 +29,17 @@ import {Initializable} from "@openzeppelin/contracts-upgradeable/proxy/utils/Ini import {PausableUpgradeable} from "@openzeppelin/contracts-upgradeable/security/PausableUpgradeable.sol"; import {ReentrancyGuardUpgradeable} from "@openzeppelin/contracts-upgradeable/security/ReentrancyGuardUpgradeable.sol"; -/// @title ExocoreGateway -/// @author ExocoreNetwork -/// @notice The gateway contract deployed on Exocore chain for client chain operations. +/// @title ImuachainGateway +/// @author imua-xyz +/// @notice The gateway contract deployed on Imuachain for client chain operations. /// @dev This contract address must be registered in the `x/assets` module for the precompile operations to go through. -contract ExocoreGateway is +contract ImuachainGateway is Initializable, PausableUpgradeable, OwnableUpgradeable, ReentrancyGuardUpgradeable, - IExocoreGateway, - ExocoreGatewayStorage, + IImuachainGateway, + ImuachainGatewayStorage, OAppUpgradeable { @@ -48,12 +48,12 @@ contract ExocoreGateway is /// @dev Ensures that the function is called only from this contract via low-level call. modifier onlyCalledFromThis() { if (msg.sender != address(this)) { - revert Errors.ExocoreGatewayOnlyCalledFromThis(); + revert Errors.ImuachainGatewayOnlyCalledFromThis(); } _; } - /// @notice Creates the ExocoreGateway contract. + /// @notice Creates the ImuachainGateway contract. /// @param endpoint_ The LayerZero endpoint address deployed on this chain constructor(address endpoint_) OAppUpgradeable(endpoint_) { _disableInitializers(); @@ -61,7 +61,7 @@ contract ExocoreGateway is receive() external payable {} - /// @notice Initializes the ExocoreGateway contract. + /// @notice Initializes the ImuachainGateway contract. /// @param owner_ The address of the contract owner. function initialize(address owner_) external initializer { if (owner_ == address(0)) { @@ -116,7 +116,7 @@ contract ExocoreGateway is emit BootstrapRequestSent(chainIndex); } - /// @inheritdoc IExocoreGateway + /// @inheritdoc IImuachainGateway function registerOrUpdateClientChain( uint32 clientChainId, bytes32 peer, @@ -162,7 +162,7 @@ contract ExocoreGateway is super.setPeer(clientChainId, clientChainGateway); } - /// @inheritdoc IExocoreGateway + /// @inheritdoc IImuachainGateway /// @notice Tokens can only be normal reward-bearing LST tokens like wstETH, rETH, jitoSol... /// And they are not intended to be: 1) rebasing tokens like stETH, since we assume staker's /// balance would not change if nothing is done after deposit, 2) fee-on-transfer tokens, since we @@ -179,11 +179,21 @@ contract ExocoreGateway is string calldata oracleInfo, uint128 tvlLimit ) external payable onlyOwner whenNotPaused nonReentrant { - require(clientChainId != 0, "ExocoreGateway: client chain id cannot be zero"); - require(token != bytes32(0), "ExocoreGateway: token cannot be zero address"); - require(bytes(name).length != 0, "ExocoreGateway: name cannot be empty"); - require(bytes(metaData).length != 0, "ExocoreGateway: meta data cannot be empty"); - require(bytes(oracleInfo).length != 0, "ExocoreGateway: oracleInfo cannot be empty"); + if (clientChainId == 0) { + revert Errors.ZeroValue(); + } + if (token == bytes32(0)) { + revert Errors.ZeroAddress(); + } + if (bytes(name).length == 0) { + revert Errors.ZeroValue(); + } + if (bytes(metaData).length == 0) { + revert Errors.ZeroValue(); + } + if (bytes(oracleInfo).length == 0) { + revert Errors.ZeroValue(); + } // setting a TVL limit of 0 is permitted to simply add an inactive token, which may // be activated later by updating the TVL limit on the client chain @@ -205,16 +215,22 @@ contract ExocoreGateway is } } - /// @inheritdoc IExocoreGateway + /// @inheritdoc IImuachainGateway function updateWhitelistToken(uint32 clientChainId, bytes32 token, string calldata metaData) external onlyOwner whenNotPaused nonReentrant { - require(clientChainId != 0, "ExocoreGateway: client chain id cannot be zero"); - require(token != bytes32(0), "ExocoreGateway: token cannot be zero address"); - require(bytes(metaData).length != 0, "ExocoreGateway: meta data cannot be empty"); + if (clientChainId == 0) { + revert Errors.ZeroValue(); + } + if (token == bytes32(0)) { + revert Errors.ZeroAddress(); + } + if (bytes(metaData).length == 0) { + revert Errors.ZeroValue(); + } bool success = ASSETS_CONTRACT.updateToken(clientChainId, abi.encodePacked(token), metaData); if (success) { emit WhitelistTokenUpdated(clientChainId, token); @@ -224,10 +240,10 @@ contract ExocoreGateway is } /** - * @notice Associate an Exocore operator with an EVM staker(msg.sender), and this would count staker's delegation + * @notice Associate an Imuachain operator with an EVM staker(msg.sender), and this would count staker's delegation * as operator's self-delegation when staker delegates to operator. * @param clientChainId The id of client chain - * @param operator The Exocore operator address + * @param operator The Imuachain operator address * @dev one staker(chainId+stakerAddress) can only associate one operator, while one operator might be associated * with multiple stakers */ @@ -244,7 +260,7 @@ contract ExocoreGateway is } /** - * @notice Dissociate an Exocore operator from an EVM staker(msg.sender), and this requires that the staker has + * @notice Dissociate an Imuachain operator from an EVM staker(msg.sender), and this requires that the staker has * already been associated to operator. * @param clientChainId The id of client chain */ @@ -264,10 +280,10 @@ contract ExocoreGateway is function _validateClientChainIdRegistered(uint32 clientChainId) internal view { (bool success, bool isRegistered) = ASSETS_CONTRACT.isRegisteredClientChain(clientChainId); if (!success) { - revert Errors.ExocoreGatewayFailedToCheckClientChainId(); + revert Errors.ImuachainGatewayFailedToCheckClientChainId(); } if (!isRegistered) { - revert Errors.ExocoreGatewayNotRegisteredClientChainId(); + revert Errors.ImuachainGatewayNotRegisteredClientChainId(); } } @@ -287,7 +303,7 @@ contract ExocoreGateway is (bool success, bool updated) = ASSETS_CONTRACT.registerOrUpdateClientChain(clientChainId, addressLength, name, metaInfo, signatureType); if (!success) { - revert Errors.RegisterClientChainToExocoreFailed(clientChainId); + revert Errors.RegisterClientChainToImuachainFailed(clientChainId); } return updated; } @@ -354,11 +370,7 @@ contract ExocoreGateway is } emit LSTTransfer(isDeposit, success, bytes32(token), bytes32(staker), amount); - if (_isSolana(srcChainId)) { - response = isDeposit ? bytes("") : abi.encodePacked(lzNonce, success, bytes32(token), bytes32(staker)); - } else { - response = isDeposit ? bytes("") : abi.encodePacked(lzNonce, success); - } + response = isDeposit ? bytes("") : abi.encodePacked(lzNonce, success); } /// @notice Handles NST transfer from a client chain. @@ -427,13 +439,7 @@ contract ExocoreGateway is } emit RewardOperation(isSubmitReward, success, bytes32(token), bytes32(avsOrWithdrawer), amount); - if (_isSolana(srcChainId)) { - response = isSubmitReward - ? bytes("") - : abi.encodePacked(lzNonce, success, bytes32(token), bytes32(avsOrWithdrawer)); - } else { - response = isSubmitReward ? bytes("") : abi.encodePacked(lzNonce, success); - } + response = isSubmitReward ? bytes("") : abi.encodePacked(lzNonce, success); } /// @notice Handles delegation request from a client chain. @@ -508,8 +514,7 @@ contract ExocoreGateway is bool isAssociate = act == Action.REQUEST_ASSOCIATE_OPERATOR; if (isAssociate) { - bytes calldata operator = payload[32:74]; - + bytes calldata operator = payload[32:]; success = DELEGATION_CONTRACT.associateOperatorWithStaker(srcChainId, staker, operator); } else { success = DELEGATION_CONTRACT.dissociateOperatorFromStaker(srcChainId, staker); @@ -540,7 +545,7 @@ contract ExocoreGateway is emit MessageSent(act, receipt.guid, receipt.nonce, receipt.fee.nativeFee); } - /// @inheritdoc IExocoreGateway + /// @inheritdoc IImuachainGateway function quote(uint32 srcChainId, bytes calldata _message) public view returns (uint256 nativeFee) { Action act = Action(uint8(_message[0])); diff --git a/src/core/LSTRestakingController.sol b/src/core/LSTRestakingController.sol index 3681d481..b79fa70f 100644 --- a/src/core/LSTRestakingController.sol +++ b/src/core/LSTRestakingController.sol @@ -13,7 +13,7 @@ import {PausableUpgradeable} from "@openzeppelin/contracts-upgradeable/security/ import {ReentrancyGuardUpgradeable} from "@openzeppelin/contracts-upgradeable/security/ReentrancyGuardUpgradeable.sol"; /// @title LSTRestakingController -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice Implementation of ILSTRestakingController, used to restake tokens. abstract contract LSTRestakingController is PausableUpgradeable, @@ -42,7 +42,7 @@ abstract contract LSTRestakingController is } /// @inheritdoc ILSTRestakingController - function claimPrincipalFromExocore(address token, uint256 principalAmount) + function claimPrincipalFromImuachain(address token, uint256 principalAmount) external payable isTokenWhitelisted(token) diff --git a/src/core/NativeRestakingController.sol b/src/core/NativeRestakingController.sol index d9f35674..822462dd 100644 --- a/src/core/NativeRestakingController.sol +++ b/src/core/NativeRestakingController.sol @@ -1,7 +1,7 @@ // SPDX-License-Identifier: MIT pragma solidity ^0.8.19; -import {IExoCapsule} from "../interfaces/IExoCapsule.sol"; +import {IImuaCapsule} from "../interfaces/IImuaCapsule.sol"; import {INativeRestakingController} from "../interfaces/INativeRestakingController.sol"; import {BeaconChainProofs} from "../libraries/BeaconChainProofs.sol"; import {ValidatorContainer} from "../libraries/ValidatorContainer.sol"; @@ -17,7 +17,7 @@ import {ReentrancyGuardUpgradeable} from "@openzeppelin/contracts-upgradeable/se import {Create2} from "@openzeppelin/contracts/utils/Create2.sol"; /// @title NativeRestakingController -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice This is the implementation of INativeRestakingController. It allows Ethereum validators /// to stake, deposit and withdraw from the Ethereum beacon chain. /// @dev This contract is abstract because it does not call the base constructor. @@ -47,31 +47,32 @@ abstract contract NativeRestakingController is revert Errors.NativeRestakingControllerInvalidStakeValue(); } - IExoCapsule capsule = ownerToCapsule[msg.sender]; + IImuaCapsule capsule = ownerToCapsule[msg.sender]; if (address(capsule) == address(0)) { - capsule = IExoCapsule(createExoCapsule()); + capsule = IImuaCapsule(createImuaCapsule()); } ETH_POS.deposit{value: 32 ether}(pubkey, capsule.capsuleWithdrawalCredentials(), signature, depositDataRoot); emit StakedWithCapsule(msg.sender, address(capsule)); } - /// @notice Creates a new ExoCapsule contract for the message sender. + /// @notice Creates a new ImuaCapsule contract for the message sender. /// @notice The message sender must be payable - /// @return The address of the newly created ExoCapsule contract. - // The bytecode returned by `BEACON_PROXY_BYTECODE` and `EXO_CAPSULE_BEACON` address are actually fixed size of byte + /// @return The address of the newly created ImuaCapsule contract. + // The bytecode returned by `BEACON_PROXY_BYTECODE` and `IMUA_CAPSULE_BEACON` address are actually fixed size of + // byte // array, so it would not cause collision for encodePacked // slither-disable-next-line encode-packed-collision - function createExoCapsule() public whenNotPaused nativeRestakingEnabled returns (address) { + function createImuaCapsule() public whenNotPaused nativeRestakingEnabled returns (address) { if (address(ownerToCapsule[msg.sender]) != address(0)) { revert Errors.NativeRestakingControllerCapsuleAlreadyCreated(); } - IExoCapsule capsule = IExoCapsule( + IImuaCapsule capsule = IImuaCapsule( Create2.deploy( 0, bytes32(uint256(uint160(msg.sender))), // set the beacon address for beacon proxy - abi.encodePacked(BEACON_PROXY_BYTECODE.getBytecode(), abi.encode(address(EXO_CAPSULE_BEACON), "")) + abi.encodePacked(BEACON_PROXY_BYTECODE.getBytecode(), abi.encode(address(IMUA_CAPSULE_BEACON), "")) ) ); @@ -84,14 +85,14 @@ abstract contract NativeRestakingController is return address(capsule); } - /// @notice Verifies a deposit proof from the beacon chain and forwards the information to Exocore. + /// @notice Verifies a deposit proof from the beacon chain and forwards the information to Imuachain. /// @param validatorContainer The validator container which made the deposit. /// @param proof The proof of the validator container. function verifyAndDepositNativeStake( bytes32[] calldata validatorContainer, BeaconChainProofs.ValidatorContainerProof calldata proof ) external payable whenNotPaused nonReentrant nativeRestakingEnabled { - IExoCapsule capsule = _getCapsule(msg.sender); + IImuaCapsule capsule = _getCapsule(msg.sender); uint256 depositValue = capsule.verifyDepositProof(validatorContainer, proof); bytes memory actionArgs = abi.encodePacked(bytes32(bytes20(msg.sender)), depositValue, proof.validatorIndex); @@ -100,7 +101,7 @@ abstract contract NativeRestakingController is _processRequest(Action.REQUEST_DEPOSIT_NST, actionArgs, bytes("")); } - /// @notice Verifies a withdrawal proof from the beacon chain and forwards the information to Exocore. + /// @notice Verifies a withdrawal proof from the beacon chain and forwards the information to Imuachain. /// @param validatorContainer The validator container which made the withdrawal. /// @param validatorProof The proof of the validator container. /// @param withdrawalContainer The withdrawal container. @@ -111,7 +112,7 @@ abstract contract NativeRestakingController is bytes32[] calldata withdrawalContainer, BeaconChainProofs.WithdrawalProof calldata withdrawalProof ) external payable whenNotPaused nonReentrant nativeRestakingEnabled { - IExoCapsule capsule = _getCapsule(msg.sender); + IImuaCapsule capsule = _getCapsule(msg.sender); (bool partialWithdrawal, uint256 withdrawalAmount) = capsule.verifyWithdrawalProof(validatorContainer, validatorProof, withdrawalContainer, withdrawalProof); if (!partialWithdrawal) { @@ -120,12 +121,12 @@ abstract contract NativeRestakingController is abi.encodePacked(bytes32(bytes20(msg.sender)), withdrawalAmount, validatorProof.validatorIndex); bytes memory encodedRequest = abi.encode(VIRTUAL_NST_ADDRESS, msg.sender, withdrawalAmount); - // a full withdrawal needs response from Exocore, so we don't pass empty bytes + // a full withdrawal needs response from Imuachain, so we don't pass empty bytes _processRequest(Action.REQUEST_WITHDRAW_NST, actionArgs, encodedRequest); } } - /// @notice Withdraws the nonBeaconChainETHBalance from the ExoCapsule contract. + /// @notice Withdraws the nonBeaconChainETHBalance from the ImuaCapsule contract. /// @dev @param amountToWithdraw can not be greater than the available nonBeaconChainETHBalance. /// @param recipient The payable destination address to which the ETH are sent. /// @param amountToWithdraw The amount to withdraw. @@ -135,7 +136,7 @@ abstract contract NativeRestakingController is nonReentrant nativeRestakingEnabled { - IExoCapsule capsule = _getCapsule(msg.sender); + IImuaCapsule capsule = _getCapsule(msg.sender); capsule.withdrawNonBeaconChainETHBalance(recipient, amountToWithdraw); } diff --git a/src/core/UTXOGateway.sol b/src/core/UTXOGateway.sol index a3acc6f6..5d88b450 100644 --- a/src/core/UTXOGateway.sol +++ b/src/core/UTXOGateway.sol @@ -2,7 +2,7 @@ pragma solidity ^0.8.19; import {Errors} from "../libraries/Errors.sol"; -import {ExocoreBytes} from "../libraries/ExocoreBytes.sol"; +import {ImuachainBytes} from "../libraries/ImuachainBytes.sol"; import {ASSETS_CONTRACT} from "../interfaces/precompiles/IAssets.sol"; import {DELEGATION_CONTRACT} from "../interfaces/precompiles/IDelegation.sol"; @@ -16,7 +16,7 @@ import {ReentrancyGuardUpgradeable} from "@openzeppelin/contracts-upgradeable/se /** * @title UTXOGateway - * @dev This contract manages the gateway between Bitcoin like chains and the Exocore system. + * @dev This contract manages the gateway between Bitcoin like chains and Imua * It handles deposits, delegations, withdrawals, and peg-out requests for BTC like tokens. */ contract UTXOGateway is @@ -27,7 +27,7 @@ contract UTXOGateway is UTXOGatewayStorage { - using ExocoreBytes for address; + using ImuachainBytes for address; using SignatureVerifier for bytes32; /** @@ -40,7 +40,7 @@ contract UTXOGateway is /** * @notice Returns the app version. - * @dev This is used to check the compatibility of the gateway with the Exocore system. + * @dev This is used to check the compatibility of the gateway with Imua * @return The app version. */ function appVersion() external pure returns (uint256) { @@ -48,7 +48,7 @@ contract UTXOGateway is } /** - * @notice Initializes the contract with the Exocore witness address, owner address and required proofs. + * @notice Initializes the contract with the Imuachain witness address, owner address and required proofs. * @dev If the witnesses length is greater or equal to the required proofs, the consensus requirement for stake * message would be activated. * @param owner_ The address of the owner. @@ -89,7 +89,7 @@ contract UTXOGateway is } /** - * @notice Activates token staking by registering or updating the chain and token with the Exocore system. + * @notice Activates token staking by registering or updating the chain and token with Imua */ function activateStakingForClientChain(ClientChainID clientChainId) external onlyOwner whenNotPaused { if (clientChainId == ClientChainID.BITCOIN) { @@ -226,7 +226,7 @@ contract UTXOGateway is } /** - * @notice Deposits BTC like tokens to the Exocore system. + * @notice Deposits BTC like tokens to Imua * @param witness The witness address that signed the message. * @param _msg The stake message. * @param signature The signature of the message. @@ -251,7 +251,7 @@ contract UTXOGateway is /** * @notice Delegates BTC like tokens to an operator. * @param token The value of the token enum. - * @param operator The operator's exocore address. + * @param operator The operator's Imuachain address. * @param amount The amount to delegate. */ function delegateTo(Token token, string calldata operator, uint256 amount) @@ -278,7 +278,7 @@ contract UTXOGateway is /** * @notice Undelegates BTC like tokens from an operator. * @param token The value of the token enum. - * @param operator The operator's exocore address. + * @param operator The operator's Imuachain address. * @param amount The amount to undelegate. */ function undelegateFrom(Token token, string calldata operator, uint256 amount) @@ -296,7 +296,7 @@ contract UTXOGateway is uint64 nonce = ++delegationNonce[clientChainId]; bool success = DELEGATION_CONTRACT.undelegate( - uint32(uint8(clientChainId)), nonce, VIRTUAL_TOKEN, msg.sender.toExocoreBytes(), bytes(operator), amount + uint32(uint8(clientChainId)), nonce, VIRTUAL_TOKEN, msg.sender.toImuachainBytes(), bytes(operator), amount ); if (!success) { revert Errors.UndelegationFailed(); @@ -318,7 +318,7 @@ contract UTXOGateway is } (bool success, uint256 updatedBalance) = ASSETS_CONTRACT.withdrawLST( - uint32(uint8(clientChainId)), VIRTUAL_TOKEN, msg.sender.toExocoreBytes(), amount + uint32(uint8(clientChainId)), VIRTUAL_TOKEN, msg.sender.toImuachainBytes(), amount ); if (!success) { revert Errors.WithdrawPrincipalFailed(); @@ -342,7 +342,7 @@ contract UTXOGateway is } (bool success, uint256 updatedBalance) = REWARD_CONTRACT.claimReward( - uint32(uint8(clientChainId)), VIRTUAL_TOKEN, msg.sender.toExocoreBytes(), amount + uint32(uint8(clientChainId)), VIRTUAL_TOKEN, msg.sender.toImuachainBytes(), amount ); if (!success) { revert Errors.WithdrawRewardFailed(); @@ -423,26 +423,26 @@ contract UTXOGateway is } /** - * @notice Gets the client chain address for a given Exocore address + * @notice Gets the client chain address for a given Imuachain address * @param clientChainId The client chain ID - * @param exocoreAddress The Exocore address + * @param imuachainAddress The Imuachain address * @return The client chain address */ - function getClientAddress(ClientChainID clientChainId, address exocoreAddress) + function getClientAddress(ClientChainID clientChainId, address imuachainAddress) external view returns (bytes memory) { - return outboundRegistry[clientChainId][exocoreAddress]; + return outboundRegistry[clientChainId][imuachainAddress]; } /** - * @notice Gets the Exocore address for a given client chain address + * @notice Gets the Imuachain address for a given client chain address * @param clientChainId The client chain ID * @param clientAddress The client chain address - * @return The Exocore address + * @return The Imuachain address */ - function getExocoreAddress(ClientChainID clientChainId, bytes calldata clientAddress) + function getImuachainAddress(ClientChainID clientChainId, bytes calldata clientAddress) external view returns (address) @@ -610,7 +610,7 @@ contract UTXOGateway is } /** - * @notice Registers or updates the Bitcoin chain with the Exocore system. + * @notice Registers or updates the Bitcoin chain with Imua */ function _registerOrUpdateClientChain( ClientChainID clientChainId, @@ -623,7 +623,7 @@ contract UTXOGateway is uint32(uint8(clientChainId)), stakerAccountLength, name, metadata, signatureScheme ); if (!success) { - revert Errors.RegisterClientChainToExocoreFailed(uint32(uint8(clientChainId))); + revert Errors.RegisterClientChainToImuachainFailed(uint32(uint8(clientChainId))); } if (updated) { emit ClientChainUpdated(clientChainId); @@ -671,7 +671,7 @@ contract UTXOGateway is _msg.nonce, _msg.clientTxId, _msg.clientAddress, - _msg.exocoreAddress, + _msg.imuachainAddress, _msg.operator, _msg.amount ); @@ -732,7 +732,7 @@ contract UTXOGateway is * @dev This function creates a new peg-out request and stores it in the contract's state * @param clientChainId The client chain to be pegged out * @param _amount The amount of tokens to be pegged out - * @param withdrawer The Exocore address associated with the Bitcoin address + * @param withdrawer The Imuachain address associated with the Bitcoin address * @param clientAddress The client chain address * @param _withdrawType The type of withdrawal (e.g., normal, fast) * @return requestId The unique identifier for the peg-out request @@ -767,31 +767,31 @@ contract UTXOGateway is * @notice Internal function to deposit BTC like token. * @param clientChainId The client chain ID. * @param srcAddress The source address. - * @param depositorExoAddr The Exocore address. + * @param depositorImAddr The Imuachain address. * @param amount The amount to deposit. * @param clientTxId The client chain transaction ID. */ function _deposit( ClientChainID clientChainId, bytes memory srcAddress, - address depositorExoAddr, + address depositorImAddr, uint256 amount, bytes32 clientTxId ) internal { (bool success, uint256 updatedBalance) = ASSETS_CONTRACT.depositLST( - uint32(uint8(clientChainId)), VIRTUAL_TOKEN, depositorExoAddr.toExocoreBytes(), amount + uint32(uint8(clientChainId)), VIRTUAL_TOKEN, depositorImAddr.toImuachainBytes(), amount ); if (!success) { revert Errors.DepositFailed(clientTxId); } - emit DepositCompleted(clientChainId, clientTxId, depositorExoAddr, srcAddress, amount, updatedBalance); + emit DepositCompleted(clientChainId, clientTxId, depositorImAddr, srcAddress, amount, updatedBalance); } /** * @notice Internal function to delegate BTC like token. * @param clientChainId The client chain ID. - * @param delegator The Exocore address. + * @param delegator The Imuachain address. * @param operator The operator's address. * @param amount The amount to delegate. * @return success True if the delegation was successful, false otherwise. @@ -803,7 +803,7 @@ contract UTXOGateway is { uint64 nonce = ++delegationNonce[clientChainId]; success = DELEGATION_CONTRACT.delegate( - uint32(uint8(clientChainId)), nonce, VIRTUAL_TOKEN, delegator.toExocoreBytes(), bytes(operator), amount + uint32(uint8(clientChainId)), nonce, VIRTUAL_TOKEN, delegator.toImuachainBytes(), bytes(operator), amount ); } @@ -815,15 +815,15 @@ contract UTXOGateway is } } - function _registerAddress(ClientChainID clientChainId, bytes memory depositor, address exocoreAddress) internal { - require(depositor.length > 0 && exocoreAddress != address(0), "Invalid address"); + function _registerAddress(ClientChainID clientChainId, bytes memory depositor, address imuachainAddress) internal { + require(depositor.length > 0 && imuachainAddress != address(0), "Invalid address"); require(inboundRegistry[clientChainId][depositor] == address(0), "Depositor address already registered"); - require(outboundRegistry[clientChainId][exocoreAddress].length == 0, "Exocore address already registered"); + require(outboundRegistry[clientChainId][imuachainAddress].length == 0, "Imuachain address already registered"); - inboundRegistry[clientChainId][depositor] = exocoreAddress; - outboundRegistry[clientChainId][exocoreAddress] = depositor; + inboundRegistry[clientChainId][depositor] = imuachainAddress; + outboundRegistry[clientChainId][imuachainAddress] = depositor; - emit AddressRegistered(clientChainId, depositor, exocoreAddress); + emit AddressRegistered(clientChainId, depositor, imuachainAddress); } function _processStakeMsg(StakeMsg memory _msg) internal { @@ -835,34 +835,34 @@ contract UTXOGateway is // register address if not already registered if ( inboundRegistry[_msg.clientChainId][_msg.clientAddress] == address(0) - && outboundRegistry[_msg.clientChainId][_msg.exocoreAddress].length == 0 + && outboundRegistry[_msg.clientChainId][_msg.imuachainAddress].length == 0 ) { - if (_msg.exocoreAddress == address(0)) { + if (_msg.imuachainAddress == address(0)) { revert Errors.ZeroAddress(); } - _registerAddress(_msg.clientChainId, _msg.clientAddress, _msg.exocoreAddress); + _registerAddress(_msg.clientChainId, _msg.clientAddress, _msg.imuachainAddress); } - address stakerExoAddr = inboundRegistry[_msg.clientChainId][_msg.clientAddress]; + address stakerImAddr = inboundRegistry[_msg.clientChainId][_msg.clientAddress]; uint256 fee = _msg.amount * bridgeFeeRate / BASIS_POINTS; uint256 amountAfterFee = _msg.amount - fee; - // we use registered exocore address as the depositor + // we use registered Imuachain address as the depositor // this should always succeed and never revert, otherwise something is wrong. - _deposit(_msg.clientChainId, _msg.clientAddress, stakerExoAddr, amountAfterFee, _msg.clientTxId); + _deposit(_msg.clientChainId, _msg.clientAddress, stakerImAddr, amountAfterFee, _msg.clientTxId); // delegate to operator if operator is provided, and do not revert if it fails since we need to count the stake // as deposited if (bytes(_msg.operator).length > 0) { - bool success = _delegate(_msg.clientChainId, stakerExoAddr, _msg.operator, amountAfterFee); + bool success = _delegate(_msg.clientChainId, stakerImAddr, _msg.operator, amountAfterFee); if (!success) { - emit DelegationFailedForStake(_msg.clientChainId, stakerExoAddr, _msg.operator, amountAfterFee); + emit DelegationFailedForStake(_msg.clientChainId, stakerImAddr, _msg.operator, amountAfterFee); } else { - emit DelegationCompleted(_msg.clientChainId, stakerExoAddr, _msg.operator, amountAfterFee); + emit DelegationCompleted(_msg.clientChainId, stakerImAddr, _msg.operator, amountAfterFee); } } - emit StakeMsgExecuted(_msg.clientChainId, _msg.nonce, stakerExoAddr, amountAfterFee); + emit StakeMsgExecuted(_msg.clientChainId, _msg.nonce, stakerImAddr, amountAfterFee); } } diff --git a/src/core/Vault.sol b/src/core/Vault.sol index be895402..4bb795d5 100644 --- a/src/core/Vault.sol +++ b/src/core/Vault.sol @@ -11,7 +11,7 @@ import {IERC20} from "@openzeppelin/contracts/token/ERC20/IERC20.sol"; import {SafeERC20} from "@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol"; /// @title Vault -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice Implementation of IVault, used to store user tokens. Each Vault is unique to an /// underlying token and is controlled by a gateway. contract Vault is Initializable, VaultStorage, IVault { diff --git a/src/interfaces/IBaseRestakingController.sol b/src/interfaces/IBaseRestakingController.sol index 66d127ee..aa3a4ad7 100644 --- a/src/interfaces/IBaseRestakingController.sol +++ b/src/interfaces/IBaseRestakingController.sol @@ -2,7 +2,7 @@ pragma solidity ^0.8.19; /// @title IBaseRestakingController -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice The IBaseRestakingController interface provides a set of functions for staker operations. interface IBaseRestakingController { @@ -20,7 +20,7 @@ interface IBaseRestakingController { /// @notice Client chain users call to withdraw their unlocked assets from the vault. /// @dev This function assumes that the withdrawable assets should have been unlocked before calling this. - /// @dev This function does not interact with Exocore. + /// @dev This function does not interact with Imuachain. /// @param token The address of specific token that the user wants to claim from the vault. /// @param amount The amount of @param token that the user wants to claim from the vault. /// @param recipient The destination address that the assets would be transfered to. @@ -32,10 +32,10 @@ interface IBaseRestakingController { /// @param rewardAmount The amount of reward tokens that the user wants to submit. function submitReward(address token, address avs, uint256 rewardAmount) external payable; - /// @notice Claims reward tokens from Exocore. + /// @notice Claims reward tokens from Imuachain. /// @param token The address of the specific token that the user wants to claim as a reward. /// @param rewardAmount The amount of reward tokens that the user wants to claim. - function claimRewardFromExocore(address token, uint256 rewardAmount) external payable; + function claimRewardFromImuachain(address token, uint256 rewardAmount) external payable; /// @notice Withdraws reward tokens from vault to the recipient. /// @param token The address of the specific token that the user wants to withdraw as a reward. diff --git a/src/interfaces/ICustomProxyAdmin.sol b/src/interfaces/ICustomProxyAdmin.sol index 28efd61c..aa04a2db 100644 --- a/src/interfaces/ICustomProxyAdmin.sol +++ b/src/interfaces/ICustomProxyAdmin.sol @@ -4,7 +4,7 @@ pragma solidity ^0.8.19; import {ITransparentUpgradeableProxy} from "@openzeppelin/contracts/proxy/transparent/TransparentUpgradeableProxy.sol"; /// @title ICustomProxyAdmin -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice ICustomProxyAdmin provides a set of functions for custom proxy admin operations. /// The additional function, beyond the standard OpenZeppelin ProxyAdmin, is changeImplementation. interface ICustomProxyAdmin { diff --git a/src/interfaces/IExoCapsule.sol b/src/interfaces/IImuaCapsule.sol similarity index 87% rename from src/interfaces/IExoCapsule.sol rename to src/interfaces/IImuaCapsule.sol index d80eea41..ccd3fc9a 100644 --- a/src/interfaces/IExoCapsule.sol +++ b/src/interfaces/IImuaCapsule.sol @@ -3,15 +3,15 @@ pragma solidity ^0.8.19; import {BeaconChainProofs} from "../libraries/BeaconChainProofs.sol"; -/// @title ExoCapsule interface -/// @author ExocoreNetwork -/// @notice IExoCapsule is the interface for the ExoCapsule contract. It provides a set of functions for ExoCapsule +/// @title ImuaCapsule interface +/// @author imua-xyz +/// @notice ImuaCapsule is the interface for the ImuaCapsule contract. It provides a set of functions for ImuaCapsule /// operations. It is a contract used for native restaking. -interface IExoCapsule { +interface IImuaCapsule { - /// @notice Initializes the ExoCapsule contract with the given parameters. + /// @notice Initializes the ImuaCapsule contract with the given parameters. /// @param gateway The address of the ClientChainGateway contract. - /// @param capsuleOwner The payable address of the ExoCapsule owner. + /// @param capsuleOwner The payable address of the ImuaCapsule owner. /// @param beaconOracle The address of the BeaconOracle contract. function initialize(address gateway, address payable capsuleOwner, address beaconOracle) external; @@ -56,11 +56,11 @@ interface IExoCapsule { /// @param amountToWithdraw The amount to withdraw. function withdrawNonBeaconChainETHBalance(address payable recipient, uint256 amountToWithdraw) external; - /// @notice Unlock and increase the withdrawable balance of the ExoCapsule for later withdrawal. + /// @notice Unlock and increase the withdrawable balance of the ImuaCapsule for later withdrawal. /// @param amount The amount of the ETH balance unlocked. function unlockETHPrincipal(uint256 amount) external; - /// @notice Returns the withdrawal credentials of the ExoCapsule. + /// @notice Returns the withdrawal credentials of the ImuaCapsule. /// @return The withdrawal credentials. /// @dev Returns '0x1' + '0x0' * 11 + 'address' of capsule. function capsuleWithdrawalCredentials() external view returns (bytes memory); diff --git a/src/interfaces/IExocoreGateway.sol b/src/interfaces/IImuachainGateway.sol similarity index 88% rename from src/interfaces/IExocoreGateway.sol rename to src/interfaces/IImuachainGateway.sol index 53fb0e30..f8bf435f 100644 --- a/src/interfaces/IExocoreGateway.sol +++ b/src/interfaces/IImuachainGateway.sol @@ -4,13 +4,13 @@ pragma solidity ^0.8.19; import {IOAppCore} from "@layerzerolabs/lz-evm-oapp-v2/contracts/oapp/interfaces/IOAppCore.sol"; import {IOAppReceiver} from "@layerzerolabs/lz-evm-oapp-v2/contracts/oapp/interfaces/IOAppReceiver.sol"; -/// @title IExocoreGateway -/// @author ExocoreNetwork -/// @notice IExocoreGateway is the interface for the ExocoreGateway contract. It provides a set of functions for -/// ExocoreGateway operations. -/// @dev It is deployed on the Exocore end and is designed to interact with other chains, -/// as well as precompiles on the Exocore chain in response to messages from other chains. -interface IExocoreGateway is IOAppReceiver, IOAppCore { +/// @title ImuachainGateway interface +/// @author imua-xyz +/// @notice ImuachainGateway is the interface for the ImuachainGateway contract. It provides a set of functions for +/// ImuachainGateway operations. +/// @dev It is deployed on the Imuachain end and is designed to interact with other chains, +/// as well as precompiles on Imuachain in response to messages from other chains. +interface IImuachainGateway is IOAppReceiver, IOAppCore { /// @notice Calculates the native fee for sending a message with specific options. /// @param srcChainid The chain id of the source chain, from which a message was received, @@ -19,7 +19,7 @@ interface IExocoreGateway is IOAppReceiver, IOAppCore { /// @return nativeFee The calculated native fee for the given message. function quote(uint32 srcChainid, bytes memory _message) external view returns (uint256 nativeFee); - /// @notice Registers the @param clientChainId and other meta data to Exocore native module or update the client + /// @notice Registers the @param clientChainId and other meta data to Imuachain native module or update the client /// chain's meta data, if a chain identified by @param clientChainId already exists. Sets trusted @param peer to /// enable cross-chain communication. /// @param clientChainId The endpoint ID for client chain. diff --git a/src/interfaces/ILSTRestakingController.sol b/src/interfaces/ILSTRestakingController.sol index 69b151d9..06c132f3 100644 --- a/src/interfaces/ILSTRestakingController.sol +++ b/src/interfaces/ILSTRestakingController.sol @@ -4,32 +4,32 @@ pragma solidity ^0.8.19; import {IBaseRestakingController} from "./IBaseRestakingController.sol"; /// @title ILSTRestakingController -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice Interface for the LSTRestakingController contract. It offers functions to deposit, withdraw principal, /// withdraw rewards, and deposit + delegate. -/// @dev Provides methods for interacting with the Exocore network, including depositing tokens, withdrawing principal +/// @dev Provides methods for interacting with Imuachain, including depositing tokens, withdrawing principal /// and rewards, and delegating tokens to node operators. interface ILSTRestakingController is IBaseRestakingController { - /// @notice Deposits tokens into the Exocore system for further operations like delegation and staking. - /// @dev This function locks the specified amount of tokens into a vault and forwards the information to Exocore - /// @dev Deposit is always considered successful on the Exocore chain side. + /// @notice Deposits tokens into Imua for further operations like delegation and staking. + /// @dev This function locks the specified amount of tokens into a vault and forwards the information to Imuachain + /// @dev Deposit is always considered successful on Imuachain /// @param token The address of the specific token that the user wants to deposit. /// @param amount The amount of the token that the user wants to deposit. function deposit(address token, uint256 amount) external payable; - /// @notice Send request to Exocore to claim the LST principal. - /// @dev This function requests claim approval from Exocore. If approved, the assets are + /// @notice Send request to Imuachain to claim the LST principal. + /// @dev This function requests claim approval from Imuachain. If approved, the assets are /// unlocked and can be withdrawn by the user. Otherwise, they remain locked. - /// @param token The address of the specific token that the user wants to claim from Exocore. - /// @param principalAmount The principal amount of assets the user deposited into Exocore for delegation and + /// @param token The address of the specific token that the user wants to claim from Imuachain. + /// @param principalAmount The principal amount of assets the user deposited into Imuachain for delegation and /// staking. - function claimPrincipalFromExocore(address token, uint256 principalAmount) external payable; + function claimPrincipalFromImuachain(address token, uint256 principalAmount) external payable; /// @notice Deposits tokens and then delegates them to a specific node operator. - /// @dev This function locks the specified amount of tokens into a vault, informs Exocore, and + /// @dev This function locks the specified amount of tokens into a vault, informs Imuachain, and /// delegates the tokens to the specified node operator. - /// Delegation can fail if the node operator is not registered in Exocore. + /// Delegation can fail if the node operator is not registered in Imuachain. /// @param token The address of the specific token that the user wants to deposit and delegate. /// @param amount The amount of the token that the user wants to deposit and delegate. /// @param operator The address of a registered node operator that the user wants to delegate to. diff --git a/src/interfaces/INativeRestakingController.sol b/src/interfaces/INativeRestakingController.sol index d6cc8f73..d6651d1e 100644 --- a/src/interfaces/INativeRestakingController.sol +++ b/src/interfaces/INativeRestakingController.sol @@ -5,30 +5,31 @@ import {BeaconChainProofs} from "../libraries/BeaconChainProofs.sol"; import {IBaseRestakingController} from "./IBaseRestakingController.sol"; /// @title INativeRestakingController -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice Interface for the NativeRestakingController contract. -/// @dev Provides methods for interacting with the Ethereum beacon chain and Exocore network, including staking, -/// creating ExoCapsules, and processing withdrawals. +/// @dev Provides methods for interacting with the Ethereum beacon chain and Imuachain, including staking, +/// creating ImuaCapsules, and processing withdrawals. interface INativeRestakingController is IBaseRestakingController { - /// @notice Deposits to a beacon chain validator and sets withdrawal credentials to the staker's ExoCapsule contract + /// @notice Deposits to a beacon chain validator and sets withdrawal credentials to the staker's ImuaCapsule + /// contract /// address. - /// @dev If the ExoCapsule contract does not exist, it will be created. + /// @dev If the ImuaCapsule contract does not exist, it will be created. /// @param pubkey The BLS pubkey of the beacon chain validator. /// @param signature The BLS signature. /// @param depositDataRoot The SHA-256 hash of the SSZ-encoded DepositData object, used as a protection against /// malformed input. function stake(bytes calldata pubkey, bytes calldata signature, bytes32 depositDataRoot) external payable; - /// @notice Creates an ExoCapsule owned by the Ethereum native restaker. + /// @notice Creates an ImuaCapsule owned by the Ethereum native restaker. /// @dev This should be done before staking to the beacon chain. - /// @return capsule The address of the created ExoCapsule. - function createExoCapsule() external returns (address capsule); + /// @return capsule The address of the created ImuaCapsule. + function createImuaCapsule() external returns (address capsule); - /// @notice Deposits ETH staked on the Ethereum beacon chain to the Exocore network for future restaking. - /// @dev Before depositing, the staker should have created an ExoCapsule and set the validator's withdrawal + /// @notice Deposits ETH staked on the Ethereum beacon chain to Imua for future restaking. + /// @dev Before depositing, the staker should have created an ImuaCapsule and set the validator's withdrawal /// credentials to it. - /// The effective balance of `validatorContainer` will be credited as the deposited value by the Exocore network. + /// The effective balance of `validatorContainer` will be credited as the deposited value by the Imuachain. /// @param validatorContainer The data structure included in the `BeaconState` of `BeaconBlock` that contains beacon /// chain validator information. /// @param proof The proof needed to verify the validator container. @@ -37,10 +38,10 @@ interface INativeRestakingController is IBaseRestakingController { BeaconChainProofs.ValidatorContainerProof calldata proof ) external payable; - /// @notice Processes a partial withdrawal from the beacon chain to an ExoCapsule contract. + /// @notice Processes a partial withdrawal from the beacon chain to an ImuaCapsule contract. /// @dev This function is called with `validatorContainer`, `withdrawalContainer`, and corresponding proofs to prove /// the partial withdrawal. - /// The withdrawn ETH will be unlocked and claimable for the ExoCapsule owner. + /// The withdrawn ETH will be unlocked and claimable for the ImuaCapsule owner. /// @param validatorContainer The data structure included in the `BeaconState` of `BeaconBlock` that contains beacon /// chain validator information. /// @param validatorProof The merkle proof needed to verify that `validatorContainer` is included in a beacon block @@ -56,7 +57,7 @@ interface INativeRestakingController is IBaseRestakingController { BeaconChainProofs.WithdrawalProof calldata withdrawalProof ) external payable; - /// @notice Withdraws the nonBeaconChainETHBalance from the ExoCapsule contract. + /// @notice Withdraws the nonBeaconChainETHBalance from the ImuaCapsule contract. /// @dev @param amountToWithdraw can not be greater than the available nonBeaconChainETHBalance. /// @param recipient The payable destination address to which the ETH are sent. /// @param amountToWithdraw The amount to withdraw. diff --git a/src/interfaces/INetworkConfig.sol b/src/interfaces/INetworkConfig.sol index 2d599d64..b5be5e7f 100644 --- a/src/interfaces/INetworkConfig.sol +++ b/src/interfaces/INetworkConfig.sol @@ -4,7 +4,7 @@ pragma solidity ^0.8.19; /// @title INetworkConfig /// @notice Interface for a network config contract to report params like slots per epoch and seconds per slot. /// @dev This interface defines the necessary functions for interacting with the NetworkConfig contract. -/// @author ExocoreNetwork +/// @author imua-xyz interface INetworkConfig { /// @notice Returns the deposit contract address. diff --git a/src/interfaces/ITokenWhitelister.sol b/src/interfaces/ITokenWhitelister.sol index 3be68aee..69e312b3 100644 --- a/src/interfaces/ITokenWhitelister.sol +++ b/src/interfaces/ITokenWhitelister.sol @@ -2,7 +2,7 @@ pragma solidity ^0.8.19; /// @title ITokenWhitelister -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice An interface for the TokenWhitelister contract that allows whitelisting and obtaining /// the count of whitelisted tokens. interface ITokenWhitelister { diff --git a/src/interfaces/IValidatorRegistry.sol b/src/interfaces/IValidatorRegistry.sol index 6b8bcf1f..7b4b3af2 100644 --- a/src/interfaces/IValidatorRegistry.sol +++ b/src/interfaces/IValidatorRegistry.sol @@ -21,7 +21,7 @@ interface IValidatorRegistry { /// @param name The name (meta info) for the validator. /// @param commission The commission for the validator. /// @param consensusPublicKey The public key used by the validator for consensus - /// on the Exocore chain. + /// on Imuachain. struct Validator { string name; Commission commission; @@ -30,8 +30,8 @@ interface IValidatorRegistry { /// @notice Registers a new validator in the registry with the provided details. /// @dev The set of validators is a subset of operators; the validators represent the subset of operators that - /// intend to validate blocks on the Exocore chain. - /// @param validatorAddress The Exocore address of the operator (corresponding to the validator) as a string. + /// intend to validate blocks on the Imuachain. + /// @param validatorAddress The Imuachain address of the operator (corresponding to the validator) as a string. /// @param name The human-readable name of the operator (corresponding to the validator). /// @param commission A `Commission` struct containing the commission details for this operator (corresponding to /// the validator). @@ -57,7 +57,7 @@ interface IValidatorRegistry { /// @dev Emitted when a new validator is registered in the contract. /// @param ethAddress The Ethereum address of the validator. - /// @param validatorAddress The Exocore address of the validator. + /// @param validatorAddress The Imuachain address of the validator. /// @param name The human-readable name of the validator. /// @param commission The commission details for the validator. /// @param consensusPublicKey The public key used for consensus operations. @@ -70,7 +70,7 @@ interface IValidatorRegistry { ); /// @dev Emitted when a validator's consensus key is updated. - /// @param validatorAddress The Exocore address of the validator. + /// @param validatorAddress The Imuachain address of the validator. /// @param newConsensusPublicKey The new consensus key for the validator. event ValidatorKeyReplaced(string validatorAddress, bytes32 newConsensusPublicKey); diff --git a/src/interfaces/IVault.sol b/src/interfaces/IVault.sol index 0d04fb54..e30f5aaa 100644 --- a/src/interfaces/IVault.sol +++ b/src/interfaces/IVault.sol @@ -4,7 +4,7 @@ pragma solidity ^0.8.19; /// @title IVault /// @notice Interface for a Vault contract handling deposits, withdrawals, and balance updates. /// @dev This interface defines the necessary functions for interacting with the Vault. -/// @author ExocoreNetwork +/// @author imua-xyz interface IVault { /// @notice Withdraws a specified amount from the vault. diff --git a/src/interfaces/precompiles/IAssets.sol b/src/interfaces/precompiles/IAssets.sol index a904078e..5ff87f6a 100644 --- a/src/interfaces/precompiles/IAssets.sol +++ b/src/interfaces/precompiles/IAssets.sol @@ -44,7 +44,7 @@ struct StakerBalance { uint256 totalDeposited; } -/// @author Exocore Team +/// @author imua-xyz /// @title Assets Precompile Contract /// @dev The interface through which solidity contracts will interact with assets module /// @custom:address 0x0000000000000000000000000000000000000804 @@ -55,7 +55,7 @@ interface IAssets { /// that will change the state in assets module /// Note that this address cannot be a module account. /// @param clientChainID is the layerZero chainID if it is supported. - // It might be allocated by Exocore when the client chain isn't supported + // It might be allocated by Imuachain when the client chain isn't supported // by layerZero /// @param assetsAddress The client chain asset address /// @param stakerAddress The staker address @@ -71,7 +71,7 @@ interface IAssets { /// that will change the state in assets module /// Note that this address cannot be a module account. /// @param clientChainID is the layerZero chainID if it is supported. - // It might be allocated by Exocore when the client chain isn't supported + // It might be allocated by Imuachain when the client chain isn't supported // by layerZero /// @param validatorID The validator's identifier: index (uint256 as bytes32) or pubkey. /// @param stakerAddress The staker address @@ -86,7 +86,7 @@ interface IAssets { /// @dev withdraw LST To the staker, that will change the state in assets module /// Note that this address cannot be a module account. /// @param clientChainID is the layerZero chainID if it is supported. - // It might be allocated by Exocore when the client chain isn't supported + // It might be allocated by Imuachain when the client chain isn't supported // by layerZero /// @param assetsAddress The client chain asset Address /// @param withdrawAddress The withdraw address @@ -101,7 +101,7 @@ interface IAssets { /// @dev withdraw NST To the staker, that will change the state in assets module /// Note that this address cannot be a module account. /// @param clientChainID is the layerZero chainID if it is supported. - // It might be allocated by Exocore when the client chain isn't supported + // It might be allocated by Imuachain when the client chain isn't supported // by layerZero /// @param validatorID The validator's identifier: index (uint256 as bytes32) or pubkey. /// @param withdrawAddress The withdraw address @@ -116,7 +116,7 @@ interface IAssets { /// @dev registers or updates a client chain to allow deposits / staking, etc. /// from that chain. /// @param clientChainID is the layerZero chainID if it is supported. - // It might be allocated by Exocore when the client chain isn't supported + // It might be allocated by Imuachain when the client chain isn't supported // by layerZero function registerOrUpdateClientChain( uint32 clientChainID, diff --git a/src/interfaces/precompiles/IBech32.sol b/src/interfaces/precompiles/IBech32.sol new file mode 100644 index 00000000..dc1d5f6e --- /dev/null +++ b/src/interfaces/precompiles/IBech32.sol @@ -0,0 +1,28 @@ +// SPDX-License-Identifier: MIT +pragma solidity >=0.8.17; + +/// @dev The IBech32 contract's address. +address constant BECH32_PRECOMPILE_ADDRESS = 0x0000000000000000000000000000000000000400; + +IBech32 constant BECH32_CONTRACT = IBech32(BECH32_PRECOMPILE_ADDRESS); + +/// @author imua-xyz +/// @title Bech32 Precompiled Contract +/// @dev This contract can be used by Solidity devs to convert from `string bech32Addr` to +/// `address 0xAddr` and vice versa. The bech32-prefix used is the chain's prefix, via +/// `sdk.Config#SetBech32PrefixForAccount`. +/// @custom:address 0x0000000000000000000000000000000000000400 +interface IBech32 { + + /// @dev Defines a method for converting a hex formatted address to bech32. + /// @param addr The hex address to be converted. + /// @param prefix The human readable prefix (HRP) of the bech32 address. + /// @return bech32Address The address in bech32 format. + function hexToBech32(address addr, string memory prefix) external view returns (string memory bech32Address); + + /// @dev Defines a method for converting a bech32 formatted address to hex. + /// @param bech32Address The bech32 address to be converted. + /// @return addr The address in hex format. + function bech32ToHex(string memory bech32Address) external view returns (address addr); + +} diff --git a/src/interfaces/precompiles/IDelegation.sol b/src/interfaces/precompiles/IDelegation.sol index 8e75eae1..e6f839ca 100644 --- a/src/interfaces/precompiles/IDelegation.sol +++ b/src/interfaces/precompiles/IDelegation.sol @@ -7,7 +7,7 @@ address constant DELEGATION_PRECOMPILE_ADDRESS = 0x00000000000000000000000000000 /// @dev The delegation contract's instance. IDelegation constant DELEGATION_CONTRACT = IDelegation(DELEGATION_PRECOMPILE_ADDRESS); -/// @author Exocore Team +/// @author imua-xyz /// @title delegation Precompile Contract /// @dev The interface through which solidity contracts will interact with delegation /// @custom:address 0x0000000000000000000000000000000000000805 @@ -18,7 +18,7 @@ interface IDelegation { /// delegation and assets module /// Note that this address cannot be a module account. /// @param clientChainID is the layerZero chainID if it is supported. - // It might be allocated by Exocore when the client chain isn't supported + // It might be allocated by Imuachain when the client chain isn't supported // by layerZero /// @param lzNonce The cross chain tx layerZero nonce /// @param assetsAddress The client chain asset Address @@ -39,7 +39,7 @@ interface IDelegation { /// delegation and assets module /// Note that this address cannot be a module account. /// @param clientChainID is the layerZero chainID if it is supported. - // It might be allocated by Exocore when the client chain isn't supported + // It might be allocated by Imuachain when the client chain isn't supported // by layerZero /// @param lzNonce The cross chain tx layerZero nonce /// @param assetsAddress The client chain asset Address @@ -59,7 +59,7 @@ interface IDelegation { /// @dev associate the operator with staker so that we could count staker's delegation as self-delegate /// @notice a staker could only be associated with one operator while one operator could associate multiple stakers /// @param clientChainID is the layerZero chainID if it is supported. - // It might be allocated by Exocore when the client chain isn't supported + // It might be allocated by Imuachain when the client chain isn't supported // by layerZero /// @param staker is the EVM address of the staker /// @param operator is the address that is to be marked as the owner. @@ -70,7 +70,7 @@ interface IDelegation { /// TRANSACTIONS /// @dev dissociate the operator that has already been associated with the staker /// @param clientChainID is the layerZero chainID if it is supported. - // It might be allocated by Exocore when the client chain isn't supported + // It might be allocated by Imuachain when the client chain isn't supported // by layerZero /// @param staker is the EVM address to remove the marking from. function dissociateOperatorFromStaker(uint32 clientChainID, bytes calldata staker) diff --git a/src/interfaces/precompiles/IReward.sol b/src/interfaces/precompiles/IReward.sol index af30462a..1dc93c0e 100644 --- a/src/interfaces/precompiles/IReward.sol +++ b/src/interfaces/precompiles/IReward.sol @@ -1,8 +1,8 @@ // SPDX-License-Identifier: MIT pragma solidity >=0.8.17; -/// TODO: we might remove this precompile contract and merge it into assets precompile -/// if we decide to handle reward withdrawal request by assets precompile +// TODO: we might remove this precompile contract and merge it into assets precompile +// if we decide to handle reward withdrawal request by assets precompile /// @dev The reward contract's address. address constant REWARD_PRECOMPILE_ADDRESS = 0x0000000000000000000000000000000000000806; @@ -10,7 +10,7 @@ address constant REWARD_PRECOMPILE_ADDRESS = 0x000000000000000000000000000000000 /// @dev The reward contract's instance. IReward constant REWARD_CONTRACT = IReward(REWARD_PRECOMPILE_ADDRESS); -/// @author Exocore Team +/// @author imua-xyz /// @title reward Precompile Contract /// @dev The interface through which solidity contracts will interact with Reward precompile. /// @custom:address 0x0000000000000000000000000000000000000806 diff --git a/src/libraries/ActionAttributes.sol b/src/libraries/ActionAttributes.sol index ecbf3a4c..89f3cd8c 100644 --- a/src/libraries/ActionAttributes.sol +++ b/src/libraries/ActionAttributes.sol @@ -7,8 +7,8 @@ library ActionAttributes { // Message length constants uint256 internal constant ASSET_OPERATION_LENGTH = 97; - uint256 internal constant DELEGATION_OPERATION_LENGTH = 139; - uint256 internal constant ASSOCIATE_OPERATOR_LENGTH = 75; + uint256 internal constant DELEGATION_OPERATION_LENGTH = 138; + uint256 internal constant ASSOCIATE_OPERATOR_LENGTH = 74; uint256 internal constant DISSOCIATE_OPERATOR_LENGTH = 33; // Bitmaps for operation types diff --git a/src/libraries/Errors.sol b/src/libraries/Errors.sol index 4be7dcdd..588ee6b2 100644 --- a/src/libraries/Errors.sol +++ b/src/libraries/Errors.sol @@ -4,8 +4,8 @@ pragma solidity ^0.8.19; import {Action} from "../storage/GatewayStorage.sol"; /// @dev @title Errors library -/// @dev @notice A library for all errors that can be thrown in the Exocore contracts -/// @dev All errors in Exocore follow the following syntax: 'error ContractNameErrorName(arg1, arg2, ...)', where +/// @dev @notice A library for all errors that can be thrown in imua-contracts +/// @dev All errors in imua-contracts follow the following syntax: 'error ContractNameErrorName(arg1, arg2, ...)', where /// @dev 'ContractName' is the name of the contract /// @dev that the error originates from and 'ErrorName' is the name of the error. The arguments are optional and are /// used to @@ -83,7 +83,7 @@ library Errors { /// @param validator The Ethereum address of the validator error BootstrapValidatorAlreadyHasAddress(address validator); - /// @dev Bootstrap: Validator with this Exocore address is already registered + /// @dev Bootstrap: Validator with this Imuachain address is already registered error BootstrapValidatorAlreadyRegistered(); /// @dev Bootstrap: Consensus public key already in use @@ -157,9 +157,9 @@ library Errors { /// @dev ClientChainGateway: token should not be whitelisted before error ClientChainGatewayAlreadyWhitelisted(address token); - /// @dev ClientChainGateway: token addition must happen via Exocore - error ClientChainGatewayTokenAdditionViaExocore(); - /// @notice Error thrown when the ExoCapsule does not exist. + /// @dev ClientChainGateway: token addition must happen via Imuachain + error ClientChainGatewayTokenAdditionViaImuachain(); + /// @notice Error thrown when the ImuaCapsule does not exist. error CapsuleDoesNotExist(); ////////////////////////////////////// @@ -178,20 +178,21 @@ library Errors { /// @param nonce The nonce of the request. error UnexpectedResponse(uint64 nonce); - /// @dev Thrown when deposit fails on the Exocore end. + /// @dev Thrown when deposit fails on Imuachain. /// @param token The token address. /// @param depositor The depositor address. - error DepositShouldNotFailOnExocore(address token, address depositor); + /// @dev This error will result in an irrecoverable failure. + error DepositShouldNotFailOnImuachain(address token, address depositor); /// @dev Thrown when the whitelist tokens length is invalid. /// @param expectedLength The expected length of the request payload. /// @param actualLength The actual length of the request payload. error InvalidAddWhitelistTokensRequest(uint256 expectedLength, uint256 actualLength); - /// @notice Emitted when withdrawal fails on the Exocore end. + /// @notice Emitted when withdrawal fails on Imuachain. /// @param token The token address. /// @param withdrawer The withdrawer address. - event WithdrawFailedOnExocore(address indexed token, address indexed withdrawer); + event WithdrawFailedOnImuachain(address indexed token, address indexed withdrawer); /////////////////////////////// // CustomProxyAdmin Errors // @@ -204,38 +205,38 @@ library Errors { error CustomProxyAdminOnlyCalledFromProxy(); ///////////////////////// - // ExoCapsule Errors // + // ImuaCapsule Errors // ///////////////////////// - /// @dev ExoCapsule: withdrawal amount is larger than staker's withdrawable balance - error ExoCapsuleWithdrawalAmountExceeds(); + /// @dev ImuaCapsule: withdrawal amount is larger than staker's withdrawable balance + error ImuaCapsuleWithdrawalAmountExceeds(); - /// @dev ExoCapsule: withdrawNonBeaconChainETHBalance: amountToWithdraw is greater than nonBeaconChainETHBalance - error ExoCapsuleNonBeaconChainWithdrawalAmountExceeds(); + /// @dev ImuaCapsule: withdrawNonBeaconChainETHBalance: amountToWithdraw is greater than nonBeaconChainETHBalance + error ImuaCapsuleNonBeaconChainWithdrawalAmountExceeds(); - /// @dev ExoCapsule: timestamp should be greater than beacon chain genesis timestamp - error ExoCapsuleTimestampBeforeGenesis(); + /// @dev ImuaCapsule: timestamp should be greater than beacon chain genesis timestamp + error ImuaCapsuleTimestampBeforeGenesis(); ///////////////////////////// - // ExocoreGateway Errors // + // ImuachainGateway Errors // ///////////////////////////// - /// @dev ExocoreGateway: can only be called from this contract itself with a low-level call - error ExocoreGatewayOnlyCalledFromThis(); + /// @dev ImuachainGateway: can only be called from this contract itself with a low-level call + error ImuachainGatewayOnlyCalledFromThis(); - /// @dev ExocoreGateway: failed to get client chain ids - error ExocoreGatewayFailedToGetClientChainIds(); + /// @dev ImuachainGateway: failed to get client chain ids + error ImuachainGatewayFailedToGetClientChainIds(); - /// @dev ExocoreGateway: client chain should be registered before. - error ExocoreGatewayNotRegisteredClientChainId(); + /// @dev ImuachainGateway: client chain should be registered before. + error ImuachainGatewayNotRegisteredClientChainId(); - /// @dev ExocoreGateway: failed to check if the client id is registered - error ExocoreGatewayFailedToCheckClientChainId(); + /// @dev ImuachainGateway: failed to check if the client id is registered + error ImuachainGatewayFailedToCheckClientChainId(); - /// @dev ExocoreGateway: thrown when associateOperatorWithEVMStaker failed + /// @dev ImuachainGateway: thrown when associateOperatorWithEVMStaker failed error AssociateOperatorFailed(uint32 clientChainId, address staker, string operator); - /// @dev thrown when dissociateOperatorFromEVMStaker failed + /// @dev ImuachainGateway: thrown when dissociateOperatorFromEVMStaker failed error DissociateOperatorFailed(uint32 clientChainId, address staker); /// @notice Thrown when the execution of a precompile call fails. @@ -254,7 +255,7 @@ library Errors { /// @notice Thrown when a client chain registration fails /// @param clientChainId The LayerZero chain ID of the client chain. - error RegisterClientChainToExocoreFailed(uint32 clientChainId); + error RegisterClientChainToImuachainFailed(uint32 clientChainId); /// @notice Thrown when a whitelist token addition fails /// @param clientChainId The LayerZero chain ID (or otherwise) of the client chain. diff --git a/src/libraries/ExocoreBytes.sol b/src/libraries/ExocoreBytes.sol deleted file mode 100644 index 7d5ee374..00000000 --- a/src/libraries/ExocoreBytes.sol +++ /dev/null @@ -1,13 +0,0 @@ -// SPDX-License-Identifier: MIT -pragma solidity ^0.8.0; - -library ExocoreBytes { - - /// @notice Converts an Ethereum address to Exocore's 32-byte address format - /// @param addr The Ethereum address to convert - /// @return The address as 32-byte Exocore format (20 bytes + right padding) - function toExocoreBytes(address addr) internal pure returns (bytes memory) { - return abi.encodePacked(bytes32(bytes20(addr))); - } - -} diff --git a/src/libraries/ImuachainBytes.sol b/src/libraries/ImuachainBytes.sol new file mode 100644 index 00000000..5252fe54 --- /dev/null +++ b/src/libraries/ImuachainBytes.sol @@ -0,0 +1,13 @@ +// SPDX-License-Identifier: MIT +pragma solidity ^0.8.0; + +library ImuachainBytes { + + /// @notice Converts an Ethereum address to Imuachain's 32-byte address format + /// @param addr The Ethereum address to convert + /// @return The address as 32-byte Imuachain format (20 bytes + right padding) + function toImuachainBytes(address addr) internal pure returns (bytes memory) { + return abi.encodePacked(bytes32(bytes20(addr))); + } + +} diff --git a/src/libraries/NetworkConstants.sol b/src/libraries/NetworkConstants.sol index 5161c3ed..841c39cf 100644 --- a/src/libraries/NetworkConstants.sol +++ b/src/libraries/NetworkConstants.sol @@ -6,7 +6,7 @@ import {NetworkParams} from "../interfaces/INetworkConfig.sol"; /// @title NetworkConstants /// @notice This library provides constants for known Ethereum PoS networks. -/// @author ExocoreNetwork +/// @author imua-xyz /// @dev It does not have `is INetworkConfig` since libraries cannot do that. /// @dev It is a library because we do not expect the parameters to change at all. library NetworkConstants { diff --git a/src/storage/BootstrapStorage.sol b/src/storage/BootstrapStorage.sol index e32d92d4..a99e37d9 100644 --- a/src/storage/BootstrapStorage.sol +++ b/src/storage/BootstrapStorage.sol @@ -6,7 +6,7 @@ import {NetworkConstants} from "../libraries/NetworkConstants.sol"; import {Vault} from "../core/Vault.sol"; import {IETHPOSDeposit} from "../interfaces/IETHPOSDeposit.sol"; -import {IExoCapsule} from "../interfaces/IExoCapsule.sol"; +import {IImuaCapsule} from "../interfaces/IImuaCapsule.sol"; import {INetworkConfig} from "../interfaces/INetworkConfig.sol"; import {IValidatorRegistry} from "../interfaces/IValidatorRegistry.sol"; import {IVault} from "../interfaces/IVault.sol"; @@ -20,8 +20,8 @@ import {Create2} from "@openzeppelin/contracts/utils/Create2.sol"; /// @title BootstrapStorage /// @notice The storage contract for the Bootstrap contract. It later upgrades to ClientChainGatewayStorage. -/// @dev This contract is used as the base storage and is inherited by the storage for Bootstrap and ExocoreGateway. -/// @author ExocoreNetwork +/// @dev This contract is used as the base storage and is inherited by the storage for Bootstrap and ImuachainGateway. +/// @author imua-xyz contract BootstrapStorage is GatewayStorage { /* -------------------------------------------------------------------------- */ @@ -29,13 +29,13 @@ contract BootstrapStorage is GatewayStorage { /* -------------------------------------------------------------------------- */ // time and duration - /// @notice A timestamp representing the scheduled spawn time of the Exocore chain, which influences the contract's + /// @notice A timestamp representing the scheduled spawn time of Imuachain, which influences the contract's /// operational restrictions. /// @dev `offsetDuration` before `spawnTime`, the contract freezes and most actions are prohibited. uint256 public spawnTime; - /// @notice The amount of time before the Exocore spawn time during which operations are restricted. - /// @dev The duration before the Exocore spawn time during which most contract operations are locked. + /// @notice The amount of time before Imuachain's spawn time during which operations are restricted. + /// @dev The duration before Imuachain's spawn time during which most contract operations are locked. uint256 public offsetDuration; /// @notice This mapping is used to track the deposits made by all depositors for each token. @@ -43,29 +43,29 @@ contract BootstrapStorage is GatewayStorage { mapping(address tokenAddress => uint256 amount) public depositsByToken; /// @notice This array stores the Ethereum addresses of all validators that have been registered in the contract. - /// These validators, sorted by their vote power, will be used to initialize the Exocore chain's validator set. + /// These validators, sorted by their vote power, will be used to initialize Imuachain's validator set. /// @dev A public array holding the Ethereum addresses of all validators that have been registered in the contract. address[] public registeredValidators; - /// @notice This mapping is used to track which Ethereum address is linked to which Exocore address. - /// @dev Maps Ethereum addresses to their corresponding Exocore addresses. - mapping(address ethAddress => string exoAddress) public ethToExocoreAddress; + /// @notice This mapping is used to track which Ethereum address is linked to which Imuachain address. + /// @dev Maps Ethereum addresses to their corresponding Imuachain addresses. + mapping(address ethAddress => string imAddress) public ethToImAddress; - /// @notice Use this mapping to access or modify validator details associated with a specific Exocore address. - /// @dev Maps Exocore addresses to their corresponding validator details stored in a `Validator` struct. - mapping(string exoAddress => IValidatorRegistry.Validator validator) public validators; + /// @notice Use this mapping to access or modify validator details associated with a specific Imuachain address. + /// @dev Maps Imuachain addresses to their corresponding validator details stored in a `Validator` struct. + mapping(string imAddress => IValidatorRegistry.Validator validator) public validators; /// @notice This mapping is used to enforce a once-only commission rate change for validators before the chain /// bootstrap. - /// @dev A mapping of validator Exocore address to a boolean indicating whether said validator has edited their + /// @dev A mapping of validator Imuachain address to a boolean indicating whether said validator has edited their /// commission rate. - mapping(string exoAddress => bool hasEdited) public commissionEdited; + mapping(string imAddress => bool hasEdited) public commissionEdited; /// @notice This allows tracking of how much each validator has been delegated by all delegators for each of the /// whitelisted tokens. /// @dev Maps a validator address to a mapping, where the key is the token address and the value is the amount of /// delegated tokens. - mapping(string exoAddress => mapping(address tokenAddress => uint256 amount)) public delegationsByValidator; + mapping(string imAddress => mapping(address tokenAddress => uint256 amount)) public delegationsByValidator; /// @notice This array stores all unique depositor addresses to manage and track staking participation. /// @dev List of addresses that have staked or deposited into the contract. @@ -91,12 +91,12 @@ contract BootstrapStorage is GatewayStorage { /// whitelisted tokens. /// @dev Maps a delegator address to a nested mapping, where the first key is the validator address and the second /// key is the token's address, pointing to the amount of tokens delegated. - mapping(address delegator => mapping(string exoAddress => mapping(address tokenAddress => uint256 amount))) public + mapping(address delegator => mapping(string imAddress => mapping(address tokenAddress => uint256 amount))) public delegations; /// @notice This flag is used to determine whether the implementation of this contract has been switched over to the /// client chain gateway. - /// @dev A boolean indicating whether the Exocore chain has been bootstrapped. + /// @dev A boolean indicating whether Imuachain has been bootstrapped. bool public bootstrapped; /// @notice This proxy admin facilitates the implementation switch from Bootstrap to ClientChainGateway based on @@ -133,8 +133,8 @@ contract BootstrapStorage is GatewayStorage { /// @dev Maps token addresses to their corresponding vault contracts. mapping(address token => IVault vault) public tokenToVault; - /// @notice The beacon for the ExoCapsule contract, which stores the ExoCapsule implementation. - IBeacon public immutable EXO_CAPSULE_BEACON; + /// @notice The beacon for the ImuaCapsule contract, which stores the ImuaCapsule implementation. + IBeacon public immutable IMUA_CAPSULE_BEACON; /// @notice The address of the beacon chain oracle. address public immutable BEACON_ORACLE_ADDRESS; @@ -145,10 +145,9 @@ contract BootstrapStorage is GatewayStorage { /// @dev The address of the ETHPOS deposit contract. IETHPOSDeposit internal immutable ETH_POS; - /// @notice Used to identify the specific Exocore chain this contract interacts with for cross-chain - /// functionalities. - /// @dev Stores the Layer Zero chain ID of the Exocore chain. - uint32 public immutable EXOCORE_CHAIN_ID; + /// @notice Used to identify the specific chain this contract interacts with for cross-chain functionalities. + /// @dev Stores the Layer Zero chain ID of Imuachain. + uint32 public immutable IMUACHAIN_CHAIN_ID; /// @notice This stores the Vault implementation contract address for proxy, and it is shared among all beacon /// proxies. @@ -179,23 +178,23 @@ contract BootstrapStorage is GatewayStorage { // slither-disable-next-line shadowing-state uint256[38] private __gap; - /// @notice Mapping of owner addresses to their corresponding ExoCapsule contracts. - /// @dev Maps owner addresses to their corresponding ExoCapsule contracts. + /// @notice Mapping of owner addresses to their corresponding ImuaCapsule contracts. + /// @dev Maps owner addresses to their corresponding ImuaCapsule contracts. /// @dev This state has been moved from ClientChainGatewayStorage to BootstrapStorage since it is shared by both /// contracts and we put it after __gap to maintain the storage layout compatible with deployed contracts. It was, /// before the move, at the top of the storage layout of ClientChainGatewayStorage. - mapping(address owner => IExoCapsule capsule) public ownerToCapsule; + mapping(address owner => IImuaCapsule capsule) public ownerToCapsule; /* -------------------------------------------------------------------------- */ /* Events */ /* -------------------------------------------------------------------------- */ - /// @notice Emitted when the spawn time of the Exocore chain is updated. - /// @dev This event is triggered whenever the contract owner updates the spawn time of the Exocore chain. + /// @notice Emitted when the spawn time of Imuachain is updated. + /// @dev This event is triggered whenever the contract owner updates the spawn time of Imuachain. /// @param newSpawnTime The new time (in UNIX seconds) that has been set. event SpawnTimeUpdated(uint256 newSpawnTime); - /// @notice Emitted when the offset duration before the Exocore spawn time, during which operations are restricted, + /// @notice Emitted when the offset duration before Imuachain's spawn time, during which operations are restricted, /// is updated. /// @dev This event is triggered whenever the contract owner updates the offset duration. /// @param newOffsetDuration The new offset duration (in seconds) that has been set. @@ -221,7 +220,7 @@ contract BootstrapStorage is GatewayStorage { /// @dev This event is triggered whenever a delegator delegates tokens to an operator. /// @param success Whether the operation succeeded. /// @param delegator The address of the delegator, on this chain. - /// @param delegatee The Exocore address of the operator. + /// @param delegatee The Imuachain address of the operator. /// @param token The address of the token being delegated, on this chain. /// @param amount The amount of the token delegated. event DelegateResult( @@ -232,7 +231,7 @@ contract BootstrapStorage is GatewayStorage { /// @dev This event is triggered whenever a delegator removes a delegation from an operator. /// @param success Whether the operation succeeded. /// @param undelegator The address of the delegator, on this chain. - /// @param undelegatee The Exocore address of the operator. + /// @param undelegatee The Imuachain address of the operator. /// @param token The address of the token being undelegated, on this chain. /// @param amount The amount of the token undelegated. event UndelegateResult( @@ -243,7 +242,7 @@ contract BootstrapStorage is GatewayStorage { /// @dev This event is triggered whenever a delegator deposits and then delegates tokens to an operator. /// @param delegateSuccess Whether the delegation succeeded (deposits always succeed!). /// @param delegator The address of the delegator, on this chain. - /// @param delegatee The Exocore address of the operator. + /// @param delegatee The Imuachain address of the operator. /// @param token The address of the token being delegated, on this chain. /// @param delegatedAmount The amount of the token delegated. event DepositThenDelegateResult( @@ -254,9 +253,9 @@ contract BootstrapStorage is GatewayStorage { uint256 delegatedAmount ); - /// @notice Emitted after the Exocore chain is bootstrapped. - /// @dev This event is triggered after the Exocore chain is bootstrapped, indicating that the contract has - /// successfully transitioned to the Client Chain Gateway logic. Exocore must send a message to the contract to + /// @notice Emitted after Imuachain is bootstrapped. + /// @dev This event is triggered after Imuachain is bootstrapped, indicating that the contract has + /// successfully transitioned to the Client Chain Gateway logic. Imuachain must send a message to the contract to /// trigger this event. event Bootstrapped(); @@ -291,9 +290,9 @@ contract BootstrapStorage is GatewayStorage { event WhitelistTokenAdded(address _token); /* ---------------------------- native restaking events ---------------------------- */ - /// @notice Emitted when a new ExoCapsule is created. - /// @param owner Owner of the ExoCapsule. - /// @param capsule Address of the ExoCapsule. + /// @notice Emitted when a new ImuaCapsule is created. + /// @param owner Owner of the ImuaCapsule. + /// @param capsule Address of the ImuaCapsule. event CapsuleCreated(address indexed owner, address indexed capsule); /// @notice Emitted when a staker stakes with a capsule. @@ -318,18 +317,18 @@ contract BootstrapStorage is GatewayStorage { /** * @dev Struct to store the parameters to initialize the immutable variables for the contract. - * @param exocoreChainId The chain ID of the Exocore chain. + * @param imuachainChainId The LZ chain ID of Imuachain. * @param beaconOracleAddress The address of the beacon chain oracle. * @param vaultBeacon The address of the vault beacon. - * @param exoCapsuleBeacon The address of the ExoCapsule beacon. + * @param imuaCapsuleBeacon The address of the ImuaCapsule beacon. * @param beaconProxyBytecode The address of the beacon proxy bytecode contract. * @param networkConfig The address of the network config contract, if any. */ struct ImmutableConfig { - uint32 exocoreChainId; + uint32 imuachainChainId; address beaconOracleAddress; address vaultBeacon; - address exoCapsuleBeacon; + address imuaCapsuleBeacon; address beaconProxyBytecode; address networkConfig; } @@ -367,17 +366,17 @@ contract BootstrapStorage is GatewayStorage { /// @param config The parameters to initialize the contract immutable variables. constructor(ImmutableConfig memory config) { if ( - config.exocoreChainId == 0 || config.beaconOracleAddress == address(0) || config.vaultBeacon == address(0) - || config.exoCapsuleBeacon == address(0) || config.beaconProxyBytecode == address(0) + config.imuachainChainId == 0 || config.beaconOracleAddress == address(0) || config.vaultBeacon == address(0) + || config.imuaCapsuleBeacon == address(0) || config.beaconProxyBytecode == address(0) ) { // networkConfig is allowed to be 0 revert Errors.InvalidImmutableConfig(); } - EXOCORE_CHAIN_ID = config.exocoreChainId; + IMUACHAIN_CHAIN_ID = config.imuachainChainId; BEACON_ORACLE_ADDRESS = config.beaconOracleAddress; VAULT_BEACON = IBeacon(config.vaultBeacon); - EXO_CAPSULE_BEACON = IBeacon(config.exoCapsuleBeacon); + IMUA_CAPSULE_BEACON = IBeacon(config.imuaCapsuleBeacon); BEACON_PROXY_BYTECODE = BeaconProxyBytecode(config.beaconProxyBytecode); address depositContract; if (config.networkConfig == address(0)) { @@ -400,10 +399,10 @@ contract BootstrapStorage is GatewayStorage { return vault; } - /// @dev Returns the ExoCapsule for the given owner, if it exists. Fails if the ExoCapsule does not exist. - /// @param owner The owner of the ExoCapsule. - function _getCapsule(address owner) internal view returns (IExoCapsule) { - IExoCapsule capsule = ownerToCapsule[owner]; + /// @dev Returns the ImuaCapsule for the given owner, if it exists. Fails if the ImuaCapsule does not exist. + /// @param owner The owner of the ImuaCapsule. + function _getCapsule(address owner) internal view returns (IImuaCapsule) { + IImuaCapsule capsule = ownerToCapsule[owner]; if (address(capsule) == address(0)) { revert Errors.CapsuleDoesNotExist(); } @@ -415,7 +414,8 @@ contract BootstrapStorage is GatewayStorage { /// @param underlyingToken The address of the underlying token. /// @param tvlLimit The TVL limit for the vault. /// @return The address of the newly deployed vault. - // The bytecode returned by `BEACON_PROXY_BYTECODE` and `EXO_CAPSULE_BEACON` address are actually fixed size of byte + // The bytecode returned by `BEACON_PROXY_BYTECODE` and `VAULT_BEACON` address are actually fixed size of + // byte // array, so it would not cause collision for encodePacked // slither-disable-next-line encode-packed-collision function _deployVault(address underlyingToken, uint256 tvlLimit) internal returns (IVault) { diff --git a/src/storage/ClientChainGatewayStorage.sol b/src/storage/ClientChainGatewayStorage.sol index 47f0a235..1f44d8f9 100644 --- a/src/storage/ClientChainGatewayStorage.sol +++ b/src/storage/ClientChainGatewayStorage.sol @@ -10,7 +10,7 @@ import {Action} from "../storage/GatewayStorage.sol"; import {IBeacon} from "@openzeppelin/contracts/proxy/beacon/IBeacon.sol"; /// @title ClientChainGatewayStorage -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice ClientChainGatewayStorage is the storage used by the ClientChainGateway contract. It inherits from /// BootstrapStorage, since the Bootstrap contract upgrades itself to the ClientChainGateway contract in response to a /// cross-chain message. @@ -51,7 +51,7 @@ contract ClientChainGatewayStorage is BootstrapStorage { /// @param amount Amount of @param token claimed. event ClaimSucceeded(address token, address recipient, uint256 amount); - /// @notice Emitted upon reward withdrawal response from Exocore. + /// @notice Emitted upon reward withdrawal response from Imuachain. /// @param success Whether the withdrawal was successful. /// @param token Address of the token. /// @param withdrawer Address of the withdrawer. @@ -61,7 +61,7 @@ contract ClientChainGatewayStorage is BootstrapStorage { /// @notice Emitted when a response is processed. /// @param action The correspoding request action. /// @param requestId The corresponding request ID. - /// @param success Whether the corresponding request was successful on Exocore. + /// @param success Whether the corresponding request was successful on Imuachain. event ResponseProcessed(Action indexed action, uint64 indexed requestId, bool indexed success); /// @notice Emitted when a reward vault is created. diff --git a/src/storage/GatewayStorage.sol b/src/storage/GatewayStorage.sol index d37604fa..3475cdf5 100644 --- a/src/storage/GatewayStorage.sol +++ b/src/storage/GatewayStorage.sol @@ -23,11 +23,11 @@ enum Action { /// @title GatewayStorage /// @notice Storage used by both ends of the gateway contract. -/// @dev This contract is used as the base storage and is inherited by the storage for Bootstrap and ExocoreGateway. +/// @dev This contract is used as the base storage and is inherited by the storage for Bootstrap and ImuachainGateway. contract GatewayStorage { - /// @notice the human readable prefix for Exocore bech32 encoded address. - bytes public constant EXO_ADDRESS_PREFIX = bytes("exo1"); + /// @notice the human readable prefix for Imuachain bech32 encoded address. + bytes public constant IMUA_ADDRESS_PREFIX = bytes("im1"); /// @dev Mapping of actions to their corresponding function selectors. mapping(Action => bytes4) internal _whiteListFunctionSelectors; @@ -50,25 +50,25 @@ contract GatewayStorage { /// @param nonce The nonce associated with the message. event MessageExecuted(Action indexed act, uint64 nonce); - /// @notice Ensures the provided address is a valid exo Bech32 encoded address. + /// @notice Ensures the provided address is a valid im Bech32 encoded address. /// @param addressToValidate The address to check. modifier isValidBech32Address(string calldata addressToValidate) { - require(isValidExocoreAddress(addressToValidate), "BootstrapStorage: invalid bech32 encoded Exocore address"); + require(isValidImAddress(addressToValidate), "BootstrapStorage: invalid bech32 encoded Imuachain address"); _; } - /// @notice Checks if the provided string is a valid Exocore address. + /// @notice Checks if the provided string is a valid Imuachain account address. /// @param addressToValidate The string to check. /// @return True if the string is valid, false otherwise. /// @dev Since implementation of bech32 is difficult in Solidity, this function only - /// checks that the address is 42 characters long and starts with "exo1". - function isValidExocoreAddress(string calldata addressToValidate) public pure returns (bool) { + /// checks that the address is 41 characters long and starts with "im1". + function isValidImAddress(string calldata addressToValidate) public pure returns (bool) { bytes memory stringBytes = bytes(addressToValidate); - if (stringBytes.length != 42) { + if (stringBytes.length != 41) { return false; } - for (uint256 i = 0; i < EXO_ADDRESS_PREFIX.length; ++i) { - if (stringBytes[i] != EXO_ADDRESS_PREFIX[i]) { + for (uint256 i = 0; i < IMUA_ADDRESS_PREFIX.length; ++i) { + if (stringBytes[i] != IMUA_ADDRESS_PREFIX[i]) { return false; } } diff --git a/src/storage/ExoCapsuleStorage.sol b/src/storage/ImuaCapsuleStorage.sol similarity index 92% rename from src/storage/ExoCapsuleStorage.sol rename to src/storage/ImuaCapsuleStorage.sol index c353d0db..5ffb3ac1 100644 --- a/src/storage/ExoCapsuleStorage.sol +++ b/src/storage/ImuaCapsuleStorage.sol @@ -8,25 +8,25 @@ import {INetworkConfig} from "../interfaces/INetworkConfig.sol"; import {IBeaconChainOracle} from "@beacon-oracle/contracts/src/IBeaconChainOracle.sol"; -/// @title ExoCapsuleStorage -/// @author ExocoreNetwork -/// @notice The storage contract for the ExoCapsule contract. +/// @title ImuaCapsuleStorage +/// @author imua-xyz +/// @notice The storage contract for the ImuaCapsule contract. /// @dev It does not inherit from INetworkConfig because the functions are `internal` and not `external` or `public`. -/// Additionally, not all functions are used in the ExoCapsule contract. -contract ExoCapsuleStorage { +/// Additionally, not all functions are used in the ImuaCapsule contract. +contract ImuaCapsuleStorage { /// @notice Enum representing the status of a validator. // solhint-disable-next-line contract-name-camelcase enum VALIDATOR_STATUS { - UNREGISTERED, // the validator has not been registered in this ExoCapsule - REGISTERED, // staked on ethpos and withdrawal credentials are pointed to the ExoCapsule + UNREGISTERED, // the validator has not been registered in this ImuaCapsule + REGISTERED, // staked on ethpos and withdrawal credentials are pointed to the ImuaCapsule WITHDRAWN // withdrawn from the Beacon Chain } - /// @notice Struct representing a validator in the ExoCapsule. + /// @notice Struct representing a validator in the ImuaCapsule. /// @param validatorIndex The index of the validator in the Beacon Chain. - /// @param restakedBalanceGwei The amount of Beacon Chain ETH restaked on Exocore in gwei. + /// @param restakedBalanceGwei The amount of Beacon Chain ETH restaked on Imuachain in gwei. /// @param mostRecentBalanceUpdateTimestamp The timestamp of the validator's most recent balance update. /// @param status The status of the validator. struct Validator { @@ -61,14 +61,14 @@ contract ExoCapsuleStorage { address public immutable NETWORK_CONFIG; /// @notice the amount of execution layer ETH in this contract that is staked in(i.e. withdrawn from the Beacon - /// Chain but not from Exocore) + /// Chain but not from Imuachain) uint256 public withdrawableBalance; /// @notice The amount of non-beacon chain ETH balance. /// @dev This variable tracks any ETH deposited into this contract via the `receive` fallback function uint256 public nonBeaconChainETHBalance; - /// @notice The owner of the ExoCapsule. + /// @notice The owner of the ImuaCapsule. address payable public capsuleOwner; /// @notice The address of the NativeRestakingController contract. @@ -90,7 +90,7 @@ contract ExoCapsuleStorage { /// @dev Storage gap to allow for future upgrades. uint256[40] private __gap; - /// @notice Sets the network configuration contract address for the ExoCapsule contract. + /// @notice Sets the network configuration contract address for the ImuaCapsule contract. /// @param networkConfig_ The address of the NetworkConfig contract. constructor(address networkConfig_) { NETWORK_CONFIG = networkConfig_; diff --git a/src/storage/ExocoreGatewayStorage.sol b/src/storage/ImuachainGatewayStorage.sol similarity index 95% rename from src/storage/ExocoreGatewayStorage.sol rename to src/storage/ImuachainGatewayStorage.sol index 4a81f3ed..558df3cd 100644 --- a/src/storage/ExocoreGatewayStorage.sol +++ b/src/storage/ImuachainGatewayStorage.sol @@ -5,10 +5,10 @@ import {ActionAttributes} from "../libraries/ActionAttributes.sol"; import {Errors} from "../libraries/Errors.sol"; import {Action, GatewayStorage} from "./GatewayStorage.sol"; -/// @title ExocoreGatewayStorage -/// @notice Storage used by the ExocoreGateway contract. -/// @author ExocoreNetwork -contract ExocoreGatewayStorage is GatewayStorage { +/// @title ImuachainGatewayStorage +/// @notice Storage used by the ImuachainGateway contract. +/// @author imua-xyz +contract ImuachainGatewayStorage is GatewayStorage { using ActionAttributes for Action; @@ -39,7 +39,7 @@ contract ExocoreGatewayStorage is GatewayStorage { /// @notice Emitted when a precompile call fails. /// @param precompile Address of the precompile contract. /// @param nonce The LayerZero nonce - event ExocorePrecompileError(address indexed precompile, uint64 nonce); + event ImuachainPrecompileError(address indexed precompile, uint64 nonce); /// @notice Emitted upon the registration of a new client chain. /// @param clientChainId The LayerZero chain ID of the client chain. @@ -101,7 +101,7 @@ contract ExocoreGatewayStorage is GatewayStorage { /// rejected. /// @param token The address of the token. /// @param delegator The address of the delegator. - /// @param operator The Exo account address of the operator. + /// @param operator The im-prefix account address of the operator. /// @param amount The amount of the token delegated/undelegated. event DelegationRequest( bool isDelegate, diff --git a/src/storage/UTXOGatewayStorage.sol b/src/storage/UTXOGatewayStorage.sol index 895e799b..b7d38b60 100644 --- a/src/storage/UTXOGatewayStorage.sol +++ b/src/storage/UTXOGatewayStorage.sol @@ -54,7 +54,7 @@ contract UTXOGatewayStorage { * @param nonce The nonce * @param clientTxId The client chain transaction ID * @param clientAddress The client chain address - * @param exocoreAddress The Exocore address + * @param imuachainAddress The Imuachain address * @param operator The operator * @param amount The amount */ @@ -63,7 +63,7 @@ contract UTXOGatewayStorage { uint64 nonce; bytes32 clientTxId; bytes clientAddress; - address exocoreAddress; + address imuachainAddress; string operator; uint256 amount; } @@ -107,8 +107,8 @@ contract UTXOGatewayStorage { /// @notice the app version uint256 public constant APP_VERSION = 1; - /// @notice the human readable prefix for Exocore bech32 encoded address. - bytes public constant EXO_ADDRESS_PREFIX = bytes("exo1"); + /// @notice the human readable prefix for Imuachain bech32 encoded account address. + bytes public constant IMUA_ADDRESS_PREFIX = bytes("im1"); // the virtual chain id for Bitcoin, compatible with other chain ids(endpoint ids) maintained by layerzero string public constant BITCOIN_NAME = "Bitcoin"; @@ -177,17 +177,17 @@ contract UTXOGatewayStorage { mapping(address => bool) public authorizedWitnesses; /** - * @dev Maps client chain addresses to their registered Exocore addresses + * @dev Maps client chain addresses to their registered Imuachain addresses * @dev Key1: Client chain ID (Bitcoin, etc.) * @dev Key2: Client chain address in bytes - * @dev Value: Registered Exocore address + * @dev Value: Registered Imuachain address */ mapping(ClientChainID => mapping(bytes => address)) public inboundRegistry; /** - * @dev Maps Exocore addresses to their registered client chain addresses + * @dev Maps Imuachain addresses to their registered client chain addresses * @dev Key1: Client chain ID (Bitcoin, etc.) - * @dev Key2: Exocore address + * @dev Key2: Imuachain address * @dev Value: Registered client chain address in bytes */ mapping(ClientChainID => mapping(address => bytes)) public outboundRegistry; @@ -232,11 +232,11 @@ contract UTXOGatewayStorage { * @dev Emitted when a stake message is executed * @param clientChainId The chain ID of the client chain, should not violate the layerzero chain id * @param nonce The nonce of the stake message - * @param exocoreAddress The Exocore address of the depositor + * @param imAddress The Imuachain address of the depositor * @param amount The amount deposited(delegated) */ event StakeMsgExecuted( - ClientChainID indexed clientChainId, uint64 indexed nonce, address indexed exocoreAddress, uint256 amount + ClientChainID indexed clientChainId, uint64 indexed nonce, address indexed imAddress, uint256 amount ); /** @@ -249,7 +249,7 @@ contract UTXOGatewayStorage { * @dev Emitted when a deposit is completed * @param clientChainId The client chain ID * @param clientTxId The client chain transaction ID - * @param depositorExoAddr The depositor's Exocore address + * @param depositorImAddr The depositor's Imuachain * @param depositorClientChainAddr The depositor's client chain address * @param amount The amount deposited * @param updatedBalance The updated balance after deposit @@ -257,7 +257,7 @@ contract UTXOGatewayStorage { event DepositCompleted( ClientChainID indexed clientChainId, bytes32 indexed clientTxId, - address indexed depositorExoAddr, + address indexed depositorImAddr, bytes depositorClientChainAddr, uint256 amount, uint256 updatedBalance @@ -267,7 +267,7 @@ contract UTXOGatewayStorage { * @dev Emitted when a principal withdrawal is requested * @param requestId The unique identifier for the withdrawal request * @param clientChainId The client chain ID - * @param withdrawerExoAddr The withdrawer's Exocore address + * @param withdrawerImAddr The withdrawer's Imuachain * @param withdrawerClientChainAddr The withdrawer's client chain address * @param amount The amount to withdraw * @param updatedBalance The updated balance after withdrawal request @@ -275,7 +275,7 @@ contract UTXOGatewayStorage { event WithdrawPrincipalRequested( ClientChainID indexed clientChainId, uint64 indexed requestId, - address indexed withdrawerExoAddr, + address indexed withdrawerImAddr, bytes withdrawerClientChainAddr, uint256 amount, uint256 updatedBalance @@ -285,7 +285,7 @@ contract UTXOGatewayStorage { * @dev Emitted when a reward withdrawal is requested * @param requestId The unique identifier for the withdrawal request * @param clientChainId The client chain ID - * @param withdrawerExoAddr The withdrawer's Exocore address + * @param withdrawerImAddr The withdrawer's Imuachain * @param withdrawerClientChainAddr The withdrawer's client chain address * @param amount The amount to withdraw * @param updatedBalance The updated balance after withdrawal request @@ -293,7 +293,7 @@ contract UTXOGatewayStorage { event WithdrawRewardRequested( ClientChainID indexed clientChainId, uint64 indexed requestId, - address indexed withdrawerExoAddr, + address indexed withdrawerImAddr, bytes withdrawerClientChainAddr, uint256 amount, uint256 updatedBalance @@ -302,43 +302,43 @@ contract UTXOGatewayStorage { /** * @dev Emitted when a delegation is completed * @param clientChainId The chain ID of the client chain, should not violate the layerzero chain id - * @param exoDelegator The delegator's Exocore address + * @param imDelegator The delegator's Imuachain address * @param operator The operator's address * @param amount The amount delegated */ event DelegationCompleted( - ClientChainID indexed clientChainId, address indexed exoDelegator, string operator, uint256 amount + ClientChainID indexed clientChainId, address indexed imDelegator, string operator, uint256 amount ); /** * @dev Emitted when a delegation fails for a stake message * @param clientChainId The chain ID of the client chain, should not violate the layerzero chain id - * @param exoDelegator The delegator's Exocore address + * @param imDelegator The delegator's Imuachain address * @param operator The operator's address * @param amount The amount delegated */ event DelegationFailedForStake( - ClientChainID indexed clientChainId, address indexed exoDelegator, string operator, uint256 amount + ClientChainID indexed clientChainId, address indexed imDelegator, string operator, uint256 amount ); /** * @dev Emitted when an undelegation is completed * @param clientChainId The chain ID of the client chain, should not violate the layerzero chain id - * @param exoDelegator The delegator's Exocore address + * @param imDelegator The delegator's Imuachain address * @param operator The operator's address * @param amount The amount undelegated */ event UndelegationCompleted( - ClientChainID indexed clientChainId, address indexed exoDelegator, string operator, uint256 amount + ClientChainID indexed clientChainId, address indexed imDelegator, string operator, uint256 amount ); /** * @dev Emitted when an address is registered * @param clientChainId The client chain ID * @param depositor The depositor's address - * @param exocoreAddress The corresponding Exocore address + * @param imAddress The corresponding Imuachain address */ - event AddressRegistered(ClientChainID indexed clientChainId, bytes depositor, address indexed exocoreAddress); + event AddressRegistered(ClientChainID indexed clientChainId, bytes depositor, address indexed imAddress); /** * @dev Emitted when a new witness is added @@ -458,8 +458,8 @@ contract UTXOGatewayStorage { _; } - modifier isRegistered(Token token, address exocoreAddress) { - if (outboundRegistry[ClientChainID(uint8(token))][exocoreAddress].length == 0) { + modifier isRegistered(Token token, address imAddress) { + if (outboundRegistry[ClientChainID(uint8(token))][imAddress].length == 0) { revert Errors.AddressNotRegistered(); } _; @@ -475,18 +475,18 @@ contract UTXOGatewayStorage { _; } - /// @notice Checks if the provided string is a valid Exocore address. + /// @notice Checks if the provided string is a valid Imuachain address. /// @param addressToValidate The string to check. /// @return True if the string is valid, false otherwise. /// @dev Since implementation of bech32 is difficult in Solidity, this function only - /// checks that the address is 42 characters long and starts with "exo1". + /// checks that the address is 42 characters long and starts with "im1". function isValidOperatorAddress(string calldata addressToValidate) public pure returns (bool) { bytes memory stringBytes = bytes(addressToValidate); - if (stringBytes.length != 42) { + if (stringBytes.length != 41) { return false; } - for (uint256 i = 0; i < EXO_ADDRESS_PREFIX.length; ++i) { - if (stringBytes[i] != EXO_ADDRESS_PREFIX[i]) { + for (uint256 i = 0; i < IMUA_ADDRESS_PREFIX.length; ++i) { + if (stringBytes[i] != IMUA_ADDRESS_PREFIX[i]) { return false; } } diff --git a/src/storage/VaultStorage.sol b/src/storage/VaultStorage.sol index 512d7bbe..41756c7c 100644 --- a/src/storage/VaultStorage.sol +++ b/src/storage/VaultStorage.sol @@ -5,7 +5,7 @@ import {ILSTRestakingController} from "../interfaces/ILSTRestakingController.sol import {IERC20} from "@openzeppelin/contracts/token/ERC20/IERC20.sol"; /// @title VaultStorage -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice Storage contract for the Vault contract. contract VaultStorage { diff --git a/src/utils/BeaconProxyBytecode.sol b/src/utils/BeaconProxyBytecode.sol index dc569b2c..c18d4c60 100644 --- a/src/utils/BeaconProxyBytecode.sol +++ b/src/utils/BeaconProxyBytecode.sol @@ -2,16 +2,15 @@ pragma solidity ^0.8.19; /// @title BeaconProxyBytecode -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice The BeaconProxyBytecode contract stores the creation code of the BeaconProxy contract. contract BeaconProxyBytecode { /// /// @notice Stored code of type(BeaconProxy).creationCode /// @dev Maintained as a constant to solve an edge case - changes to OpenZeppelin's BeaconProxy code should not - /// cause - /// addresses of ExoCapsules that are pre-computed with Create2 to change, even upon upgrading this contract, - /// changing compiler version, etc. + /// cause addresses of ImuaCapsules that are pre-computed with Create2 to change, even upon upgrading this + /// contract, changing compiler version, etc. // It is not possible to verify the init bytecode against a specific version of the contract // because it appears to be deployed using a mix of versions of the imported contracts or // another reason we don't understand yet. diff --git a/src/utils/CustomProxyAdmin.sol b/src/utils/CustomProxyAdmin.sol index c5b997a2..139e4a52 100644 --- a/src/utils/CustomProxyAdmin.sol +++ b/src/utils/CustomProxyAdmin.sol @@ -8,7 +8,7 @@ import {ProxyAdmin} from "@openzeppelin/contracts/proxy/transparent/ProxyAdmin.s import {ITransparentUpgradeableProxy} from "@openzeppelin/contracts/proxy/transparent/TransparentUpgradeableProxy.sol"; /// @title CustomProxyAdmin -/// @author ExocoreNetwork +/// @author imua-xyz /// @notice CustomProxyAdmin is a custom implementation of ProxyAdmin that allows a proxy contract to upgrade its own /// implementation. /// @dev This contract is not upgradeable intentionally, since doing so would produce a lot of risk. diff --git a/test/foundry/BootstrapDepositNST.t.sol b/test/foundry/BootstrapDepositNST.t.sol index 44d54547..d9d58863 100644 --- a/test/foundry/BootstrapDepositNST.t.sol +++ b/test/foundry/BootstrapDepositNST.t.sol @@ -10,13 +10,12 @@ import "forge-std/Test.sol"; import {NonShortCircuitEndpointV2Mock} from "test/mocks/NonShortCircuitEndpointV2Mock.sol"; import "../../src/core/Bootstrap.sol"; -import "../../src/core/ExoCapsule.sol"; +import "../../src/core/ImuaCapsule.sol"; import "../../src/utils/BeaconProxyBytecode.sol"; import {BeaconChainProofs} from "src/libraries/BeaconChainProofs.sol"; import {Endian} from "src/libraries/Endian.sol"; import "test/mocks/ETHPOSDepositMock.sol"; -import "../../src/core/ExoCapsule.sol"; import {ClientChainGateway} from "src/core/ClientChainGateway.sol"; import {Vault} from "src/core/Vault.sol"; import {CustomProxyAdmin} from "src/utils/CustomProxyAdmin.sol"; @@ -36,7 +35,7 @@ contract BootstrapDepositNSTTest is Test { uint256 spawnTime; uint256 offsetDuration; - uint16 exocoreChainId = 1; + uint16 imuachainChainId = 1; uint16 clientChainId = 2; address[] whitelistTokens; uint256[] tvlLimits; @@ -46,11 +45,11 @@ contract BootstrapDepositNSTTest is Test { EigenLayerBeaconOracle beaconOracle; IVault vaultImplementation; - IExoCapsule capsuleImplementation; + IImuaCapsule capsuleImplementation; IBeacon vaultBeacon; IBeacon capsuleBeacon; BeaconProxyBytecode beaconProxyBytecode; - ExoCapsule capsule; + ImuaCapsule capsule; bytes32[] validatorContainer; BeaconChainProofs.ValidatorContainerProof validatorProof; @@ -82,7 +81,7 @@ contract BootstrapDepositNSTTest is Test { // deploy vault implementationcontract that has logics called by proxy vaultImplementation = new Vault(); - capsuleImplementation = new ExoCapsule(address(0)); + capsuleImplementation = new ImuaCapsule(address(0)); // deploy the vault beacon that store the implementation contract address vaultBeacon = new UpgradeableBeacon(address(vaultImplementation)); @@ -97,10 +96,10 @@ contract BootstrapDepositNSTTest is Test { clientChainLzEndpoint = new NonShortCircuitEndpointV2Mock(clientChainId, owner); // Create ImmutableConfig struct BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(beaconOracle), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -176,7 +175,7 @@ contract BootstrapDepositNSTTest is Test { _simulateBlockEnvironmentForNativeDeposit(); // 1. firstly depositor should stake to beacon chain by depositing 32 ETH to ETHPOS contract - IExoCapsule expectedCapsule = IExoCapsule( + IImuaCapsule expectedCapsule = IImuaCapsule( Create2.computeAddress( bytes32(uint256(uint160(depositor))), keccak256(abi.encodePacked(BEACON_PROXY_BYTECODE, abi.encode(address(capsuleBeacon), ""))), @@ -284,10 +283,10 @@ contract BootstrapDepositNSTTest is Test { vm.mockCall(address(ETH_POS), abi.encodeWithSelector(ETH_POS.deposit.selector), abi.encode(true)); } - function _attachCapsuleToWithdrawalCredentials(IExoCapsule createdCapsule, address depositor_) internal { + function _attachCapsuleToWithdrawalCredentials(IImuaCapsule createdCapsule, address depositor_) internal { address capsuleAddress = _getCapsuleFromWithdrawalCredentials(_getWithdrawalCredentials(validatorContainer)); vm.etch(capsuleAddress, address(createdCapsule).code); - capsule = ExoCapsule(payable(capsuleAddress)); + capsule = ImuaCapsule(payable(capsuleAddress)); // TODO: load this dynamically somehow instead of hardcoding it bytes32 beaconSlotInCapsule = bytes32(uint256(keccak256("eip1967.proxy.beacon")) - 1); bytes32 beaconAddress = bytes32(uint256(uint160(address(capsuleBeacon)))); diff --git a/test/foundry/Delegation.t.sol b/test/foundry/Delegation.t.sol index f5c3c502..27caeb01 100644 --- a/test/foundry/Delegation.t.sol +++ b/test/foundry/Delegation.t.sol @@ -1,18 +1,18 @@ pragma solidity ^0.8.19; -import "../../src/core/ExocoreGateway.sol"; +import "../../src/core/ImuachainGateway.sol"; import "../../src/interfaces/precompiles/IDelegation.sol"; import {Action, GatewayStorage} from "../../src/storage/GatewayStorage.sol"; import "../mocks/DelegationMock.sol"; -import "./ExocoreDeployer.t.sol"; +import "./ImuachainDeployer.t.sol"; import {OptionsBuilder} from "@layerzerolabs/lz-evm-oapp-v2/contracts/oapp/libs/OptionsBuilder.sol"; import "@layerzerolabs/lz-evm-protocol-v2/contracts/libs/AddressCast.sol"; import "@layerzerolabs/lz-evm-protocol-v2/contracts/libs/GUID.sol"; import "forge-std/Test.sol"; -contract DelegateTest is ExocoreDeployer { +contract DelegateTest is ImuachainDeployer { using AddressCast for address; @@ -54,12 +54,12 @@ contract DelegateTest is ExocoreDeployer { delegator = players[0]; relayer = players[1]; - operatorAddress = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + operatorAddress = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; } function test_Delegation() public { deal(delegator.addr, 1e22); - deal(address(exocoreGateway), 1e22); + deal(address(imuachainGateway), 1e22); uint256 delegateAmount = 10_000; // before delegate we should add whitelist tokens @@ -71,7 +71,7 @@ contract DelegateTest is ExocoreDeployer { function test_Undelegation() public { deal(delegator.addr, 1e22); - deal(address(exocoreGateway), 1e22); + deal(address(imuachainGateway), 1e22); uint256 delegateAmount = 10_000; uint256 undelegateAmount = 5000; @@ -102,9 +102,9 @@ contract DelegateTest is ExocoreDeployer { /// layerzero endpoint should emit the message packet including delegate payload. vm.expectEmit(true, true, true, true, address(clientChainLzEndpoint)); emit NewPacket( - exocoreChainId, + imuachainChainId, address(clientGateway), - address(exocoreGateway).toBytes32(), + address(imuachainGateway).toBytes32(), outboundNonces[clientChainId], delegateRequestPayload ); @@ -132,8 +132,8 @@ contract DelegateTest is ExocoreDeployer { delegateAmount ); - /// exocoreGateway contract should emit DelegateResult event - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + /// imuachainGateway contract should emit DelegateResult event + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit DelegationRequest( true, true, @@ -143,14 +143,14 @@ contract DelegateTest is ExocoreDeployer { delegateAmount ); - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_DELEGATE_TO, inboundNonces[exocoreChainId]++); + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_DELEGATE_TO, inboundNonces[imuachainChainId]++); /// relayer call layerzero endpoint to deliver request messages and generate response message vm.startPrank(relayer.addr); - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), requestId, delegateRequestPayload, bytes("") @@ -187,9 +187,9 @@ contract DelegateTest is ExocoreDeployer { /// layerzero endpoint should emit the message packet including undelegate payload. vm.expectEmit(true, true, true, true, address(clientChainLzEndpoint)); emit NewPacket( - exocoreChainId, + imuachainChainId, address(clientGateway), - address(exocoreGateway).toBytes32(), + address(imuachainGateway).toBytes32(), outboundNonces[clientChainId], undelegateRequestPayload ); @@ -217,8 +217,8 @@ contract DelegateTest is ExocoreDeployer { undelegateAmount ); - /// exocoreGateway contract should emit UndelegateResult event - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + /// imuachainGateway contract should emit UndelegateResult event + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit DelegationRequest( false, true, @@ -228,14 +228,14 @@ contract DelegateTest is ExocoreDeployer { undelegateAmount ); - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_UNDELEGATE_FROM, inboundNonces[exocoreChainId]++); + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_UNDELEGATE_FROM, inboundNonces[imuachainChainId]++); /// relayer call layerzero endpoint to deliver request messages and generate response message vm.startPrank(relayer.addr); - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), requestId, undelegateRequestPayload, bytes("") diff --git a/test/foundry/DepositThenDelegateTo.t.sol b/test/foundry/DepositThenDelegateTo.t.sol index a0c3b5b3..2eacc5db 100644 --- a/test/foundry/DepositThenDelegateTo.t.sol +++ b/test/foundry/DepositThenDelegateTo.t.sol @@ -1,13 +1,13 @@ pragma solidity ^0.8.19; -import "../../src/core/ExocoreGateway.sol"; +import "../../src/core/ImuachainGateway.sol"; import "../../src/interfaces/precompiles/IDelegation.sol"; import {Action, GatewayStorage} from "../../src/storage/GatewayStorage.sol"; import "../mocks/AssetsMock.sol"; import "../mocks/DelegationMock.sol"; -import "./ExocoreDeployer.t.sol"; +import "./ImuachainDeployer.t.sol"; import {OptionsBuilder} from "@layerzerolabs/lz-evm-oapp-v2/contracts/oapp/libs/OptionsBuilder.sol"; import "@layerzerolabs/lz-evm-protocol-v2/contracts/libs/AddressCast.sol"; @@ -15,11 +15,11 @@ import "@layerzerolabs/lz-evm-protocol-v2/contracts/libs/GUID.sol"; import {IERC20} from "@openzeppelin/contracts/token/ERC20/IERC20.sol"; import "forge-std/Test.sol"; -contract DepositThenDelegateToTest is ExocoreDeployer { +contract DepositThenDelegateToTest is ImuachainDeployer { using AddressCast for address; - // ExocoreGateway emits these two events after handling the request + // ImuachainGateway emits these two events after handling the request event LSTTransfer( bool isDeposit, bool indexed success, bytes32 indexed token, bytes32 indexed depositor, uint256 amount ); @@ -45,10 +45,10 @@ contract DepositThenDelegateToTest is ExocoreDeployer { function test_DepositThenDelegateTo() public { address delegator = players[0].addr; address relayer = players[1].addr; - string memory operatorAddress = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory operatorAddress = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; deal(delegator, 1e22); - deal(address(exocoreGateway), 1e22); + deal(address(imuachainGateway), 1e22); uint256 delegateAmount = 10_000; @@ -56,11 +56,11 @@ contract DepositThenDelegateToTest is ExocoreDeployer { test_AddWhitelistTokens(); // ensure there is enough balance - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); restakeToken.transfer(delegator, delegateAmount); vm.stopPrank(); - // approve it + // // approve it vm.startPrank(delegator); restakeToken.approve(address(vault), delegateAmount); vm.stopPrank(); @@ -73,10 +73,10 @@ contract DepositThenDelegateToTest is ExocoreDeployer { function test_BalanceUpdatedWhen_DepositThenDelegateToResponseNotSuccess() public { address delegator = players[0].addr; address relayer = players[1].addr; - string memory operatorAddress = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory operatorAddress = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; deal(delegator, 1e22); - deal(address(exocoreGateway), 1e22); + deal(address(imuachainGateway), 1e22); uint256 delegateAmount = 10_000; @@ -84,7 +84,7 @@ contract DepositThenDelegateToTest is ExocoreDeployer { test_AddWhitelistTokens(); // ensure there is enough balance - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); restakeToken.transfer(delegator, delegateAmount); vm.stopPrank(); @@ -96,7 +96,7 @@ contract DepositThenDelegateToTest is ExocoreDeployer { (bytes32 requestId, bytes memory requestPayload) = _testRequest(delegator, operatorAddress, delegateAmount); _testRequestExecutionFailure(delegator, relayer, delegateAmount); // this cannot be called here because we have artificially failed the delegation and avoided the - // inboundNonce increment on Exocore + // inboundNonce increment on Imuachain // _validateNonces(); } @@ -122,9 +122,9 @@ contract DepositThenDelegateToTest is ExocoreDeployer { vm.expectEmit(address(clientChainLzEndpoint)); emit NewPacket( - exocoreChainId, + imuachainChainId, address(clientGateway), - address(exocoreGateway).toBytes32(), + address(imuachainGateway).toBytes32(), outboundNonces[clientChainId], requestPayload ); @@ -147,7 +147,7 @@ contract DepositThenDelegateToTest is ExocoreDeployer { assertEq(afterBalanceVault, beforeBalanceVault + delegateAmount); } - // test that request is successfully executed on Exocore side + // test that request is successfully executed on Imuachain function _testRequestExecutionSuccess( bytes32 requestId, bytes memory requestPayload, @@ -157,7 +157,7 @@ contract DepositThenDelegateToTest is ExocoreDeployer { uint256 delegateAmount ) private { // deposit request is firstly handled and its event is firstly emitted - vm.expectEmit(address(exocoreGateway)); + vm.expectEmit(address(imuachainGateway)); emit LSTTransfer( true, true, bytes32(bytes20(address(restakeToken))), bytes32(bytes20(delegator)), delegateAmount ); @@ -173,7 +173,7 @@ contract DepositThenDelegateToTest is ExocoreDeployer { delegateAmount ); - vm.expectEmit(address(exocoreGateway)); + vm.expectEmit(address(imuachainGateway)); emit DelegationRequest( true, true, @@ -183,13 +183,13 @@ contract DepositThenDelegateToTest is ExocoreDeployer { delegateAmount ); - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_DEPOSIT_THEN_DELEGATE_TO, inboundNonces[exocoreChainId]++); + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_DEPOSIT_THEN_DELEGATE_TO, inboundNonces[imuachainChainId]++); vm.startPrank(relayer); - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), requestId, requestPayload, bytes("") @@ -223,25 +223,25 @@ contract DepositThenDelegateToTest is ExocoreDeployer { outboundNonces[clientChainId] - 1, abi.encodePacked(bytes32(bytes20(address(restakeToken)))), abi.encodePacked(bytes32(bytes20(delegator))), - "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", + "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", delegateAmount ); vm.mockCall(DELEGATION_PRECOMPILE_ADDRESS, delegateCalldata, abi.encode(false)); // Expect LSTTransfer event for successful deposit - vm.expectEmit(address(exocoreGateway)); + vm.expectEmit(address(imuachainGateway)); emit LSTTransfer( true, true, bytes32(bytes20(address(restakeToken))), bytes32(bytes20(delegator)), delegateAmount ); // Expect DelegationRequest event with 'accepted' as false - vm.expectEmit(address(exocoreGateway)); + vm.expectEmit(address(imuachainGateway)); emit DelegationRequest( true, false, bytes32(bytes20(address(restakeToken))), bytes32(bytes20(delegator)), - "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", + "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", delegateAmount ); @@ -251,17 +251,17 @@ contract DepositThenDelegateToTest is ExocoreDeployer { abi.encodePacked(bytes32(bytes20(delegator))), delegateAmount, abi.encodePacked(bytes32(bytes20(address(restakeToken)))), - bytes("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac") + bytes("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla") ); bytes32 requestId = generateUID(outboundNonces[clientChainId] - 1, true); - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_DEPOSIT_THEN_DELEGATE_TO, inboundNonces[exocoreChainId]++); + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_DEPOSIT_THEN_DELEGATE_TO, inboundNonces[imuachainChainId]++); vm.startPrank(relayer); - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), requestId, requestPayload, bytes("") @@ -278,7 +278,7 @@ contract DepositThenDelegateToTest is ExocoreDeployer { // Verify that the delegation was not successful uint256 actualDelegateAmount = DelegationMock(DELEGATION_PRECOMPILE_ADDRESS).getDelegateAmount( - delegator, "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", clientChainId, address(restakeToken) + delegator, "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", clientChainId, address(restakeToken) ); assertEq(actualDelegateAmount, 0); diff --git a/test/foundry/DepositWithdrawPrincipal.t.sol b/test/foundry/DepositWithdrawPrincipal.t.sol index 60e4e6fc..b1bf9aa1 100644 --- a/test/foundry/DepositWithdrawPrincipal.t.sol +++ b/test/foundry/DepositWithdrawPrincipal.t.sol @@ -1,21 +1,21 @@ pragma solidity ^0.8.19; -import "../../src/core/ExoCapsule.sol"; -import "../../src/core/ExocoreGateway.sol"; +import "../../src/core/ImuaCapsule.sol"; +import "../../src/core/ImuachainGateway.sol"; import "../mocks/AssetsMock.sol"; -import {IExoCapsule} from "../../src/interfaces/IExoCapsule.sol"; +import {IImuaCapsule} from "../../src/interfaces/IImuaCapsule.sol"; import {ILSTRestakingController} from "../../src/interfaces/ILSTRestakingController.sol"; import {Action, GatewayStorage} from "../../src/storage/GatewayStorage.sol"; -import "./ExocoreDeployer.t.sol"; +import "./ImuachainDeployer.t.sol"; import "forge-std/Test.sol"; import "@layerzerolabs/lz-evm-protocol-v2/contracts/libs/AddressCast.sol"; import "@layerzerolabs/lz-evm-protocol-v2/contracts/libs/GUID.sol"; import "@openzeppelin/contracts/utils/Create2.sol"; -contract DepositWithdrawPrincipalTest is ExocoreDeployer { +contract DepositWithdrawPrincipalTest is ImuachainDeployer { using AddressCast for address; using stdStorage for StdStorage; @@ -38,15 +38,15 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { function test_LSTDepositWithdrawByLayerZero() public { Player memory depositor = players[0]; - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); restakeToken.transfer(depositor.addr, 1_000_000); vm.stopPrank(); // transfer some gas fee to depositor deal(depositor.addr, 1e22); - // transfer some gas fee to exocore gateway as it has to pay for the relay fee to layerzero endpoint when + // transfer some gas fee to imuachain gateway as it has to pay for the relay fee to layerzero endpoint when // sending back response - deal(address(exocoreGateway), 1e22); + deal(address(imuachainGateway), 1e22); uint256 depositAmount = 10_000; uint256 withdrawAmount = 100; @@ -106,9 +106,9 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { // client chain layerzero endpoint should emit the message packet including deposit payload. vm.expectEmit(true, true, true, true, address(clientChainLzEndpoint)); emit NewPacket( - exocoreChainId, + imuachainChainId, address(clientGateway), - address(exocoreGateway).toBytes32(), + address(imuachainGateway).toBytes32(), outboundNonces[clientChainId], depositRequestPayload ); @@ -122,8 +122,8 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { // second layerzero relayers should watch the request message packet and relay the message to destination // endpoint - // exocore gateway should emit LSTTransfer event - vm.expectEmit(address(exocoreGateway)); + // imuachain gateway should emit LSTTransfer event + vm.expectEmit(address(imuachainGateway)); emit LSTTransfer( true, // isDeposit true, // success @@ -132,12 +132,12 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { depositAmount ); - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_DEPOSIT_LST, inboundNonces[exocoreChainId]++); - // inboundNonces[exocoreChainId]++; - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_DEPOSIT_LST, inboundNonces[imuachainChainId]++); + // inboundNonces[imuachainChainId]++; + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), depositRequestId, depositRequestPayload, bytes("") @@ -163,9 +163,9 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { // client chain layerzero endpoint should emit the message packet including withdraw payload. vm.expectEmit(true, true, true, true, address(clientChainLzEndpoint)); emit NewPacket( - exocoreChainId, + imuachainChainId, address(clientGateway), - address(exocoreGateway).toBytes32(), + address(imuachainGateway).toBytes32(), outboundNonces[clientChainId], withdrawRequestPayload ); @@ -174,17 +174,19 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { emit MessageSent( Action.REQUEST_WITHDRAW_LST, withdrawRequestId, outboundNonces[clientChainId]++, withdrawRequestNativeFee ); - clientGateway.claimPrincipalFromExocore{value: withdrawRequestNativeFee}(address(restakeToken), withdrawAmount); + clientGateway.claimPrincipalFromImuachain{value: withdrawRequestNativeFee}( + address(restakeToken), withdrawAmount + ); // second layerzero relayers should watch the request message packet and relay the message to destination // endpoint lastlyUpdatedPrincipalBalance -= withdrawAmount; bytes memory withdrawResponsePayload = abi.encodePacked(Action.RESPOND, outboundNonces[clientChainId] - 1, true); - uint256 withdrawResponseNativeFee = exocoreGateway.quote(clientChainId, withdrawResponsePayload); - bytes32 withdrawResponseId = generateUID(outboundNonces[exocoreChainId], false); + uint256 withdrawResponseNativeFee = imuachainGateway.quote(clientChainId, withdrawResponsePayload); + bytes32 withdrawResponseId = generateUID(outboundNonces[imuachainChainId], false); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit LSTTransfer( false, // isDeposit (false for withdrawal) true, // success @@ -193,26 +195,26 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { withdrawAmount ); - // exocore gateway should return response message to exocore network layerzero endpoint - vm.expectEmit(true, true, true, true, address(exocoreLzEndpoint)); + // imuachain gateway should return response message to imuachain network layerzero endpoint + vm.expectEmit(true, true, true, true, address(imuachainLzEndpoint)); emit NewPacket( clientChainId, - address(exocoreGateway), + address(imuachainGateway), address(clientGateway).toBytes32(), - outboundNonces[exocoreChainId], + outboundNonces[imuachainChainId], withdrawResponsePayload ); - // exocore gateway should emit MessageSent event - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + // imuachain gateway should emit MessageSent event + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit MessageSent( - Action.RESPOND, withdrawResponseId, outboundNonces[exocoreChainId]++, withdrawResponseNativeFee + Action.RESPOND, withdrawResponseId, outboundNonces[imuachainChainId]++, withdrawResponseNativeFee ); - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_WITHDRAW_LST, inboundNonces[exocoreChainId]++); - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_WITHDRAW_LST, inboundNonces[imuachainChainId]++); + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), withdrawRequestId, withdrawRequestPayload, bytes("") @@ -229,7 +231,7 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { vm.expectEmit(address(clientGateway)); emit MessageExecuted(Action.RESPOND, inboundNonces[clientChainId]++); clientChainLzEndpoint.lzReceive( - Origin(exocoreChainId, address(exocoreGateway).toBytes32(), inboundNonces[clientChainId] - 1), + Origin(imuachainChainId, address(imuachainGateway).toBytes32(), inboundNonces[clientChainId] - 1), address(clientGateway), withdrawResponseId, withdrawResponsePayload, @@ -253,9 +255,9 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { deal(depositor.addr, 1e22); // transfer some gas fee to relayer for paying for onboarding cross-chain message packet deal(relayer.addr, 1e22); - // transfer some gas fee to exocore gateway as it has to pay for the relay fee to layerzero endpoint when + // transfer some gas fee to imuachain gateway as it has to pay for the relay fee to layerzero endpoint when // sending back response - deal(address(exocoreGateway), 1e22); + deal(address(imuachainGateway), 1e22); // before deposit we should add whitelist tokens test_AddWhitelistTokens(); @@ -298,7 +300,7 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { function _testNativeDeposit(Player memory depositor, Player memory relayer, uint256 lastlyUpdatedPrincipalBalance) internal { - // 1. next depositor call clientGateway.verifyAndDepositNativeStake to deposit into Exocore from client chain + // 1. next depositor call clientGateway.verifyAndDepositNativeStake to deposit into Imuachain from client chain // through layerzero /// client chain layerzero endpoint should emit the message packet including deposit payload. @@ -316,9 +318,9 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { vm.expectEmit(true, true, true, true, address(clientChainLzEndpoint)); emit NewPacket( - exocoreChainId, + imuachainChainId, address(clientGateway), - address(exocoreGateway).toBytes32(), + address(imuachainGateway).toBytes32(), outboundNonces[clientChainId], depositRequestPayload ); @@ -336,8 +338,8 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { // 2. thirdly layerzero relayers should watch the request message packet and relay the message to destination // endpoint - /// exocore gateway should emit NSTTransfer event - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + /// imuachain gateway should emit NSTTransfer event + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit NSTTransfer( true, // isDeposit true, // success @@ -346,14 +348,14 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { depositAmount ); - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_DEPOSIT_NST, inboundNonces[exocoreChainId]++); + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_DEPOSIT_NST, inboundNonces[imuachainChainId]++); - /// relayer catches the request message packet by listening to client chain event and feed it to Exocore network + /// relayer catches the request message packet by listening to client chain event and feed it to Imuachain vm.startPrank(relayer.addr); - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), depositRequestId, depositRequestPayload, bytes("") @@ -366,7 +368,7 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { _simulateBlockEnvironmentForNativeDeposit(); // 1. firstly depositor should stake to beacon chain by depositing 32 ETH to ETHPOS contract - IExoCapsule expectedCapsule = IExoCapsule( + IImuaCapsule expectedCapsule = IImuaCapsule( Create2.computeAddress( bytes32(uint256(uint160(depositor.addr))), keccak256(abi.encodePacked(BEACON_PROXY_BYTECODE, abi.encode(address(capsuleBeacon), ""))), @@ -406,10 +408,10 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { ); } - function _attachCapsuleToWithdrawalCredentials(IExoCapsule createdCapsule, Player memory depositor) internal { + function _attachCapsuleToWithdrawalCredentials(IImuaCapsule createdCapsule, Player memory depositor) internal { address capsuleAddress = _getCapsuleFromWithdrawalCredentials(_getWithdrawalCredentials(validatorContainer)); vm.etch(capsuleAddress, address(createdCapsule).code); - capsule = ExoCapsule(payable(capsuleAddress)); + capsule = ImuaCapsule(payable(capsuleAddress)); // TODO: load this dynamically somehow instead of hardcoding it bytes32 beaconSlotInCapsule = bytes32(uint256(keccak256("eip1967.proxy.beacon")) - 1); bytes32 beaconAddress = bytes32(uint256(uint160(address(capsuleBeacon)))); @@ -430,7 +432,7 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { function _testNativeWithdraw(Player memory withdrawer, Player memory relayer, uint256 lastlyUpdatedPrincipalBalance) internal { - // 1. withdrawer will call clientGateway.processBeaconChainWithdrawal to withdraw from Exocore thru layerzero + // 1. withdrawer will call clientGateway.processBeaconChainWithdrawal to withdraw from Imuachain thru layerzero /// client chain layerzero endpoint should emit the message packet including deposit payload. uint64 withdrawalAmountGwei = _getWithdrawalAmount(withdrawalContainer); @@ -452,9 +454,9 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { // client chain layerzero endpoint should emit the message packet including withdraw payload. vm.expectEmit(true, true, true, true, address(clientChainLzEndpoint)); emit NewPacket( - exocoreChainId, + imuachainChainId, address(clientGateway), - address(exocoreGateway).toBytes32(), + address(imuachainGateway).toBytes32(), outboundNonces[clientChainId], withdrawRequestPayload ); @@ -470,14 +472,14 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { ); vm.stopPrank(); - /// exocore gateway should return response message to exocore network layerzero endpoint + /// imuachain gateway should return response message to imuachain network layerzero endpoint lastlyUpdatedPrincipalBalance -= withdrawalAmount; bytes memory withdrawResponsePayload = abi.encodePacked(Action.RESPOND, outboundNonces[clientChainId] - 1, true); - uint256 withdrawResponseNativeFee = exocoreGateway.quote(clientChainId, withdrawResponsePayload); - bytes32 withdrawResponseId = generateUID(outboundNonces[exocoreChainId], false); + uint256 withdrawResponseNativeFee = imuachainGateway.quote(clientChainId, withdrawResponsePayload); + bytes32 withdrawResponseId = generateUID(outboundNonces[imuachainChainId], false); - // exocore gateway should emit NSTTransfer event - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + // imuachain gateway should emit NSTTransfer event + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit NSTTransfer( false, // isDeposit (false for withdrawal) true, // success @@ -486,27 +488,27 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { withdrawalAmount ); - // exocore gateway should return response message to exocore network layerzero endpoint - vm.expectEmit(true, true, true, true, address(exocoreLzEndpoint)); + // imuachain gateway should return response message to imuachain network layerzero endpoint + vm.expectEmit(true, true, true, true, address(imuachainLzEndpoint)); emit NewPacket( clientChainId, - address(exocoreGateway), + address(imuachainGateway), address(clientGateway).toBytes32(), - outboundNonces[exocoreChainId], + outboundNonces[imuachainChainId], withdrawResponsePayload ); - // exocore gateway should emit MessageSent event - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + // imuachain gateway should emit MessageSent event + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit MessageSent( - Action.RESPOND, withdrawResponseId, outboundNonces[exocoreChainId]++, withdrawResponseNativeFee + Action.RESPOND, withdrawResponseId, outboundNonces[imuachainChainId]++, withdrawResponseNativeFee ); - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_WITHDRAW_NST, inboundNonces[exocoreChainId]++); + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_WITHDRAW_NST, inboundNonces[imuachainChainId]++); - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), withdrawRequestId, withdrawRequestPayload, bytes("") @@ -520,7 +522,7 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { emit MessageExecuted(Action.RESPOND, inboundNonces[clientChainId]++); clientChainLzEndpoint.lzReceive( - Origin(exocoreChainId, address(exocoreGateway).toBytes32(), inboundNonces[clientChainId] - 1), + Origin(imuachainChainId, address(imuachainGateway).toBytes32(), inboundNonces[clientChainId] - 1), address(clientGateway), withdrawResponseId, withdrawResponsePayload, @@ -555,7 +557,7 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { address addr = players[0].addr; deal(addr, 1e22); // for gas - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); restakeToken.transfer(addr, 1_000_000); vm.stopPrank(); @@ -584,24 +586,24 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { // deposit succeeded on client chain assertTrue(vault.getConsumedTvl() == consumedTvl); - deal(address(exocoreGateway), 1e22); // for lz fees + deal(address(imuachainGateway), 1e22); // for lz fees - // run the message on the Exocore gateway + // run the message on the Imuachain gateway principalBalance += depositAmount; - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_DEPOSIT_LST, inboundNonces[exocoreChainId]++); - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_DEPOSIT_LST, inboundNonces[imuachainChainId]++); + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), requestId, requestPayload, bytes("") ); - // given that the above transaction went through, the deposit succeeded on Exocore + // given that the above transaction went through, the deposit succeeded on Imuachain uint256 newTvlLimit = depositAmount / 2; // divisible by 4 so no need to check for 2 - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); // a reduction is always allowed clientGateway.updateTvlLimit(address(restakeToken), newTvlLimit); vm.stopPrank(); @@ -619,24 +621,24 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { nativeFee = clientGateway.quote(requestPayload); vm.expectEmit(address(clientGateway)); emit MessageSent(Action.REQUEST_WITHDRAW_LST, requestId, outboundNonces[clientChainId]++, nativeFee); - clientGateway.claimPrincipalFromExocore{value: nativeFee}(address(restakeToken), withdrawAmount); + clientGateway.claimPrincipalFromImuachain{value: nativeFee}(address(restakeToken), withdrawAmount); vm.stopPrank(); principalBalance -= withdrawAmount; bytes memory responsePayload = abi.encodePacked(Action.RESPOND, outboundNonces[clientChainId] - 1, true); - bytes32 responseId = generateUID(outboundNonces[exocoreChainId], false); - vm.expectEmit(address(exocoreGateway)); + bytes32 responseId = generateUID(outboundNonces[imuachainChainId], false); + vm.expectEmit(address(imuachainGateway)); emit MessageSent( Action.RESPOND, responseId, - outboundNonces[exocoreChainId]++, - exocoreGateway.quote(clientChainId, responsePayload) - ); - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_WITHDRAW_LST, inboundNonces[exocoreChainId]++); - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + outboundNonces[imuachainChainId]++, + imuachainGateway.quote(clientChainId, responsePayload) + ); + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_WITHDRAW_LST, inboundNonces[imuachainChainId]++); + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), requestId, requestPayload, bytes("") @@ -645,7 +647,7 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { vm.expectEmit(address(clientGateway)); emit MessageExecuted(Action.RESPOND, inboundNonces[clientChainId]++); clientChainLzEndpoint.lzReceive( - Origin(exocoreChainId, address(exocoreGateway).toBytes32(), inboundNonces[clientChainId] - 1), + Origin(imuachainChainId, address(imuachainGateway).toBytes32(), inboundNonces[clientChainId] - 1), address(clientGateway), responseId, responsePayload, @@ -687,23 +689,23 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { nativeFee = clientGateway.quote(requestPayload); vm.expectEmit(address(clientGateway)); emit MessageSent(Action.REQUEST_WITHDRAW_LST, requestId, outboundNonces[clientChainId]++, nativeFee); - clientGateway.claimPrincipalFromExocore{value: nativeFee}(address(restakeToken), withdrawAmount); + clientGateway.claimPrincipalFromImuachain{value: nativeFee}(address(restakeToken), withdrawAmount); // obtain the response responsePayload = abi.encodePacked(Action.RESPOND, outboundNonces[clientChainId] - 1, true); - responseId = generateUID(outboundNonces[exocoreChainId], false); - vm.expectEmit(address(exocoreGateway)); + responseId = generateUID(outboundNonces[imuachainChainId], false); + vm.expectEmit(address(imuachainGateway)); emit MessageSent( Action.RESPOND, responseId, - outboundNonces[exocoreChainId]++, - exocoreGateway.quote(clientChainId, responsePayload) - ); - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_WITHDRAW_LST, inboundNonces[exocoreChainId]++); - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + outboundNonces[imuachainChainId]++, + imuachainGateway.quote(clientChainId, responsePayload) + ); + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_WITHDRAW_LST, inboundNonces[imuachainChainId]++); + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), requestId, requestPayload, bytes("") @@ -713,7 +715,7 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { vm.expectEmit(address(clientGateway)); emit MessageExecuted(Action.RESPOND, inboundNonces[clientChainId]++); clientChainLzEndpoint.lzReceive( - Origin(exocoreChainId, address(exocoreGateway).toBytes32(), inboundNonces[clientChainId] - 1), + Origin(imuachainChainId, address(imuachainGateway).toBytes32(), inboundNonces[clientChainId] - 1), address(clientGateway), responseId, responsePayload, @@ -754,14 +756,14 @@ contract DepositWithdrawPrincipalTest is ExocoreDeployer { consumedTvl += depositAmount; vm.stopPrank(); - // execute the deposit request on Exocore + // execute the deposit request on Imuachain principalBalance += depositAmount; - vm.expectEmit(address(exocoreGateway)); - emit MessageExecuted(Action.REQUEST_DEPOSIT_LST, inboundNonces[exocoreChainId]++); - exocoreLzEndpoint.lzReceive( - Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[exocoreChainId] - 1), - address(exocoreGateway), + vm.expectEmit(address(imuachainGateway)); + emit MessageExecuted(Action.REQUEST_DEPOSIT_LST, inboundNonces[imuachainChainId]++); + imuachainLzEndpoint.lzReceive( + Origin(clientChainId, address(clientGateway).toBytes32(), inboundNonces[imuachainChainId] - 1), + address(imuachainGateway), requestId, requestPayload, bytes("") diff --git a/test/foundry/Governance.t.sol b/test/foundry/Governance.t.sol index b27c0d6f..79c57eea 100644 --- a/test/foundry/Governance.t.sol +++ b/test/foundry/Governance.t.sol @@ -23,14 +23,14 @@ import "@openzeppelin/contracts/token/ERC20/presets/ERC20PresetFixedSupply.sol"; import "src/core/ClientChainGateway.sol"; import "src/storage/ClientChainGatewayStorage.sol"; -import "src/core/ExoCapsule.sol"; +import "src/core/ImuaCapsule.sol"; import {RewardVault} from "src/core/RewardVault.sol"; import {Vault} from "src/core/Vault.sol"; import {IRewardVault} from "src/interfaces/IRewardVault.sol"; import {NonShortCircuitEndpointV2Mock} from "../mocks/NonShortCircuitEndpointV2Mock.sol"; -import "src/interfaces/IExoCapsule.sol"; +import "src/interfaces/IImuaCapsule.sol"; import "src/interfaces/IVault.sol"; import "src/utils/BeaconProxyBytecode.sol"; @@ -68,13 +68,13 @@ contract GovernanceTest is Test { IBeaconChainOracle beaconOracle; IVault vaultImplementation; IRewardVault rewardVaultImplementation; - IExoCapsule capsuleImplementation; + IImuaCapsule capsuleImplementation; IBeacon vaultBeacon; IBeacon rewardVaultBeacon; IBeacon capsuleBeacon; BeaconProxyBytecode beaconProxyBytecode; - uint32 exocoreChainId = 2; + uint32 imuachainChainId = 2; uint32 clientChainId = 1; uint256 holeskyFork; @@ -140,7 +140,7 @@ contract GovernanceTest is Test { vaultImplementation = new Vault(); rewardVaultImplementation = new RewardVault(); - capsuleImplementation = new ExoCapsule(address(0)); + capsuleImplementation = new ImuaCapsule(address(0)); vaultBeacon = new UpgradeableBeacon(address(vaultImplementation)); rewardVaultBeacon = new UpgradeableBeacon(address(rewardVaultImplementation)); @@ -155,10 +155,10 @@ contract GovernanceTest is Test { // Create ImmutableConfig struct BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(beaconOracle), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); diff --git a/test/foundry/ExocoreDeployer.t.sol b/test/foundry/ImuachainDeployer.t.sol similarity index 87% rename from test/foundry/ExocoreDeployer.t.sol rename to test/foundry/ImuachainDeployer.t.sol index fafa53ea..7bb814bb 100644 --- a/test/foundry/ExocoreDeployer.t.sol +++ b/test/foundry/ImuachainDeployer.t.sol @@ -15,8 +15,8 @@ import "forge-std/Test.sol"; import "../../src/core/ClientChainGateway.sol"; -import "../../src/core/ExoCapsule.sol"; -import "../../src/core/ExocoreGateway.sol"; +import "../../src/core/ImuaCapsule.sol"; +import "../../src/core/ImuachainGateway.sol"; import {RewardVault} from "../../src/core/RewardVault.sol"; import {Vault} from "../../src/core/Vault.sol"; @@ -36,7 +36,6 @@ import "../mocks/DelegationMock.sol"; import {NonShortCircuitEndpointV2Mock} from "../mocks/NonShortCircuitEndpointV2Mock.sol"; import "../mocks/RewardMock.sol"; -import "src/core/ExoCapsule.sol"; import "src/utils/BeaconProxyBytecode.sol"; import "src/libraries/BeaconChainProofs.sol"; @@ -47,14 +46,14 @@ import {BootstrapStorage} from "../../src/storage/BootstrapStorage.sol"; import {NetworkConstants} from "src/libraries/NetworkConstants.sol"; -contract ExocoreDeployer is Test { +contract ImuachainDeployer is Test { using AddressCast for address; using Endian for bytes32; Player[] players; bytes32[] whitelistTokens; - Player exocoreValidatorSet; + Player owner; address[] vaults; ERC20PresetFixedSupply restakeToken; @@ -62,15 +61,15 @@ contract ExocoreDeployer is Test { ClientChainGateway clientGatewayLogic; IRewardVault rewardVault; Vault vault; - ExoCapsule capsule; - ExocoreGateway exocoreGateway; - ExocoreGateway exocoreGatewayLogic; + ImuaCapsule capsule; + ImuachainGateway imuachainGateway; + ImuachainGateway imuachainGatewayLogic; ILayerZeroEndpointV2 clientChainLzEndpoint; - ILayerZeroEndpointV2 exocoreLzEndpoint; + ILayerZeroEndpointV2 imuachainLzEndpoint; IBeaconChainOracle beaconOracle; IVault vaultImplementation; IRewardVault rewardVaultImplementation; - IExoCapsule capsuleImplementation; + IImuaCapsule capsuleImplementation; IBeacon vaultBeacon; IBeacon rewardVaultBeacon; IBeacon capsuleBeacon; @@ -102,7 +101,7 @@ contract ExocoreDeployer is Test { uint256 mockCurrentBlockTimestamp; uint256 activationTimestamp; - uint32 exocoreChainId = 2; + uint32 imuachainChainId = 2; uint32 clientChainId = 1; // the nonces to use for sending messages, incremented when there is a MessageSent event @@ -128,15 +127,15 @@ contract ExocoreDeployer is Test { function setUp() public virtual { // the nonces start from 1 - outboundNonces[exocoreChainId] = 1; + outboundNonces[imuachainChainId] = 1; outboundNonces[clientChainId] = 1; - inboundNonces[exocoreChainId] = 1; + inboundNonces[imuachainChainId] = 1; inboundNonces[clientChainId] = 1; players.push(Player({privateKey: uint256(0x1), addr: vm.addr(uint256(0x1))})); players.push(Player({privateKey: uint256(0x2), addr: vm.addr(uint256(0x2))})); players.push(Player({privateKey: uint256(0x3), addr: vm.addr(uint256(0x3))})); - exocoreValidatorSet = Player({privateKey: uint256(0xa), addr: vm.addr(uint256(0xa))}); + owner = Player({privateKey: uint256(0xa), addr: vm.addr(uint256(0xa))}); // bind precompile mock contracts code to constant precompile address bytes memory AssetsMockCode = vm.getDeployedCode("AssetsMock.sol"); @@ -162,7 +161,7 @@ contract ExocoreDeployer is Test { } // transfer some gas fee to the owner / deployer - deal(exocoreValidatorSet.addr, 1e22); + deal(owner.addr, 1e22); uint8[] memory decimals = new uint8[](2); string[] memory names = new string[](2); @@ -188,33 +187,33 @@ contract ExocoreDeployer is Test { // -- add whitelist tokens workflow test -- - // first user call exocore gateway to add whitelist tokens - vm.startPrank(exocoreValidatorSet.addr); + // first user call imuachain gateway to add whitelist tokens + vm.startPrank(owner.addr); uint256 nativeFee; - for (; outboundNonces[exocoreChainId] < whitelistTokens.length + 1; outboundNonces[exocoreChainId]++) { - uint256 i = outboundNonces[exocoreChainId] - 1; // only one var in the loop is allowed + for (; outboundNonces[imuachainChainId] < whitelistTokens.length + 1; outboundNonces[imuachainChainId]++) { + uint256 i = outboundNonces[imuachainChainId] - 1; // only one var in the loop is allowed // estimate the fee from the payload payloads[i] = abi.encodePacked(Action.REQUEST_ADD_WHITELIST_TOKEN, abi.encodePacked(whitelistTokens[i], tvlLimits[i])); - nativeFee = exocoreGateway.quote(clientChainId, payloads[i]); + nativeFee = imuachainGateway.quote(clientChainId, payloads[i]); requestIds[i] = generateUID(uint64(i + 1), false); // gateway should emit the packet for the outgoing message - vm.expectEmit(address(exocoreLzEndpoint)); + vm.expectEmit(address(imuachainLzEndpoint)); emit NewPacket( clientChainId, - address(exocoreGateway), + address(imuachainGateway), address(clientGateway).toBytes32(), uint64(i) + 1, // nonce payloads[i] ); - vm.expectEmit(address(exocoreGateway)); + vm.expectEmit(address(imuachainGateway)); emit MessageSent( Action.REQUEST_ADD_WHITELIST_TOKEN, requestIds[i], uint64(i) + 1, // nonce nativeFee ); - exocoreGateway.addWhitelistToken{value: nativeFee}( + imuachainGateway.addWhitelistToken{value: nativeFee}( clientChainId, whitelistTokens[i], decimals[i], names[i], metaDatas[i], oracleInfos[i], tvlLimits[i] ); } @@ -234,7 +233,7 @@ contract ExocoreDeployer is Test { vm.expectEmit(address(clientGateway)); emit MessageExecuted(Action.REQUEST_ADD_WHITELIST_TOKEN, inboundNonces[clientChainId]++); clientChainLzEndpoint.lzReceive( - Origin(exocoreChainId, address(exocoreGateway).toBytes32(), inboundNonces[clientChainId] - 1), + Origin(imuachainChainId, address(imuachainGateway).toBytes32(), inboundNonces[clientChainId] - 1), address(clientGateway), requestIds[0], payloads[0], @@ -246,7 +245,7 @@ contract ExocoreDeployer is Test { vm.expectEmit(address(clientGateway)); emit MessageExecuted(Action.REQUEST_ADD_WHITELIST_TOKEN, inboundNonces[clientChainId]++); clientChainLzEndpoint.lzReceive( - Origin(exocoreChainId, address(exocoreGateway).toBytes32(), inboundNonces[clientChainId] - 1), + Origin(imuachainChainId, address(imuachainGateway).toBytes32(), inboundNonces[clientChainId] - 1), address(clientGateway), requestIds[1], payloads[1], @@ -272,8 +271,8 @@ contract ExocoreDeployer is Test { // at the end of it, we should have executed outbound nonces from chain A on chain B // this helps check that all outbound messages were executed on the destination chain, within the test, and // also validates the nonce incrementing logic in the contracts - assertEq(outboundNonces[exocoreChainId], inboundNonces[clientChainId]); - assertEq(outboundNonces[clientChainId], inboundNonces[exocoreChainId]); + assertEq(outboundNonces[imuachainChainId], inboundNonces[clientChainId]); + assertEq(outboundNonces[clientChainId], inboundNonces[imuachainChainId]); } function _loadValidatorContainer(string memory validatorInfo) internal { @@ -327,15 +326,15 @@ contract ExocoreDeployer is Test { function _deploy() internal { // prepare outside contracts like ERC20 token contract and layerzero endpoint contract - restakeToken = new ERC20PresetFixedSupply("rest", "rest", 1e34, exocoreValidatorSet.addr); - clientChainLzEndpoint = new NonShortCircuitEndpointV2Mock(clientChainId, exocoreValidatorSet.addr); - exocoreLzEndpoint = new NonShortCircuitEndpointV2Mock(exocoreChainId, exocoreValidatorSet.addr); + restakeToken = new ERC20PresetFixedSupply("rest", "rest", 1e34, owner.addr); + clientChainLzEndpoint = new NonShortCircuitEndpointV2Mock(clientChainId, owner.addr); + imuachainLzEndpoint = new NonShortCircuitEndpointV2Mock(imuachainChainId, owner.addr); beaconOracle = IBeaconChainOracle(new EigenLayerBeaconOracle(NetworkConstants.getBeaconGenesisTimestamp())); // deploy vault implementation contract and capsule implementation contract // that has logics called by proxy vaultImplementation = new Vault(); - capsuleImplementation = new ExoCapsule(address(0)); + capsuleImplementation = new ImuaCapsule(address(0)); rewardVaultImplementation = new RewardVault(); // deploy the vault beacon and capsule beacon that store the implementation contract address @@ -356,10 +355,10 @@ contract ExocoreDeployer is Test { // Create ImmutableConfig struct BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(beaconOracle), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -373,9 +372,7 @@ contract ExocoreDeployer is Test { new TransparentUpgradeableProxy( address(clientGatewayLogic), address(proxyAdmin), - abi.encodeWithSelector( - clientGatewayLogic.initialize.selector, payable(exocoreValidatorSet.addr) - ) + abi.encodeWithSelector(clientGatewayLogic.initialize.selector, payable(owner.addr)) ) ) ) @@ -388,17 +385,15 @@ contract ExocoreDeployer is Test { "reward vault should be empty since it is not deployed in initialization" ); - // deploy Exocore network contracts - exocoreGatewayLogic = new ExocoreGateway(address(exocoreLzEndpoint)); - exocoreGateway = ExocoreGateway( + // deploy imuachain network contracts + imuachainGatewayLogic = new ImuachainGateway(address(imuachainLzEndpoint)); + imuachainGateway = ImuachainGateway( payable( address( new TransparentUpgradeableProxy( - address(exocoreGatewayLogic), + address(imuachainGatewayLogic), address(proxyAdmin), - abi.encodeWithSelector( - exocoreGatewayLogic.initialize.selector, payable(exocoreValidatorSet.addr) - ) + abi.encodeWithSelector(imuachainGatewayLogic.initialize.selector, payable(owner.addr)) ) ) ) @@ -406,19 +401,18 @@ contract ExocoreDeployer is Test { // set the destination endpoint for corresponding destinations in endpoint mock NonShortCircuitEndpointV2Mock(address(clientChainLzEndpoint)).setDestLzEndpoint( - address(exocoreGateway), address(exocoreLzEndpoint) + address(imuachainGateway), address(imuachainLzEndpoint) ); - NonShortCircuitEndpointV2Mock(address(exocoreLzEndpoint)).setDestLzEndpoint( + NonShortCircuitEndpointV2Mock(address(imuachainLzEndpoint)).setDestLzEndpoint( address(clientGateway), address(clientChainLzEndpoint) ); - // Exocore validator set should be the owner of gateway contracts and only owner could call these functions. - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); // as LzReceivers, gateway should set bytes(sourceChainGatewayAddress+thisAddress) as trusted remote to receive - // messages. On Exocore side, this is done by calling registerClientChain - clientGateway.setPeer(exocoreChainId, address(exocoreGateway).toBytes32()); - exocoreGateway.registerOrUpdateClientChain( + // messages. On Imuachain, this is done by calling registerClientChain + clientGateway.setPeer(imuachainChainId, address(imuachainGateway).toBytes32()); + imuachainGateway.registerOrUpdateClientChain( clientChainId, address(clientGateway).toBytes32(), 20, @@ -457,14 +451,14 @@ contract ExocoreDeployer is Test { return wc[3].fromLittleEndianUint64(); } - function generateUID(uint64 nonce, bool fromClientChainToExocore) internal view returns (bytes32 uid) { - if (fromClientChainToExocore) { + function generateUID(uint64 nonce, bool fromClientChainToImuachain) internal view returns (bytes32 uid) { + if (fromClientChainToImuachain) { uid = GUID.generate( - nonce, clientChainId, address(clientGateway), exocoreChainId, address(exocoreGateway).toBytes32() + nonce, clientChainId, address(clientGateway), imuachainChainId, address(imuachainGateway).toBytes32() ); } else { uid = GUID.generate( - nonce, exocoreChainId, address(exocoreGateway), clientChainId, address(clientGateway).toBytes32() + nonce, imuachainChainId, address(imuachainGateway), clientChainId, address(clientGateway).toBytes32() ); } } diff --git a/test/foundry/TvlLimits.t.sol b/test/foundry/TvlLimits.t.sol index 23ef83eb..47179edc 100644 --- a/test/foundry/TvlLimits.t.sol +++ b/test/foundry/TvlLimits.t.sol @@ -1,20 +1,20 @@ pragma solidity ^0.8.19; -import "../../src/core/ExoCapsule.sol"; -import "../../src/core/ExocoreGateway.sol"; +import "../../src/core/ImuaCapsule.sol"; +import "../../src/core/ImuachainGateway.sol"; -import {IExoCapsule} from "../../src/interfaces/IExoCapsule.sol"; +import {IImuaCapsule} from "../../src/interfaces/IImuaCapsule.sol"; import {ILSTRestakingController} from "../../src/interfaces/ILSTRestakingController.sol"; import "../../src/storage/GatewayStorage.sol"; -import "./ExocoreDeployer.t.sol"; +import "./ImuachainDeployer.t.sol"; import "forge-std/Test.sol"; import "@layerzerolabs/lz-evm-protocol-v2/contracts/libs/AddressCast.sol"; import "@layerzerolabs/lz-evm-protocol-v2/contracts/libs/GUID.sol"; import "@openzeppelin/contracts/utils/Create2.sol"; -contract TvlLimitsTest is ExocoreDeployer { +contract TvlLimitsTest is ImuachainDeployer { event TvlLimitUpdated(uint256 newTvlLimit); @@ -26,7 +26,7 @@ contract TvlLimitsTest is ExocoreDeployer { // for a token that is not whitelisted, nothing should happen function test07_UpdateTvlLimit_NotWhitelisted() public { address addr = address(0xa); - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); vm.expectRevert(abi.encodeWithSelector(Errors.TokenNotWhitelisted.selector, addr)); clientGateway.updateTvlLimit(addr, 500); vm.stopPrank(); @@ -34,7 +34,7 @@ contract TvlLimitsTest is ExocoreDeployer { // native restaking does not have a TVL limit function test07_UpdateTvlLimit_NativeEth() public { - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); vm.expectRevert(Errors.NoTvlLimitForNativeRestaking.selector); clientGateway.updateTvlLimit(VIRTUAL_STAKED_ETH_ADDRESS, 500); vm.stopPrank(); @@ -50,7 +50,7 @@ contract TvlLimitsTest is ExocoreDeployer { } function test07_UpdateTvlLimit_Paused() public { - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); clientGateway.pause(); IVault vault = clientGateway.tokenToVault(address(restakeToken)); assertTrue(address(vault) != address(0)); @@ -66,8 +66,8 @@ contract TvlLimitsTest is ExocoreDeployer { tokens[0] = address(restakeToken); uint256[] memory tvlLimits = new uint256[](1); tvlLimits[0] = 500; - vm.startPrank(exocoreValidatorSet.addr); - vm.expectRevert(Errors.ClientChainGatewayTokenAdditionViaExocore.selector); + vm.startPrank(owner.addr); + vm.expectRevert(Errors.ClientChainGatewayTokenAdditionViaImuachain.selector); clientGateway.addWhitelistTokens(tokens, tvlLimits); } @@ -78,7 +78,7 @@ contract TvlLimitsTest is ExocoreDeployer { assertTrue(address(vault) != address(0)); uint256 tvlLimit = vault.getTvlLimit(); uint256 proposedTvlLimit = tvlLimit * factor; - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); vm.expectEmit(address(vault)); emit TvlLimitUpdated(proposedTvlLimit); clientGateway.updateTvlLimit(address(restakeToken), proposedTvlLimit); @@ -92,7 +92,7 @@ contract TvlLimitsTest is ExocoreDeployer { assertTrue(address(vault) != address(0)); uint256 tvlLimit = vault.getTvlLimit(); uint256 proposedTvlLimit = tvlLimit / factor; - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); vm.expectEmit(address(vault)); emit TvlLimitUpdated(proposedTvlLimit); clientGateway.updateTvlLimit(address(restakeToken), proposedTvlLimit); diff --git a/test/foundry/unit/Bootstrap.t.sol b/test/foundry/unit/Bootstrap.t.sol index c3bdb69b..9e173c8f 100644 --- a/test/foundry/unit/Bootstrap.t.sol +++ b/test/foundry/unit/Bootstrap.t.sol @@ -36,7 +36,7 @@ import "@openzeppelin/contracts/utils/Create2.sol"; import "forge-std/Test.sol"; import "src/libraries/Errors.sol"; -import "src/core/ExoCapsule.sol"; +import "src/core/ImuaCapsule.sol"; import "src/storage/GatewayStorage.sol"; import "src/utils/BeaconProxyBytecode.sol"; @@ -60,19 +60,19 @@ contract BootstrapTest is Test { address deployer = address(0xdeadbeef); uint256 spawnTime; uint256 offsetDuration; - uint16 exocoreChainId = 1; + uint16 imuachainChainId = 1; uint16 clientChainId = 2; address[] whitelistTokens; uint256[] tvlLimits; NonShortCircuitEndpointV2Mock clientChainLzEndpoint; - address exocoreValidatorSet = vm.addr(uint256(0x8)); - address undeployedExocoreGateway = vm.addr(uint256(0x9)); - address undeployedExocoreLzEndpoint = vm.addr(uint256(0xb)); + address owner = vm.addr(uint256(0x8)); + address undeployedImuachainGateway = vm.addr(uint256(0x9)); + address undeployedImuachainLzEndpoint = vm.addr(uint256(0xb)); address constant lzActor = address(0x20); IVault vaultImplementation; IRewardVault rewardVaultImplementation; - IExoCapsule capsuleImplementation; + IImuaCapsule capsuleImplementation; IBeacon vaultBeacon; IBeacon rewardVaultBeacon; IBeacon capsuleBeacon; @@ -102,7 +102,7 @@ contract BootstrapTest is Test { // deploy vault implementationcontract that has logics called by proxy vaultImplementation = new Vault(); rewardVaultImplementation = new RewardVault(); - capsuleImplementation = new ExoCapsule(address(0)); + capsuleImplementation = new ImuaCapsule(address(0)); // deploy the vault beacon that store the implementation contract address vaultBeacon = new UpgradeableBeacon(address(vaultImplementation)); @@ -115,13 +115,13 @@ contract BootstrapTest is Test { // then the ProxyAdmin proxyAdmin = new CustomProxyAdmin(); // then the logic - clientChainLzEndpoint = new NonShortCircuitEndpointV2Mock(clientChainId, exocoreValidatorSet); + clientChainLzEndpoint = new NonShortCircuitEndpointV2Mock(clientChainId, owner); // Create ImmutableConfig struct BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(0x1), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -130,7 +130,7 @@ contract BootstrapTest is Test { ClientChainGateway clientGatewayLogic = new ClientChainGateway(address(clientChainLzEndpoint), config, address(rewardVaultBeacon)); // we could also use encodeWithSelector and supply .initialize.selector instead. - bytes memory initialization = abi.encodeCall(clientGatewayLogic.initialize, (payable(exocoreValidatorSet))); + bytes memory initialization = abi.encodeCall(clientGatewayLogic.initialize, (payable(owner))); // then the params + proxy spawnTime = block.timestamp + 1 hours; offsetDuration = 30 minutes; @@ -172,9 +172,9 @@ contract BootstrapTest is Test { IVault vault = bootstrap.tokenToVault(address(myToken)); assertTrue(address(vault) == expectedVaultAddress); assertTrue(vault.getTvlLimit() == tvlLimits[0]); - // now set the gateway address for Exocore. - clientChainLzEndpoint.setDestLzEndpoint(undeployedExocoreGateway, undeployedExocoreLzEndpoint); - bootstrap.setPeer(exocoreChainId, bytes32(bytes20(undeployedExocoreGateway))); + // now set the gateway address for Imuachain. + clientChainLzEndpoint.setDestLzEndpoint(undeployedImuachainGateway, undeployedImuachainLzEndpoint); + bootstrap.setPeer(imuachainChainId, bytes32(bytes20(undeployedImuachainGateway))); vm.stopPrank(); } @@ -410,7 +410,7 @@ contract BootstrapTest is Test { // now attempt to withdraw, which should go through vm.startPrank(addr); - bootstrap.claimPrincipalFromExocore(address(myToken), withdrawAmount); + bootstrap.claimPrincipalFromImuachain(address(myToken), withdrawAmount); bootstrap.withdrawPrincipal(address(myToken), withdrawAmount, addr); vm.stopPrank(); @@ -429,7 +429,7 @@ contract BootstrapTest is Test { // withdraw to get just below tvl limit withdrawAmount = vault.getConsumedTvl() - vault.getTvlLimit() + 1; vm.startPrank(addr); - bootstrap.claimPrincipalFromExocore(address(myToken), withdrawAmount); + bootstrap.claimPrincipalFromImuachain(address(myToken), withdrawAmount); bootstrap.withdrawPrincipal(address(myToken), withdrawAmount, addr); vm.stopPrank(); @@ -458,9 +458,9 @@ contract BootstrapTest is Test { assertTrue(bootstrap.getValidatorsCount() == 0); // Register validators. The keys used below do not matter since they are unit test only. string[3] memory validators = [ - "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", - "exo1wnw7zcl9fy04ax69uffumwkdxftfqsjyj37wt2", - "exo1rtg0cgw94ep744epyvanc0wdd5kedwql73vlmr" + "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", + "im1wnw7zcl9fy04ax69uffumwkdxftfqsjyz0akf0", + "im1rtg0cgw94ep744epyvanc0wdd5kedwqlw008ex" ]; string[3] memory names = ["validator1", "validator2", "validator3"]; bytes32[3] memory pubKeys = [ @@ -474,11 +474,11 @@ contract BootstrapTest is Test { bootstrap.registerValidator(validators[i], names[i], commission, pubKeys[i]); // check count assertTrue(bootstrap.getValidatorsCount() == i + 1); - // check ethToExocoreAddress mapping - string memory exoAddress = bootstrap.ethToExocoreAddress(addrs[i]); - assertTrue(keccak256(abi.encodePacked(exoAddress)) == keccak256(abi.encodePacked(validators[i]))); + // check ethToImAddress mapping + string memory imAddress = bootstrap.ethToImAddress(addrs[i]); + assertTrue(keccak256(abi.encodePacked(imAddress)) == keccak256(abi.encodePacked(validators[i]))); (string memory name, IValidatorRegistry.Commission memory thisCommision, bytes32 key) = - bootstrap.validators(exoAddress); + bootstrap.validators(imAddress); assertTrue(keccak256(abi.encodePacked(name)) == keccak256(abi.encodePacked(names[i]))); assertTrue(key == pubKeys[i]); assertTrue(thisCommision.rate == commission.rate); @@ -490,96 +490,96 @@ contract BootstrapTest is Test { function test03_RegisterValidator_EthAlreadyRegistered() public { IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e18, 1e18); // Register validator - string memory exo = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory im = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; string memory name = "validator1"; bytes32 pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540782); vm.startPrank(addrs[0]); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); // change all identifying params except eth address of validator - exo = "exo1wnw7zcl9fy04ax69uffumwkdxftfqsjyj37wt2"; + im = "im1wnw7zcl9fy04ax69uffumwkdxftfqsjyz0akf0"; name = "validator1_re"; pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540783); vm.expectRevert(abi.encodeWithSelector(Errors.BootstrapValidatorAlreadyHasAddress.selector, addrs[0])); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); vm.stopPrank(); } - function test03_RegisterValidator_ExoAlreadyRegistered() public { + function test03_RegisterValidator_ImAlreadyRegistered() public { IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e18, 1e18); // Register validator - string memory exo = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory im = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; string memory name = "validator1"; bytes32 pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540782); vm.startPrank(addrs[0]); - bootstrap.registerValidator(exo, name, commission, pubKey); - // change all identifying params except exo address of validator + bootstrap.registerValidator(im, name, commission, pubKey); + // change all identifying params except im address of validator vm.stopPrank(); vm.startPrank(addrs[1]); name = "validator1_re"; pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540783); vm.expectRevert(Errors.BootstrapValidatorAlreadyRegistered.selector); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); vm.stopPrank(); } function test03_RegisterValidator_ConsensusKeyInUse() public { IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e18, 1e18); // Register validator - string memory exo = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory im = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; string memory name = "validator1"; bytes32 pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540782); vm.startPrank(addrs[0]); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); // change all identifying params except consensus key of validator vm.stopPrank(); vm.startPrank(addrs[1]); - exo = "exo1wnw7zcl9fy04ax69uffumwkdxftfqsjyj37wt2"; + im = "im1wnw7zcl9fy04ax69uffumwkdxftfqsjyz0akf0"; name = "validator1_re"; vm.expectRevert(abi.encodeWithSelector(Errors.BootstrapConsensusPubkeyAlreadyUsed.selector, pubKey)); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); vm.stopPrank(); } function test03_RegisterValidator_NameInUse() public { IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e18, 1e18); // Register validator - string memory exo = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory im = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; string memory name = "validator1"; bytes32 pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540782); vm.startPrank(addrs[0]); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); // change all identifying params except name of validator vm.stopPrank(); vm.startPrank(addrs[1]); - exo = "exo1wnw7zcl9fy04ax69uffumwkdxftfqsjyj37wt2"; + im = "im1wnw7zcl9fy04ax69uffumwkdxftfqsjyz0akf0"; pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540783); vm.expectRevert(Errors.BootstrapValidatorNameAlreadyUsed.selector); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); vm.stopPrank(); } function test03_RegisterValidator_EmptyName() public { IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e18, 1e18); // Register validator - string memory exo = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory im = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; string memory name = ""; bytes32 pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540782); vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapValidatorNameLengthZero.selector); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); } function test03_RegisterValidator_ZeroConsensusKey() public { IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e18, 1e18); // Register validator - string memory exo = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory im = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; string memory name = "validator1"; bytes32 pubKey = bytes32(0); vm.startPrank(addrs[0]); vm.expectRevert(Errors.ZeroValue.selector); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); } function test04_DepositThenDelegate() public { @@ -589,32 +589,32 @@ contract BootstrapTest is Test { vm.startPrank(addrs[0]); IVault vault = IVault(bootstrap.tokenToVault(address(myToken))); myToken.approve(address(vault), amounts[0]); - bootstrap.depositThenDelegateTo(address(myToken), amounts[0], "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"); + bootstrap.depositThenDelegateTo(address(myToken), amounts[0], "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"); vm.stopPrank(); uint256 deposited = bootstrap.totalDepositAmounts(addrs[0], address(myToken)); assertTrue(deposited == amounts[0]); uint256 delegated = - bootstrap.delegations(addrs[0], "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken)); + bootstrap.delegations(addrs[0], "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken)); assertTrue(delegated == amounts[0]); } function test05_ReplaceKey() public { IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e18, 1e18); // Register validator - string memory exo = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory im = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; string memory name = "validator1"; bytes32 pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540782); vm.startPrank(addrs[0]); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); assertTrue(bootstrap.getValidatorsCount() == 1); - (,, bytes32 consensusPublicKey) = bootstrap.validators(exo); + (,, bytes32 consensusPublicKey) = bootstrap.validators(im); assertTrue(consensusPublicKey == pubKey); // Then change the key bytes32 newKey = bytes32(0xd995b7f4b2178b0466cfa512955ce2299a4487ebcd86f817d686880dd2b7c4b0); bootstrap.replaceKey(newKey); - (,, consensusPublicKey) = bootstrap.validators(exo); + (,, consensusPublicKey) = bootstrap.validators(im); assertTrue(consensusPublicKey == newKey); vm.stopPrank(); // check the key values @@ -662,13 +662,13 @@ contract BootstrapTest is Test { function test06_UpdateRate() public { IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e18, 1e18); // Register one validator - string memory exo = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory im = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; string memory name = "validator1"; bytes32 pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540782); vm.startPrank(addrs[0]); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); bootstrap.updateRate(1e17); - (, IValidatorRegistry.Commission memory newCommission,) = bootstrap.validators(exo); + (, IValidatorRegistry.Commission memory newCommission,) = bootstrap.validators(im); assertTrue(newCommission.rate == 1e17); vm.stopPrank(); } @@ -676,13 +676,13 @@ contract BootstrapTest is Test { function test06_UpdateRate_Twice() public { IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e18, 1e18); // Register one validator - string memory exo = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory im = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; string memory name = "validator1"; bytes32 pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540782); vm.startPrank(addrs[0]); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); bootstrap.updateRate(1e17); - (, IValidatorRegistry.Commission memory newCommission,) = bootstrap.validators(exo); + (, IValidatorRegistry.Commission memory newCommission,) = bootstrap.validators(im); assertTrue(newCommission.rate == 1e17); vm.expectRevert(Errors.BootstrapComissionAlreadyEdited.selector); bootstrap.updateRate(1e17); @@ -692,11 +692,11 @@ contract BootstrapTest is Test { function test06_UpdateRate_MoreThanMaxRate() public { IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e17, 1e17); // Register one validator - string memory exo = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory im = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; string memory name = "validator1"; bytes32 pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540782); vm.startPrank(addrs[0]); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); vm.expectRevert(Errors.BootstrapRateExceedsMaxRate.selector); bootstrap.updateRate(2e17); vm.stopPrank(); @@ -706,11 +706,11 @@ contract BootstrapTest is Test { // 0, 0.1, 0.01 IValidatorRegistry.Commission memory commission = IValidatorRegistry.Commission(0, 1e17, 1e16); // Register one validator - string memory exo = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string memory im = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; string memory name = "validator1"; bytes32 pubKey = bytes32(0x27165ec2f29a4815b7c29e47d8700845b5ae267f2d61ad29fb3939aec5540782); vm.startPrank(addrs[0]); - bootstrap.registerValidator(exo, name, commission, pubKey); + bootstrap.registerValidator(im, name, commission, pubKey); vm.expectRevert(Errors.BootstrapRateChangeExceedsMaxChangeRate.selector); bootstrap.updateRate(2e16); vm.stopPrank(); @@ -754,16 +754,16 @@ contract BootstrapTest is Test { vm.stopPrank(); } - function test08_ExocoreAddressIsValid() public { - assertTrue(bootstrap.isValidExocoreAddress("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac")); + function test08_ImuachainAddressIsValid() public { + assertTrue(bootstrap.isValidImAddress("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla")); } - function test08_ExocoreAddressIsValid_Length() public { - assertFalse(bootstrap.isValidExocoreAddress("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7acaa")); + function test08_ImuachainAddressIsValid_Length() public { + assertFalse(bootstrap.isValidImAddress("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xlaaa")); } - function test08_ExocoreAddressIsValid_Prefix() public { - assertFalse(bootstrap.isValidExocoreAddress("asd")); + function test08_ImuachainAddressIsValid_Prefix() public { + assertFalse(bootstrap.isValidImAddress("mi13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xlaaa")); } function test09_DelegateTo() public { @@ -774,13 +774,13 @@ contract BootstrapTest is Test { // first, self delegate for (uint256 i = 0; i < 3; i++) { vm.startPrank(addrs[i]); - string memory exo = bootstrap.ethToExocoreAddress(addrs[i]); - uint256 prevDelegation = bootstrap.delegations(addrs[i], exo, address(myToken)); - uint256 prevDelegationByValidator = bootstrap.delegationsByValidator(exo, address(myToken)); + string memory im = bootstrap.ethToImAddress(addrs[i]); + uint256 prevDelegation = bootstrap.delegations(addrs[i], im, address(myToken)); + uint256 prevDelegationByValidator = bootstrap.delegationsByValidator(im, address(myToken)); uint256 prevWithdrawableAmount = bootstrap.withdrawableAmounts(addrs[i], address(myToken)); - bootstrap.delegateTo(exo, address(myToken), amounts[i]); - uint256 postDelegation = bootstrap.delegations(addrs[i], exo, address(myToken)); - uint256 postDelegationByValidator = bootstrap.delegationsByValidator(exo, address(myToken)); + bootstrap.delegateTo(im, address(myToken), amounts[i]); + uint256 postDelegation = bootstrap.delegations(addrs[i], im, address(myToken)); + uint256 postDelegationByValidator = bootstrap.delegationsByValidator(im, address(myToken)); uint256 postWithdrawableAmount = bootstrap.withdrawableAmounts(addrs[i], address(myToken)); assertTrue(postDelegation == prevDelegation + amounts[i]); assertTrue(postDelegationByValidator == prevDelegationByValidator + amounts[i]); @@ -795,13 +795,13 @@ contract BootstrapTest is Test { for (uint256 j = 0; j < 3; j++) { uint256 amount = delegations[i][j] * 10 ** 18; if (amount != 0) { - string memory exo = bootstrap.ethToExocoreAddress(addrs[j]); - uint256 prevDelegation = bootstrap.delegations(delegator, exo, address(myToken)); - uint256 prevDelegationByValidator = bootstrap.delegationsByValidator(exo, address(myToken)); + string memory im = bootstrap.ethToImAddress(addrs[j]); + uint256 prevDelegation = bootstrap.delegations(delegator, im, address(myToken)); + uint256 prevDelegationByValidator = bootstrap.delegationsByValidator(im, address(myToken)); uint256 prevWithdrawableAmount = bootstrap.withdrawableAmounts(delegator, address(myToken)); - bootstrap.delegateTo(exo, address(myToken), uint256(amount)); - uint256 postDelegation = bootstrap.delegations(delegator, exo, address(myToken)); - uint256 postDelegationByValidator = bootstrap.delegationsByValidator(exo, address(myToken)); + bootstrap.delegateTo(im, address(myToken), uint256(amount)); + uint256 postDelegation = bootstrap.delegations(delegator, im, address(myToken)); + uint256 postDelegationByValidator = bootstrap.delegationsByValidator(im, address(myToken)); uint256 postWithdrawableAmount = bootstrap.withdrawableAmounts(delegator, address(myToken)); assertTrue(postDelegation == prevDelegation + amount); assertTrue(postDelegationByValidator == prevDelegationByValidator + amount); @@ -816,7 +816,7 @@ contract BootstrapTest is Test { test02_Deposit(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapValidatorNotExist.selector); - bootstrap.delegateTo("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken), amounts[0]); + bootstrap.delegateTo("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken), amounts[0]); } function test09_DelegateTo_TokenNotWhitelisted() public { @@ -824,7 +824,7 @@ contract BootstrapTest is Test { test02_Deposit(); vm.startPrank(addrs[0]); vm.expectRevert("BootstrapStorage: token is not whitelisted"); - bootstrap.delegateTo("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(0xa), amounts[0]); + bootstrap.delegateTo("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(0xa), amounts[0]); } function test09_DelegateTo_NotEnoughBalance() public { @@ -832,7 +832,7 @@ contract BootstrapTest is Test { MyToken myToken = test01_AddWhitelistToken(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapInsufficientWithdrawableBalance.selector); - bootstrap.delegateTo("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken), amounts[0]); + bootstrap.delegateTo("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken), amounts[0]); } function test09_DelegateTo_ZeroAmount() public { @@ -840,14 +840,14 @@ contract BootstrapTest is Test { test02_Deposit(); vm.startPrank(addrs[0]); vm.expectRevert("BootstrapStorage: amount should be greater than zero"); - bootstrap.delegateTo("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken), 0); + bootstrap.delegateTo("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken), 0); } function test09_DelegateTo_NoDeposits() public { test03_RegisterValidator(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapInsufficientWithdrawableBalance.selector); - bootstrap.delegateTo("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken), amounts[0]); + bootstrap.delegateTo("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken), amounts[0]); } function test09_DelegateTo_Excess() public { @@ -855,7 +855,7 @@ contract BootstrapTest is Test { test02_Deposit(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapInsufficientWithdrawableBalance.selector); - bootstrap.delegateTo("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken), amounts[0] + 1); + bootstrap.delegateTo("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken), amounts[0] + 1); } function test10_UndelegateFrom() public { @@ -863,13 +863,13 @@ contract BootstrapTest is Test { // first, self undelegate for (uint256 i = 0; i < 3; i++) { vm.startPrank(addrs[i]); - string memory exo = bootstrap.ethToExocoreAddress(addrs[i]); - uint256 prevDelegation = bootstrap.delegations(addrs[i], exo, address(myToken)); - uint256 prevDelegationByValidator = bootstrap.delegationsByValidator(exo, address(myToken)); + string memory im = bootstrap.ethToImAddress(addrs[i]); + uint256 prevDelegation = bootstrap.delegations(addrs[i], im, address(myToken)); + uint256 prevDelegationByValidator = bootstrap.delegationsByValidator(im, address(myToken)); uint256 prevWithdrawableAmount = bootstrap.withdrawableAmounts(addrs[i], address(myToken)); - bootstrap.undelegateFrom(exo, address(myToken), amounts[i]); - uint256 postDelegation = bootstrap.delegations(addrs[i], exo, address(myToken)); - uint256 postDelegationByValidator = bootstrap.delegationsByValidator(exo, address(myToken)); + bootstrap.undelegateFrom(im, address(myToken), amounts[i]); + uint256 postDelegation = bootstrap.delegations(addrs[i], im, address(myToken)); + uint256 postDelegationByValidator = bootstrap.delegationsByValidator(im, address(myToken)); uint256 postWithdrawableAmount = bootstrap.withdrawableAmounts(addrs[i], address(myToken)); assertTrue(postDelegation == prevDelegation - amounts[i]); assertTrue(postDelegationByValidator == prevDelegationByValidator - amounts[i]); @@ -884,13 +884,13 @@ contract BootstrapTest is Test { for (uint256 j = 0; j < 3; j++) { uint256 amount = delegations[i][j] * 10 ** 18; if (amount != 0) { - string memory exo = bootstrap.ethToExocoreAddress(addrs[j]); - uint256 prevDelegation = bootstrap.delegations(delegator, exo, address(myToken)); - uint256 prevDelegationByValidator = bootstrap.delegationsByValidator(exo, address(myToken)); + string memory im = bootstrap.ethToImAddress(addrs[j]); + uint256 prevDelegation = bootstrap.delegations(delegator, im, address(myToken)); + uint256 prevDelegationByValidator = bootstrap.delegationsByValidator(im, address(myToken)); uint256 prevWithdrawableAmount = bootstrap.withdrawableAmounts(delegator, address(myToken)); - bootstrap.undelegateFrom(exo, address(myToken), uint256(amount)); - uint256 postDelegation = bootstrap.delegations(delegator, exo, address(myToken)); - uint256 postDelegationByValidator = bootstrap.delegationsByValidator(exo, address(myToken)); + bootstrap.undelegateFrom(im, address(myToken), uint256(amount)); + uint256 postDelegation = bootstrap.delegations(delegator, im, address(myToken)); + uint256 postDelegationByValidator = bootstrap.delegationsByValidator(im, address(myToken)); uint256 postWithdrawableAmount = bootstrap.withdrawableAmounts(delegator, address(myToken)); assertTrue(postDelegation == prevDelegation - amount); assertTrue(postDelegationByValidator == prevDelegationByValidator - amount); @@ -905,14 +905,14 @@ contract BootstrapTest is Test { test09_DelegateTo(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapValidatorNotExist.selector); - bootstrap.undelegateFrom("exo1awm72f4sc5yhedurdunx9afcshfq6ymqva8an4", address(myToken), amounts[0]); + bootstrap.undelegateFrom("im1awm72f4sc5yhedurdunx9afcshfq6ymqury93s", address(myToken), amounts[0]); } function test10_UndelegateFrom_TokenNotWhitelisted() public { test03_RegisterValidator(); vm.startPrank(addrs[0]); vm.expectRevert("BootstrapStorage: token is not whitelisted"); - bootstrap.undelegateFrom("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(0xa), amounts[0]); + bootstrap.undelegateFrom("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(0xa), amounts[0]); } function test10_UndelegateFrom_NotEnoughBalance() public { @@ -920,7 +920,7 @@ contract BootstrapTest is Test { MyToken myToken = test01_AddWhitelistToken(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapInsufficientDelegatedBalance.selector); - bootstrap.undelegateFrom("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken), amounts[0]); + bootstrap.undelegateFrom("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken), amounts[0]); } function test10_UndelegateFrom_ZeroAmount() public { @@ -928,24 +928,24 @@ contract BootstrapTest is Test { test02_Deposit(); vm.startPrank(addrs[0]); vm.expectRevert("BootstrapStorage: amount should be greater than zero"); - bootstrap.undelegateFrom("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken), 0); + bootstrap.undelegateFrom("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken), 0); } function test10_UndelegateFromValidator_Excess() public { test09_DelegateTo(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapInsufficientDelegatedBalance.selector); - bootstrap.undelegateFrom("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken), amounts[0] + 1); + bootstrap.undelegateFrom("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken), amounts[0] + 1); } function test10_UndelegateFrom_NoDelegation() public { test03_RegisterValidator(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapInsufficientDelegatedBalance.selector); - bootstrap.undelegateFrom("exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken), amounts[0]); + bootstrap.undelegateFrom("im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken), amounts[0]); } - function test11_ClaimPrincipalFromExocore() public { + function test11_ClaimPrincipalFromImuachain() public { // delegate and then undelegate test10_UndelegateFrom(); // now, withdraw @@ -956,7 +956,7 @@ contract BootstrapTest is Test { uint256 prevTokenDeposit = bootstrap.depositsByToken(address(myToken)); uint256 prevVaultWithdrawable = Vault(address(bootstrap.tokenToVault(address(myToken)))).withdrawableBalances(addrs[i]); - bootstrap.claimPrincipalFromExocore(address(myToken), amounts[i]); + bootstrap.claimPrincipalFromImuachain(address(myToken), amounts[i]); uint256 postDeposit = bootstrap.totalDepositAmounts(addrs[i], address(myToken)); uint256 postWithdrawable = bootstrap.withdrawableAmounts(addrs[i], address(myToken)); uint256 postTokenDeposit = bootstrap.depositsByToken(address(myToken)); @@ -971,40 +971,40 @@ contract BootstrapTest is Test { } } - function test11_ClaimPrincipalFromExocore_TokenNotWhitelisted() public { + function test11_ClaimPrincipalFromImuachain_TokenNotWhitelisted() public { vm.startPrank(addrs[0]); vm.expectRevert("BootstrapStorage: token is not whitelisted"); - bootstrap.claimPrincipalFromExocore(address(0xa), amounts[0]); + bootstrap.claimPrincipalFromImuachain(address(0xa), amounts[0]); vm.stopPrank(); } - function test11_ClaimPrincipalFromExocore_ZeroAmount() public { + function test11_ClaimPrincipalFromImuachain_ZeroAmount() public { vm.startPrank(addrs[0]); vm.expectRevert("BootstrapStorage: amount should be greater than zero"); - bootstrap.claimPrincipalFromExocore(address(myToken), 0); + bootstrap.claimPrincipalFromImuachain(address(myToken), 0); vm.stopPrank(); } - function test11_ClaimPrincipalFromExocore_NoDeposits() public { + function test11_ClaimPrincipalFromImuachain_NoDeposits() public { vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapInsufficientDepositedBalance.selector); - bootstrap.claimPrincipalFromExocore(address(myToken), amounts[0]); + bootstrap.claimPrincipalFromImuachain(address(myToken), amounts[0]); vm.stopPrank(); } - function test11_ClaimPrincipalFromExocore_Excess() public { + function test11_ClaimPrincipalFromImuachain_Excess() public { test10_UndelegateFrom(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapInsufficientDepositedBalance.selector); - bootstrap.claimPrincipalFromExocore(address(myToken), amounts[0] + 1); + bootstrap.claimPrincipalFromImuachain(address(myToken), amounts[0] + 1); vm.stopPrank(); } - function test11_ClaimPrincipalFromExocore_ExcessFree() public { + function test11_ClaimPrincipalFromImuachain_ExcessFree() public { test09_DelegateTo(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.BootstrapInsufficientWithdrawableBalance.selector); - bootstrap.claimPrincipalFromExocore(address(myToken), amounts[0]); + bootstrap.claimPrincipalFromImuachain(address(myToken), amounts[0]); vm.stopPrank(); } @@ -1017,7 +1017,7 @@ contract BootstrapTest is Test { function _markBootstrapped(uint64 nonce, bool success) internal { vm.startPrank(lzActor); clientChainLzEndpoint.lzReceive( - Origin(exocoreChainId, bytes32(bytes20(undeployedExocoreGateway)), nonce), + Origin(imuachainChainId, bytes32(bytes20(undeployedImuachainGateway)), nonce), address(bootstrap), generateUID(nonce), abi.encodePacked(Action.REQUEST_MARK_BOOTSTRAP, ""), @@ -1029,7 +1029,7 @@ contract BootstrapTest is Test { // no more upgrades are possible assertTrue(bootstrap.customProxyAdmin() == address(0)); assertTrue(proxyAdmin.bootstrapper() == address(0)); - assertTrue(bootstrap.owner() == exocoreValidatorSet); + assertTrue(bootstrap.owner() == owner); } else { assertFalse(bootstrap.bootstrapped()); } @@ -1118,8 +1118,8 @@ contract BootstrapTest is Test { function generateUID(uint64 nonce) internal view returns (bytes32 uid) { uid = GUID.generate( nonce, - exocoreChainId, - address(undeployedExocoreGateway), + imuachainChainId, + address(undeployedImuachainGateway), clientChainId, bytes32(bytes20(address(bootstrap))) ); @@ -1128,10 +1128,10 @@ contract BootstrapTest is Test { function test15_Initialize_OwnerZero() public { vm.startPrank(deployer); BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(0x1), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -1165,10 +1165,10 @@ contract BootstrapTest is Test { function test15_Initialize_SpawnTimeNotFuture() public { vm.startPrank(deployer); BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(0x1), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -1203,10 +1203,10 @@ contract BootstrapTest is Test { function test15_Initialize_OffsetDurationZero() public { vm.startPrank(deployer); BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(0x1), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -1240,10 +1240,10 @@ contract BootstrapTest is Test { function test15_Initialize_SpawnTimeLTOffsetDuration() public { vm.startPrank(deployer); BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(0x1), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -1278,10 +1278,10 @@ contract BootstrapTest is Test { function test15_Initialize_LockTimeNotFuture() public { vm.startPrank(deployer); BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(0x1), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -1316,10 +1316,10 @@ contract BootstrapTest is Test { function test15_Initialize_CustomProxyAdminZero() public { vm.startPrank(deployer); BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(0x1), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -1353,10 +1353,10 @@ contract BootstrapTest is Test { function test15_Initialize_GatewayZero() public { vm.startPrank(deployer); BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(0x1), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -1390,10 +1390,10 @@ contract BootstrapTest is Test { function test15_Initialize_GatewayLogicZero() public { vm.startPrank(deployer); BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(0x1), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -1477,13 +1477,13 @@ contract BootstrapTest is Test { bootstrap.setOffsetDuration(offsetDuration + 2); } - function test20_WithdrawRewardFromExocore() public { + function test20_WithdrawRewardFromImuachain() public { vm.expectRevert(abi.encodeWithSignature("NotYetSupported()")); - bootstrap.claimRewardFromExocore(address(0x0), 1); + bootstrap.claimRewardFromImuachain(address(0x0), 1); } function test22_WithdrawPrincipal() public { - test11_ClaimPrincipalFromExocore(); + test11_ClaimPrincipalFromImuachain(); for (uint256 i = 0; i < 6; i++) { vm.startPrank(addrs[i]); uint256 prevBalance = myToken.balanceOf(addrs[i]); @@ -1507,7 +1507,7 @@ contract BootstrapTest is Test { } function test22_WithdrawPrincipal_Excess() public { - test11_ClaimPrincipalFromExocore(); + test11_ClaimPrincipalFromImuachain(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.VaultWithdrawalAmountExceeds.selector); bootstrap.withdrawPrincipal(address(myToken), amounts[0] + 5, addrs[0]); @@ -1521,11 +1521,11 @@ contract BootstrapTest is Test { vm.stopPrank(); } - function test23_RevertWhen_ClaimPrincipalFromExocore_WithEther() public { + function test23_RevertWhen_ClaimPrincipalFromImuachain_WithEther() public { vm.startPrank(addrs[0]); vm.deal(addrs[0], 1 ether); vm.expectRevert(Errors.NonZeroValue.selector); - bootstrap.claimPrincipalFromExocore{value: 0.1 ether}(address(myToken), amounts[0]); + bootstrap.claimPrincipalFromImuachain{value: 0.1 ether}(address(myToken), amounts[0]); vm.stopPrank(); } @@ -1534,7 +1534,7 @@ contract BootstrapTest is Test { vm.deal(addrs[0], 1 ether); vm.expectRevert(Errors.NonZeroValue.selector); bootstrap.delegateTo{value: 0.1 ether}( - "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken), amounts[0] + "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken), amounts[0] ); vm.stopPrank(); } @@ -1544,7 +1544,7 @@ contract BootstrapTest is Test { vm.deal(addrs[0], 1 ether); vm.expectRevert(Errors.NonZeroValue.selector); bootstrap.undelegateFrom{value: 0.1 ether}( - "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac", address(myToken), amounts[0] + "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla", address(myToken), amounts[0] ); vm.stopPrank(); } @@ -1554,7 +1554,7 @@ contract BootstrapTest is Test { vm.deal(addrs[0], 1 ether); vm.expectRevert(Errors.NonZeroValue.selector); bootstrap.depositThenDelegateTo{value: 0.1 ether}( - address(myToken), amounts[0], "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac" + address(myToken), amounts[0], "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla" ); vm.stopPrank(); } @@ -1577,7 +1577,7 @@ contract BootstrapTest is Test { // First stake should create new capsule bootstrap.stake{value: 32 ether}(pubkey, signature, depositDataRoot); - IExoCapsule capsule = bootstrap.ownerToCapsule(addrs[0]); + IImuaCapsule capsule = bootstrap.ownerToCapsule(addrs[0]); address expectedCapsuleAddress = Create2.computeAddress( bytes32(uint256(uint160(addrs[0]))), keccak256(abi.encodePacked(BEACON_PROXY_BYTECODE, abi.encode(address(capsuleBeacon), ""))), @@ -1617,36 +1617,36 @@ contract BootstrapTest is Test { vm.stopPrank(); } - function test25_CreateExoCapsule() public { + function test25_CreateImuaCapsule() public { _enableNativeRestaking(); vm.startPrank(addrs[0]); - address capsuleAddr = bootstrap.createExoCapsule(); + address capsuleAddr = bootstrap.createImuaCapsule(); assertTrue(capsuleAddr != address(0), "Capsule address should not be zero"); - IExoCapsule capsule = bootstrap.ownerToCapsule(addrs[0]); + IImuaCapsule capsule = bootstrap.ownerToCapsule(addrs[0]); assertTrue(address(capsule) == capsuleAddr, "Capsule should be registered"); vm.stopPrank(); } - function test25_CreateExoCapsule_AlreadyExists() public { + function test25_CreateImuaCapsule_AlreadyExists() public { _enableNativeRestaking(); vm.startPrank(addrs[0]); - bootstrap.createExoCapsule(); + bootstrap.createImuaCapsule(); vm.expectRevert(Errors.NativeRestakingControllerCapsuleAlreadyCreated.selector); - bootstrap.createExoCapsule(); + bootstrap.createImuaCapsule(); vm.stopPrank(); } - function test25_CreateExoCapsule_WhenDisabled() public { + function test25_CreateImuaCapsule_WhenDisabled() public { _disableNativeRestaking(); vm.startPrank(addrs[0]); vm.expectRevert(Errors.NativeRestakingControllerNotWhitelisted.selector); - bootstrap.createExoCapsule(); + bootstrap.createImuaCapsule(); vm.stopPrank(); } @@ -1655,7 +1655,7 @@ contract BootstrapTest is Test { // First create a capsule vm.startPrank(addrs[0]); - bootstrap.createExoCapsule(); + bootstrap.createImuaCapsule(); bytes32[] memory validatorContainer = new bytes32[](3); BeaconChainProofs.ValidatorContainerProof memory proof; @@ -1664,7 +1664,7 @@ contract BootstrapTest is Test { uint256 expectedDepositValue = 32 ether; vm.mockCall( address(bootstrap.ownerToCapsule(addrs[0])), - abi.encodeWithSelector(IExoCapsule.verifyDepositProof.selector), + abi.encodeWithSelector(IImuaCapsule.verifyDepositProof.selector), abi.encode(expectedDepositValue) ); @@ -1694,7 +1694,7 @@ contract BootstrapTest is Test { _enableNativeRestaking(); vm.startPrank(addrs[0]); - bootstrap.createExoCapsule(); + bootstrap.createImuaCapsule(); bytes32[] memory validatorContainer = new bytes32[](3); BeaconChainProofs.ValidatorContainerProof memory proof; @@ -1735,7 +1735,7 @@ contract BootstrapTest is Test { // First create a capsule vm.startPrank(addrs[0]); - bootstrap.createExoCapsule(); + bootstrap.createImuaCapsule(); uint256 withdrawAmount = 1 ether; address payable recipient = payable(addrs[1]); @@ -1743,7 +1743,7 @@ contract BootstrapTest is Test { // Mock the capsule withdrawal call vm.mockCall( address(bootstrap.ownerToCapsule(addrs[0])), - abi.encodeWithSelector(IExoCapsule.withdrawNonBeaconChainETHBalance.selector), + abi.encodeWithSelector(IImuaCapsule.withdrawNonBeaconChainETHBalance.selector), abi.encode() ); diff --git a/test/foundry/unit/ClientChainGateway.t.sol b/test/foundry/unit/ClientChainGateway.t.sol index 331e0f4b..c88b20ae 100644 --- a/test/foundry/unit/ClientChainGateway.t.sol +++ b/test/foundry/unit/ClientChainGateway.t.sol @@ -23,15 +23,15 @@ import "src/core/ClientChainGateway.sol"; import {BootstrapStorage} from "src/storage/BootstrapStorage.sol"; import "src/storage/ClientChainGatewayStorage.sol"; -import "src/core/ExoCapsule.sol"; -import "src/core/ExocoreGateway.sol"; +import "src/core/ImuaCapsule.sol"; +import "src/core/ImuachainGateway.sol"; import {Vault} from "src/core/Vault.sol"; import {Action, GatewayStorage} from "src/storage/GatewayStorage.sol"; import {NonShortCircuitEndpointV2Mock} from "../../mocks/NonShortCircuitEndpointV2Mock.sol"; import {RewardVault} from "src/core/RewardVault.sol"; -import "src/interfaces/IExoCapsule.sol"; +import "src/interfaces/IImuaCapsule.sol"; import {IRewardVault} from "src/interfaces/IRewardVault.sol"; import "src/interfaces/IVault.sol"; @@ -50,27 +50,27 @@ contract SetUp is Test { Player[] players; address[] whitelistTokens; - Player exocoreValidatorSet; + Player owner; Player deployer; address[] vaults; ERC20PresetFixedSupply restakeToken; ClientChainGateway clientGateway; ClientChainGateway clientGatewayLogic; - ExocoreGateway exocoreGateway; + ImuachainGateway imuachainGateway; ILayerZeroEndpointV2 clientChainLzEndpoint; - ILayerZeroEndpointV2 exocoreLzEndpoint; + ILayerZeroEndpointV2 imuachainLzEndpoint; IBeaconChainOracle beaconOracle; IVault vaultImplementation; IRewardVault rewardVaultImplementation; - IExoCapsule capsuleImplementation; + IImuaCapsule capsuleImplementation; IBeacon vaultBeacon; IBeacon rewardVaultBeacon; IBeacon capsuleBeacon; BeaconProxyBytecode beaconProxyBytecode; - string operatorAddress = "exo1v4s6vtjpmxwu9rlhqms5urzrc3tc2ae2gnuqhc"; - uint32 exocoreChainId = 2; + string operatorAddress = "im13hasr43vvq8v44xpzh0l6yuym4kca983u4aj5n"; + uint32 imuachainChainId = 2; uint32 clientChainId = 1; event Paused(address account); @@ -81,23 +81,23 @@ contract SetUp is Test { players.push(Player({privateKey: uint256(0x1), addr: vm.addr(uint256(0x1))})); players.push(Player({privateKey: uint256(0x2), addr: vm.addr(uint256(0x2))})); players.push(Player({privateKey: uint256(0x3), addr: vm.addr(uint256(0x3))})); - exocoreValidatorSet = Player({privateKey: uint256(0xa), addr: vm.addr(uint256(0xa))}); + owner = Player({privateKey: uint256(0xa), addr: vm.addr(uint256(0xa))}); deployer = Player({privateKey: uint256(0xb), addr: vm.addr(uint256(0xb))}); - exocoreGateway = ExocoreGateway(payable(address(0xc))); - exocoreLzEndpoint = ILayerZeroEndpointV2(address(0xd)); + imuachainGateway = ImuachainGateway(payable(address(0xc))); + imuachainLzEndpoint = ILayerZeroEndpointV2(address(0xd)); - vm.deal(exocoreValidatorSet.addr, 100 ether); + vm.deal(owner.addr, 100 ether); vm.deal(deployer.addr, 100 ether); vm.chainId(clientChainId); _deploy(); NonShortCircuitEndpointV2Mock(address(clientChainLzEndpoint)).setDestLzEndpoint( - address(exocoreGateway), address(exocoreLzEndpoint) + address(imuachainGateway), address(imuachainLzEndpoint) ); - vm.prank(exocoreValidatorSet.addr); - clientGateway.setPeer(exocoreChainId, address(exocoreGateway).toBytes32()); + vm.prank(owner.addr); + clientGateway.setPeer(imuachainChainId, address(imuachainGateway).toBytes32()); vm.stopPrank(); } @@ -108,7 +108,7 @@ contract SetUp is Test { vaultImplementation = new Vault(); rewardVaultImplementation = new RewardVault(); - capsuleImplementation = new ExoCapsule(address(0)); + capsuleImplementation = new ImuaCapsule(address(0)); vaultBeacon = new UpgradeableBeacon(address(vaultImplementation)); rewardVaultBeacon = new UpgradeableBeacon(address(rewardVaultImplementation)); @@ -116,17 +116,17 @@ contract SetUp is Test { beaconProxyBytecode = new BeaconProxyBytecode(); - restakeToken = new ERC20PresetFixedSupply("rest", "rest", 1e16, exocoreValidatorSet.addr); + restakeToken = new ERC20PresetFixedSupply("rest", "rest", 1e16, owner.addr); whitelistTokens.push(address(restakeToken)); - clientChainLzEndpoint = new NonShortCircuitEndpointV2Mock(clientChainId, exocoreValidatorSet.addr); + clientChainLzEndpoint = new NonShortCircuitEndpointV2Mock(clientChainId, owner.addr); ProxyAdmin proxyAdmin = new ProxyAdmin(); BootstrapStorage.ImmutableConfig memory config = BootstrapStorage.ImmutableConfig({ - exocoreChainId: exocoreChainId, + imuachainChainId: imuachainChainId, beaconOracleAddress: address(beaconOracle), vaultBeacon: address(vaultBeacon), - exoCapsuleBeacon: address(capsuleBeacon), + imuaCapsuleBeacon: address(capsuleBeacon), beaconProxyBytecode: address(beaconProxyBytecode), networkConfig: address(0) }); @@ -137,19 +137,19 @@ contract SetUp is Test { payable(address(new TransparentUpgradeableProxy(address(clientGatewayLogic), address(proxyAdmin), ""))) ); - clientGateway.initialize(payable(exocoreValidatorSet.addr)); + clientGateway.initialize(payable(owner.addr)); vm.stopPrank(); } - function generateUID(uint64 nonce, bool fromClientChainToExocore) internal view returns (bytes32 uid) { - if (fromClientChainToExocore) { + function generateUID(uint64 nonce, bool fromClientChainToImuachain) internal view returns (bytes32 uid) { + if (fromClientChainToImuachain) { uid = GUID.generate( - nonce, clientChainId, address(clientGateway), exocoreChainId, address(exocoreGateway).toBytes32() + nonce, clientChainId, address(clientGateway), imuachainChainId, address(imuachainGateway).toBytes32() ); } else { uid = GUID.generate( - nonce, exocoreChainId, address(exocoreGateway), clientChainId, address(clientGateway).toBytes32() + nonce, imuachainChainId, address(imuachainGateway), clientChainId, address(clientGateway).toBytes32() ); } } @@ -175,22 +175,22 @@ contract Pausable is SetUp { function test_PauseClientChainGateway() public { vm.expectEmit(true, true, true, true, address(clientGateway)); - emit Paused(exocoreValidatorSet.addr); - vm.prank(exocoreValidatorSet.addr); + emit Paused(owner.addr); + vm.prank(owner.addr); clientGateway.pause(); assertEq(clientGateway.paused(), true); } function test_UnpauseClientChainGateway() public { - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); vm.expectEmit(true, true, true, true, address(clientGateway)); - emit PausableUpgradeable.Paused(exocoreValidatorSet.addr); + emit PausableUpgradeable.Paused(owner.addr); clientGateway.pause(); assertEq(clientGateway.paused(), true); vm.expectEmit(true, true, true, true, address(clientGateway)); - emit PausableUpgradeable.Unpaused(exocoreValidatorSet.addr); + emit PausableUpgradeable.Unpaused(owner.addr); clientGateway.unpause(); assertEq(clientGateway.paused(), false); } @@ -202,7 +202,7 @@ contract Pausable is SetUp { } function test_RevertWhen_CallDisabledFunctionsWhenPaused() public { - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); clientGateway.pause(); vm.expectRevert("Pausable: paused"); @@ -215,7 +215,7 @@ contract Pausable is SetUp { clientGateway.deposit(address(restakeToken), uint256(1)); vm.expectRevert("Pausable: paused"); - clientGateway.claimPrincipalFromExocore(address(restakeToken), uint256(1)); + clientGateway.claimPrincipalFromImuachain(address(restakeToken), uint256(1)); vm.expectRevert("Pausable: paused"); clientGateway.undelegateFrom(operatorAddress, address(restakeToken), uint256(1)); @@ -225,8 +225,8 @@ contract Pausable is SetUp { contract Initialize is SetUp { - function test_ExocoreChainIdInitialized() public { - assertEq(clientGateway.EXOCORE_CHAIN_ID(), exocoreChainId); + function test_ImuachainChainIdInitialized() public { + assertEq(clientGateway.IMUACHAIN_CHAIN_ID(), imuachainChainId); } function test_LzEndpointInitialized() public { @@ -249,13 +249,13 @@ contract Initialize is SetUp { assertEq(clientGateway.BEACON_ORACLE_ADDRESS(), address(beaconOracle)); } - function test_ExoCapsuleBeaconInitialized() public { + function test_ImuaCapsuleBeaconInitialized() public { assertFalse(address(capsuleBeacon) == address(0)); - assertEq(address(clientGateway.EXO_CAPSULE_BEACON()), address(capsuleBeacon)); + assertEq(address(clientGateway.IMUA_CAPSULE_BEACON()), address(capsuleBeacon)); } function test_OwnerInitialized() public { - assertEq(clientGateway.owner(), exocoreValidatorSet.addr); + assertEq(clientGateway.owner(), owner.addr); } function test_NotPaused() public { @@ -295,7 +295,7 @@ contract WithdrawNonBeaconChainETHFromCapsule is SetUp { // 1. User creates capsule through ClientChainGateway vm.prank(user); - capsuleAddress = payable(clientGateway.createExoCapsule()); + capsuleAddress = payable(clientGateway.createImuaCapsule()); } function test_success_withdrawNonBeaconChainETH() public { @@ -336,14 +336,14 @@ contract WithdrawNonBeaconChainETHFromCapsule is SetUp { vm.prank(user); vm.expectRevert( - "ExoCapsule.withdrawNonBeaconChainETHBalance: amountToWithdraw is greater than nonBeaconChainETHBalance" + "ImuaCapsule.withdrawNonBeaconChainETHBalance: amountToWithdraw is greater than nonBeaconChainETHBalance" ); clientGateway.withdrawNonBeaconChainETHFromCapsule(user, excessiveWithdrawAmount); } } -contract WithdrawalPrincipalFromExocore is SetUp { +contract WithdrawalPrincipalFromImuachain is SetUp { using stdStorage for StdStorage; using AddressCast for address; @@ -366,7 +366,8 @@ contract WithdrawalPrincipalFromExocore is SetUp { // Simulate adding VIRTUAL_STAKED_ETH_ADDRESS to whitelist via lzReceive bytes memory message = abi.encodePacked(Action.REQUEST_ADD_WHITELIST_TOKEN, abi.encodePacked(tokens[0], uint128(0))); - Origin memory origin = Origin({srcEid: exocoreChainId, sender: address(exocoreGateway).toBytes32(), nonce: 1}); + Origin memory origin = + Origin({srcEid: imuachainChainId, sender: address(imuachainGateway).toBytes32(), nonce: 1}); vm.prank(address(clientChainLzEndpoint)); clientGateway.lzReceive(origin, bytes32(0), message, address(0), bytes("")); @@ -385,7 +386,7 @@ contract WithdrawalPrincipalFromExocore is SetUp { // Try to withdraw VIRTUAL_STAKED_ETH vm.prank(user); vm.expectRevert(Errors.VaultDoesNotExist.selector); - clientGateway.claimPrincipalFromExocore(VIRTUAL_STAKED_ETH_ADDRESS, WITHDRAWAL_AMOUNT); + clientGateway.claimPrincipalFromImuachain(VIRTUAL_STAKED_ETH_ADDRESS, WITHDRAWAL_AMOUNT); } function test_revert_withdrawNonWhitelistedToken() public { @@ -393,13 +394,13 @@ contract WithdrawalPrincipalFromExocore is SetUp { vm.prank(players[0].addr); vm.expectRevert("BootstrapStorage: token is not whitelisted"); - clientGateway.claimPrincipalFromExocore(nonWhitelistedToken, WITHDRAWAL_AMOUNT); + clientGateway.claimPrincipalFromImuachain(nonWhitelistedToken, WITHDRAWAL_AMOUNT); } function test_revert_withdrawZeroAmount() public { vm.prank(user); vm.expectRevert("BootstrapStorage: amount should be greater than zero"); - clientGateway.claimPrincipalFromExocore(address(restakeToken), 0); + clientGateway.claimPrincipalFromImuachain(address(restakeToken), 0); } } diff --git a/test/foundry/unit/ExoCapsule.t.sol b/test/foundry/unit/ImuaCapsule.t.sol similarity index 92% rename from test/foundry/unit/ExoCapsule.t.sol rename to test/foundry/unit/ImuaCapsule.t.sol index 7873360c..79fd477b 100644 --- a/test/foundry/unit/ExoCapsule.t.sol +++ b/test/foundry/unit/ImuaCapsule.t.sol @@ -6,12 +6,12 @@ import "@openzeppelin/contracts/proxy/transparent/TransparentUpgradeableProxy.so import "@openzeppelin/contracts/token/ERC20/presets/ERC20PresetFixedSupply.sol"; import "forge-std/Test.sol"; -import "src/core/ExoCapsule.sol"; -import "src/interfaces/IExoCapsule.sol"; +import "src/core/ImuaCapsule.sol"; +import "src/interfaces/IImuaCapsule.sol"; import "src/libraries/BeaconChainProofs.sol"; import "src/libraries/Endian.sol"; -import {ExoCapsuleStorage} from "src/storage/ExoCapsuleStorage.sol"; +import {ImuaCapsuleStorage} from "src/storage/ImuaCapsuleStorage.sol"; contract DepositSetup is Test { @@ -31,7 +31,7 @@ contract DepositSetup is Test { BeaconChainProofs.ValidatorContainerProof validatorProof; bytes32 beaconBlockRoot; - ExoCapsule capsule; + ImuaCapsule capsule; IBeaconChainOracle beaconOracle; address payable capsuleOwner; @@ -73,11 +73,11 @@ contract DepositSetup is Test { capsuleOwner = payable(address(0x125)); - ExoCapsule phantomCapsule = new ExoCapsule(address(0)); + ImuaCapsule phantomCapsule = new ImuaCapsule(address(0)); address capsuleAddress = _getCapsuleFromWithdrawalCredentials(_getWithdrawalCredentials(validatorContainer)); vm.etch(capsuleAddress, address(phantomCapsule).code); - capsule = ExoCapsule(payable(capsuleAddress)); + capsule = ImuaCapsule(payable(capsuleAddress)); capsule.initialize(address(this), capsuleOwner, address(beaconOracle)); } @@ -156,9 +156,9 @@ contract VerifyDepositProof is DepositSetup { capsule.verifyDepositProof(validatorContainer, validatorProof); - ExoCapsuleStorage.Validator memory validator = + ImuaCapsuleStorage.Validator memory validator = capsule.getRegisteredValidatorByPubkey(_getPubkey(validatorContainer)); - assertEq(uint8(validator.status), uint8(ExoCapsuleStorage.VALIDATOR_STATUS.REGISTERED)); + assertEq(uint8(validator.status), uint8(ImuaCapsuleStorage.VALIDATOR_STATUS.REGISTERED)); assertEq(validator.validatorIndex, validatorProof.validatorIndex); } @@ -180,7 +180,7 @@ contract VerifyDepositProof is DepositSetup { // deposit again should revert vm.expectRevert( - abi.encodeWithSelector(ExoCapsule.DoubleDepositedValidator.selector, _getPubkey(validatorContainer)) + abi.encodeWithSelector(ImuaCapsule.DoubleDepositedValidator.selector, _getPubkey(validatorContainer)) ); capsule.verifyDepositProof(validatorContainer, validatorProof); } @@ -202,7 +202,7 @@ contract VerifyDepositProof is DepositSetup { // deposit should revert because of proof is stale vm.expectRevert( abi.encodeWithSelector( - ExoCapsule.StaleValidatorContainer.selector, _getPubkey(validatorContainer), mockProofTimestamp + ImuaCapsule.StaleValidatorContainer.selector, _getPubkey(validatorContainer), mockProofTimestamp ) ); capsule.verifyDepositProof(validatorContainer, validatorProof); @@ -227,7 +227,7 @@ contract VerifyDepositProof is DepositSetup { // construct malformed validator container that has extra fields validatorContainer.push(bytes32(uint256(123))); vm.expectRevert( - abi.encodeWithSelector(ExoCapsule.InvalidValidatorContainer.selector, _getPubkey(validatorContainer)) + abi.encodeWithSelector(ImuaCapsule.InvalidValidatorContainer.selector, _getPubkey(validatorContainer)) ); capsule.verifyDepositProof(validatorContainer, validatorProof); @@ -235,7 +235,7 @@ contract VerifyDepositProof is DepositSetup { // construct malformed validator container that misses fields validatorContainer.pop(); vm.expectRevert( - abi.encodeWithSelector(ExoCapsule.InvalidValidatorContainer.selector, _getPubkey(validatorContainer)) + abi.encodeWithSelector(ImuaCapsule.InvalidValidatorContainer.selector, _getPubkey(validatorContainer)) ); capsule.verifyDepositProof(validatorContainer, validatorProof); } @@ -258,9 +258,9 @@ contract VerifyDepositProof is DepositSetup { capsule.verifyDepositProof(validatorContainer, validatorProof); - ExoCapsuleStorage.Validator memory validator = + ImuaCapsuleStorage.Validator memory validator = capsule.getRegisteredValidatorByPubkey(_getPubkey(validatorContainer)); - assertEq(uint8(validator.status), uint8(ExoCapsuleStorage.VALIDATOR_STATUS.REGISTERED)); + assertEq(uint8(validator.status), uint8(ImuaCapsuleStorage.VALIDATOR_STATUS.REGISTERED)); assertEq(validator.validatorIndex, validatorProof.validatorIndex); } @@ -279,7 +279,7 @@ contract VerifyDepositProof is DepositSetup { ); // validator container withdrawal credentials are pointed to another capsule - ExoCapsule anotherCapsule = new ExoCapsule(address(0)); + ImuaCapsule anotherCapsule = new ImuaCapsule(address(0)); bytes32 gatewaySlot = bytes32(stdstore.target(address(anotherCapsule)).sig("gateway()").find()); vm.store(address(anotherCapsule), gatewaySlot, bytes32(uint256(uint160(address(this))))); @@ -290,7 +290,7 @@ contract VerifyDepositProof is DepositSetup { bytes32 beaconOraclerSlot = bytes32(stdstore.target(address(anotherCapsule)).sig("beaconOracle()").find()); vm.store(address(anotherCapsule), beaconOraclerSlot, bytes32(uint256(uint160(address(beaconOracle))))); - vm.expectRevert(abi.encodeWithSelector(ExoCapsule.WithdrawalCredentialsNotMatch.selector)); + vm.expectRevert(abi.encodeWithSelector(ImuaCapsule.WithdrawalCredentialsNotMatch.selector)); anotherCapsule.verifyDepositProof(validatorContainer, validatorProof); } @@ -311,7 +311,7 @@ contract VerifyDepositProof is DepositSetup { // verify proof against mismatch beacon block root vm.expectRevert( - abi.encodeWithSelector(ExoCapsule.InvalidValidatorContainer.selector, _getPubkey(validatorContainer)) + abi.encodeWithSelector(ImuaCapsule.InvalidValidatorContainer.selector, _getPubkey(validatorContainer)) ); capsule.verifyDepositProof(validatorContainer, validatorProof); } @@ -339,7 +339,7 @@ contract WithdrawalSetup is Test { BeaconChainProofs.WithdrawalProof withdrawalProof; bytes32 beaconBlockRoot; // latest beacon block root - ExoCapsule capsule; + ImuaCapsule capsule; IBeaconChainOracle beaconOracle; address capsuleOwner; @@ -366,11 +366,11 @@ contract WithdrawalSetup is Test { capsuleOwner = address(0x125); - ExoCapsule phantomCapsule = new ExoCapsule(address(0)); + ImuaCapsule phantomCapsule = new ImuaCapsule(address(0)); address capsuleAddress = _getCapsuleFromWithdrawalCredentials(_getWithdrawalCredentials(validatorContainer)); vm.etch(capsuleAddress, address(phantomCapsule).code); - capsule = ExoCapsule(payable(capsuleAddress)); + capsule = ImuaCapsule(payable(capsuleAddress)); assertEq(bytes32(capsule.capsuleWithdrawalCredentials()), _getWithdrawalCredentials(validatorContainer)); stdstore.target(capsuleAddress).sig("gateway()").checked_write(bytes32(uint256(uint160(address(this))))); @@ -396,9 +396,9 @@ contract WithdrawalSetup is Test { uint256 depositAmount = capsule.verifyDepositProof(validatorContainer, validatorProof); - ExoCapsuleStorage.Validator memory validator = + ImuaCapsuleStorage.Validator memory validator = capsule.getRegisteredValidatorByPubkey(_getPubkey(validatorContainer)); - assertEq(uint8(validator.status), uint8(ExoCapsuleStorage.VALIDATOR_STATUS.REGISTERED)); + assertEq(uint8(validator.status), uint8(ImuaCapsuleStorage.VALIDATOR_STATUS.REGISTERED)); assertEq(validator.validatorIndex, validatorProof.validatorIndex); vm.deal(address(capsule), 1 ether); // Deposit 1 ether to handle excess amount withdraw @@ -517,7 +517,7 @@ contract VerifyWithdrawalProof is WithdrawalSetup { vm.expectRevert( bytes( - "ExoCapsule.withdrawNonBeaconChainETHBalance: amountToWithdraw is greater than nonBeaconChainETHBalance" + "ImuaCapsule.withdrawNonBeaconChainETHBalance: amountToWithdraw is greater than nonBeaconChainETHBalance" ) ); capsule.withdrawNonBeaconChainETHBalance(payable(recipient), 0.5 ether); @@ -535,7 +535,7 @@ contract VerifyWithdrawalProof is WithdrawalSetup { vm.expectRevert( abi.encodeWithSelector( - ExoCapsule.WithdrawalAlreadyProven.selector, + ImuaCapsule.WithdrawalAlreadyProven.selector, _getPubkey(validatorContainer), uint256(_getWithdrawalIndex(withdrawalContainer)) ) diff --git a/test/foundry/unit/ExocoreGateway.t.sol b/test/foundry/unit/ImuachainGateway.t.sol similarity index 69% rename from test/foundry/unit/ExocoreGateway.t.sol rename to test/foundry/unit/ImuachainGateway.t.sol index 69ea922c..2cf5d45b 100644 --- a/test/foundry/unit/ExocoreGateway.t.sol +++ b/test/foundry/unit/ImuachainGateway.t.sol @@ -22,32 +22,32 @@ import "forge-std/Test.sol"; import "src/core/ClientChainGateway.sol"; import "src/core/ClientChainGateway.sol"; -import "src/core/ExocoreGateway.sol"; +import "src/core/ImuachainGateway.sol"; import {Vault} from "src/core/Vault.sol"; -import {ExocoreGatewayStorage} from "src/storage/ExocoreGatewayStorage.sol"; import {Action, GatewayStorage} from "src/storage/GatewayStorage.sol"; +import {ImuachainGatewayStorage} from "src/storage/ImuachainGatewayStorage.sol"; contract SetUp is Test { using AddressCast for address; Player[] players; - Player exocoreValidatorSet; + Player owner; Player deployer; Player withdrawer; - ExocoreGateway exocoreGateway; + ImuachainGateway imuachainGateway; ClientChainGateway clientGateway; ClientChainGateway solanaClientGateway; - NonShortCircuitEndpointV2Mock exocoreLzEndpoint; + NonShortCircuitEndpointV2Mock imuachainLzEndpoint; NonShortCircuitEndpointV2Mock clientLzEndpoint; NonShortCircuitEndpointV2Mock solanaClientLzEndpoint; ERC20 restakeToken; - uint16 exocoreChainId = 1; + uint16 imuachainChainId = 1; uint16 clientChainId = 2; uint16 solanaClientChainId = 40_168; @@ -58,14 +58,14 @@ contract SetUp is Test { event Paused(address account); event Unpaused(address account); - event ExocorePrecompileError(address indexed precompile, uint64 nonce); + event ImuachainPrecompileError(address indexed precompile, uint64 nonce); event MessageSent(Action indexed act, bytes32 packetId, uint64 nonce, uint256 nativeFee); function setUp() public virtual { players.push(Player({privateKey: uint256(0x1), addr: vm.addr(uint256(0x1))})); players.push(Player({privateKey: uint256(0x2), addr: vm.addr(uint256(0x2))})); players.push(Player({privateKey: uint256(0x3), addr: vm.addr(uint256(0x3))})); - exocoreValidatorSet = Player({privateKey: uint256(0xa), addr: vm.addr(uint256(0xa))}); + owner = Player({privateKey: uint256(0xa), addr: vm.addr(uint256(0xa))}); deployer = Player({privateKey: uint256(0xb), addr: vm.addr(uint256(0xb))}); withdrawer = Player({privateKey: uint256(0xc), addr: vm.addr(uint256(0xb))}); clientGateway = ClientChainGateway(payable(address(0xd))); @@ -83,31 +83,31 @@ contract SetUp is Test { _deploy(); - vm.deal(exocoreValidatorSet.addr, 100 ether); + vm.deal(owner.addr, 100 ether); vm.deal(deployer.addr, 100 ether); } function _deploy() internal { vm.startPrank(deployer.addr); - restakeToken = new ERC20PresetFixedSupply("rest", "rest", 1e34, exocoreValidatorSet.addr); + restakeToken = new ERC20PresetFixedSupply("rest", "rest", 1e34, owner.addr); - exocoreLzEndpoint = new NonShortCircuitEndpointV2Mock(exocoreChainId, exocoreValidatorSet.addr); - clientLzEndpoint = new NonShortCircuitEndpointV2Mock(clientChainId, exocoreValidatorSet.addr); - solanaClientLzEndpoint = new NonShortCircuitEndpointV2Mock(solanaClientChainId, exocoreValidatorSet.addr); + imuachainLzEndpoint = new NonShortCircuitEndpointV2Mock(imuachainChainId, owner.addr); + clientLzEndpoint = new NonShortCircuitEndpointV2Mock(clientChainId, owner.addr); + solanaClientLzEndpoint = new NonShortCircuitEndpointV2Mock(solanaClientChainId, owner.addr); ProxyAdmin proxyAdmin = new ProxyAdmin(); - ExocoreGateway exocoreGatewayLogic = new ExocoreGateway(address(exocoreLzEndpoint)); - exocoreGateway = ExocoreGateway( - payable(address(new TransparentUpgradeableProxy(address(exocoreGatewayLogic), address(proxyAdmin), ""))) + ImuachainGateway imuachainGatewayLogic = new ImuachainGateway(address(imuachainLzEndpoint)); + imuachainGateway = ImuachainGateway( + payable(address(new TransparentUpgradeableProxy(address(imuachainGatewayLogic), address(proxyAdmin), ""))) ); - exocoreGateway.initialize(payable(exocoreValidatorSet.addr)); + imuachainGateway.initialize(payable(owner.addr)); vm.stopPrank(); - vm.startPrank(exocoreValidatorSet.addr); - exocoreLzEndpoint.setDestLzEndpoint(address(clientGateway), address(clientLzEndpoint)); - exocoreGateway.registerOrUpdateClientChain( + vm.startPrank(owner.addr); + imuachainLzEndpoint.setDestLzEndpoint(address(clientGateway), address(clientLzEndpoint)); + imuachainGateway.registerOrUpdateClientChain( clientChainId, address(clientGateway).toBytes32(), 20, @@ -116,8 +116,8 @@ contract SetUp is Test { "secp256k1" ); - exocoreLzEndpoint.setDestLzEndpoint(address(solanaClientGateway), address(clientLzEndpoint)); - exocoreGateway.registerOrUpdateClientChain( + imuachainLzEndpoint.setDestLzEndpoint(address(solanaClientGateway), address(solanaClientLzEndpoint)); + imuachainGateway.registerOrUpdateClientChain( solanaClientChainId, address(solanaClientGateway).toBytes32(), 20, @@ -128,30 +128,30 @@ contract SetUp is Test { vm.stopPrank(); - // transfer some gas fee to exocore gateway as it has to pay for the relay fee to layerzero endpoint when + // transfer some gas fee to imuachain gateway as it has to pay for the relay fee to layerzero endpoint when // sending back response - deal(address(exocoreGateway), 1e22); + deal(address(imuachainGateway), 1e22); } - function generateUID(uint64 nonce, bool fromClientChainToExocore) internal view returns (bytes32 uid) { - uid = generateUID(nonce, fromClientChainToExocore, false); + function generateUID(uint64 nonce, bool fromClientChainToImuachain) internal view returns (bytes32 uid) { + uid = generateUID(nonce, fromClientChainToImuachain, false); } - function generateUID(uint64 nonce, bool fromClientChainToExocore, bool isSolanaClient) + function generateUID(uint64 nonce, bool fromClientChainToImuachain, bool isSolanaClient) internal view returns (bytes32 uid) { - if (fromClientChainToExocore) { + if (fromClientChainToImuachain) { uid = GUID.generate( - nonce, clientChainId, address(clientGateway), exocoreChainId, address(exocoreGateway).toBytes32() + nonce, clientChainId, address(clientGateway), imuachainChainId, address(imuachainGateway).toBytes32() ); } else { uint16 targetChainId = isSolanaClient ? solanaClientChainId : clientChainId; bytes32 targetGateway = isSolanaClient ? address(solanaClientGateway).toBytes32() : address(clientGateway).toBytes32(); - return GUID.generate(nonce, exocoreChainId, address(exocoreGateway), targetChainId, targetGateway); + return GUID.generate(nonce, imuachainChainId, address(imuachainGateway), targetChainId, targetGateway); } } @@ -161,41 +161,41 @@ contract Pausable is SetUp { using AddressCast for address; - function test_PauseExocoreGateway() public { - vm.expectEmit(true, true, true, true, address(exocoreGateway)); - emit Paused(exocoreValidatorSet.addr); - vm.prank(exocoreValidatorSet.addr); - exocoreGateway.pause(); - assertEq(exocoreGateway.paused(), true); + function test_PauseImuachainGateway() public { + vm.expectEmit(true, true, true, true, address(imuachainGateway)); + emit Paused(owner.addr); + vm.prank(owner.addr); + imuachainGateway.pause(); + assertEq(imuachainGateway.paused(), true); } - function test_UnpauseExocoreGateway() public { - vm.startPrank(exocoreValidatorSet.addr); + function test_UnpauseImuachainGateway() public { + vm.startPrank(owner.addr); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); - emit Paused(exocoreValidatorSet.addr); - exocoreGateway.pause(); - assertEq(exocoreGateway.paused(), true); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); + emit Paused(owner.addr); + imuachainGateway.pause(); + assertEq(imuachainGateway.paused(), true); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); - emit Unpaused(exocoreValidatorSet.addr); - exocoreGateway.unpause(); - assertEq(exocoreGateway.paused(), false); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); + emit Unpaused(owner.addr); + imuachainGateway.unpause(); + assertEq(imuachainGateway.paused(), false); } function test_RevertWhen_UnauthorizedPauser() public { vm.expectRevert(bytes("Ownable: caller is not the owner")); vm.startPrank(deployer.addr); - exocoreGateway.pause(); + imuachainGateway.pause(); } function test_RevertWhen_CallDisabledFunctionsWhenPaused() public { - vm.prank(exocoreValidatorSet.addr); - exocoreGateway.pause(); + vm.prank(owner.addr); + imuachainGateway.pause(); - vm.prank(address(exocoreLzEndpoint)); + vm.prank(address(imuachainLzEndpoint)); vm.expectRevert("Pausable: paused"); - exocoreGateway.lzReceive( + imuachainGateway.lzReceive( Origin(clientChainId, address(clientGateway).toBytes32(), uint64(1)), bytes32(0), bytes(""), @@ -211,7 +211,7 @@ contract LzReceive is SetUp { using AddressCast for address; uint256 constant WITHDRAWAL_AMOUNT = 123; - string operator = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + string operator = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; event AssociationResult(bool indexed success, bool indexed isAssociate, bytes32 indexed staker); @@ -237,8 +237,8 @@ contract LzReceive is SetUp { ); bytes memory msg_ = abi.encodePacked(Action.REQUEST_WITHDRAW_LST, payload); - vm.prank(address(exocoreLzEndpoint)); - exocoreGateway.lzReceive( + vm.prank(address(imuachainLzEndpoint)); + imuachainGateway.lzReceive( Origin(clientChainId, address(clientGateway).toBytes32(), uint64(1)), bytes32(0), msg_, @@ -253,11 +253,11 @@ contract LzReceive is SetUp { bytes memory payload = abi.encodePacked(abi.encodePacked(bytes32(bytes20(staker.addr))), bytes(operator)); bytes memory msg_ = abi.encodePacked(Action.REQUEST_ASSOCIATE_OPERATOR, payload); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit AssociationResult(true, true, bytes32(bytes20(staker.addr))); - vm.prank(address(exocoreLzEndpoint)); - exocoreGateway.lzReceive( + vm.prank(address(imuachainLzEndpoint)); + imuachainGateway.lzReceive( Origin(clientChainId, address(clientGateway).toBytes32(), uint64(1)), bytes32(0), msg_, @@ -270,16 +270,16 @@ contract LzReceive is SetUp { test_Success_AssociateOperatorWithStaker(); Player memory staker = players[0]; - string memory anotherOperator = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f811111"; + string memory anotherOperator = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; bytes memory payload = abi.encodePacked(abi.encodePacked(bytes32(bytes20(staker.addr))), bytes(anotherOperator)); bytes memory msg_ = abi.encodePacked(Action.REQUEST_ASSOCIATE_OPERATOR, payload); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit AssociationResult(false, true, bytes32(bytes20(staker.addr))); - vm.prank(address(exocoreLzEndpoint)); - exocoreGateway.lzReceive( + vm.prank(address(imuachainLzEndpoint)); + imuachainGateway.lzReceive( Origin(clientChainId, address(clientGateway).toBytes32(), uint64(2)), bytes32(0), msg_, @@ -297,14 +297,14 @@ contract LzReceive is SetUp { test_Success_AssociateOperatorWithStaker(); Player memory staker = players[0]; - string memory anotherOperator = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f811111"; + string memory anotherOperator = "im13hasr43vvq8v44xpzh0l6yuym4kca98q5zpluj"; uint32 anotherChainId = 123; bytes memory payload = abi.encodePacked(abi.encodePacked(bytes32(bytes20(staker.addr))), bytes(anotherOperator)); bytes memory msg_ = abi.encodePacked(Action.REQUEST_ASSOCIATE_OPERATOR, payload); - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.registerOrUpdateClientChain( + vm.startPrank(owner.addr); + imuachainGateway.registerOrUpdateClientChain( anotherChainId, address(clientGateway).toBytes32(), 20, @@ -314,11 +314,11 @@ contract LzReceive is SetUp { ); vm.stopPrank(); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit AssociationResult(true, true, bytes32(bytes20(staker.addr))); - vm.prank(address(exocoreLzEndpoint)); - exocoreGateway.lzReceive( + vm.prank(address(imuachainLzEndpoint)); + imuachainGateway.lzReceive( Origin(anotherChainId, address(clientGateway).toBytes32(), uint64(1)), bytes32(0), msg_, @@ -340,11 +340,11 @@ contract LzReceive is SetUp { bytes memory payload = abi.encodePacked(abi.encodePacked(bytes32(bytes20(staker.addr)))); bytes memory msg_ = abi.encodePacked(Action.REQUEST_DISSOCIATE_OPERATOR, payload); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit AssociationResult(true, false, bytes32(bytes20(staker.addr))); - vm.prank(address(exocoreLzEndpoint)); - exocoreGateway.lzReceive( + vm.prank(address(imuachainLzEndpoint)); + imuachainGateway.lzReceive( Origin(clientChainId, address(clientGateway).toBytes32(), uint64(2)), bytes32(0), msg_, @@ -359,11 +359,11 @@ contract LzReceive is SetUp { bytes memory payload = abi.encodePacked(abi.encodePacked(bytes32(bytes20(staker.addr)))); bytes memory msg_ = abi.encodePacked(Action.REQUEST_DISSOCIATE_OPERATOR, payload); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit AssociationResult(false, false, bytes32(bytes20(staker.addr))); - vm.prank(address(exocoreLzEndpoint)); - exocoreGateway.lzReceive( + vm.prank(address(imuachainLzEndpoint)); + imuachainGateway.lzReceive( Origin(clientChainId, address(clientGateway).toBytes32(), uint64(1)), bytes32(0), msg_, @@ -391,10 +391,10 @@ contract RegisterOrUpdateClientChain is SetUp { function test_Success_RegisterClientChain() public { _prepareClientChainData(); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit ClientChainRegistered(anotherClientChain); - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.registerOrUpdateClientChain( + vm.startPrank(owner.addr); + imuachainGateway.registerOrUpdateClientChain( anotherClientChain, peer, addressLength, name, metaInfo, signatureType ); } @@ -405,10 +405,10 @@ contract RegisterOrUpdateClientChain is SetUp { peer = bytes32(uint256(321)); metaInfo = "Testnet"; - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit ClientChainUpdated(anotherClientChain); - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.registerOrUpdateClientChain( + vm.startPrank(owner.addr); + imuachainGateway.registerOrUpdateClientChain( anotherClientChain, peer, addressLength, name, metaInfo, signatureType ); } @@ -418,20 +418,20 @@ contract RegisterOrUpdateClientChain is SetUp { vm.startPrank(deployer.addr); vm.expectRevert("Ownable: caller is not the owner"); - exocoreGateway.registerOrUpdateClientChain( + imuachainGateway.registerOrUpdateClientChain( anotherClientChain, peer, addressLength, name, metaInfo, signatureType ); } function test_RevertWhen_Paused() public { - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.pause(); + vm.startPrank(owner.addr); + imuachainGateway.pause(); _prepareClientChainData(); vm.expectRevert("Pausable: paused"); - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.registerOrUpdateClientChain( + vm.startPrank(owner.addr); + imuachainGateway.registerOrUpdateClientChain( anotherClientChain, peer, addressLength, name, metaInfo, signatureType ); } @@ -441,8 +441,8 @@ contract RegisterOrUpdateClientChain is SetUp { anotherClientChain = 0; vm.expectRevert(Errors.ZeroValue.selector); - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.registerOrUpdateClientChain( + vm.startPrank(owner.addr); + imuachainGateway.registerOrUpdateClientChain( anotherClientChain, peer, addressLength, name, metaInfo, signatureType ); } @@ -452,8 +452,8 @@ contract RegisterOrUpdateClientChain is SetUp { peer = bytes32(0); vm.expectRevert(Errors.ZeroValue.selector); - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.registerOrUpdateClientChain( + vm.startPrank(owner.addr); + imuachainGateway.registerOrUpdateClientChain( anotherClientChain, peer, addressLength, name, metaInfo, signatureType ); } @@ -463,8 +463,8 @@ contract RegisterOrUpdateClientChain is SetUp { addressLength = 0; vm.expectRevert(Errors.ZeroValue.selector); - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.registerOrUpdateClientChain( + vm.startPrank(owner.addr); + imuachainGateway.registerOrUpdateClientChain( anotherClientChain, peer, addressLength, name, metaInfo, signatureType ); } @@ -474,8 +474,8 @@ contract RegisterOrUpdateClientChain is SetUp { name = ""; vm.expectRevert(Errors.ZeroValue.selector); - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.registerOrUpdateClientChain( + vm.startPrank(owner.addr); + imuachainGateway.registerOrUpdateClientChain( anotherClientChain, peer, addressLength, name, metaInfo, signatureType ); } @@ -485,8 +485,8 @@ contract RegisterOrUpdateClientChain is SetUp { metaInfo = ""; vm.expectRevert(Errors.ZeroValue.selector); - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.registerOrUpdateClientChain( + vm.startPrank(owner.addr); + imuachainGateway.registerOrUpdateClientChain( anotherClientChain, peer, addressLength, name, metaInfo, signatureType ); } @@ -504,7 +504,7 @@ contract RegisterOrUpdateClientChain is SetUp { contract SetPeer is SetUp { - ExocoreGateway gateway; + ImuachainGateway gateway; uint32 anotherClientChain = clientChainId + 1; bytes32 anotherPeer = bytes32("0xabcdef"); @@ -513,36 +513,36 @@ contract SetPeer is SetUp { event PeerSet(uint32 eid, bytes32 peer); function test_Success_SetPeer() public { - vm.startPrank(exocoreValidatorSet.addr); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + vm.startPrank(owner.addr); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit PeerSet(anotherClientChain, anotherPeer); - exocoreGateway.registerOrUpdateClientChain( + imuachainGateway.registerOrUpdateClientChain( anotherClientChain, anotherPeer, 20, "Test Chain", "Test Meta", "ECDSA" ); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit PeerSet(anotherClientChain, newPeer); - exocoreGateway.setPeer(anotherClientChain, newPeer); + imuachainGateway.setPeer(anotherClientChain, newPeer); } function test_RevertWhen_CallerNotOwner() public { - vm.startPrank(exocoreValidatorSet.addr); - vm.expectEmit(true, true, true, true, address(exocoreGateway)); + vm.startPrank(owner.addr); + vm.expectEmit(true, true, true, true, address(imuachainGateway)); emit PeerSet(anotherClientChain, anotherPeer); - exocoreGateway.registerOrUpdateClientChain( + imuachainGateway.registerOrUpdateClientChain( anotherClientChain, anotherPeer, 20, "Test Chain", "Test Meta", "ECDSA" ); vm.stopPrank(); vm.startPrank(deployer.addr); vm.expectRevert("Ownable: caller is not the owner"); - exocoreGateway.setPeer(anotherClientChain, newPeer); + imuachainGateway.setPeer(anotherClientChain, newPeer); } function test_RevertWhen_ClientChainNotRegistered() public { - vm.startPrank(exocoreValidatorSet.addr); - vm.expectRevert(Errors.ExocoreGatewayNotRegisteredClientChainId.selector); - exocoreGateway.setPeer(anotherClientChain, newPeer); + vm.startPrank(owner.addr); + vm.expectRevert(Errors.ImuachainGatewayNotRegisteredClientChainId.selector); + imuachainGateway.setPeer(anotherClientChain, newPeer); } } @@ -562,52 +562,52 @@ contract AddWhitelistTokens is SetUp { function setUp() public virtual override { super.setUp(); - nativeFee = exocoreGateway.quote(clientChainId, new bytes(MESSAGE_LENGTH)); + nativeFee = imuachainGateway.quote(clientChainId, new bytes(MESSAGE_LENGTH)); bytes memory message = new bytes(MESSAGE_LENGTH); message[0] = bytes1(abi.encodePacked(Action.REQUEST_ADD_WHITELIST_TOKEN)); - nativeFeeForSolana = exocoreGateway.quote(solanaClientChainId, message); + nativeFeeForSolana = imuachainGateway.quote(solanaClientChainId, message); } function test_RevertWhen_CallerNotOwner() public { vm.startPrank(deployer.addr); vm.expectRevert("Ownable: caller is not the owner"); - exocoreGateway.addWhitelistToken{value: nativeFee}( + imuachainGateway.addWhitelistToken{value: nativeFee}( clientChainId, bytes32(0), 18, "name", "metadata", "oracleInfo", 0 ); } function test_RevertWhen_Paused() public { - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.pause(); + vm.startPrank(owner.addr); + imuachainGateway.pause(); vm.expectRevert("Pausable: paused"); - exocoreGateway.addWhitelistToken{value: nativeFee}( + imuachainGateway.addWhitelistToken{value: nativeFee}( clientChainId, bytes32(0), 18, "name", "metadata", "oracleInfo", 0 ); } function test_RevertWhen_ZeroValue() public { - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); vm.expectRevert(abi.encodeWithSelector(IncorrectNativeFee.selector, uint256(0))); - exocoreGateway.addWhitelistToken{value: 0}( + imuachainGateway.addWhitelistToken{value: 0}( clientChainId, bytes32(bytes20(address(restakeToken))), 18, "name", "metadata", "oracleInfo", 0 ); } function test_RevertWhen_HasZeroAddressToken() public { - vm.startPrank(exocoreValidatorSet.addr); - vm.expectRevert("ExocoreGateway: token cannot be zero address"); - exocoreGateway.addWhitelistToken{value: nativeFee}( + vm.startPrank(owner.addr); + vm.expectRevert(abi.encodeWithSelector(Errors.ZeroAddress.selector)); + imuachainGateway.addWhitelistToken{value: nativeFee}( clientChainId, bytes32(0), 18, "name", "metadata", "oracleInfo", 0 ); } function test_Success_AddWhiteListToken() public { - vm.startPrank(exocoreValidatorSet.addr); - vm.expectEmit(address(exocoreGateway)); + vm.startPrank(owner.addr); + vm.expectEmit(address(imuachainGateway)); emit WhitelistTokenAdded(clientChainId, bytes32(bytes20(address(restakeToken)))); - vm.expectEmit(address(exocoreGateway)); + vm.expectEmit(address(imuachainGateway)); emit MessageSent(Action.REQUEST_ADD_WHITELIST_TOKEN, generateUID(1, false), 1, nativeFee); - exocoreGateway.addWhitelistToken{value: nativeFee}( + imuachainGateway.addWhitelistToken{value: nativeFee}( clientChainId, bytes32(bytes20(address(restakeToken))), 18, @@ -620,12 +620,12 @@ contract AddWhitelistTokens is SetUp { } function test_Success_AddWhiteListTokenOnSolana() public { - vm.startPrank(exocoreValidatorSet.addr); - vm.expectEmit(address(exocoreGateway)); + vm.startPrank(owner.addr); + vm.expectEmit(address(imuachainGateway)); emit WhitelistTokenAdded(solanaClientChainId, bytes32(bytes20(address(restakeToken)))); - vm.expectEmit(address(exocoreGateway)); + vm.expectEmit(address(imuachainGateway)); emit MessageSent(Action.REQUEST_ADD_WHITELIST_TOKEN, generateUID(1, false, true), 1, nativeFeeForSolana); - exocoreGateway.addWhitelistToken{value: nativeFeeForSolana}( + imuachainGateway.addWhitelistToken{value: nativeFeeForSolana}( solanaClientChainId, bytes32(bytes20(address(restakeToken))), 9, @@ -659,13 +659,13 @@ contract UpdateWhitelistTokens is SetUp { // the below code is intentionally repeated here, instead of inheriting it from AddWhitelistTokens // this is done to not conflate the tests of AddWhitelistTokens with UpdateWhitelistTokens uint256 MESSAGE_LENGTH = 1 + 32 + 16; // action + token address as bytes32 + uint128 - uint256 nativeFee = exocoreGateway.quote(clientChainId, new bytes(MESSAGE_LENGTH)); - vm.startPrank(exocoreValidatorSet.addr); - vm.expectEmit(address(exocoreGateway)); + uint256 nativeFee = imuachainGateway.quote(clientChainId, new bytes(MESSAGE_LENGTH)); + vm.startPrank(owner.addr); + vm.expectEmit(address(imuachainGateway)); emit WhitelistTokenAdded(clientChainId, bytes32(bytes20(address(restakeToken)))); - vm.expectEmit(address(exocoreGateway)); + vm.expectEmit(address(imuachainGateway)); emit MessageSent(Action.REQUEST_ADD_WHITELIST_TOKEN, generateUID(1, false), 1, nativeFee); - exocoreGateway.addWhitelistToken{value: nativeFee}( + imuachainGateway.addWhitelistToken{value: nativeFee}( clientChainId, bytes32(bytes20(address(restakeToken))), 18, @@ -687,33 +687,33 @@ contract UpdateWhitelistTokens is SetUp { function test_RevertUpdateWhen_CallerNotOwner() public { vm.startPrank(deployer.addr); vm.expectRevert("Ownable: caller is not the owner"); - exocoreGateway.updateWhitelistToken(clientChainId, tokenDetails.tokenAddress, tokenDetails.metaData); + imuachainGateway.updateWhitelistToken(clientChainId, tokenDetails.tokenAddress, tokenDetails.metaData); } function test_RevertUpdateWhen_Paused() public { - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.pause(); + vm.startPrank(owner.addr); + imuachainGateway.pause(); vm.expectRevert("Pausable: paused"); - exocoreGateway.updateWhitelistToken(clientChainId, tokenDetails.tokenAddress, tokenDetails.metaData); + imuachainGateway.updateWhitelistToken(clientChainId, tokenDetails.tokenAddress, tokenDetails.metaData); } function test_RevertUpdateWhen_HasZeroAddress() public { - vm.startPrank(exocoreValidatorSet.addr); - vm.expectRevert("ExocoreGateway: token cannot be zero address"); - exocoreGateway.updateWhitelistToken(clientChainId, bytes32(0), tokenDetails.metaData); + vm.startPrank(owner.addr); + vm.expectRevert(abi.encodeWithSelector(Errors.ZeroAddress.selector)); + imuachainGateway.updateWhitelistToken(clientChainId, bytes32(0), tokenDetails.metaData); } function test_RevertUpdateWhen_HasZeroChainId() public { - vm.startPrank(exocoreValidatorSet.addr); - vm.expectRevert("ExocoreGateway: client chain id cannot be zero"); - exocoreGateway.updateWhitelistToken(0, tokenDetails.tokenAddress, tokenDetails.metaData); + vm.startPrank(owner.addr); + vm.expectRevert(abi.encodeWithSelector(Errors.ZeroValue.selector)); + imuachainGateway.updateWhitelistToken(0, tokenDetails.tokenAddress, tokenDetails.metaData); } function test_Success_UpdateWhitelistToken() public { - vm.startPrank(exocoreValidatorSet.addr); - vm.expectEmit(address(exocoreGateway)); + vm.startPrank(owner.addr); + vm.expectEmit(address(imuachainGateway)); emit WhitelistTokenUpdated(clientChainId, tokenDetails.tokenAddress); - exocoreGateway.updateWhitelistToken(clientChainId, tokenDetails.tokenAddress, "new metadata"); + imuachainGateway.updateWhitelistToken(clientChainId, tokenDetails.tokenAddress, "new metadata"); } } @@ -722,14 +722,14 @@ contract AssociateOperatorWithEVMStaker is SetUp { using AddressCast for address; - string operator = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; - string anotherOperator = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f811111"; + string operator = "im13hasr43vvq8v44xpzh0l6yuym4kca98q5zpluj"; + string anotherOperator = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; uint32 anotherChainId = 123; function test_Success_AssociateEVMStaker() public { Player memory staker = players[0]; vm.startPrank(staker.addr); - exocoreGateway.associateOperatorWithEVMStaker(clientChainId, operator); + imuachainGateway.associateOperatorWithEVMStaker(clientChainId, operator); bytes memory associatedOperator = DelegationMock(DELEGATION_PRECOMPILE_ADDRESS).getAssociatedOperator( clientChainId, abi.encodePacked(bytes32(bytes20(staker.addr))) @@ -743,7 +743,7 @@ contract AssociateOperatorWithEVMStaker is SetUp { abi.encodeWithSelector(Errors.AssociateOperatorFailed.selector, anotherChainId, staker.addr, operator) ); vm.startPrank(staker.addr); - exocoreGateway.associateOperatorWithEVMStaker(anotherChainId, operator); + imuachainGateway.associateOperatorWithEVMStaker(anotherChainId, operator); } function test_RevertWhen_AssociateMarkedStaker() public { @@ -754,14 +754,14 @@ contract AssociateOperatorWithEVMStaker is SetUp { abi.encodeWithSelector(Errors.AssociateOperatorFailed.selector, clientChainId, staker.addr, anotherOperator) ); vm.startPrank(staker.addr); - exocoreGateway.associateOperatorWithEVMStaker(clientChainId, anotherOperator); + imuachainGateway.associateOperatorWithEVMStaker(clientChainId, anotherOperator); } function test_Success_AssociateSameStakerButAnotherChain() public { test_Success_AssociateEVMStaker(); - vm.startPrank(exocoreValidatorSet.addr); - exocoreGateway.registerOrUpdateClientChain( + vm.startPrank(owner.addr); + imuachainGateway.registerOrUpdateClientChain( anotherChainId, address(clientGateway).toBytes32(), 20, @@ -773,7 +773,7 @@ contract AssociateOperatorWithEVMStaker is SetUp { Player memory staker = players[0]; vm.startPrank(staker.addr); - exocoreGateway.associateOperatorWithEVMStaker(anotherChainId, anotherOperator); + imuachainGateway.associateOperatorWithEVMStaker(anotherChainId, anotherOperator); bytes memory associatedOperator = DelegationMock(DELEGATION_PRECOMPILE_ADDRESS).getAssociatedOperator( clientChainId, abi.encodePacked(bytes32(bytes20(staker.addr))) @@ -790,7 +790,7 @@ contract AssociateOperatorWithEVMStaker is SetUp { Player memory staker = players[0]; vm.startPrank(staker.addr); - exocoreGateway.dissociateOperatorFromEVMStaker(clientChainId); + imuachainGateway.dissociateOperatorFromEVMStaker(clientChainId); bytes memory associatedOperator = DelegationMock(DELEGATION_PRECOMPILE_ADDRESS).getAssociatedOperator( clientChainId, abi.encodePacked(bytes32(bytes20(staker.addr))) @@ -802,14 +802,14 @@ contract AssociateOperatorWithEVMStaker is SetUp { Player memory staker = players[0]; vm.expectRevert(abi.encodeWithSelector(Errors.DissociateOperatorFailed.selector, anotherChainId, staker.addr)); vm.startPrank(staker.addr); - exocoreGateway.dissociateOperatorFromEVMStaker(anotherChainId); + imuachainGateway.dissociateOperatorFromEVMStaker(anotherChainId); } function test_RevertWhen_DissociatePureStaker() public { Player memory staker = players[0]; vm.expectRevert(abi.encodeWithSelector(Errors.DissociateOperatorFailed.selector, clientChainId, staker.addr)); vm.startPrank(staker.addr); - exocoreGateway.dissociateOperatorFromEVMStaker(clientChainId); + imuachainGateway.dissociateOperatorFromEVMStaker(clientChainId); } } @@ -822,20 +822,20 @@ contract MarkBootstrap is SetUp { function setUp() public virtual override { super.setUp(); - nativeFee = exocoreGateway.quote(clientChainId, abi.encodePacked(Action.REQUEST_MARK_BOOTSTRAP, "")); + nativeFee = imuachainGateway.quote(clientChainId, abi.encodePacked(Action.REQUEST_MARK_BOOTSTRAP, "")); } function test_Success() public { - vm.startPrank(exocoreValidatorSet.addr); - vm.expectEmit(address(exocoreGateway)); - emit ExocoreGatewayStorage.BootstrapRequestSent(clientChainId); - exocoreGateway.markBootstrap{value: nativeFee}(clientChainId); + vm.startPrank(owner.addr); + vm.expectEmit(address(imuachainGateway)); + emit ImuachainGatewayStorage.BootstrapRequestSent(clientChainId); + imuachainGateway.markBootstrap{value: nativeFee}(clientChainId); } function test_Fail() public { - vm.startPrank(exocoreValidatorSet.addr); + vm.startPrank(owner.addr); vm.expectRevert(abi.encodeWithSelector(NoPeer.selector, clientChainId + 1)); - exocoreGateway.markBootstrap{value: nativeFee}(clientChainId + 1); + imuachainGateway.markBootstrap{value: nativeFee}(clientChainId + 1); } } diff --git a/test/foundry/unit/UTXOGateway.t.sol b/test/foundry/unit/UTXOGateway.t.sol index 01897a18..14bbe6ba 100644 --- a/test/foundry/unit/UTXOGateway.t.sol +++ b/test/foundry/unit/UTXOGateway.t.sol @@ -9,7 +9,7 @@ import "src/interfaces/precompiles/IDelegation.sol"; import "src/interfaces/precompiles/IReward.sol"; import {Errors} from "src/libraries/Errors.sol"; -import {ExocoreBytes} from "src/libraries/ExocoreBytes.sol"; +import {ImuachainBytes} from "src/libraries/ImuachainBytes.sol"; import {SignatureVerifier} from "src/libraries/SignatureVerifier.sol"; import {UTXOGatewayStorage} from "src/storage/UTXOGatewayStorage.sol"; import "test/mocks/AssetsMock.sol"; @@ -22,7 +22,7 @@ contract UTXOGatewayTest is Test { using stdStorage for StdStorage; using SignatureVerifier for bytes32; - using ExocoreBytes for address; + using ImuachainBytes for address; struct Player { uint256 privateKey; @@ -38,7 +38,7 @@ contract UTXOGatewayTest is Test { bytes btcAddress; string operator; - address public constant EXOCORE_WITNESS = address(0xf39Fd6e51aad88F6F4ce6aB8827279cffFb92266); + address public constant IMUACHAIN_WITNESS = address(0xf39Fd6e51aad88F6F4ce6aB8827279cffFb92266); // chain id from layerzero, virtual for bitcoin since it's not yet a layerzero chain string public constant BITCOIN_NAME = "Bitcoin"; @@ -61,12 +61,12 @@ contract UTXOGatewayTest is Test { event WitnessAdded(address indexed witness); event WitnessRemoved(address indexed witness); event AddressRegistered( - UTXOGatewayStorage.ClientChainID indexed chainId, bytes depositor, address indexed exocoreAddress + UTXOGatewayStorage.ClientChainID indexed chainId, bytes depositor, address indexed imuachainAddress ); event DepositCompleted( UTXOGatewayStorage.ClientChainID indexed chainId, bytes32 indexed clientTxId, - address indexed exocoreAddress, + address indexed imuachainAddress, bytes srcAddress, uint256 amount, uint256 updatedBalance @@ -76,7 +76,7 @@ contract UTXOGatewayTest is Test { ); event UndelegationCompleted( UTXOGatewayStorage.ClientChainID indexed clientChainId, - address indexed exoDelegator, + address indexed imDelegator, string operator, uint256 amount ); @@ -89,14 +89,14 @@ contract UTXOGatewayTest is Test { event WhitelistTokenUpdated(UTXOGatewayStorage.ClientChainID indexed clientChainId, address indexed token); event DelegationFailedForStake( UTXOGatewayStorage.ClientChainID indexed clientChainId, - address indexed exoDelegator, + address indexed imDelegator, string operator, uint256 amount ); event StakeMsgExecuted( UTXOGatewayStorage.ClientChainID indexed chainId, uint64 indexed nonce, - address indexed exocoreAddress, + address indexed imuachainAddress, uint256 amount ); event TransactionProcessed(bytes32 indexed txId); @@ -104,7 +104,7 @@ contract UTXOGatewayTest is Test { event WithdrawPrincipalRequested( UTXOGatewayStorage.ClientChainID indexed srcChainId, uint64 indexed requestId, - address indexed withdrawerExoAddr, + address indexed withdrawerImAddr, bytes withdrawerClientChainAddr, uint256 amount, uint256 updatedBalance @@ -112,7 +112,7 @@ contract UTXOGatewayTest is Test { event WithdrawRewardRequested( UTXOGatewayStorage.ClientChainID indexed srcChainId, uint64 indexed requestId, - address indexed withdrawerExoAddr, + address indexed withdrawerImAddr, bytes withdrawerClientChainAddr, uint256 amount, uint256 updatedBalance @@ -142,7 +142,7 @@ contract UTXOGatewayTest is Test { witnesses[2] = Player({privateKey: 0xc, addr: vm.addr(0xc)}); btcAddress = bytes("1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa"); - operator = "exo13hasr43vvq8v44xpzh0l6yuym4kca98f87j7ac"; + operator = "im13hasr43vvq8v44xpzh0l6yuym4kca98fhq3xla"; // Deploy and initialize gateway gatewayLogic = new UTXOGateway(); @@ -606,7 +606,7 @@ contract UTXOGatewayTest is Test { vm.expectRevert( abi.encodeWithSelector( - Errors.RegisterClientChainToExocoreFailed.selector, + Errors.RegisterClientChainToImuachainFailed.selector, uint32(uint8(UTXOGatewayStorage.ClientChainID.BITCOIN)) ) ); @@ -691,7 +691,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -726,7 +726,7 @@ contract UTXOGatewayTest is Test { signature = _generateSignature(stakeMsg, witnesses[2].privateKey); vm.prank(relayer); vm.expectEmit(true, false, false, false); - emit StakeMsgExecuted(stakeMsg.clientChainId, stakeMsg.nonce, stakeMsg.exocoreAddress, stakeMsg.amount); + emit StakeMsgExecuted(stakeMsg.clientChainId, stakeMsg.nonce, stakeMsg.imuachainAddress, stakeMsg.amount); vm.expectEmit(true, false, false, false); emit TransactionProcessed(txId); gateway.submitProofForStakeMsg(witnesses[2].addr, stakeMsg, signature); @@ -747,7 +747,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -769,7 +769,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -790,7 +790,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -812,7 +812,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -848,7 +848,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -886,7 +886,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -929,7 +929,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -954,7 +954,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -974,7 +974,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: "", amount: 1 ether }); @@ -1000,7 +1000,7 @@ contract UTXOGatewayTest is Test { // Verify address registration assertEq(gateway.getClientAddress(UTXOGatewayStorage.ClientChainID.BITCOIN, user), btcAddress); - assertEq(gateway.getExocoreAddress(UTXOGatewayStorage.ClientChainID.BITCOIN, btcAddress), user); + assertEq(gateway.getImuachainAddress(UTXOGatewayStorage.ClientChainID.BITCOIN, btcAddress), user); } function test_ProcessStakeMessage_WithBridgeFee() public { @@ -1011,7 +1011,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -1059,7 +1059,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -1088,7 +1088,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: operator, amount: 1 ether }); @@ -1132,7 +1132,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: "", amount: 1 ether }); @@ -1157,7 +1157,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: "", amount: 1 ether }); @@ -1180,7 +1180,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: "", amount: 1 ether }); @@ -1202,7 +1202,7 @@ contract UTXOGatewayTest is Test { nonce: 0, clientTxId: bytes32(uint256(123)), clientAddress: bytes(""), - exocoreAddress: address(0), + imuachainAddress: address(0), operator: "", amount: 0 }); @@ -1214,7 +1214,7 @@ contract UTXOGatewayTest is Test { gateway.processStakeMessage(witnesses[0].addr, stakeMsg, signature); } - function test_ProcessStakeMessage_RevertZeroExocoreAddressBeforeRegistration() public { + function test_ProcessStakeMessage_RevertZeroImuachainAddressBeforeRegistration() public { _deactivateConsensus(); UTXOGatewayStorage.StakeMsg memory stakeMsg = UTXOGatewayStorage.StakeMsg({ @@ -1222,7 +1222,7 @@ contract UTXOGatewayTest is Test { nonce: 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: address(0), // Zero address + imuachainAddress: address(0), // Zero address operator: "", amount: 1 ether }); @@ -1242,7 +1242,7 @@ contract UTXOGatewayTest is Test { nonce: gateway.nextInboundNonce(UTXOGatewayStorage.ClientChainID.BITCOIN) + 1, clientTxId: bytes32(uint256(123)), clientAddress: btcAddress, - exocoreAddress: user, + imuachainAddress: user, operator: "", amount: 1 ether }); @@ -1580,7 +1580,7 @@ contract UTXOGatewayTest is Test { IReward.claimReward.selector, uint32(uint8(UTXOGatewayStorage.ClientChainID.BITCOIN)), VIRTUAL_TOKEN, - user.toExocoreBytes(), + user.toImuachainBytes(), 1 ether ); vm.mockCall(REWARD_PRECOMPILE_ADDRESS, claimCall1, abi.encode(true, 2 ether)); @@ -1589,7 +1589,7 @@ contract UTXOGatewayTest is Test { IReward.claimReward.selector, uint32(uint8(UTXOGatewayStorage.ClientChainID.BITCOIN)), VIRTUAL_TOKEN, - user.toExocoreBytes(), + user.toImuachainBytes(), 0.5 ether ); vm.mockCall(REWARD_PRECOMPILE_ADDRESS, claimCall2, abi.encode(true, 1.5 ether)); @@ -1694,13 +1694,13 @@ contract UTXOGatewayTest is Test { } // Helper functions - function _mockRegisterAddress(address exocoreAddr, bytes memory btcAddr) internal { + function _mockRegisterAddress(address imuachainAddr, bytes memory btcAddr) internal { UTXOGatewayStorage.StakeMsg memory stakeMsg = UTXOGatewayStorage.StakeMsg({ clientChainId: UTXOGatewayStorage.ClientChainID.BITCOIN, nonce: gateway.nextInboundNonce(UTXOGatewayStorage.ClientChainID.BITCOIN), clientTxId: bytes32(uint256(123)), clientAddress: btcAddr, - exocoreAddress: exocoreAddr, + imuachainAddress: imuachainAddr, operator: "", amount: 1 ether }); @@ -1718,14 +1718,14 @@ contract UTXOGatewayTest is Test { bytes memory signature = _generateSignature(stakeMsg, witnesses[0].privateKey); vm.expectEmit(true, true, true, true, address(gateway)); - emit AddressRegistered(UTXOGatewayStorage.ClientChainID.BITCOIN, btcAddr, exocoreAddr); + emit AddressRegistered(UTXOGatewayStorage.ClientChainID.BITCOIN, btcAddr, imuachainAddr); vm.prank(relayer); gateway.processStakeMessage(witnesses[0].addr, stakeMsg, signature); // Verify address registration - assertEq(gateway.getClientAddress(UTXOGatewayStorage.ClientChainID.BITCOIN, exocoreAddr), btcAddr); - assertEq(gateway.getExocoreAddress(UTXOGatewayStorage.ClientChainID.BITCOIN, btcAddr), exocoreAddr); + assertEq(gateway.getClientAddress(UTXOGatewayStorage.ClientChainID.BITCOIN, imuachainAddr), btcAddr); + assertEq(gateway.getImuachainAddress(UTXOGatewayStorage.ClientChainID.BITCOIN, btcAddr), imuachainAddr); } function _addAllWitnesses() internal { @@ -1746,7 +1746,7 @@ contract UTXOGatewayTest is Test { msg_.nonce, // uint64 msg_.clientTxId, // bytes32 msg_.clientAddress, // bytes - Bitcoin address - msg_.exocoreAddress, // address + msg_.imuachainAddress, // address msg_.operator, // string msg_.amount // uint256 ) diff --git a/test/hardhat/integration/btc-stake-e2e.test.js b/test/hardhat/integration/btc-stake-e2e.test.js index 6310d21d..106e7447 100644 --- a/test/hardhat/integration/btc-stake-e2e.test.js +++ b/test/hardhat/integration/btc-stake-e2e.test.js @@ -278,7 +278,7 @@ describe("Bitcoin Staking E2E Test", function() { // Initialize contracts from deployed addresses utxoGateway = await ethers.getContractAt( "UTXOGateway", - deployedContracts.exocore.utxoGateway + deployedContracts.imuachain.utxoGateway ); assetsPrecompile = await ethers.getContractAt( "IAssets", diff --git a/test/hardhat/integration/btc-stake.test.js b/test/hardhat/integration/btc-stake.test.js index 0244e090..f7fe818b 100644 --- a/test/hardhat/integration/btc-stake.test.js +++ b/test/hardhat/integration/btc-stake.test.js @@ -38,7 +38,7 @@ describe("BTC Stake", () => { const VIRTUAL_BTC_ADDR = "0xbBbBBBBbbBBBbbbBbbBbbbbBBbBbbbbBbBbbBBbB"; const BTC_ID = ethers.getBytes(VIRTUAL_BTC_ADDR); - const OPERATOR = "exo18cggcpvwspnd5c6ny8wrqxpffj5zmhklprtnph"; + const OPERATOR = "im18cggcpvwspnd5c6ny8wrqxpffj5zmhkl3agtrj"; // Run once before all tests before(async () => { @@ -143,7 +143,7 @@ describe("BTC Stake", () => { const stakeMsg = { clientChainId: CLIENT_CHAIN.BTC, // enum value, probably 1 clientAddress: ethers.toUtf8Bytes(STAKER_BTC_ADDR), // convert address to bytes - exocoreAddress: staker.address, // use signer's address + imuachainAddress: staker.address, // use signer's address operator: OPERATOR, amount: ethers.parseUnits("1.0", 8), nonce: BigInt(1), @@ -156,7 +156,7 @@ describe("BTC Stake", () => { [ 'uint8', // clientChainId (enum is uint8) 'bytes', // clientAddress - 'address', // exocoreAddress + 'address', // imuachainAddress 'string', // operator 'uint256', // amount 'uint64', // nonce @@ -165,7 +165,7 @@ describe("BTC Stake", () => { [ stakeMsg.clientChainId, stakeMsg.clientAddress, - stakeMsg.exocoreAddress, + stakeMsg.imuachainAddress, stakeMsg.operator, stakeMsg.amount, stakeMsg.nonce, diff --git a/test/mocks/DelegationMock.sol b/test/mocks/DelegationMock.sol index 1d146389..d6812892 100644 --- a/test/mocks/DelegationMock.sol +++ b/test/mocks/DelegationMock.sol @@ -38,7 +38,7 @@ contract DelegationMock is IDelegation { if (!AssetsMock(ASSETS_PRECOMPILE_ADDRESS).isRegisteredChain(clientChainLzId)) { return false; } - if (operatorAddr.length != 42) { + if (operatorAddr.length != 41) { return false; } delegateToRecords[stakerAddress][operatorAddr][clientChainLzId][assetsAddress] += opAmount; @@ -60,7 +60,7 @@ contract DelegationMock is IDelegation { if (!AssetsMock(ASSETS_PRECOMPILE_ADDRESS).isRegisteredChain(clientChainLzId)) { return false; } - if (operatorAddr.length != 42) { + if (operatorAddr.length != 41) { return false; } if (opAmount > delegateToRecords[stakerAddress][operatorAddr][clientChainLzId][assetsAddress]) { diff --git a/test/mocks/ExocoreGatewayMock.sol b/test/mocks/ImuachainGatewayMock.sol similarity index 92% rename from test/mocks/ExocoreGatewayMock.sol rename to test/mocks/ImuachainGatewayMock.sol index 5a6dff12..9f1c3ab6 100644 --- a/test/mocks/ExocoreGatewayMock.sol +++ b/test/mocks/ImuachainGatewayMock.sol @@ -1,6 +1,6 @@ pragma solidity ^0.8.19; -import {IExocoreGateway} from "src/interfaces/IExocoreGateway.sol"; +import {IImuachainGateway} from "src/interfaces/IImuachainGateway.sol"; import {Action} from "src/storage/GatewayStorage.sol"; import {IAssets} from "src/interfaces/precompiles/IAssets.sol"; @@ -15,7 +15,7 @@ import { OAppUpgradeable, Origin } from "src/lzApp/OAppUpgradeable.sol"; -import {ExocoreGatewayStorage} from "src/storage/ExocoreGatewayStorage.sol"; +import {ImuachainGatewayStorage} from "src/storage/ImuachainGatewayStorage.sol"; import {IOAppCore} from "@layerzerolabs/lz-evm-oapp-v2/contracts/oapp/interfaces/IOAppCore.sol"; import {OptionsBuilder} from "@layerzerolabs/lz-evm-oapp-v2/contracts/oapp/libs/OptionsBuilder.sol"; @@ -27,13 +27,13 @@ import {ReentrancyGuardUpgradeable} from "@openzeppelin/contracts-upgradeable/se import {Errors} from "src/libraries/Errors.sol"; import {OAppCoreUpgradeable} from "src/lzApp/OAppCoreUpgradeable.sol"; -contract ExocoreGatewayMock is +contract ImuachainGatewayMock is Initializable, PausableUpgradeable, OwnableUpgradeable, ReentrancyGuardUpgradeable, - IExocoreGateway, - ExocoreGatewayStorage, + IImuachainGateway, + ImuachainGatewayStorage, OAppUpgradeable { @@ -50,7 +50,7 @@ contract ExocoreGatewayMock is modifier onlyCalledFromThis() { require( msg.sender == address(this), - "ExocoreGateway: can only be called from this contract itself with a low-level call" + "ImuachainGateway: can only be called from this contract itself with a low-level call" ); _; } @@ -79,7 +79,7 @@ contract ExocoreGatewayMock is receive() external payable {} - /// @notice Initializes the ExocoreGateway contract. + /// @notice Initializes the ImuachainGateway contract. /// @param owner_ The address of the contract owner. function initialize(address owner_) external initializer { if (owner_ == address(0)) { @@ -134,7 +134,7 @@ contract ExocoreGatewayMock is emit BootstrapRequestSent(chainIndex); } - /// @inheritdoc IExocoreGateway + /// @inheritdoc IImuachainGateway function registerOrUpdateClientChain( uint32 clientChainId, bytes32 peer, @@ -180,7 +180,7 @@ contract ExocoreGatewayMock is super.setPeer(clientChainId, clientChainGateway); } - /// @inheritdoc IExocoreGateway + /// @inheritdoc IImuachainGateway /// @notice Tokens can only be normal reward-bearing LST tokens like wstETH, rETH, jitoSol... /// And they are not intended to be: 1) rebasing tokens like stETH, since we assume staker's /// balance would not change if nothing is done after deposit, 2) fee-on-transfer tokens, since we @@ -197,11 +197,21 @@ contract ExocoreGatewayMock is string calldata oracleInfo, uint128 tvlLimit ) external payable onlyOwner whenNotPaused nonReentrant { - require(clientChainId != 0, "ExocoreGateway: client chain id cannot be zero"); - require(token != bytes32(0), "ExocoreGateway: token cannot be zero address"); - require(bytes(name).length != 0, "ExocoreGateway: name cannot be empty"); - require(bytes(metaData).length != 0, "ExocoreGateway: meta data cannot be empty"); - require(bytes(oracleInfo).length != 0, "ExocoreGateway: oracleInfo cannot be empty"); + if (clientChainId == 0) { + revert Errors.ZeroValue(); + } + if (token == bytes32(0)) { + revert Errors.ZeroAddress(); + } + if (bytes(name).length == 0) { + revert Errors.ZeroValue(); + } + if (bytes(metaData).length == 0) { + revert Errors.ZeroValue(); + } + if (bytes(oracleInfo).length == 0) { + revert Errors.ZeroValue(); + } // setting a TVL limit of 0 is permitted to simply add an inactive token, which may // be activated later by updating the TVL limit on the client chain @@ -223,16 +233,22 @@ contract ExocoreGatewayMock is } } - /// @inheritdoc IExocoreGateway + /// @inheritdoc IImuachainGateway function updateWhitelistToken(uint32 clientChainId, bytes32 token, string calldata metaData) external onlyOwner whenNotPaused nonReentrant { - require(clientChainId != 0, "ExocoreGateway: client chain id cannot be zero"); - require(token != bytes32(0), "ExocoreGateway: token cannot be zero address"); - require(bytes(metaData).length != 0, "ExocoreGateway: meta data cannot be empty"); + if (clientChainId == 0) { + revert Errors.ZeroValue(); + } + if (token == bytes32(0)) { + revert Errors.ZeroAddress(); + } + if (bytes(metaData).length == 0) { + revert Errors.ZeroValue(); + } bool success = ASSETS_CONTRACT.updateToken(clientChainId, abi.encodePacked(token), metaData); if (success) { emit WhitelistTokenUpdated(clientChainId, token); @@ -242,10 +258,10 @@ contract ExocoreGatewayMock is } /** - * @notice Associate an Exocore operator with an EVM staker(msg.sender), and this would count staker's delegation + * @notice Associate an Imuachain operator with an EVM staker(msg.sender), and this would count staker's delegation * as operator's self-delegation when staker delegates to operator. * @param clientChainId The id of client chain - * @param operator The Exocore operator address + * @param operator The Imuachain operator address * @dev one staker(chainId+stakerAddress) can only associate one operator, while one operator might be associated * with multiple stakers */ @@ -262,7 +278,7 @@ contract ExocoreGatewayMock is } /** - * @notice Dissociate an Exocore operator from an EVM staker(msg.sender), and this requires that the staker has + * @notice Dissociate an Imuachain operator from an EVM staker(msg.sender), and this requires that the staker has * already been associated to operator. * @param clientChainId The id of client chain */ @@ -282,10 +298,10 @@ contract ExocoreGatewayMock is function _validateClientChainIdRegistered(uint32 clientChainId) internal view { (bool success, bool isRegistered) = ASSETS_CONTRACT.isRegisteredClientChain(clientChainId); if (!success) { - revert Errors.ExocoreGatewayFailedToCheckClientChainId(); + revert Errors.ImuachainGatewayFailedToCheckClientChainId(); } if (!isRegistered) { - revert Errors.ExocoreGatewayNotRegisteredClientChainId(); + revert Errors.ImuachainGatewayNotRegisteredClientChainId(); } } @@ -305,7 +321,7 @@ contract ExocoreGatewayMock is (bool success, bool updated) = ASSETS_CONTRACT.registerOrUpdateClientChain(clientChainId, addressLength, name, metaInfo, signatureType); if (!success) { - revert Errors.RegisterClientChainToExocoreFailed(clientChainId); + revert Errors.RegisterClientChainToImuachainFailed(clientChainId); } return updated; } @@ -508,8 +524,7 @@ contract ExocoreGatewayMock is bool isAssociate = act == Action.REQUEST_ASSOCIATE_OPERATOR; if (isAssociate) { - bytes calldata operator = payload[32:74]; - + bytes calldata operator = payload[32:]; success = DELEGATION_CONTRACT.associateOperatorWithStaker(srcChainId, staker, operator); } else { success = DELEGATION_CONTRACT.dissociateOperatorFromStaker(srcChainId, staker); @@ -538,7 +553,7 @@ contract ExocoreGatewayMock is emit MessageSent(act, receipt.guid, receipt.nonce, receipt.fee.nativeFee); } - /// @inheritdoc IExocoreGateway + /// @inheritdoc IImuachainGateway function quote(uint32 srcChainId, bytes calldata _message) public view returns (uint256 nativeFee) { Action act = Action(uint8(_message[0])); bytes memory options = _buildOptions(srcChainId, act); diff --git a/test/mocks/NonShortCircuitEndpointV2Mock.sol b/test/mocks/NonShortCircuitEndpointV2Mock.sol index 3da36f56..37330a61 100644 --- a/test/mocks/NonShortCircuitEndpointV2Mock.sol +++ b/test/mocks/NonShortCircuitEndpointV2Mock.sol @@ -69,7 +69,7 @@ contract NonShortCircuitEndpointV2Mock is ILayerZeroEndpointV2, MessagingContext uint8 internal constant _NOT_ENTERED = 1; uint8 internal constant _ENTERED = 2; uint8 internal _receive_entered_state = 1; - address exocoreValidatorSet; + address owner; modifier receiveNonReentrant() { require(_receive_entered_state == _NOT_ENTERED, "LayerZeroMock: no receive reentrancy"); @@ -78,8 +78,8 @@ contract NonShortCircuitEndpointV2Mock is ILayerZeroEndpointV2, MessagingContext _receive_entered_state = _NOT_ENTERED; } - modifier onlyExocoreValidatorSet() { - require(msg.sender == exocoreValidatorSet, "only authorized to exocore validator set"); + modifier onlyOwner() { + require(msg.sender == owner, "only authorized to owner"); _; } @@ -89,10 +89,10 @@ contract NonShortCircuitEndpointV2Mock is ILayerZeroEndpointV2, MessagingContext uint32 srcChainId, bytes32 srcAddress, address dstAddress, uint64 nonce, bytes payload, bytes reason ); - constructor(uint32 _eid, address _exocoreValidatorSet) { - require(_exocoreValidatorSet != address(0), "exocore validator set address should not be empty"); + constructor(uint32 _eid, address _owner) { + require(_owner != address(0), "owner address should not be empty"); - exocoreValidatorSet = _exocoreValidatorSet; + owner = _owner; eid = _eid; // init config relayerFeeConfig = RelayerFeeConfig({ @@ -259,10 +259,7 @@ contract NonShortCircuitEndpointV2Mock is ILayerZeroEndpointV2, MessagingContext return lazyInboundNonce[_receiver][_srcEid][_sender]; } - function resetInboundNonce(address _receiver, uint32 _srcEid, bytes32 _sender, uint64 _nonce) - external - onlyExocoreValidatorSet - { + function resetInboundNonce(address _receiver, uint32 _srcEid, bytes32 _sender, uint64 _nonce) external onlyOwner { lazyInboundNonce[_receiver][_srcEid][_sender] = _nonce; } @@ -270,10 +267,7 @@ contract NonShortCircuitEndpointV2Mock is ILayerZeroEndpointV2, MessagingContext return outboundNonce[_sender][_dstEid][_receiver]; } - function resetOutboundNonce(address _sender, uint32 _dstEid, bytes32 _receiver, uint64 _nonce) - external - onlyExocoreValidatorSet - { + function resetOutboundNonce(address _sender, uint32 _dstEid, bytes32 _receiver, uint64 _nonce) external onlyOwner { outboundNonce[_sender][_dstEid][_receiver] = _nonce; }