Skip to content

Commit

Permalink
feat: add rc upgrade script
Browse files Browse the repository at this point in the history
  • Loading branch information
ypatil12 committed Sep 14, 2024
1 parent 4e9b422 commit fa8c5fd
Show file tree
Hide file tree
Showing 4 changed files with 196 additions and 2 deletions.
2 changes: 1 addition & 1 deletion script/configs/mainnet/mainnet-addresses.config.json
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
{
"lastUpdated": "v0.4.2-mainnet-pepe",
"lastUpdated": "v0.4.3-mainnet-foundation-incentives",
"addresses": {
"avsDirectory": "0x135dda560e946695d6f155dacafc6f1f25c1f5af",
"avsDirectoryImplementation": "0xdabdb3cd346b7d5f5779b0b614ede1cc9dcba5b7",
Expand Down
190 changes: 190 additions & 0 deletions script/deploy/mainnet/v0.4.3-upgrade-rewardsCoordinator.s.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,190 @@
// SPDX-License-Identifier: BUSL-1.1
pragma solidity ^0.8.12;

import "../../utils/ExistingDeploymentParser.sol";
import "../../utils/Multisend.sol";
import "script/utils/TimelockEncoding.sol";

/**
* @notice Script used for the first deployment of EigenLayer core contracts to Holesky
* anvil --fork-url $MAINNET_RPC
*
* Holesky testnet: Deploy/Upgrade RewardsCoordinator
* forge script script/deploy/holesky/v0.4.3-upgrade-rewardsCoordinator.s.sol --rpc-url $MAINNET_RPC --private-key $PRIVATE_KEY --broadcast -vvvv --verify --etherscan-api-key $ETHERSCAN_API_KEY
*
*/
contract Upgrade_Mainnet_RewardsCoordinator is ExistingDeploymentParser, TimelockEncoding {

// CALLDATA FOR CALL TO TIMELOCK
// TUESDAY, SEPTEMBER 17 2024 22:00:00 GMT (6pm EST/3pm PST)
uint256 timelockEta = 1727215200;

// Calldatas for upgrading RC
bytes final_calldata_to_executor_multisig;
bytes calldata_to_timelock_queuing_action;
bytes calldata_to_timelock_executing_action;

// Calldatas for setting reward for all submitter
bytes hopper_setter_final_calldata_to_ops_multisig;

function run() public parseState {
_parseInitialDeploymentParams("script/configs/mainnet/mainnet-config.config.json");
_parseDeployedContracts("script/configs/mainnet/mainnet-addresses.config.json");

RewardsCoordinator oldRewardsCoordinator = rewardsCoordinatorImplementation;

// Deploy Rewards Coordinator
vm.startBroadcast();
rewardsCoordinatorImplementation = new RewardsCoordinator(
delegationManager,
strategyManager,
REWARDS_COORDINATOR_CALCULATION_INTERVAL_SECONDS,
REWARDS_COORDINATOR_MAX_REWARDS_DURATION,
REWARDS_COORDINATOR_MAX_RETROACTIVE_LENGTH,
REWARDS_COORDINATOR_MAX_FUTURE_LENGTH,
REWARDS_COORDINATOR_GENESIS_REWARDS_TIMESTAMP
);
vm.stopBroadcast();

_sanityCheckImplementations(oldRewardsCoordinator, rewardsCoordinatorImplementation);

emit log_named_address("Rewards Coordinator Implementation", address(rewardsCoordinatorImplementation));

// Create Upgrade Txs via Operations Multisig to Timelock to:
// 1. Upgrade RewardsCoordinator
// 2. Set owner of RewardsCoordinator to OperationsMultisig
Tx[] memory txs = new Tx[](2);
address timelockTarget = executorMultisig;

// 1. Upgrade Rewards Coordiantor
txs[0] = Tx({
to: address(eigenLayerProxyAdmin),
value: 0,
data: abi.encodeWithSelector(
ProxyAdmin.upgrade.selector,
TransparentUpgradeableProxy(payable(address(rewardsCoordinator))),
rewardsCoordinatorImplementation
)
});

// 2. Set owner of RewardsCoordinator to OperationsMultisig
txs[1] = Tx({
to: address(rewardsCoordinator),
value: 0,
data: abi.encodeWithSelector(
Ownable.transferOwnership.selector,
address(operationsMultisig)
)
});

bytes memory calldata_to_multisend_contract = abi.encodeWithSelector(MultiSendCallOnly.multiSend.selector, encodeMultisendTxs(txs));
emit log_named_bytes("calldata_to_multisend_contract", calldata_to_multisend_contract);

final_calldata_to_executor_multisig = encodeForExecutor({
from: timelock,
to: multiSendCallOnly,
value: 0,
data: calldata_to_multisend_contract,
operation: ISafe.Operation.DelegateCall
});

calldata_to_timelock_queuing_action = abi.encodeWithSelector(ITimelock.queueTransaction.selector,
timelockTarget,
timelockValue,
timelockSignature,
final_calldata_to_executor_multisig,
timelockEta
);

emit log_named_bytes("calldata_to_timelock_queuing_action", calldata_to_timelock_queuing_action);

calldata_to_timelock_executing_action = abi.encodeWithSelector(ITimelock.executeTransaction.selector,
timelockTarget,
timelockValue,
timelockSignature,
final_calldata_to_executor_multisig,
timelockEta
);

emit log_named_bytes("calldata_to_timelock_executing_action", calldata_to_timelock_executing_action);
}

function test_mainnet_rc_upgrade() public {
run();

// Queue Transaction
vm.prank(operationsMultisig);
(bool success, ) = address(timelock).call(calldata_to_timelock_queuing_action);
require(success, "Timelock queueTransaction failed");

// Fast forwart to after ETA
vm.warp(timelockEta + 1);
vm.prank(operationsMultisig);
(success, ) = address(timelock).call(calldata_to_timelock_executing_action);
require(success, "Timelock executeTransaction failed");

// Assert owner
assertEq(address(rewardsCoordinator.owner()), address(operationsMultisig), "RewardsCoordinator owner is not OperationsMultisig");

// Sanity Checks
_verifyContractPointers();
_verifyImplementations();
_verifyContractsInitialized();
_verifyInitializationParams();
}

function _sanityCheckImplementations(RewardsCoordinator oldRc, RewardsCoordinator newRc) internal {
// Verify configs between both rewardsCoordinatorImplementations
assertEq(
address(oldRc.delegationManager()),
address(newRc.delegationManager()),
"DM mismatch"
);
assertEq(
address(oldRc.strategyManager()),
address(newRc.strategyManager()),
"SM mismatch"
);
assertEq(
oldRc.CALCULATION_INTERVAL_SECONDS(),
newRc.CALCULATION_INTERVAL_SECONDS(),
"CALCULATION_INTERVAL_SECONDS mismatch"
);
assertEq(
oldRc.MAX_REWARDS_DURATION(),
newRc.MAX_REWARDS_DURATION(),
"MAX_REWARDS_DURATION mismatch"
);
assertEq(
oldRc.MAX_RETROACTIVE_LENGTH(),
newRc.MAX_RETROACTIVE_LENGTH(),
"MAX_RETROACTIVE_LENGTH mismatch"
);
assertEq(
oldRc.MAX_FUTURE_LENGTH(),
newRc.MAX_FUTURE_LENGTH(),
"MAX_FUTURE_LENGTH mismatch"
);
assertEq(
oldRc.GENESIS_REWARDS_TIMESTAMP(),
newRc.GENESIS_REWARDS_TIMESTAMP(),
"GENESIS_REWARDS_TIMESTAMP mismatch"
);
}

function test_set_reward_for_all_submitter(address hopper) public {
test_mainnet_rc_upgrade();

// Set reward for all submitters
vm.prank(operationsMultisig);
rewardsCoordinator.setRewardsForAllSubmitter(hopper, true);

assertTrue(rewardsCoordinator.isRewardsForAllSubmitter(hopper), "Hopper not set for all submitters");
}

modifier parseState() {
_parseInitialDeploymentParams("script/configs/mainnet/mainnet-config.config.json");
_parseDeployedContracts("script/configs/mainnet/mainnet-addresses.config.json");
_;
}
}
6 changes: 5 additions & 1 deletion script/utils/ExistingDeploymentParser.sol
Original file line number Diff line number Diff line change
Expand Up @@ -181,6 +181,10 @@ contract ExistingDeploymentParser is Script, Test {
strategyManagerImplementation = StrategyManager(
stdJson.readAddress(existingDeploymentData, ".addresses.strategyManagerImplementation")
);
strategyFactory = StrategyFactory(stdJson.readAddress(existingDeploymentData, ".addresses.strategyFactory"));
strategyFactoryImplementation = StrategyFactory(
stdJson.readAddress(existingDeploymentData, ".addresses.strategyFactoryImplementation")
);
eigenPodManager = EigenPodManager(stdJson.readAddress(existingDeploymentData, ".addresses.eigenPodManager"));
eigenPodManagerImplementation = EigenPodManager(
stdJson.readAddress(existingDeploymentData, ".addresses.eigenPodManagerImplementation")
Expand Down Expand Up @@ -571,7 +575,7 @@ contract ExistingDeploymentParser is Script, Test {
);
if (block.chainid == 1) {
require(
strategyManager.strategyWhitelister() == operationsMultisig,
strategyManager.strategyWhitelister() == address(strategyFactory),
"strategyManager: strategyWhitelister not set correctly"
);
} else if (block.chainid == 17000) {
Expand Down

0 comments on commit fa8c5fd

Please sign in to comment.