diff --git a/hardhat.config.ts b/hardhat.config.ts index f5347fd16..521e8bf90 100644 --- a/hardhat.config.ts +++ b/hardhat.config.ts @@ -83,7 +83,7 @@ function isFork() { blockNumber: 21068448, }, accounts: { - accountsBalance: "1000000000000000000", + accountsBalance: "100000000000000000000000", }, live: false, } diff --git a/simulations/vip-174/abi/Comptroller.json b/simulations/vip-174/abi/Comptroller.json new file mode 100644 index 000000000..fb2b4582e --- /dev/null +++ b/simulations/vip-174/abi/Comptroller.json @@ -0,0 +1,2782 @@ +[ + { + "inputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + }, + { + "indexed": true, + "internalType": "enum ComptrollerV9Storage.Action", + "name": "action", + "type": "uint8" + }, + { + "indexed": false, + "internalType": "bool", + "name": "pauseState", + "type": "bool" + } + ], + "name": "ActionPausedMarket", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "bool", + "name": "state", + "type": "bool" + } + ], + "name": "ActionProtocolPaused", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "delegate", + "type": "address" + }, + { + "indexed": false, + "internalType": "bool", + "name": "allowDelegatedBorrows", + "type": "bool" + } + ], + "name": "DelegateUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "venusDelta", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "venusBorrowIndex", + "type": "uint256" + } + ], + "name": "DistributedBorrowerVenus", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "supplier", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "venusDelta", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "venusSupplyIndex", + "type": "uint256" + } + ], + "name": "DistributedSupplierVenus", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "DistributedVAIVaultVenus", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "error", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "info", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "detail", + "type": "uint256" + } + ], + "name": "Failure", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "account", + "type": "address" + } + ], + "name": "MarketEntered", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "account", + "type": "address" + } + ], + "name": "MarketExited", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + } + ], + "name": "MarketListed", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "oldAccessControlAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "newAccessControlAddress", + "type": "address" + } + ], + "name": "NewAccessControl", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newBorrowCap", + "type": "uint256" + } + ], + "name": "NewBorrowCap", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "oldCloseFactorMantissa", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newCloseFactorMantissa", + "type": "uint256" + } + ], + "name": "NewCloseFactor", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "oldCollateralFactorMantissa", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newCollateralFactorMantissa", + "type": "uint256" + } + ], + "name": "NewCollateralFactor", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "oldComptrollerLens", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "newComptrollerLens", + "type": "address" + } + ], + "name": "NewComptrollerLens", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "oldLiquidationIncentiveMantissa", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newLiquidationIncentiveMantissa", + "type": "uint256" + } + ], + "name": "NewLiquidationIncentive", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "oldLiquidatorContract", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "newLiquidatorContract", + "type": "address" + } + ], + "name": "NewLiquidatorContract", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "oldPauseGuardian", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "newPauseGuardian", + "type": "address" + } + ], + "name": "NewPauseGuardian", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "contract PriceOracle", + "name": "oldPriceOracle", + "type": "address" + }, + { + "indexed": false, + "internalType": "contract PriceOracle", + "name": "newPriceOracle", + "type": "address" + } + ], + "name": "NewPriceOracle", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newSupplyCap", + "type": "uint256" + } + ], + "name": "NewSupplyCap", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "oldTreasuryAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "newTreasuryAddress", + "type": "address" + } + ], + "name": "NewTreasuryAddress", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "oldTreasuryGuardian", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "newTreasuryGuardian", + "type": "address" + } + ], + "name": "NewTreasuryGuardian", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "oldTreasuryPercent", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newTreasuryPercent", + "type": "uint256" + } + ], + "name": "NewTreasuryPercent", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "contract VAIControllerInterface", + "name": "oldVAIController", + "type": "address" + }, + { + "indexed": false, + "internalType": "contract VAIControllerInterface", + "name": "newVAIController", + "type": "address" + } + ], + "name": "NewVAIController", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "oldVAIMintRate", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newVAIMintRate", + "type": "uint256" + } + ], + "name": "NewVAIMintRate", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "vault_", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "releaseStartBlock_", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "releaseInterval_", + "type": "uint256" + } + ], + "name": "NewVAIVaultInfo", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "oldVenusVAIVaultRate", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newVenusVAIVaultRate", + "type": "uint256" + } + ], + "name": "NewVenusVAIVaultRate", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newSpeed", + "type": "uint256" + } + ], + "name": "VenusBorrowSpeedUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "recipient", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "VenusGranted", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newSpeed", + "type": "uint256" + } + ], + "name": "VenusSupplySpeedUpdated", + "type": "event" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract Unitroller", + "name": "unitroller", + "type": "address" + } + ], + "name": "_become", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "recipient", + "type": "address" + }, + { + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "_grantXVS", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "newAccessControlAddress", + "type": "address" + } + ], + "name": "_setAccessControl", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address[]", + "name": "markets", + "type": "address[]" + }, + { + "internalType": "enum ComptrollerV9Storage.Action[]", + "name": "actions", + "type": "uint8[]" + }, + { + "internalType": "bool", + "name": "paused", + "type": "bool" + } + ], + "name": "_setActionsPaused", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "newCloseFactorMantissa", + "type": "uint256" + } + ], + "name": "_setCloseFactor", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + }, + { + "internalType": "uint256", + "name": "newCollateralFactorMantissa", + "type": "uint256" + } + ], + "name": "_setCollateralFactor", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract ComptrollerLensInterface", + "name": "comptrollerLens_", + "type": "address" + } + ], + "name": "_setComptrollerLens", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "newLiquidationIncentiveMantissa", + "type": "uint256" + } + ], + "name": "_setLiquidationIncentive", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "newLiquidatorContract_", + "type": "address" + } + ], + "name": "_setLiquidatorContract", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract VToken[]", + "name": "vTokens", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "newBorrowCaps", + "type": "uint256[]" + } + ], + "name": "_setMarketBorrowCaps", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract VToken[]", + "name": "vTokens", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "newSupplyCaps", + "type": "uint256[]" + } + ], + "name": "_setMarketSupplyCaps", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "newPauseGuardian", + "type": "address" + } + ], + "name": "_setPauseGuardian", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract PriceOracle", + "name": "newOracle", + "type": "address" + } + ], + "name": "_setPriceOracle", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "bool", + "name": "state", + "type": "bool" + } + ], + "name": "_setProtocolPaused", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "newTreasuryGuardian", + "type": "address" + }, + { + "internalType": "address", + "name": "newTreasuryAddress", + "type": "address" + }, + { + "internalType": "uint256", + "name": "newTreasuryPercent", + "type": "uint256" + } + ], + "name": "_setTreasuryData", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract VAIControllerInterface", + "name": "vaiController_", + "type": "address" + } + ], + "name": "_setVAIController", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "newVAIMintRate", + "type": "uint256" + } + ], + "name": "_setVAIMintRate", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vault_", + "type": "address" + }, + { + "internalType": "uint256", + "name": "releaseStartBlock_", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "minReleaseAmount_", + "type": "uint256" + } + ], + "name": "_setVAIVaultInfo", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract VToken[]", + "name": "vTokens", + "type": "address[]" + }, + { + "internalType": "uint256[]", + "name": "supplySpeeds", + "type": "uint256[]" + }, + { + "internalType": "uint256[]", + "name": "borrowSpeeds", + "type": "uint256[]" + } + ], + "name": "_setVenusSpeeds", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "venusVAIVaultRate_", + "type": "uint256" + } + ], + "name": "_setVenusVAIVaultRate", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + } + ], + "name": "_supportMarket", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + }, + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "accountAssets", + "outputs": [ + { + "internalType": "contract VToken", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "market", + "type": "address" + }, + { + "internalType": "enum ComptrollerV9Storage.Action", + "name": "action", + "type": "uint8" + } + ], + "name": "actionPaused", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "admin", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "allMarkets", + "outputs": [ + { + "internalType": "contract VToken", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + }, + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "approvedDelegates", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vToken", + "type": "address" + }, + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "borrowAmount", + "type": "uint256" + } + ], + "name": "borrowAllowed", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "borrowCapGuardian", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "borrowCaps", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vToken", + "type": "address" + }, + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "borrowAmount", + "type": "uint256" + } + ], + "name": "borrowVerify", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "account", + "type": "address" + }, + { + "internalType": "contract VToken", + "name": "vToken", + "type": "address" + } + ], + "name": "checkMembership", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address[]", + "name": "holders", + "type": "address[]" + }, + { + "internalType": "contract VToken[]", + "name": "vTokens", + "type": "address[]" + }, + { + "internalType": "bool", + "name": "borrowers", + "type": "bool" + }, + { + "internalType": "bool", + "name": "suppliers", + "type": "bool" + }, + { + "internalType": "bool", + "name": "collateral", + "type": "bool" + } + ], + "name": "claimVenus", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "holder", + "type": "address" + }, + { + "internalType": "contract VToken[]", + "name": "vTokens", + "type": "address[]" + } + ], + "name": "claimVenus", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "holder", + "type": "address" + } + ], + "name": "claimVenus", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address[]", + "name": "holders", + "type": "address[]" + }, + { + "internalType": "contract VToken[]", + "name": "vTokens", + "type": "address[]" + }, + { + "internalType": "bool", + "name": "borrowers", + "type": "bool" + }, + { + "internalType": "bool", + "name": "suppliers", + "type": "bool" + } + ], + "name": "claimVenus", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "holder", + "type": "address" + } + ], + "name": "claimVenusAsCollateral", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "closeFactorMantissa", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "comptrollerImplementation", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "comptrollerLens", + "outputs": [ + { + "internalType": "contract ComptrollerLensInterface", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address[]", + "name": "vTokens", + "type": "address[]" + } + ], + "name": "enterMarkets", + "outputs": [ + { + "internalType": "uint256[]", + "name": "", + "type": "uint256[]" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vTokenAddress", + "type": "address" + } + ], + "name": "exitMarket", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "account", + "type": "address" + } + ], + "name": "getAccountLiquidity", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "getAllMarkets", + "outputs": [ + { + "internalType": "contract VToken[]", + "name": "", + "type": "address[]" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "account", + "type": "address" + } + ], + "name": "getAssetsIn", + "outputs": [ + { + "internalType": "contract VToken[]", + "name": "", + "type": "address[]" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "getBlockNumber", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "account", + "type": "address" + }, + { + "internalType": "address", + "name": "vTokenModify", + "type": "address" + }, + { + "internalType": "uint256", + "name": "redeemTokens", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "borrowAmount", + "type": "uint256" + } + ], + "name": "getHypotheticalAccountLiquidity", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "getXVSAddress", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "getXVSVTokenAddress", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "isComptroller", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vTokenBorrowed", + "type": "address" + }, + { + "internalType": "address", + "name": "vTokenCollateral", + "type": "address" + }, + { + "internalType": "address", + "name": "liquidator", + "type": "address" + }, + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "repayAmount", + "type": "uint256" + } + ], + "name": "liquidateBorrowAllowed", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vTokenBorrowed", + "type": "address" + }, + { + "internalType": "address", + "name": "vTokenCollateral", + "type": "address" + }, + { + "internalType": "address", + "name": "liquidator", + "type": "address" + }, + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "actualRepayAmount", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "seizeTokens", + "type": "uint256" + } + ], + "name": "liquidateBorrowVerify", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "vTokenBorrowed", + "type": "address" + }, + { + "internalType": "address", + "name": "vTokenCollateral", + "type": "address" + }, + { + "internalType": "uint256", + "name": "actualRepayAmount", + "type": "uint256" + } + ], + "name": "liquidateCalculateSeizeTokens", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "vTokenCollateral", + "type": "address" + }, + { + "internalType": "uint256", + "name": "actualRepayAmount", + "type": "uint256" + } + ], + "name": "liquidateVAICalculateSeizeTokens", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "liquidationIncentiveMantissa", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "liquidatorContract", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "markets", + "outputs": [ + { + "internalType": "bool", + "name": "isListed", + "type": "bool" + }, + { + "internalType": "uint256", + "name": "collateralFactorMantissa", + "type": "uint256" + }, + { + "internalType": "bool", + "name": "isVenus", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "maxAssets", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "minReleaseAmount", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vToken", + "type": "address" + }, + { + "internalType": "address", + "name": "minter", + "type": "address" + }, + { + "internalType": "uint256", + "name": "mintAmount", + "type": "uint256" + } + ], + "name": "mintAllowed", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "mintVAIGuardianPaused", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vToken", + "type": "address" + }, + { + "internalType": "address", + "name": "minter", + "type": "address" + }, + { + "internalType": "uint256", + "name": "actualMintAmount", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "mintTokens", + "type": "uint256" + } + ], + "name": "mintVerify", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "mintedVAIs", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "oracle", + "outputs": [ + { + "internalType": "contract PriceOracle", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "pauseGuardian", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "pendingAdmin", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "pendingComptrollerImplementation", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "protocolPaused", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vToken", + "type": "address" + }, + { + "internalType": "address", + "name": "redeemer", + "type": "address" + }, + { + "internalType": "uint256", + "name": "redeemTokens", + "type": "uint256" + } + ], + "name": "redeemAllowed", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vToken", + "type": "address" + }, + { + "internalType": "address", + "name": "redeemer", + "type": "address" + }, + { + "internalType": "uint256", + "name": "redeemAmount", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "redeemTokens", + "type": "uint256" + } + ], + "name": "redeemVerify", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "releaseStartBlock", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [], + "name": "releaseToVault", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vToken", + "type": "address" + }, + { + "internalType": "address", + "name": "payer", + "type": "address" + }, + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "repayAmount", + "type": "uint256" + } + ], + "name": "repayBorrowAllowed", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vToken", + "type": "address" + }, + { + "internalType": "address", + "name": "payer", + "type": "address" + }, + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "actualRepayAmount", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "borrowerIndex", + "type": "uint256" + } + ], + "name": "repayBorrowVerify", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "repayVAIGuardianPaused", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vTokenCollateral", + "type": "address" + }, + { + "internalType": "address", + "name": "vTokenBorrowed", + "type": "address" + }, + { + "internalType": "address", + "name": "liquidator", + "type": "address" + }, + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "seizeTokens", + "type": "uint256" + } + ], + "name": "seizeAllowed", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vTokenCollateral", + "type": "address" + }, + { + "internalType": "address", + "name": "vTokenBorrowed", + "type": "address" + }, + { + "internalType": "address", + "name": "liquidator", + "type": "address" + }, + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "seizeTokens", + "type": "uint256" + } + ], + "name": "seizeVerify", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "owner", + "type": "address" + }, + { + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "setMintedVAIOf", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "supplyCaps", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vToken", + "type": "address" + }, + { + "internalType": "address", + "name": "src", + "type": "address" + }, + { + "internalType": "address", + "name": "dst", + "type": "address" + }, + { + "internalType": "uint256", + "name": "transferTokens", + "type": "uint256" + } + ], + "name": "transferAllowed", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "vToken", + "type": "address" + }, + { + "internalType": "address", + "name": "src", + "type": "address" + }, + { + "internalType": "address", + "name": "dst", + "type": "address" + }, + { + "internalType": "uint256", + "name": "transferTokens", + "type": "uint256" + } + ], + "name": "transferVerify", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "treasuryAddress", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "treasuryGuardian", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "treasuryPercent", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "delegate", + "type": "address" + }, + { + "internalType": "bool", + "name": "allowBorrows", + "type": "bool" + } + ], + "name": "updateDelegate", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "vaiController", + "outputs": [ + { + "internalType": "contract VAIControllerInterface", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "vaiMintRate", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "vaiVaultAddress", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "venusAccrued", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "venusBorrowSpeeds", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "venusBorrowState", + "outputs": [ + { + "internalType": "uint224", + "name": "index", + "type": "uint224" + }, + { + "internalType": "uint32", + "name": "block", + "type": "uint32" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + }, + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "venusBorrowerIndex", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "venusInitialIndex", + "outputs": [ + { + "internalType": "uint224", + "name": "", + "type": "uint224" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "venusRate", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "venusSpeeds", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + }, + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "venusSupplierIndex", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "venusSupplySpeeds", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "venusSupplyState", + "outputs": [ + { + "internalType": "uint224", + "name": "index", + "type": "uint224" + }, + { + "internalType": "uint32", + "name": "block", + "type": "uint32" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "venusVAIVaultRate", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + } +] diff --git a/simulations/vip-174/abi/IERC20UpgradableAbi.json b/simulations/vip-174/abi/IERC20UpgradableAbi.json new file mode 100644 index 000000000..374b04c75 --- /dev/null +++ b/simulations/vip-174/abi/IERC20UpgradableAbi.json @@ -0,0 +1,295 @@ +[ + { + "inputs": [ + { "internalType": "string", "name": "name_", "type": "string" }, + { "internalType": "string", "name": "symbol_", "type": "string" } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": true, "internalType": "address", "name": "owner", "type": "address" }, + { "indexed": true, "internalType": "address", "name": "spender", "type": "address" }, + { "indexed": false, "internalType": "uint256", "name": "value", "type": "uint256" } + ], + "name": "Approval", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": false, "internalType": "address", "name": "userAddress", "type": "address" }, + { "indexed": false, "internalType": "address payable", "name": "relayerAddress", "type": "address" }, + { "indexed": false, "internalType": "bytes", "name": "functionSignature", "type": "bytes" } + ], + "name": "MetaTransactionExecuted", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": true, "internalType": "bytes32", "name": "role", "type": "bytes32" }, + { "indexed": true, "internalType": "bytes32", "name": "previousAdminRole", "type": "bytes32" }, + { "indexed": true, "internalType": "bytes32", "name": "newAdminRole", "type": "bytes32" } + ], + "name": "RoleAdminChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": true, "internalType": "bytes32", "name": "role", "type": "bytes32" }, + { "indexed": true, "internalType": "address", "name": "account", "type": "address" }, + { "indexed": true, "internalType": "address", "name": "sender", "type": "address" } + ], + "name": "RoleGranted", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": true, "internalType": "bytes32", "name": "role", "type": "bytes32" }, + { "indexed": true, "internalType": "address", "name": "account", "type": "address" }, + { "indexed": true, "internalType": "address", "name": "sender", "type": "address" } + ], + "name": "RoleRevoked", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": true, "internalType": "address", "name": "from", "type": "address" }, + { "indexed": true, "internalType": "address", "name": "to", "type": "address" }, + { "indexed": false, "internalType": "uint256", "name": "value", "type": "uint256" } + ], + "name": "Transfer", + "type": "event" + }, + { + "inputs": [], + "name": "DEFAULT_ADMIN_ROLE", + "outputs": [{ "internalType": "bytes32", "name": "", "type": "bytes32" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "ERC712_VERSION", + "outputs": [{ "internalType": "string", "name": "", "type": "string" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "PREDICATE_ROLE", + "outputs": [{ "internalType": "bytes32", "name": "", "type": "bytes32" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { "internalType": "address", "name": "owner", "type": "address" }, + { "internalType": "address", "name": "spender", "type": "address" } + ], + "name": "allowance", + "outputs": [{ "internalType": "uint256", "name": "", "type": "uint256" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { "internalType": "address", "name": "spender", "type": "address" }, + { "internalType": "uint256", "name": "amount", "type": "uint256" } + ], + "name": "approve", + "outputs": [{ "internalType": "bool", "name": "", "type": "bool" }], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [{ "internalType": "address", "name": "account", "type": "address" }], + "name": "balanceOf", + "outputs": [{ "internalType": "uint256", "name": "", "type": "uint256" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "decimals", + "outputs": [{ "internalType": "uint8", "name": "", "type": "uint8" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { "internalType": "address", "name": "spender", "type": "address" }, + { "internalType": "uint256", "name": "subtractedValue", "type": "uint256" } + ], + "name": "decreaseAllowance", + "outputs": [{ "internalType": "bool", "name": "", "type": "bool" }], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { "internalType": "address", "name": "userAddress", "type": "address" }, + { "internalType": "bytes", "name": "functionSignature", "type": "bytes" }, + { "internalType": "bytes32", "name": "sigR", "type": "bytes32" }, + { "internalType": "bytes32", "name": "sigS", "type": "bytes32" }, + { "internalType": "uint8", "name": "sigV", "type": "uint8" } + ], + "name": "executeMetaTransaction", + "outputs": [{ "internalType": "bytes", "name": "", "type": "bytes" }], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [], + "name": "getChainId", + "outputs": [{ "internalType": "uint256", "name": "", "type": "uint256" }], + "stateMutability": "pure", + "type": "function" + }, + { + "inputs": [], + "name": "getDomainSeperator", + "outputs": [{ "internalType": "bytes32", "name": "", "type": "bytes32" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [{ "internalType": "address", "name": "user", "type": "address" }], + "name": "getNonce", + "outputs": [{ "internalType": "uint256", "name": "nonce", "type": "uint256" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [{ "internalType": "bytes32", "name": "role", "type": "bytes32" }], + "name": "getRoleAdmin", + "outputs": [{ "internalType": "bytes32", "name": "", "type": "bytes32" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { "internalType": "bytes32", "name": "role", "type": "bytes32" }, + { "internalType": "uint256", "name": "index", "type": "uint256" } + ], + "name": "getRoleMember", + "outputs": [{ "internalType": "address", "name": "", "type": "address" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [{ "internalType": "bytes32", "name": "role", "type": "bytes32" }], + "name": "getRoleMemberCount", + "outputs": [{ "internalType": "uint256", "name": "", "type": "uint256" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { "internalType": "bytes32", "name": "role", "type": "bytes32" }, + { "internalType": "address", "name": "account", "type": "address" } + ], + "name": "grantRole", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { "internalType": "bytes32", "name": "role", "type": "bytes32" }, + { "internalType": "address", "name": "account", "type": "address" } + ], + "name": "hasRole", + "outputs": [{ "internalType": "bool", "name": "", "type": "bool" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { "internalType": "address", "name": "spender", "type": "address" }, + { "internalType": "uint256", "name": "addedValue", "type": "uint256" } + ], + "name": "increaseAllowance", + "outputs": [{ "internalType": "bool", "name": "", "type": "bool" }], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { "internalType": "address", "name": "user", "type": "address" }, + { "internalType": "uint256", "name": "amount", "type": "uint256" } + ], + "name": "mint", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [{ "internalType": "string", "name": "", "type": "string" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { "internalType": "bytes32", "name": "role", "type": "bytes32" }, + { "internalType": "address", "name": "account", "type": "address" } + ], + "name": "renounceRole", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { "internalType": "bytes32", "name": "role", "type": "bytes32" }, + { "internalType": "address", "name": "account", "type": "address" } + ], + "name": "revokeRole", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "symbol", + "outputs": [{ "internalType": "string", "name": "", "type": "string" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "totalSupply", + "outputs": [{ "internalType": "uint256", "name": "", "type": "uint256" }], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { "internalType": "address", "name": "recipient", "type": "address" }, + { "internalType": "uint256", "name": "amount", "type": "uint256" } + ], + "name": "transfer", + "outputs": [{ "internalType": "bool", "name": "", "type": "bool" }], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { "internalType": "address", "name": "sender", "type": "address" }, + { "internalType": "address", "name": "recipient", "type": "address" }, + { "internalType": "uint256", "name": "amount", "type": "uint256" } + ], + "name": "transferFrom", + "outputs": [{ "internalType": "bool", "name": "", "type": "bool" }], + "stateMutability": "nonpayable", + "type": "function" + } +] diff --git a/simulations/vip-174/abi/VBep20DelegateAbi.json b/simulations/vip-174/abi/VBep20DelegateAbi.json new file mode 100644 index 000000000..0f6421ac5 --- /dev/null +++ b/simulations/vip-174/abi/VBep20DelegateAbi.json @@ -0,0 +1,1539 @@ +[ + { + "inputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "cashPrior", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "interestAccumulated", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "borrowIndex", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "totalBorrows", + "type": "uint256" + } + ], + "name": "AccrueInterest", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "owner", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "spender", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "Approval", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "borrowAmount", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "accountBorrows", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "totalBorrows", + "type": "uint256" + } + ], + "name": "Borrow", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "error", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "info", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "detail", + "type": "uint256" + } + ], + "name": "Failure", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "liquidator", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "repayAmount", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "address", + "name": "vTokenCollateral", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "seizeTokens", + "type": "uint256" + } + ], + "name": "LiquidateBorrow", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "minter", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "mintAmount", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "mintTokens", + "type": "uint256" + } + ], + "name": "Mint", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "payer", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "receiver", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "mintAmount", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "mintTokens", + "type": "uint256" + } + ], + "name": "MintBehalf", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "oldAdmin", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "newAdmin", + "type": "address" + } + ], + "name": "NewAdmin", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "contract ComptrollerInterface", + "name": "oldComptroller", + "type": "address" + }, + { + "indexed": false, + "internalType": "contract ComptrollerInterface", + "name": "newComptroller", + "type": "address" + } + ], + "name": "NewComptroller", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "contract InterestRateModel", + "name": "oldInterestRateModel", + "type": "address" + }, + { + "indexed": false, + "internalType": "contract InterestRateModel", + "name": "newInterestRateModel", + "type": "address" + } + ], + "name": "NewMarketInterestRateModel", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "oldPendingAdmin", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "newPendingAdmin", + "type": "address" + } + ], + "name": "NewPendingAdmin", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "oldReserveFactorMantissa", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newReserveFactorMantissa", + "type": "uint256" + } + ], + "name": "NewReserveFactor", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "redeemer", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "redeemAmount", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "redeemTokens", + "type": "uint256" + } + ], + "name": "Redeem", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "redeemer", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "feeAmount", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "redeemTokens", + "type": "uint256" + } + ], + "name": "RedeemFee", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "payer", + "type": "address" + }, + { + "indexed": false, + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "repayAmount", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "accountBorrows", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "totalBorrows", + "type": "uint256" + } + ], + "name": "RepayBorrow", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "benefactor", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "addAmount", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newTotalReserves", + "type": "uint256" + } + ], + "name": "ReservesAdded", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "address", + "name": "admin", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "reduceAmount", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "newTotalReserves", + "type": "uint256" + } + ], + "name": "ReservesReduced", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "from", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "to", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "Transfer", + "type": "event" + }, + { + "constant": false, + "inputs": [], + "name": "_acceptAdmin", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "addAmount", + "type": "uint256" + } + ], + "name": "_addReserves", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + } + ], + "name": "_becomeImplementation", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "reduceAmount", + "type": "uint256" + } + ], + "name": "_reduceReserves", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [], + "name": "_resignImplementation", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract ComptrollerInterface", + "name": "newComptroller", + "type": "address" + } + ], + "name": "_setComptroller", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract InterestRateModel", + "name": "newInterestRateModel", + "type": "address" + } + ], + "name": "_setInterestRateModel", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address payable", + "name": "newPendingAdmin", + "type": "address" + } + ], + "name": "_setPendingAdmin", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "newReserveFactorMantissa", + "type": "uint256" + } + ], + "name": "_setReserveFactor", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "accrualBlockNumber", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [], + "name": "accrueInterest", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "admin", + "outputs": [ + { + "internalType": "address payable", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "owner", + "type": "address" + }, + { + "internalType": "address", + "name": "spender", + "type": "address" + } + ], + "name": "allowance", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "spender", + "type": "address" + }, + { + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "approve", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "owner", + "type": "address" + } + ], + "name": "balanceOf", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "owner", + "type": "address" + } + ], + "name": "balanceOfUnderlying", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "borrowAmount", + "type": "uint256" + } + ], + "name": "borrow", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "account", + "type": "address" + } + ], + "name": "borrowBalanceCurrent", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "account", + "type": "address" + } + ], + "name": "borrowBalanceStored", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "borrowAmount", + "type": "uint256" + } + ], + "name": "borrowBehalf", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "borrowIndex", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "borrowRatePerBlock", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "comptroller", + "outputs": [ + { + "internalType": "contract ComptrollerInterface", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "decimals", + "outputs": [ + { + "internalType": "uint8", + "name": "", + "type": "uint8" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [], + "name": "exchangeRateCurrent", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "exchangeRateStored", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [ + { + "internalType": "address", + "name": "account", + "type": "address" + } + ], + "name": "getAccountSnapshot", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "getCash", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "implementation", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "underlying_", + "type": "address" + }, + { + "internalType": "contract ComptrollerInterface", + "name": "comptroller_", + "type": "address" + }, + { + "internalType": "contract InterestRateModel", + "name": "interestRateModel_", + "type": "address" + }, + { + "internalType": "uint256", + "name": "initialExchangeRateMantissa_", + "type": "uint256" + }, + { + "internalType": "string", + "name": "name_", + "type": "string" + }, + { + "internalType": "string", + "name": "symbol_", + "type": "string" + }, + { + "internalType": "uint8", + "name": "decimals_", + "type": "uint8" + } + ], + "name": "initialize", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "contract ComptrollerInterface", + "name": "comptroller_", + "type": "address" + }, + { + "internalType": "contract InterestRateModel", + "name": "interestRateModel_", + "type": "address" + }, + { + "internalType": "uint256", + "name": "initialExchangeRateMantissa_", + "type": "uint256" + }, + { + "internalType": "string", + "name": "name_", + "type": "string" + }, + { + "internalType": "string", + "name": "symbol_", + "type": "string" + }, + { + "internalType": "uint8", + "name": "decimals_", + "type": "uint8" + } + ], + "name": "initialize", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "interestRateModel", + "outputs": [ + { + "internalType": "contract InterestRateModel", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "isVToken", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "repayAmount", + "type": "uint256" + }, + { + "internalType": "contract VTokenInterface", + "name": "vTokenCollateral", + "type": "address" + } + ], + "name": "liquidateBorrow", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "mintAmount", + "type": "uint256" + } + ], + "name": "mint", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "receiver", + "type": "address" + }, + { + "internalType": "uint256", + "name": "mintAmount", + "type": "uint256" + } + ], + "name": "mintBehalf", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "pendingAdmin", + "outputs": [ + { + "internalType": "address payable", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "redeemTokens", + "type": "uint256" + } + ], + "name": "redeem", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "redeemAmount", + "type": "uint256" + } + ], + "name": "redeemUnderlying", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "uint256", + "name": "repayAmount", + "type": "uint256" + } + ], + "name": "repayBorrow", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "repayAmount", + "type": "uint256" + } + ], + "name": "repayBorrowBehalf", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "reserveFactorMantissa", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "liquidator", + "type": "address" + }, + { + "internalType": "address", + "name": "borrower", + "type": "address" + }, + { + "internalType": "uint256", + "name": "seizeTokens", + "type": "uint256" + } + ], + "name": "seize", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "supplyRatePerBlock", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "symbol", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "totalBorrows", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [], + "name": "totalBorrowsCurrent", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "totalReserves", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "totalSupply", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "dst", + "type": "address" + }, + { + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "transfer", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { + "internalType": "address", + "name": "src", + "type": "address" + }, + { + "internalType": "address", + "name": "dst", + "type": "address" + }, + { + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "transferFrom", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "underlying", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "payable": false, + "stateMutability": "view", + "type": "function" + } +] diff --git a/simulations/vip-174/abi/priceOracleAbi.json b/simulations/vip-174/abi/priceOracleAbi.json new file mode 100644 index 000000000..2eb50681a --- /dev/null +++ b/simulations/vip-174/abi/priceOracleAbi.json @@ -0,0 +1,154 @@ +[ + { + "inputs": [{ "internalType": "uint256", "name": "maxStalePeriod_", "type": "uint256" }], + "payable": false, + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": false, "internalType": "address", "name": "feed", "type": "address" }, + { "indexed": false, "internalType": "string", "name": "symbol", "type": "string" } + ], + "name": "FeedSet", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": false, "internalType": "uint256", "name": "oldMaxStalePeriod", "type": "uint256" }, + { "indexed": false, "internalType": "uint256", "name": "newMaxStalePeriod", "type": "uint256" } + ], + "name": "MaxStalePeriodUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": false, "internalType": "address", "name": "oldAdmin", "type": "address" }, + { "indexed": false, "internalType": "address", "name": "newAdmin", "type": "address" } + ], + "name": "NewAdmin", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { "indexed": false, "internalType": "address", "name": "asset", "type": "address" }, + { "indexed": false, "internalType": "uint256", "name": "previousPriceMantissa", "type": "uint256" }, + { "indexed": false, "internalType": "uint256", "name": "requestedPriceMantissa", "type": "uint256" }, + { "indexed": false, "internalType": "uint256", "name": "newPriceMantissa", "type": "uint256" } + ], + "name": "PricePosted", + "type": "event" + }, + { + "constant": true, + "inputs": [], + "name": "admin", + "outputs": [{ "internalType": "address", "name": "", "type": "address" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [{ "internalType": "address", "name": "asset", "type": "address" }], + "name": "assetPrices", + "outputs": [{ "internalType": "uint256", "name": "", "type": "uint256" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [{ "internalType": "string", "name": "symbol", "type": "string" }], + "name": "getFeed", + "outputs": [{ "internalType": "contract AggregatorV2V3Interface", "name": "", "type": "address" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [{ "internalType": "contract VToken", "name": "vToken", "type": "address" }], + "name": "getUnderlyingPrice", + "outputs": [{ "internalType": "uint256", "name": "", "type": "uint256" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "isPriceOracle", + "outputs": [{ "internalType": "bool", "name": "", "type": "bool" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "maxStalePeriod", + "outputs": [{ "internalType": "uint256", "name": "", "type": "uint256" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [{ "internalType": "address", "name": "newAdmin", "type": "address" }], + "name": "setAdmin", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { "internalType": "address", "name": "asset", "type": "address" }, + { "internalType": "uint256", "name": "price", "type": "uint256" } + ], + "name": "setDirectPrice", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { "internalType": "string", "name": "symbol", "type": "string" }, + { "internalType": "address", "name": "feed", "type": "address" } + ], + "name": "setFeed", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [{ "internalType": "uint256", "name": "newMaxStalePeriod", "type": "uint256" }], + "name": "setMaxStalePeriod", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [ + { "internalType": "contract VToken", "name": "vToken", "type": "address" }, + { "internalType": "uint256", "name": "underlyingPriceMantissa", "type": "uint256" } + ], + "name": "setUnderlyingPrice", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + } +] diff --git a/simulations/vip-174/scripts/diamond.ts b/simulations/vip-174/scripts/diamond.ts new file mode 100644 index 000000000..27adab39a --- /dev/null +++ b/simulations/vip-174/scripts/diamond.ts @@ -0,0 +1,82 @@ +import { ethers } from "hardhat"; + +const FacetCutAction = { Add: 0, Replace: 1, Remove: 2 }; + +// get function selectors from ABI +function getSelectors(contract: any) { + const signatures = Object.keys(contract.interface.functions); + const selectors: any = signatures.reduce((acc: any, val) => { + if (val !== "init(bytes)") { + acc.push(contract.interface.getSighash(val)); + } + return acc; + }, []); + selectors.contract = contract; + selectors.remove = remove; + selectors.get = get; + return selectors; +} + +// get function selector from function signature +function getSelector(func: any) { + const abiInterface = new ethers.utils.Interface([func]); + return abiInterface.getSighash(ethers.utils.Fragment.from(func)); +} + +// used with getSelectors to remove selectors from an array of selectors +// functionNames argument is an array of function signatures +function remove(functionNames: any) { + const selectors = this.filter(v => { + for (const functionName of functionNames) { + if (v === this.contract.interface.getSighash(functionName)) { + return false; + } + } + return true; + }); + selectors.contract = this.contract; + selectors.remove = this.remove; + selectors.get = this.get; + return selectors; +} + +// used with getSelectors to get selectors from an array of selectors +// functionNames argument is an array of function signatures +function get(functionNames) { + const selectors = this.filter(v => { + for (const functionName of functionNames) { + if (v === this.contract.interface.getSighash(functionName)) { + return true; + } + } + return false; + }); + selectors.contract = this.contract; + selectors.remove = this.remove; + selectors.get = this.get; + return selectors; +} + +// remove selectors using an array of signatures +function removeSelectors(selectors, signatures) { + const iface = new ethers.utils.Interface(signatures.map(v => "function " + v)); + const removeSelectors = signatures.map(v => iface.getSighash(v)); + selectors = selectors.filter(v => !removeSelectors.includes(v)); + return selectors; +} + +// find a particular address position in the return value of diamondLoupeFacet.facets() +function findAddressPositionInFacets(facetAddress, facets) { + for (let i = 0; i < facets.length; i++) { + if (facets[i].facetAddress === facetAddress) { + return i; + } + } +} + +exports.getSelectors = getSelectors; +exports.getSelector = getSelector; +exports.FacetCutAction = FacetCutAction; +exports.remove = remove; +exports.removeSelectors = removeSelectors; +exports.findAddressPositionInFacets = findAddressPositionInFacets; diff --git a/simulations/vip-174/scripts/facet-cut-params-generator.ts b/simulations/vip-174/scripts/facet-cut-params-generator.ts new file mode 100644 index 000000000..0f0c5c41a --- /dev/null +++ b/simulations/vip-174/scripts/facet-cut-params-generator.ts @@ -0,0 +1,109 @@ +import fs from "fs"; +import { ethers } from "hardhat"; + +import { FacetCutAction, getSelectors } from "./diamond"; + +/** + * This script is used to generate the cut-params which will be used in diamond proxy vip + * to add diamond facets + */ + +// Insert the addresses of the deployed facets to generate thecut params according for the same. +const facetsAddresses: any = { + MarketFacet: "", + PolicyFacet: "", + RewardFacet: "", + SetterFacet: "", +}; + +// Set actions to the cut params to perform +// i.e. Add, Remove, Replace function selectors in the mapping. +const facetsActions: any = { + MarketFacet: FacetCutAction.Add, + PolicyFacet: FacetCutAction.Add, + RewardFacet: FacetCutAction.Add, + SetterFacet: FacetCutAction.Add, +}; + +// Set interfaces for the setters to generate function selectors from +const FacetsInterfaces: any = { + MarketFacet: "IMarketFacet", + PolicyFacet: "IPolicyFacet", + RewardFacet: "IRewardFacet", + SetterFacet: "ISetterFacet", +}; + +// Facets for which cute params need to generate +const FacetNames = ["MarketFacet", "PolicyFacet", "RewardFacet", "SetterFacet"]; + +// Name of the file to write the cut-params +const jsonFileName = "cur-params-test"; + +async function generateCutParams() { + const cut: any = []; + + for (const FacetName of FacetNames) { + const FacetInterface = await ethers.getContractAt(FacetsInterfaces[FacetName], facetsAddresses[FacetName]); + + switch (facetsActions[FacetName]) { + case FacetCutAction.Add: + cut.push({ + facetAddress: facetsAddresses[FacetName], + action: FacetCutAction.Add, + functionSelectors: getSelectors(FacetInterface), + }); + break; + case FacetCutAction.Remove: + cut.push({ + facetAddress: ethers.constants.AddressZero, + action: FacetCutAction.Remove, + functionSelectors: getSelectors(FacetInterface), + }); + break; + case FacetCutAction.Replace: + cut.push({ + facetAddress: facetsAddresses[FacetName], + action: FacetCutAction.Replace, + functionSelectors: getSelectors(FacetInterface), + }); + break; + default: + break; + } + } + + function getFunctionSelector(selectors: any) { + const functionSelector: any = []; + for (let i = 0; i < selectors.length; i++) { + if (selectors[i][0] == "0") { + functionSelector.push(selectors[i]); + } else { + break; + } + } + return functionSelector; + } + + function makeCutParam(cut: any) { + const cutParams = []; + for (let i = 0; i < cut.length; i++) { + const arr: any = new Array(3); + arr[0] = cut[i].facetAddress; + arr[1] = cut[i].action; + arr[2] = getFunctionSelector(cut[i].functionSelectors); + cutParams.push(arr); + } + return cutParams; + } + const cutParams = { cutParams: makeCutParam(cut) }; + + fs.writeFileSync(`./${jsonFileName}.json`, JSON.stringify(cutParams, null, 4)); + return cutParams; +} + +generateCutParams() + .then(() => process.exit(0)) + .catch(error => { + console.error(error); + process.exit(1); + }); diff --git a/simulations/vip-174/vip-174-testnet/simulations.ts b/simulations/vip-174/vip-174-testnet/simulations.ts new file mode 100644 index 000000000..936b33c18 --- /dev/null +++ b/simulations/vip-174/vip-174-testnet/simulations.ts @@ -0,0 +1,449 @@ +import { impersonateAccount } from "@nomicfoundation/hardhat-network-helpers"; +import { expect } from "chai"; +import { BigNumberish, Contract, Signer } from "ethers"; +import { parseUnits } from "ethers/lib/utils"; +import { ethers } from "hardhat"; + +import { initMainnetUser } from "../../../src/utils"; +import { forking, pretendExecutingVip, testVip } from "../../../src/vip-framework"; +import { vip174Testnet } from "../../../vips/vip-174/vip-174-testnet"; +import Comptroller from "../abi/Comptroller.json"; +import IERC20Upgradeable from "../abi/IERC20UpgradableAbi.json"; +import VBEP20_DELEGATE_ABI from "../abi/VBep20DelegateAbi.json"; + +const UNITROLLER = "0x94d1820b2D1c7c7452A163983Dc888CEC546b77D"; +const DIAMOND = "0x7e0298880224B8116F3462c50917249E94b3DC53"; + +const Owner = "0xce10739590001705F7FF231611ba4A48B2820327"; +const zeroAddr = ethers.constants.AddressZero; +const VBUSD = "0x08e0A5575De71037aE36AbfAfb516595fE68e5e4"; +const VUSDT = "0xb7526572FFE56AB9D7489838Bf2E18e3323b441A"; + +forking(33497000, async () => { + let owner: Signer, + unitroller: Contract, + // layout variables + oracle: Contract, + maxAssets: BigNumberish, + closeFactorMantissa: BigNumberish, + liquidationIncentiveMantissa: BigNumberish, + allMarkets: Array, + venusSupplyState: any, + venusBorrowState: any, + venusAccrued: BigNumberish, + vaiMintRate: BigNumberish, + vaiController: Contract, + mintedVAIs: BigNumberish, + mintVAIGuardianPaused: boolean, + repayVAIGuardianPaused: boolean, + protocolPaused: boolean, + venusVAIVaultRate: BigNumberish, + vaiVaultAddress: string, + releaseStartBlock: BigNumberish, + minReleaseAmount: BigNumberish, + treasuryGuardian: boolean, + treasuryAddress: string, + treasuryPercent: BigNumberish, + liquidatorContract: Contract, + comptrollerLens: Contract; + + const borrowSpeeds: any = {}; + const supplySpeeds: any = {}; + const userBorrowIndexes: any = {}; + const userSupplyIndexes: any = {}; + const markets: any = {}; + + let BUSD: Contract; + let busdHolder: Signer; + let vBUSD: Contract; + let vUSDT: Contract; + let diamondUnitroller: Contract; + + before(async () => { + unitroller = new ethers.Contract(UNITROLLER, Comptroller, ethers.provider); + + diamondUnitroller = new ethers.Contract(unitroller.address, Comptroller, ethers.provider); + + await impersonateAccount(Owner); + owner = await ethers.getSigner(Owner); + const [signer] = await ethers.getSigners(); + await signer.sendTransaction({ + to: await owner.getAddress(), + value: ethers.BigNumber.from("10000000000000000000"), + data: undefined, + }); + + busdHolder = await initMainnetUser("0xC825AD791A6046991e3706b6342970f6d87e4888", parseUnits("1000", 18)); + + [vBUSD, vUSDT] = await Promise.all( + [VBUSD, VUSDT].map((address: string) => { + return new ethers.Contract(address, VBEP20_DELEGATE_ABI, ethers.provider); + }), + ); + + [BUSD] = await Promise.all( + [vBUSD].map(async (vToken: Contract) => { + const underlying = await vToken.underlying(); + return new ethers.Contract(underlying, IERC20Upgradeable, ethers.provider); + }), + ); + }); + + describe("Verify Storage slots before vip execution", async () => { + // These tests checks the storage collision of comptroller while updating it via diamond. + describe("Diamond deployed successfully before vip execution", async () => { + it("Owner of Diamond unitroller contract should match", async () => { + const UnitrollerAdmin = await unitroller.admin(); + const pendingAdmin = await unitroller.pendingAdmin(); + expect(UnitrollerAdmin.toLowerCase()).to.equal(Owner.toLowerCase()); + expect(pendingAdmin.toLowerCase()).to.equal(zeroAddr); + }); + + it("Diamond Unitroller Implementation (comptroller) should match the old comptroller address", async () => { + const comptrollerImplementation = await unitroller.comptrollerImplementation(); + const pendingComptrollerImplementation = await unitroller.pendingComptrollerImplementation(); + expect(comptrollerImplementation.toLowerCase()).to.equal( + "0xa8a476ad16727ce641f27d7738d2d341ebad81cc".toLowerCase(), + ); + expect(pendingComptrollerImplementation.toLowerCase()).to.equal(zeroAddr); + }); + }); + + describe("Verify storage layout before vip execution", async () => { + it("verify all the state before and after upgrade", async () => { + oracle = await unitroller.oracle(); + + maxAssets = await unitroller.maxAssets(); + + closeFactorMantissa = await unitroller.closeFactorMantissa(); + + liquidationIncentiveMantissa = await unitroller.liquidationIncentiveMantissa(); + + venusSupplyState = await unitroller.venusSupplyState(BUSD.address); + + venusBorrowState = await unitroller.venusBorrowState(BUSD.address); + + venusAccrued = await unitroller.venusAccrued(BUSD.address); + + vaiMintRate = await unitroller.vaiMintRate(); + + vaiController = await unitroller.vaiController(); + + mintedVAIs = await unitroller.mintedVAIs(await busdHolder.getAddress()); + + mintVAIGuardianPaused = await unitroller.mintVAIGuardianPaused(); + + repayVAIGuardianPaused = await unitroller.repayVAIGuardianPaused(); + + protocolPaused = await unitroller.protocolPaused(); + + venusVAIVaultRate = await unitroller.venusVAIVaultRate(); + + vaiVaultAddress = await unitroller.vaiVaultAddress(); + + releaseStartBlock = await unitroller.releaseStartBlock(); + + minReleaseAmount = await unitroller.minReleaseAmount(); + + treasuryGuardian = await unitroller.treasuryGuardian(); + + treasuryAddress = await unitroller.treasuryAddress(); + + treasuryPercent = await unitroller.treasuryPercent(); + + liquidatorContract = await unitroller.liquidatorContract(); + + comptrollerLens = await unitroller.comptrollerLens(); + + // checking all public mappings + allMarkets = await unitroller.getAllMarkets(); + + for (const marketIndex in allMarkets) { + const marketAddress = allMarkets[marketIndex].toString(); + + borrowSpeeds[marketAddress] = await unitroller.venusBorrowSpeeds(marketAddress); + supplySpeeds[marketAddress] = await unitroller.venusSupplySpeeds(marketAddress); + markets[marketAddress] = await unitroller.markets(marketAddress); + + userBorrowIndexes[marketAddress] = await unitroller.venusBorrowerIndex( + marketAddress, + await busdHolder.getAddress(), + ); + userSupplyIndexes[marketAddress] = await unitroller.venusSupplierIndex( + marketAddress, + await busdHolder.getAddress(), + ); + } + }); + }); + }); + + testVip("VIP-Diamond Contract Migration", vip174Testnet()); + + describe("Verify Storage slots after VIP execution", async () => { + // These tests checks the storage collision of comptroller while updating it via diamond. + describe("Diamond deployed successfully after VIP execution", async () => { + it("Owner of Diamond unitroller contract should match", async () => { + const diamondUnitrollerAdmin = await diamondUnitroller.admin(); + const pendingAdmin = await diamondUnitroller.pendingAdmin(); + expect(diamondUnitrollerAdmin.toLowerCase()).to.equal(Owner.toLowerCase()); + expect(pendingAdmin.toLowerCase()).to.equal(zeroAddr); + }); + + it("Diamond Unitroller Implementation (comptroller) should match the comptroller implementation Address", async () => { + const comptrollerImplementation = await diamondUnitroller.comptrollerImplementation(); + const pendingComptrollerImplementation = await diamondUnitroller.pendingComptrollerImplementation(); + expect(comptrollerImplementation.toLowerCase()).to.equal(DIAMOND.toLowerCase()); + expect(pendingComptrollerImplementation.toLowerCase()).to.equal(zeroAddr); + }); + }); + + describe("Verify storage layout after VIP execution", async () => { + it("verify all the state before and after upgrade", async () => { + const oracelUpgrade = await diamondUnitroller.oracle(); + expect(oracle).to.equal(oracelUpgrade); + + const maxAssetsAfterUpgrade = await diamondUnitroller.maxAssets(); + expect(maxAssets).to.equal(maxAssetsAfterUpgrade); + + const closeFactorMantissaAfterUpgrade = await diamondUnitroller.closeFactorMantissa(); + expect(closeFactorMantissa).to.equal(closeFactorMantissaAfterUpgrade); + + const liquidationIncentiveMantissaAfterUpgrade = await diamondUnitroller.liquidationIncentiveMantissa(); + expect(liquidationIncentiveMantissa).to.equal(liquidationIncentiveMantissaAfterUpgrade); + + const venusSupplyStateAfterUpgrade = await diamondUnitroller.venusSupplyState(BUSD.address); + expect(venusSupplyState.index.toString()).to.equal(venusSupplyStateAfterUpgrade.index.toString()); + + const venusBorrowStateAfterUpgrade = await diamondUnitroller.venusBorrowState(BUSD.address); + expect(venusBorrowState.index.toString()).to.equal(venusBorrowStateAfterUpgrade.index.toString()); + + const venusAccruedAfterUpgrade = await diamondUnitroller.venusAccrued(BUSD.address); + expect(venusAccrued).to.equal(venusAccruedAfterUpgrade); + + const vaiMintRateAfterUpgrade = await diamondUnitroller.vaiMintRate(); + expect(vaiMintRate).to.equal(vaiMintRateAfterUpgrade); + + const vaiControllerUpgrade = await diamondUnitroller.vaiController(); + expect(vaiControllerUpgrade).to.equal(vaiController); + + const mintedVAIsUpgrade = await diamondUnitroller.mintedVAIs(await busdHolder.getAddress()); + expect(mintedVAIsUpgrade).to.equal(mintedVAIs); + + const mintVAIGuardianPausedUpgrade = await diamondUnitroller.mintVAIGuardianPaused(); + expect(mintVAIGuardianPausedUpgrade).to.equal(mintVAIGuardianPaused); + + const repayVAIGuardianPausedUpgrade = await diamondUnitroller.repayVAIGuardianPaused(); + expect(repayVAIGuardianPausedUpgrade).to.equal(repayVAIGuardianPaused); + + const protocolPausedUpgrade = await diamondUnitroller.protocolPaused(); + expect(protocolPausedUpgrade).to.equal(protocolPaused); + + const venusVAIVaultRateUpgrade = await diamondUnitroller.venusVAIVaultRate(); + expect(venusVAIVaultRateUpgrade).to.equal(venusVAIVaultRate); + + const vaiVaultAddressUpgrade = await diamondUnitroller.vaiVaultAddress(); + expect(vaiVaultAddressUpgrade).to.equal(vaiVaultAddress); + + const releaseStartBlockUpgrade = await diamondUnitroller.releaseStartBlock(); + expect(releaseStartBlockUpgrade).to.equal(releaseStartBlock); + + const minReleaseAmountUpgrade = await diamondUnitroller.minReleaseAmount(); + expect(minReleaseAmountUpgrade).to.equal(minReleaseAmount); + + const treasuryGuardianUpgrade = await diamondUnitroller.treasuryGuardian(); + expect(treasuryGuardian).to.equal(treasuryGuardianUpgrade); + + const treasuryAddressUpgrade = await diamondUnitroller.treasuryAddress(); + expect(treasuryAddress).to.equal(treasuryAddressUpgrade); + + const treasuryPercentUpgrade = await diamondUnitroller.treasuryPercent(); + expect(treasuryPercent).to.equal(treasuryPercentUpgrade); + + const liquidatorContractUpgrade = await diamondUnitroller.liquidatorContract(); + expect(liquidatorContract).to.equal(liquidatorContractUpgrade); + + const comptrollerLensUpgrade = await diamondUnitroller.comptrollerLens(); + expect(comptrollerLens).to.equal(comptrollerLensUpgrade); + + // checking all public mappings + for (const marketIndex in allMarkets) { + const marketAddress = allMarkets[marketIndex].toString(); + + const marketUpgrade = await diamondUnitroller.markets(marketAddress); + expect(markets[marketAddress].collateralFactorMantissa).to.equal(marketUpgrade.collateralFactorMantissa); + expect(markets[marketAddress].isListed).to.equal(marketUpgrade.isListed); + expect(markets[marketAddress].isVenus).to.equal(marketUpgrade.isVenus); + + const venusBorrowSpeed = await diamondUnitroller.venusBorrowSpeeds(marketAddress); + const venusSupplySpeed = await diamondUnitroller.venusSupplySpeeds(marketAddress); + expect(borrowSpeeds[marketAddress]).to.equal(venusBorrowSpeed); + expect(supplySpeeds[marketAddress]).to.equal(venusSupplySpeed); + + const userBorrowIndex = await diamondUnitroller.venusBorrowerIndex( + marketAddress, + await busdHolder.getAddress(), + ); + const userSupplyIndex = await diamondUnitroller.venusSupplierIndex( + marketAddress, + await busdHolder.getAddress(), + ); + expect(userBorrowIndexes[marketAddress]).to.equal(userBorrowIndex); + expect(userSupplyIndexes[marketAddress]).to.equal(userSupplyIndex); + } + }); + }); + }); + + describe("Verify states of diamond Contract", () => { + describe("Diamond setters", () => { + it("setting market supply cap", async () => { + const currentSupplyCap = (await diamondUnitroller.supplyCaps(vBUSD.address)).toString(); + await diamondUnitroller.connect(owner)._setMarketSupplyCaps([vBUSD.address], [parseUnits("100000", 18)]); + expect(await diamondUnitroller.supplyCaps(vBUSD.address)).to.equals(parseUnits("100000", 18)); + await diamondUnitroller.connect(owner)._setMarketSupplyCaps([vBUSD.address], [parseUnits(currentSupplyCap, 0)]); + expect(await diamondUnitroller.supplyCaps(vBUSD.address)).to.equals(parseUnits(currentSupplyCap, 0)); + }); + + it("setting close factor", async () => { + const currentCloseFactor = (await diamondUnitroller.closeFactorMantissa()).toString(); + await diamondUnitroller.connect(owner)._setCloseFactor(parseUnits("1", 17)); + expect(await diamondUnitroller.closeFactorMantissa()).to.equals(parseUnits("1", 17)); + await diamondUnitroller.connect(owner)._setCloseFactor(parseUnits(currentCloseFactor, 0)); + expect(await diamondUnitroller.closeFactorMantissa()).to.equals(parseUnits(currentCloseFactor, 0)); + }); + + it("setting Liquidation Incentive", async () => { + await diamondUnitroller.connect(owner)._setLiquidationIncentive(parseUnits("13", 17)); + expect(await diamondUnitroller.liquidationIncentiveMantissa()).to.equal(parseUnits("13", 17)); + + await diamondUnitroller.connect(owner)._setLiquidationIncentive(parseUnits("11", 17)); + expect(await diamondUnitroller.liquidationIncentiveMantissa()).to.equal(parseUnits("11", 17)); + }); + + it("setting Pause Guardian", async () => { + const currentPauseGuardia = (await diamondUnitroller.pauseGuardian()).toString(); + + await diamondUnitroller.connect(owner)._setPauseGuardian(await owner.getAddress()); + expect(await diamondUnitroller.pauseGuardian()).to.equal(await owner.getAddress()); + + await diamondUnitroller.connect(owner)._setPauseGuardian(currentPauseGuardia); + expect(await diamondUnitroller.pauseGuardian()).to.equal(currentPauseGuardia); + }); + + it("setting market borrow cap", async () => { + const currentBorrowCap = (await diamondUnitroller.borrowCaps(vUSDT.address)).toString(); + await diamondUnitroller.connect(owner)._setMarketBorrowCaps([vUSDT.address], [parseUnits("10000", 18)]); + expect(await diamondUnitroller.borrowCaps(vUSDT.address)).to.equal(parseUnits("10000", 18)); + + await diamondUnitroller.connect(owner)._setMarketBorrowCaps([vUSDT.address], [currentBorrowCap]); + expect(await diamondUnitroller.borrowCaps(vUSDT.address)).to.equal(currentBorrowCap); + }); + + it("pausing mint action in vBUSD", async () => { + const isActionPaused = await diamondUnitroller.actionPaused(VBUSD, 0); + + await diamondUnitroller.connect(owner)._setActionsPaused([VBUSD], [0], !isActionPaused); + + await expect(await diamondUnitroller.actionPaused(VBUSD, 0)).to.be.equal(!isActionPaused); + + if (!isActionPaused) { + await diamondUnitroller.connect(owner)._setActionsPaused([VBUSD], [0], false); + } + }); + }); + }); +}); + +forking(33497000, async () => { + let owner, unitroller; + let USDT: Contract; + let usdtHolder: Signer; + let vUSDT: Contract; + let diamondUnitroller: Contract; + + before(async () => { + await pretendExecutingVip(vip174Testnet()); + unitroller = new ethers.Contract(UNITROLLER, Comptroller, ethers.provider); + + diamondUnitroller = new ethers.Contract(unitroller.address, Comptroller, ethers.provider); + + await impersonateAccount(Owner); + owner = await ethers.getSigner(Owner); + const [signer] = await ethers.getSigners(); + await signer.sendTransaction({ + to: owner.address, + value: ethers.BigNumber.from("10000000000000000000"), + data: undefined, + }); + + usdtHolder = await initMainnetUser("0xa0747a72C329377C2CE4F0F3165197B3a5359EfE", parseUnits("1000", 18)); + + [vUSDT] = await Promise.all( + [VUSDT].map((address: string) => { + return new ethers.Contract(address, VBEP20_DELEGATE_ABI, ethers.provider); + }), + ); + [USDT] = await Promise.all( + [vUSDT].map(async (vToken: Contract) => { + const underlying = await vToken.underlying(); + return new ethers.Contract(underlying, IERC20Upgradeable, ethers.provider); + }), + ); + await diamondUnitroller.connect(owner)._setActionsPaused([VBUSD], [0], false); + }); + + describe("Diamond Hooks", () => { + it("Diamond Unitroller Implementation (comptroller) should match the diamond Proxy Address", async () => { + const comptrollerImplementation = await diamondUnitroller.comptrollerImplementation(); + const pendingComptrollerImplementation = await diamondUnitroller.pendingComptrollerImplementation(); + expect(comptrollerImplementation.toLowerCase()).to.equal(DIAMOND.toLowerCase()); + expect(pendingComptrollerImplementation.toLowerCase()).to.equal(zeroAddr); + }); + + it("mint vToken vUSDT", async () => { + const vUSDTBalance = await USDT.balanceOf(vUSDT.address); + const usdtHolderBalance = await USDT.balanceOf(await usdtHolder.getAddress()); + await USDT.connect(usdtHolder).approve(vUSDT.address, 2000); + await vUSDT.connect(usdtHolder).mint(2000); + const newvUSDTBalance = await USDT.balanceOf(vUSDT.address); + const newUsdtHolderBalance = await USDT.balanceOf(await usdtHolder.getAddress()); + + expect(newvUSDTBalance).greaterThan(vUSDTBalance); + expect(newUsdtHolderBalance).lessThan(usdtHolderBalance); + }); + + it("redeem vToken", async () => { + await USDT.connect(usdtHolder).approve(vUSDT.address, 2000); + await expect(vUSDT.connect(usdtHolder).mint(2000)).to.emit(vUSDT, "Mint"); + + const vUSDTUserBal = await vUSDT.connect(usdtHolder).balanceOf(await usdtHolder.getAddress()); + await expect(vUSDT.connect(usdtHolder).redeem(2000)).to.emit(vUSDT, "Redeem"); + const newVUSDTUserBal = await vUSDT.connect(usdtHolder).balanceOf(await usdtHolder.getAddress()); + + expect(newVUSDTUserBal).to.equal(vUSDTUserBal.sub(2000)); + }); + + it("borrow vToken", async () => { + const usdtUserBal = await USDT.balanceOf(await usdtHolder.getAddress()); + + await expect(vUSDT.connect(usdtHolder).borrow(1000)).to.emit(vUSDT, "Borrow"); + + expect((await USDT.balanceOf(await usdtHolder.getAddress())).toString()).to.equal(usdtUserBal.add(1000)); + }); + + it("Repay vToken", async () => { + await USDT.connect(usdtHolder).approve(vUSDT.address, 2000); + + const usdtUserBal = await USDT.balanceOf(await usdtHolder.getAddress()); + await vUSDT.connect(usdtHolder).borrow(1000); + + expect((await USDT.balanceOf(await usdtHolder.getAddress())).toString()).to.greaterThan(usdtUserBal); + + await vUSDT.connect(usdtHolder).repayBorrow(1000); + + const balanceAfterRepay = await USDT.balanceOf(await usdtHolder.getAddress()); + expect(balanceAfterRepay).to.equal(usdtUserBal); + }); + }); +}); diff --git a/simulations/vip-174/vip-174-testnet/utils/cut-params.json b/simulations/vip-174/vip-174-testnet/utils/cut-params.json new file mode 100644 index 000000000..39f5e03c1 --- /dev/null +++ b/simulations/vip-174/vip-174-testnet/utils/cut-params.json @@ -0,0 +1,83 @@ +{ + "cutParams": [ + [ + "0x1B9806d9d2925e8Cd318E268e562eeb7e02C6E00", + 0, + [ + "0xa76b3fda", + "0x929fe9a1", + "0xc2998238", + "0xede4edd0", + "0xb0772d0b", + "0xabfceffc", + "0x007e3dd2", + "0xc488847b", + "0xa78dc775", + "0xddbf54fd" + ] + ], + [ + "0xe13A002aff3c64A72F0b9eD72d7fd861C5E0F280", + 0, + [ + "0xead1a8a0", + "0xda3d454c", + "0x5c778605", + "0x5ec88c79", + "0x4e79238f", + "0x5fc7e71e", + "0x47ef3b3b", + "0x4ef4c3e1", + "0x41c728b9", + "0xeabe7d91", + "0x51dff989", + "0x24008a62", + "0x1ededc91", + "0xd02f7351", + "0x6d35bf91", + "0xbdcdc258", + "0x6a56947e" + ] + ], + [ + "0x19fB43e4b46DCB803208253E42F5D1800D2ACEca", + 0, + [ + "0xa7604b41", + "0xe85a2960", + "0x70bf66f0", + "0x86df31ee", + "0xadcd5fb9", + "0xd09c54ba", + "0x7858524d", + "0xbf32442d", + "0xededbae6" + ] + ], + [ + "0x68f0C17bf638AB86024B923c643fD15d3A6FC28B", + 0, + [ + "0xf519fc30", + "0x2b5d790c", + "0x317b0b77", + "0xe4028eee", + "0x9bf34cbb", + "0x522c656b", + "0x4fd42e17", + "0xbb857450", + "0x607ef6c1", + "0x51a485e4", + "0x5f5af1aa", + "0x55ee1fe1", + "0x2a6a6065", + "0xd24febad", + "0x9cfdd9e6", + "0x2ec04124", + "0x4e0853db", + "0x6662c7c9", + "0xfd51a3ad" + ] + ] + ] +} diff --git a/simulations/vip-174/vip-174/simulations.ts b/simulations/vip-174/vip-174/simulations.ts new file mode 100644 index 000000000..f010c30de --- /dev/null +++ b/simulations/vip-174/vip-174/simulations.ts @@ -0,0 +1,453 @@ +import { impersonateAccount } from "@nomicfoundation/hardhat-network-helpers"; +import { expect } from "chai"; +import { BigNumberish, Contract, Signer } from "ethers"; +import { parseUnits } from "ethers/lib/utils"; +import { ethers } from "hardhat"; + +import { initMainnetUser } from "../../../src/utils"; +import { forking, pretendExecutingVip, testVip } from "../../../src/vip-framework"; +import { vip174 } from "../../../vips/vip-174/vip-174"; +import Comptroller from "../abi/Comptroller.json"; +import IERC20Upgradeable from "../abi/IERC20UpgradableAbi.json"; +import VBEP20_DELEGATE_ABI from "../abi/VBep20DelegateAbi.json"; + +const UNITROLLER = "0xfD36E2c2a6789Db23113685031d7F16329158384"; +const DIAMOND = "0xAd69AA3811fE0EE7dBd4e25C4bae40e6422c76C8"; + +const Owner = "0x939bD8d64c0A9583A7Dcea9933f7b21697ab6396"; +const zeroAddr = ethers.constants.AddressZero; +const VBUSD = "0x95c78222B3D6e262426483D42CfA53685A67Ab9D"; +const VUSDT = "0xfD5840Cd36d94D7229439859C0112a4185BC0255"; + +forking(31933620, async () => { + let owner: Signer, + unitroller: Contract, + // layout variables + oracle: Contract, + maxAssets: BigNumberish, + closeFactorMantissa: BigNumberish, + liquidationIncentiveMantissa: BigNumberish, + allMarkets: Array, + venusSupplyState: any, + venusBorrowState: any, + venusAccrued: BigNumberish, + vaiMintRate: BigNumberish, + vaiController: Contract, + mintedVAIs: BigNumberish, + mintVAIGuardianPaused: boolean, + repayVAIGuardianPaused: boolean, + protocolPaused: boolean, + venusVAIVaultRate: BigNumberish, + vaiVaultAddress: string, + releaseStartBlock: BigNumberish, + minReleaseAmount: BigNumberish, + treasuryGuardian: boolean, + treasuryAddress: string, + treasuryPercent: BigNumberish, + liquidatorContract: Contract, + comptrollerLens: Contract; + + const borrowSpeeds: any = {}; + const supplySpeeds: any = {}; + const userBorrowIndexes: any = {}; + const userSupplyIndexes: any = {}; + const markets: any = {}; + + let BUSD: Contract; + let busdHolder: Signer; + let vBUSD: Contract; + let vUSDT: Contract; + let diamondUnitroller: Contract; + + before(async () => { + unitroller = new ethers.Contract(UNITROLLER, Comptroller, ethers.provider); + + diamondUnitroller = new ethers.Contract(unitroller.address, Comptroller, ethers.provider); + + await impersonateAccount(Owner); + owner = await ethers.getSigner(Owner); + const [signer] = await ethers.getSigners(); + await signer.sendTransaction({ + to: await owner.getAddress(), + value: ethers.BigNumber.from("10000000000000000000"), + data: undefined, + }); + + busdHolder = await initMainnetUser("0x8894E0a0c962CB723c1976a4421c95949bE2D4E3", parseUnits("1000", 18)); + + [vBUSD, vUSDT] = await Promise.all( + [VBUSD, VUSDT].map((address: string) => { + return new ethers.Contract(address, VBEP20_DELEGATE_ABI, ethers.provider); + }), + ); + + [BUSD] = await Promise.all( + [vBUSD].map(async (vToken: Contract) => { + const underlying = await vToken.underlying(); + return new ethers.Contract(underlying, IERC20Upgradeable, ethers.provider); + }), + ); + }); + + describe("Verify Storage slots before vip execution", async () => { + // These tests checks the storage collision of comptroller while updating it via diamond. + describe("Diamond deployed successfully before vip execution", async () => { + it("Owner of Diamond unitroller contract should match", async () => { + const UnitrollerAdmin = await unitroller.admin(); + const pendingAdmin = await unitroller.pendingAdmin(); + expect(UnitrollerAdmin.toLowerCase()).to.equal(Owner.toLowerCase()); + expect(pendingAdmin.toLowerCase()).to.equal(zeroAddr); + }); + + it("Diamond Unitroller Implementation (comptroller) should match the old comptroller address", async () => { + const comptrollerImplementation = await unitroller.comptrollerImplementation(); + const pendingComptrollerImplementation = await unitroller.pendingComptrollerImplementation(); + expect(comptrollerImplementation.toLowerCase()).to.equal( + "0x909dd16b24CEf96c7be13065a9a0EAF8A126FFa5".toLowerCase(), + ); + expect(pendingComptrollerImplementation.toLowerCase()).to.equal(zeroAddr); + }); + }); + + describe("Verify storage layout before vip execution", async () => { + it("verify all the state before and after upgrade", async () => { + oracle = await unitroller.oracle(); + + maxAssets = await unitroller.maxAssets(); + + closeFactorMantissa = await unitroller.closeFactorMantissa(); + + liquidationIncentiveMantissa = await unitroller.liquidationIncentiveMantissa(); + + venusSupplyState = await unitroller.venusSupplyState(BUSD.address); + + venusBorrowState = await unitroller.venusBorrowState(BUSD.address); + + venusAccrued = await unitroller.venusAccrued(BUSD.address); + + vaiMintRate = await unitroller.vaiMintRate(); + + vaiController = await unitroller.vaiController(); + + mintedVAIs = await unitroller.mintedVAIs(await busdHolder.getAddress()); + + mintVAIGuardianPaused = await unitroller.mintVAIGuardianPaused(); + + repayVAIGuardianPaused = await unitroller.repayVAIGuardianPaused(); + + protocolPaused = await unitroller.protocolPaused(); + + venusVAIVaultRate = await unitroller.venusVAIVaultRate(); + + vaiVaultAddress = await unitroller.vaiVaultAddress(); + + releaseStartBlock = await unitroller.releaseStartBlock(); + + minReleaseAmount = await unitroller.minReleaseAmount(); + + treasuryGuardian = await unitroller.treasuryGuardian(); + + treasuryAddress = await unitroller.treasuryAddress(); + + treasuryPercent = await unitroller.treasuryPercent(); + + liquidatorContract = await unitroller.liquidatorContract(); + + comptrollerLens = await unitroller.comptrollerLens(); + + // checking all public mappings + allMarkets = await unitroller.getAllMarkets(); + + for (const marketIndex in allMarkets) { + const marketAddress = allMarkets[marketIndex].toString(); + + borrowSpeeds[marketAddress] = await unitroller.venusBorrowSpeeds(marketAddress); + supplySpeeds[marketAddress] = await unitroller.venusSupplySpeeds(marketAddress); + markets[marketAddress] = await unitroller.markets(marketAddress); + + userBorrowIndexes[marketAddress] = await unitroller.venusBorrowerIndex( + marketAddress, + await busdHolder.getAddress(), + ); + userSupplyIndexes[marketAddress] = await unitroller.venusSupplierIndex( + marketAddress, + await busdHolder.getAddress(), + ); + } + }); + }); + }); + + testVip("VIP-Diamond Contract Migration", vip174()); + + describe("Verify Storage slots after VIP execution", async () => { + // These tests checks the storage collision of comptroller while updating it via diamond. + describe("Diamond deployed successfully after VIP execution", async () => { + it("Owner of Diamond unitroller contract should match", async () => { + const diamondUnitrollerAdmin = await diamondUnitroller.admin(); + const pendingAdmin = await diamondUnitroller.pendingAdmin(); + expect(diamondUnitrollerAdmin.toLowerCase()).to.equal(Owner.toLowerCase()); + expect(pendingAdmin.toLowerCase()).to.equal(zeroAddr); + }); + + it("Diamond Unitroller Implementation (comptroller) should match the diamond Proxy Address", async () => { + const comptrollerImplementation = await diamondUnitroller.comptrollerImplementation(); + const pendingComptrollerImplementation = await diamondUnitroller.pendingComptrollerImplementation(); + expect(comptrollerImplementation.toLowerCase()).to.equal(DIAMOND.toLowerCase()); + expect(pendingComptrollerImplementation.toLowerCase()).to.equal(zeroAddr); + }); + }); + + describe("Verify storage layout after VIP execution", async () => { + it("verify all the state before and after upgrade", async () => { + const oracelUpgrade = await diamondUnitroller.oracle(); + expect(oracle).to.equal(oracelUpgrade); + + const maxAssetsAfterUpgrade = await diamondUnitroller.maxAssets(); + expect(maxAssets).to.equal(maxAssetsAfterUpgrade); + + const closeFactorMantissaAfterUpgrade = await diamondUnitroller.closeFactorMantissa(); + expect(closeFactorMantissa).to.equal(closeFactorMantissaAfterUpgrade); + + const liquidationIncentiveMantissaAfterUpgrade = await diamondUnitroller.liquidationIncentiveMantissa(); + expect(liquidationIncentiveMantissa).to.equal(liquidationIncentiveMantissaAfterUpgrade); + + const venusSupplyStateAfterUpgrade = await diamondUnitroller.venusSupplyState(BUSD.address); + expect(venusSupplyState.index.toString()).to.equal(venusSupplyStateAfterUpgrade.index.toString()); + + const venusBorrowStateAfterUpgrade = await diamondUnitroller.venusBorrowState(BUSD.address); + expect(venusBorrowState.index.toString()).to.equal(venusBorrowStateAfterUpgrade.index.toString()); + + const venusAccruedAfterUpgrade = await diamondUnitroller.venusAccrued(BUSD.address); + expect(venusAccrued).to.equal(venusAccruedAfterUpgrade); + + const vaiMintRateAfterUpgrade = await diamondUnitroller.vaiMintRate(); + expect(vaiMintRate).to.equal(vaiMintRateAfterUpgrade); + + const vaiControllerUpgrade = await diamondUnitroller.vaiController(); + expect(vaiControllerUpgrade).to.equal(vaiController); + + const mintedVAIsUpgrade = await diamondUnitroller.mintedVAIs(await busdHolder.getAddress()); + expect(mintedVAIsUpgrade).to.equal(mintedVAIs); + + const mintVAIGuardianPausedUpgrade = await diamondUnitroller.mintVAIGuardianPaused(); + expect(mintVAIGuardianPausedUpgrade).to.equal(mintVAIGuardianPaused); + + const repayVAIGuardianPausedUpgrade = await diamondUnitroller.repayVAIGuardianPaused(); + expect(repayVAIGuardianPausedUpgrade).to.equal(repayVAIGuardianPaused); + + const protocolPausedUpgrade = await diamondUnitroller.protocolPaused(); + expect(protocolPausedUpgrade).to.equal(protocolPaused); + + const venusVAIVaultRateUpgrade = await diamondUnitroller.venusVAIVaultRate(); + expect(venusVAIVaultRateUpgrade).to.equal(venusVAIVaultRate); + + const vaiVaultAddressUpgrade = await diamondUnitroller.vaiVaultAddress(); + expect(vaiVaultAddressUpgrade).to.equal(vaiVaultAddress); + + const releaseStartBlockUpgrade = await diamondUnitroller.releaseStartBlock(); + expect(releaseStartBlockUpgrade).to.equal(releaseStartBlock); + + const minReleaseAmountUpgrade = await diamondUnitroller.minReleaseAmount(); + expect(minReleaseAmountUpgrade).to.equal(minReleaseAmount); + + const treasuryGuardianUpgrade = await diamondUnitroller.treasuryGuardian(); + expect(treasuryGuardian).to.equal(treasuryGuardianUpgrade); + + const treasuryAddressUpgrade = await diamondUnitroller.treasuryAddress(); + expect(treasuryAddress).to.equal(treasuryAddressUpgrade); + + const treasuryPercentUpgrade = await diamondUnitroller.treasuryPercent(); + expect(treasuryPercent).to.equal(treasuryPercentUpgrade); + + const liquidatorContractUpgrade = await diamondUnitroller.liquidatorContract(); + expect(liquidatorContract).to.equal(liquidatorContractUpgrade); + + const comptrollerLensUpgrade = await diamondUnitroller.comptrollerLens(); + expect(comptrollerLens).to.equal(comptrollerLensUpgrade); + + // checking all public mappings + for (const marketIndex in allMarkets) { + const marketAddress = allMarkets[marketIndex].toString(); + + const marketUpgrade = await diamondUnitroller.markets(marketAddress); + expect(markets[marketAddress].collateralFactorMantissa).to.equal(marketUpgrade.collateralFactorMantissa); + expect(markets[marketAddress].isListed).to.equal(marketUpgrade.isListed); + expect(markets[marketAddress].isVenus).to.equal(marketUpgrade.isVenus); + + const venusBorrowSpeed = await diamondUnitroller.venusBorrowSpeeds(marketAddress); + const venusSupplySpeed = await diamondUnitroller.venusSupplySpeeds(marketAddress); + expect(borrowSpeeds[marketAddress]).to.equal(venusBorrowSpeed); + expect(supplySpeeds[marketAddress]).to.equal(venusSupplySpeed); + + const userBorrowIndex = await diamondUnitroller.venusBorrowerIndex( + marketAddress, + await busdHolder.getAddress(), + ); + const userSupplyIndex = await diamondUnitroller.venusSupplierIndex( + marketAddress, + await busdHolder.getAddress(), + ); + expect(userBorrowIndexes[marketAddress]).to.equal(userBorrowIndex); + expect(userSupplyIndexes[marketAddress]).to.equal(userSupplyIndex); + } + }); + }); + }); + + describe("Verify states of diamond Contract", () => { + describe("Diamond setters", () => { + it("setting market supply cap", async () => { + const currentSupplyCap = (await diamondUnitroller.supplyCaps(vBUSD.address)).toString(); + await diamondUnitroller.connect(owner)._setMarketSupplyCaps([vBUSD.address], [parseUnits("100000", 18)]); + expect(await diamondUnitroller.supplyCaps(vBUSD.address)).to.equals(parseUnits("100000", 18)); + await diamondUnitroller.connect(owner)._setMarketSupplyCaps([vBUSD.address], [parseUnits(currentSupplyCap, 0)]); + expect(await diamondUnitroller.supplyCaps(vBUSD.address)).to.equals(parseUnits(currentSupplyCap, 0)); + }); + + it("setting close factor", async () => { + const currentCloseFactor = (await diamondUnitroller.closeFactorMantissa()).toString(); + await diamondUnitroller.connect(owner)._setCloseFactor(parseUnits("1", 17)); + expect(await diamondUnitroller.closeFactorMantissa()).to.equals(parseUnits("1", 17)); + await diamondUnitroller.connect(owner)._setCloseFactor(parseUnits(currentCloseFactor, 0)); + expect(await diamondUnitroller.closeFactorMantissa()).to.equals(parseUnits(currentCloseFactor, 0)); + }); + + it("setting Liquidation Incentive", async () => { + await diamondUnitroller.connect(owner)._setLiquidationIncentive(parseUnits("13", 17)); + expect(await diamondUnitroller.liquidationIncentiveMantissa()).to.equal(parseUnits("13", 17)); + + await diamondUnitroller.connect(owner)._setLiquidationIncentive(parseUnits("11", 17)); + expect(await diamondUnitroller.liquidationIncentiveMantissa()).to.equal(parseUnits("11", 17)); + }); + + it("setting Pause Guardian", async () => { + const currentPauseGuardia = (await diamondUnitroller.pauseGuardian()).toString(); + + await diamondUnitroller.connect(owner)._setPauseGuardian(await owner.getAddress()); + expect(await diamondUnitroller.pauseGuardian()).to.equal(await owner.getAddress()); + + await diamondUnitroller.connect(owner)._setPauseGuardian(currentPauseGuardia); + expect(await diamondUnitroller.pauseGuardian()).to.equal(currentPauseGuardia); + }); + + it("setting market borrow cap", async () => { + const currentBorrowCap = (await diamondUnitroller.borrowCaps(vUSDT.address)).toString(); + await diamondUnitroller.connect(owner)._setMarketBorrowCaps([vUSDT.address], [parseUnits("10000", 18)]); + expect(await diamondUnitroller.borrowCaps(vUSDT.address)).to.equal(parseUnits("10000", 18)); + + await diamondUnitroller.connect(owner)._setMarketBorrowCaps([vUSDT.address], [currentBorrowCap]); + expect(await diamondUnitroller.borrowCaps(vUSDT.address)).to.equal(currentBorrowCap); + }); + + it("pausing mint action in vBUSD", async () => { + const isActionPaused = await diamondUnitroller.actionPaused(VBUSD, 0); + + await diamondUnitroller.connect(owner)._setActionsPaused([VBUSD], [0], !isActionPaused); + + await expect(await diamondUnitroller.actionPaused(VBUSD, 0)).to.be.equal(!isActionPaused); + + if (!isActionPaused) { + await diamondUnitroller.connect(owner)._setActionsPaused([VBUSD], [0], false); + } + }); + }); + }); +}); + +forking(31933620, async () => { + let owner, unitroller; + let USDT: Contract; + let usdtHolder: Signer; + let vUSDT: Contract; + let diamondUnitroller: Contract; + + before(async () => { + await pretendExecutingVip(vip174()); + unitroller = new ethers.Contract(UNITROLLER, Comptroller, ethers.provider); + + diamondUnitroller = new ethers.Contract(unitroller.address, Comptroller, ethers.provider); + + await impersonateAccount(Owner); + owner = await ethers.getSigner(Owner); + const [signer] = await ethers.getSigners(); + await signer.sendTransaction({ + to: owner.address, + value: ethers.BigNumber.from("10000000000000000000"), + data: undefined, + }); + + usdtHolder = await initMainnetUser("0x8894E0a0c962CB723c1976a4421c95949bE2D4E3", parseUnits("1000", 18)); + + [vUSDT] = await Promise.all( + [VUSDT].map((address: string) => { + return new ethers.Contract(address, VBEP20_DELEGATE_ABI, ethers.provider); + }), + ); + [USDT] = await Promise.all( + [vUSDT].map(async (vToken: Contract) => { + const underlying = await vToken.underlying(); + return new ethers.Contract(underlying, IERC20Upgradeable, ethers.provider); + }), + ); + await diamondUnitroller.connect(owner)._setActionsPaused([VBUSD], [0], false); + }); + + describe("Diamond Hooks", () => { + it("Diamond Unitroller Implementation (comptroller) should match the diamond Proxy Address", async () => { + const comptrollerImplementation = await diamondUnitroller.comptrollerImplementation(); + const pendingComptrollerImplementation = await diamondUnitroller.pendingComptrollerImplementation(); + expect(comptrollerImplementation.toLowerCase()).to.equal(DIAMOND.toLowerCase()); + expect(pendingComptrollerImplementation.toLowerCase()).to.equal(zeroAddr); + }); + + it("mint vToken vUSDT", async () => { + const vUSDTBalance = await USDT.balanceOf(vUSDT.address); + const usdtHolderBalance = await USDT.balanceOf(await usdtHolder.getAddress()); + await USDT.connect(usdtHolder).approve(vUSDT.address, parseUnits("1", 18)); + await vUSDT.connect(usdtHolder).mint(parseUnits("1", 18)); + const newvUSDTBalance = await USDT.balanceOf(vUSDT.address); + const newUsdtHolderBalance = await USDT.balanceOf(await usdtHolder.getAddress()); + + expect(newvUSDTBalance).greaterThan(vUSDTBalance); + expect(newUsdtHolderBalance).lessThan(usdtHolderBalance); + }); + + it("redeem vToken", async () => { + await USDT.connect(usdtHolder).approve(vUSDT.address, parseUnits("1", 18)); + await expect(vUSDT.connect(usdtHolder).mint(parseUnits("1", 18))).to.emit(vUSDT, "Mint"); + + const vUSDTUserBal = await vUSDT.connect(usdtHolder).balanceOf(await usdtHolder.getAddress()); + await expect(vUSDT.connect(usdtHolder).redeem(parseUnits("1", 8))).to.emit(vUSDT, "Redeem"); + const newVUSDTUserBal = await vUSDT.connect(usdtHolder).balanceOf(await usdtHolder.getAddress()); + + expect(newVUSDTUserBal).to.equal(vUSDTUserBal.sub(parseUnits("1", 8))); + }); + + it("borrow vToken", async () => { + const usdtUserBal = await USDT.balanceOf(await usdtHolder.getAddress()); + + await expect(vUSDT.connect(usdtHolder).borrow(parseUnits("1", 18))).to.emit(vUSDT, "Borrow"); + + expect((await USDT.balanceOf(await usdtHolder.getAddress())).toString()).to.equal( + usdtUserBal.add(parseUnits("1", 18)), + ); + }); + + it("Repay vToken", async () => { + await USDT.connect(usdtHolder).approve(vUSDT.address, parseUnits("1", 18)); + await expect(vUSDT.connect(usdtHolder).mint(parseUnits("1", 18))).to.emit(vUSDT, "Mint"); + + const usdtUserBal = await USDT.balanceOf(await usdtHolder.getAddress()); + await vUSDT.connect(usdtHolder).borrow(parseUnits("0.5", 18)); + + expect((await USDT.balanceOf(await usdtHolder.getAddress())).toString()).to.greaterThan(usdtUserBal); + + await USDT.connect(usdtHolder).approve(vUSDT.address, parseUnits("0.5", 18)); + await vUSDT.connect(usdtHolder).repayBorrow(parseUnits("0.5", 18)); + + const balanceAfterRepay = await USDT.balanceOf(await usdtHolder.getAddress()); + expect(balanceAfterRepay).to.equal(usdtUserBal); + }); + }); +}); diff --git a/simulations/vip-174/vip-174/utils/cut-params.json b/simulations/vip-174/vip-174/utils/cut-params.json new file mode 100644 index 000000000..902cc09fa --- /dev/null +++ b/simulations/vip-174/vip-174/utils/cut-params.json @@ -0,0 +1,83 @@ +{ + "cutParams": [ + [ + "0x40A30E1B01e0CF3eE3F22f769b0E437160550eEa", + 0, + [ + "0xa76b3fda", + "0x929fe9a1", + "0xc2998238", + "0xede4edd0", + "0xb0772d0b", + "0xabfceffc", + "0x007e3dd2", + "0xc488847b", + "0xa78dc775", + "0xddbf54fd" + ] + ], + [ + "0xCE305b594A7714E9ed8eDE23c111aFf6A2d54E0e", + 0, + [ + "0xead1a8a0", + "0xda3d454c", + "0x5c778605", + "0x5ec88c79", + "0x4e79238f", + "0x5fc7e71e", + "0x47ef3b3b", + "0x4ef4c3e1", + "0x41c728b9", + "0xeabe7d91", + "0x51dff989", + "0x24008a62", + "0x1ededc91", + "0xd02f7351", + "0x6d35bf91", + "0xbdcdc258", + "0x6a56947e" + ] + ], + [ + "0x71e7AAcb01C5764A56DB92aa31aA473e839d964F", + 0, + [ + "0xa7604b41", + "0xe85a2960", + "0x70bf66f0", + "0x86df31ee", + "0xadcd5fb9", + "0xd09c54ba", + "0x7858524d", + "0xbf32442d", + "0xededbae6" + ] + ], + [ + "0xc3CE70d9bBE8f63510f3C6dBf1C025113C79B40c", + 0, + [ + "0xf519fc30", + "0x2b5d790c", + "0x317b0b77", + "0xe4028eee", + "0x9bf34cbb", + "0x522c656b", + "0x4fd42e17", + "0xbb857450", + "0x607ef6c1", + "0x51a485e4", + "0x5f5af1aa", + "0x55ee1fe1", + "0x2a6a6065", + "0xd24febad", + "0x9cfdd9e6", + "0x2ec04124", + "0x4e0853db", + "0x6662c7c9", + "0xfd51a3ad" + ] + ] + ] +} diff --git a/vips/vip-174/vip-174-testnet.ts b/vips/vip-174/vip-174-testnet.ts new file mode 100644 index 000000000..8818d3e7a --- /dev/null +++ b/vips/vip-174/vip-174-testnet.ts @@ -0,0 +1,71 @@ +import { cutParams as params } from "../../simulations/vip-174/vip-174-testnet/utils/cut-params.json"; +import { ProposalType } from "../../src/types"; +import { makeProposal } from "../../src/utils"; + +const UNITROLLER = "0x94d1820b2D1c7c7452A163983Dc888CEC546b77D"; +const DIAMOND = "0x7e0298880224B8116F3462c50917249E94b3DC53"; +const ACM = "0x69a9e5dee4007fb1311c4d086fed4803e09a30b5"; +const NORMAL_TIMELOCK = "0xce10739590001705F7FF231611ba4A48B2820327"; +const FAST_TRACK_TIMELOCK = "0x3CFf21b7AF8390fE68799D58727d3b4C25a83cb6"; +const CRITICAL_TIMELOCK = "0x23B893a7C45a5Eb8c8C062b9F32d0D2e43eD286D"; +const PAUSE_GUARDIAN_MULTISIG = "0x2Ce1d0ffD7E869D9DF33e28552b12DdDed326706"; +const cutParams = params; + +interface GrantAccess { + target: string; + signature: string; + params: Array; +} + +const grantAccessControl = () => { + const accessProposals: Array = []; + [NORMAL_TIMELOCK, FAST_TRACK_TIMELOCK, CRITICAL_TIMELOCK, PAUSE_GUARDIAN_MULTISIG].map(target => { + accessProposals.push({ + target: ACM, + signature: "revokeCallPermission(address,string,address)", + params: [UNITROLLER, "_setActionsPaused(address[],uint256[],bool)", target], + }); + accessProposals.push({ + target: ACM, + signature: "giveCallPermission(address,string,address)", + params: [UNITROLLER, "_setActionsPaused(address[],uint8[],bool)", target], + }); + }); + + return accessProposals; +}; + +export const vip174Testnet = () => { + const meta = { + version: "v1", + title: "VIP Comptroller Diamond proxy", + description: `This vip implement diamond proxy for the comptroller to divide the comptroller logic into facets. The current implementation of the comptroller is exceeding the max limit of the contract size. To resolve this diamond proxy is implemented.`, + forDescription: + "I agree that Venus Protocol should proceed with the upgrading the Comptroller contract with diamond proxy", + againstDescription: "I do not think that Venus Protocol should proceed with the Comptroller contract upgradation", + abstainDescription: "I am indifferent to whether Venus Protocol proceeds with the Comptroller upgradation or not", + }; + + return makeProposal( + [ + { + target: UNITROLLER, + signature: "_setPendingImplementation(address)", + params: [DIAMOND], + }, + { + target: DIAMOND, + signature: "_become(address)", + params: [UNITROLLER], + }, + { + target: UNITROLLER, + signature: "diamondCut((address,uint8,bytes4[])[])", + params: [cutParams], + }, + ...grantAccessControl(), + ], + meta, + ProposalType.REGULAR, + ); +}; diff --git a/vips/vip-174/vip-174.ts b/vips/vip-174/vip-174.ts new file mode 100644 index 000000000..d41a6b018 --- /dev/null +++ b/vips/vip-174/vip-174.ts @@ -0,0 +1,125 @@ +import { cutParams as params } from "../../simulations/vip-174/vip-174/utils/cut-params.json"; +import { ProposalType } from "../../src/types"; +import { makeProposal } from "../../src/utils"; + +const UNITROLLER = "0xfD36E2c2a6789Db23113685031d7F16329158384"; +const DIAMOND = "0xAd69AA3811fE0EE7dBd4e25C4bae40e6422c76C8"; +const ACM = "0x4788629ABc6cFCA10F9f969efdEAa1cF70c23555"; +const NORMAL_TIMELOCK = "0x939bD8d64c0A9583A7Dcea9933f7b21697ab6396"; +const FAST_TRACK_TIMELOCK = "0x555ba73dB1b006F3f2C7dB7126d6e4343aDBce02"; +const CRITICAL_TIMELOCK = "0x213c446ec11e45b15a6E29C1C1b402B8897f606d"; +const PAUSE_GUARDIAN_MULTISIG = "0x1C2CAc6ec528c20800B2fe734820D87b581eAA6B"; +const cutParams = params; + +interface GrantAccess { + target: string; + signature: string; + params: Array; +} + +const grantAccessControl = () => { + const accessProposals: Array = []; + [NORMAL_TIMELOCK, FAST_TRACK_TIMELOCK, CRITICAL_TIMELOCK, PAUSE_GUARDIAN_MULTISIG].map(target => { + accessProposals.push({ + target: ACM, + signature: "revokeCallPermission(address,string,address)", + params: [UNITROLLER, "_setActionsPaused(address[],uint256[],bool)", target], + }); + accessProposals.push({ + target: ACM, + signature: "giveCallPermission(address,string,address)", + params: [UNITROLLER, "_setActionsPaused(address[],uint8[],bool)", target], + }); + }); + + return accessProposals; +}; + +export const vip174 = () => { + const meta = { + version: "v2", + title: "VIP-174 Core pool Comptroller upgrade – Diamond Comptroller", + + description: `#### Summary + +If passed this VIP will upgrade the implementation of the Comptroller contract in the Core pool. It will set a re-architectured Comptroller following the [Diamond pattern](https://eips.ethereum.org/EIPS/eip-2535), not adding new features now for the regular users. This upgrade will allow Venus to add new features in the Core pool in the future, unlocking the EVM limitation on the size of the contracts (maximum 24KB) added in the [EIP-170](https://eips.ethereum.org/EIPS/eip-170). + +#### Description + +This VIP upgrades the implementation of the [Comptroller contract in the Core pool](https://bscscan.com/address/0xfD36E2c2a6789Db23113685031d7F16329158384). As features continued to be introduced to the Core Pool Comptroller contract, it grew to exceed the [maximum allowable size of 24KB](https://eips.ethereum.org/EIPS/eip-170). In response to this challenge and to preemptively address similar issues in the future, a multifaceted diamond pattern was implemented. + +The original comptroller was refactored using the [EIP-2535](https://eips.ethereum.org/EIPS/eip-2535) diamond pattern into distinct facets. This restructuring aligns the storage layout with that of the Comptroller proxy, streamlining the contract's organization and enhancing efficiency. As a consequence user interactions now trigger two delegate calls. + +Users will continue to interact with the [Unitroller](https://bscscan.com/address/0xfD36E2c2a6789Db23113685031d7F16329158384) proxy contract same as before with one significant difference. Now the Diamond proxy serves as the implementation contract for the Unitroller, and the Comptroller's implementation has been divided into multiple facets. These facets will function as the various components of the Diamond proxy. + +Facets: + +* PolicyFacet: this facet contains all the external pre-hook functions related to vToken. +* SetterFacet: this facet contains all setter configuration functions. +* MarketFacet: this facet provides information about the asset in the market that you are in at that time. This facet is also responsible for entering and exiting the market. +* RewardFacet: this facet provides the external functions related to all claims and rewards of the protocol, it has the following. + +You can see more technical details about the Diamond Comptroller in the [documentation site](https://docs-v4.venus.io/technical-reference/reference-technical-articles/diamond-comptroller). + +**Security and additional considerations** + +We applied the following security procedures for this upgrade: + +* **Comptroller contract behavior post upgrade**: in a simulation environment, validating Comptroller work as expected after the upgrade +* **Comptroller storage layout**: in a simulation environment, validating the storage variables are accessible and correct after the upgrade +* **Deployment on testnet**: the same Diamond Comptroller has been [deployed to testnet](https://testnet.bscscan.com/tx/0x8ef7a72736d49f4babd624c8dc353589a1d659fe9995f358cca8c2305f21b2ba), and used in the Venus Protocol testnet deployment +* **Audit: OpenZeppelin, Quantstamp, Certik, Peckshield and Fairyproof have audited the deployed code** + +**Audit reports** + +* [OpenZeppelin audit report (2023/08/17)](https://github.com/VenusProtocol/venus-protocol/blob/8553387f2277be152883b4ee22211b77a8cbe5f6/audits/049_diamondComptroller_openzeppelin_20230817.pdf) +* [Quantstamp audit report (2023/09/19)](https://github.com/VenusProtocol/venus-protocol/blob/8553387f2277be152883b4ee22211b77a8cbe5f6/audits/047_diamondComptroller_quantstamp_20230919.pdf) +* [Certik audit audit report (2023/08/03)](https://github.com/VenusProtocol/venus-protocol/blob/8553387f2277be152883b4ee22211b77a8cbe5f6/audits/044_diamondComptroller_certik_20230803.pdf) +* [Peckshield audit report (2023/07/28)](https://github.com/VenusProtocol/venus-protocol/blob/8553387f2277be152883b4ee22211b77a8cbe5f6/audits/042_diamondComptroller_peckshield_20230718.pdf) +* [Fairyproof audit report (2023/06/25)](https://github.com/VenusProtocol/venus-protocol/blob/8553387f2277be152883b4ee22211b77a8cbe5f6/audits/040_diamondComptroller_fairyproof_20230625.pdf) + +**Deployed contracts on main net** + +* [Comptroller proxy (Unitroller)](https://bscscan.com/address/0xfd36e2c2a6789db23113685031d7f16329158384) +* [Current Comptroller implementation](https://bscscan.com/address/0x909dd16b24cef96c7be13065a9a0eaf8a126ffa5) +* [New Comptroller implementation (Diamond)](https://bscscan.com/address/0xAd69AA3811fE0EE7dBd4e25C4bae40e6422c76C8) +* Facets on mainnet: + * [MarketFacet](https://bscscan.com/address/0x40A30E1B01e0CF3eE3F22f769b0E437160550eEa) + * [PolicyFacet](https://bscscan.com/address/0xCE305b594A7714E9ed8eDE23c111aFf6A2d54E0e) + * [RewardFacet](https://bscscan.com/address/0x71e7AAcb01C5764A56DB92aa31aA473e839d964F) + * [SetterFacet](https://bscscan.com/address/0xc3CE70d9bBE8f63510f3C6dBf1C025113C79B40c) + +**References** + +* [Pull request with the changeset](https://github.com/VenusProtocol/venus-protocol/pull/224) +* [Simulation pre and post upgrade](https://github.com/VenusProtocol/vips/pull/11/) +* [Documentation](https://docs-v4.venus.io/technical-reference/reference-technical-articles/diamond-comptroller)`, + + forDescription: "Execute this proposal", + againstDescription: "Do not execute this proposal", + abstainDescription: "Indifferent to execution", + }; + + return makeProposal( + [ + { + target: UNITROLLER, + signature: "_setPendingImplementation(address)", + params: [DIAMOND], + }, + { + target: DIAMOND, + signature: "_become(address)", + params: [UNITROLLER], + }, + { + target: UNITROLLER, + signature: "diamondCut((address,uint8,bytes4[])[])", + params: [cutParams], + }, + ...grantAccessControl(), + ], + meta, + ProposalType.REGULAR, + ); +};