1
+ // SPDX-License-Identifier: BUSL-1.1
2
+ pragma solidity ^ 0.8.12 ;
3
+
4
+ import "@openzeppelin/contracts/token/ERC20/presets/ERC20PresetFixedSupply.sol " ;
5
+ import "@openzeppelin/contracts/proxy/transparent/ProxyAdmin.sol " ;
6
+ import "@openzeppelin/contracts/proxy/transparent/TransparentUpgradeableProxy.sol " ;
7
+ import "@openzeppelin/contracts/proxy/beacon/UpgradeableBeacon.sol " ;
8
+
9
+ import "../../../src/contracts/interfaces/IETHPOSDeposit.sol " ;
10
+ import "../../../src/contracts/interfaces/IBeaconChainOracle.sol " ;
11
+
12
+ import "../../../src/contracts/core/StrategyManager.sol " ;
13
+ import "../../../src/contracts/core/Slasher.sol " ;
14
+ import "../../../src/contracts/core/DelegationManager.sol " ;
15
+
16
+ import "../../../src/contracts/pods/EigenPod.sol " ;
17
+ import "../../../src/contracts/pods/EigenPodManager.sol " ;
18
+ import "../../../src/contracts/pods/DelayedWithdrawalRouter.sol " ;
19
+
20
+ import "../../../src/contracts/permissions/PauserRegistry.sol " ;
21
+
22
+ import "forge-std/Script.sol " ;
23
+ import "forge-std/Test.sol " ;
24
+
25
+ // # To load the variables in the .env file
26
+ // source .env
27
+
28
+ // # To deploy and verify our contract
29
+ // forge script script/deploy/mainnet/EigenPod_Minor_Upgrade_Deploy.s.sol:EigenPod_Minor_Upgrade_Deploy --rpc-url $RPC_URL --private-key $PRIVATE_KEY --broadcast -vvvv
30
+ contract EigenPod_Minor_Upgrade_Deploy is Script , Test {
31
+ Vm cheats = Vm (HEVM_ADDRESS);
32
+
33
+ string public m2DeploymentOutputPath;
34
+ string public freshOutputPath;
35
+
36
+ // EigenLayer core contracts
37
+ ISlasher public slasher;
38
+ IDelegationManager public delegation;
39
+ DelegationManager public delegationImplementation;
40
+ IStrategyManager public strategyManager;
41
+ StrategyManager public strategyManagerImplementation;
42
+ IEigenPodManager public eigenPodManager;
43
+ EigenPodManager public eigenPodManagerImplementation;
44
+ IDelayedWithdrawalRouter public delayedWithdrawalRouter;
45
+ IBeacon public eigenPodBeacon;
46
+ EigenPod public eigenPodImplementation;
47
+
48
+ // Eigenlayer Proxy Admin
49
+ ProxyAdmin public eigenLayerProxyAdmin;
50
+
51
+ // BeaconChain deposit contract & beacon chain oracle
52
+ IETHPOSDeposit public ethPOS;
53
+ address public beaconChainOracle;
54
+
55
+ // RPC url to fork from for pre-upgrade state change tests
56
+ string public rpcUrl;
57
+
58
+ uint64 public genesisTimeBefore;
59
+ uint64 public maxRestakedBalanceBefore;
60
+
61
+ function run () external {
62
+ // Read and log the chain ID
63
+ uint256 chainId = block .chainid ;
64
+ emit log_named_uint ("You are deploying on ChainID " , chainId);
65
+
66
+ // Update deployment path addresses if on mainnet
67
+ if (chainId == 1 ) {
68
+ m2DeploymentOutputPath = "script/output/mainnet/M2_mainnet_upgrade.output.json " ;
69
+ freshOutputPath = "script/output/mainnet/eigenpod_minor_upgrade_deploy.json " ;
70
+ rpcUrl = "RPC_MAINNET " ;
71
+ } else {
72
+ revert ("Chain not supported " );
73
+ }
74
+
75
+ // Read json data
76
+ string memory deployment_data = vm.readFile (m2DeploymentOutputPath);
77
+ slasher = Slasher (stdJson.readAddress (deployment_data, ".addresses.slasher " ));
78
+ delegation = DelegationManager (stdJson.readAddress (deployment_data, ".addresses.delegationManager " ));
79
+ strategyManager = DelegationManager (address (delegation)).strategyManager ();
80
+ eigenPodManager = strategyManager.eigenPodManager ();
81
+ eigenPodBeacon = eigenPodManager.eigenPodBeacon ();
82
+ ethPOS = eigenPodManager.ethPOS ();
83
+
84
+ eigenLayerProxyAdmin = ProxyAdmin (stdJson.readAddress (deployment_data, ".addresses.eigenLayerProxyAdmin " ));
85
+
86
+ genesisTimeBefore = EigenPod (payable (eigenPodBeacon.implementation ())).GENESIS_TIME ();
87
+ maxRestakedBalanceBefore = EigenPod (payable (eigenPodBeacon.implementation ())).MAX_RESTAKED_BALANCE_GWEI_PER_VALIDATOR ();
88
+ delayedWithdrawalRouter = EigenPod (payable (eigenPodBeacon.implementation ())).delayedWithdrawalRouter ();
89
+
90
+ // Begin deployment
91
+ vm.startBroadcast ();
92
+
93
+ // Deploy new implmementation contracts
94
+ eigenPodImplementation = new EigenPod ({
95
+ _ethPOS: ethPOS,
96
+ _delayedWithdrawalRouter: delayedWithdrawalRouter,
97
+ _eigenPodManager: eigenPodManager,
98
+ _MAX_RESTAKED_BALANCE_GWEI_PER_VALIDATOR: maxRestakedBalanceBefore,
99
+ _GENESIS_TIME: genesisTimeBefore
100
+ });
101
+
102
+ vm.stopBroadcast ();
103
+
104
+ // Write json data out
105
+ string memory parent_object = "parent object " ;
106
+ string memory deployed_addresses = "addresses " ;
107
+
108
+ // Add chain info
109
+ string memory chain_info = "chainInfo " ;
110
+ vm.serializeUint (chain_info, "deploymentBlock " , block .number );
111
+ string memory chain_info_output = vm.serializeUint (chain_info, "chainId " , chainId);
112
+
113
+ // Serialize new implementation addresses
114
+ string memory deployed_addresses_output = vm.serializeAddress (
115
+ deployed_addresses,
116
+ "eigenPodImplementation " ,
117
+ address (eigenPodImplementation)
118
+ );
119
+
120
+ // Save addresses
121
+ vm.serializeString (parent_object, deployed_addresses, deployed_addresses_output);
122
+ string memory finalJson = vm.serializeString (parent_object, chain_info, chain_info_output);
123
+
124
+ // Write output to file
125
+ vm.writeJson (finalJson, freshOutputPath);
126
+
127
+ // Perform post-upgrade tests
128
+ simulatePerformingUpgrade ();
129
+ checkUpgradeCorrectness ();
130
+ }
131
+
132
+ function simulatePerformingUpgrade () public {
133
+ // Upgrade beacon
134
+ cheats.prank (UpgradeableBeacon (address (eigenPodBeacon)).owner ());
135
+ UpgradeableBeacon (address (eigenPodBeacon)).upgradeTo (address (eigenPodImplementation));
136
+ }
137
+
138
+ function checkUpgradeCorrectness () public view {
139
+ _verifyEigenPodCorrectness ();
140
+ }
141
+
142
+ function _verifyEigenPodCorrectness () public view {
143
+ // Check that state is correct
144
+ require (eigenPodBeacon.implementation () == address (eigenPodImplementation),
145
+ "implementation set incorrectly " );
146
+ require (eigenPodImplementation.delayedWithdrawalRouter () == delayedWithdrawalRouter,
147
+ "delayedWithdrawalRouter set incorrectly " );
148
+ require (eigenPodImplementation.ethPOS () == ethPOS,
149
+ "ethPOS set incorrectly " );
150
+ require (eigenPodImplementation.eigenPodManager () == eigenPodManager,
151
+ "eigenPodManager set incorrectly " );
152
+ // check that values are unchanged
153
+ require (eigenPodImplementation.MAX_RESTAKED_BALANCE_GWEI_PER_VALIDATOR () == maxRestakedBalanceBefore,
154
+ "MAX_RESTAKED_BALANCE_GWEI_PER_VALIDATOR set incorrectly " );
155
+ require (eigenPodImplementation.GENESIS_TIME () == genesisTimeBefore,
156
+ "GENESIS_TIME set incorrectly " );
157
+ // redundant checks on correct values
158
+ require (eigenPodImplementation.MAX_RESTAKED_BALANCE_GWEI_PER_VALIDATOR () == 32 gwei,
159
+ "MAX_RESTAKED_BALANCE_GWEI_PER_VALIDATOR set incorrectly " );
160
+ require (eigenPodImplementation.GENESIS_TIME () == 1606824023 ,
161
+ "GENESIS_TIME set incorrectly " );
162
+
163
+
164
+ require (address (EigenPod (payable (eigenPodBeacon.implementation ())).delayedWithdrawalRouter ()) == 0x7Fe7E9CC0F274d2435AD5d56D5fa73E47F6A23D8 );
165
+ require (address (EigenPod (payable (eigenPodBeacon.implementation ())).eigenPodManager ()) == 0x91E677b07F7AF907ec9a428aafA9fc14a0d3A338 );
166
+ require (address (EigenPod (payable (eigenPodBeacon.implementation ())).ethPOS ()) == 0x00000000219ab540356cBB839Cbe05303d7705Fa );
167
+ }
168
+ }
0 commit comments