Skip to content

Commit

Permalink
update checkpoint struct
Browse files Browse the repository at this point in the history
  • Loading branch information
gpsanant committed Sep 30, 2024
1 parent 040ea97 commit 560cea6
Show file tree
Hide file tree
Showing 3 changed files with 27 additions and 21 deletions.
9 changes: 7 additions & 2 deletions src/contracts/interfaces/IEigenPod.sol
Original file line number Diff line number Diff line change
Expand Up @@ -102,9 +102,14 @@ interface IEigenPod {
bytes32 beaconBlockRoot;
uint24 proofsRemaining;
uint64 podBalanceGwei;
int128 balanceDeltasGwei;
// this used to be an int128 before the slashing release
// now it is an int64. (2^63 - 1) gwei * 1e-9 eth/gwei = 9_223_372_036.85 eth = 9 billion eth
int64 balanceDeltasGwei;
uint64 beaconChainBalanceBeforeGwei;
}

struct ExtendedCheckpoint {
uint128 beaconChainBalanceBefore;
uint128 beaconChainBalanceAfter;
}

/**
Expand Down
32 changes: 15 additions & 17 deletions src/contracts/pods/EigenPod.sol
Original file line number Diff line number Diff line change
Expand Up @@ -189,14 +189,15 @@ contract EigenPod is Initializable, ReentrancyGuardUpgradeable, EigenPodPausingC
// If the proof shows the validator has a balance of 0, they are marked `WITHDRAWN`.
// The assumption is that if this is the case, any withdrawn ETH was already in
// the pod when `startCheckpoint` was originally called.
(int128 balanceDeltaGwei, uint64 exitedBalanceGwei) = _verifyCheckpointProof({
(uint64 prevBalanceGwei, int64 balanceDeltaGwei, uint64 exitedBalanceGwei) = _verifyCheckpointProof({
validatorInfo: validatorInfo,
checkpointTimestamp: checkpointTimestamp,
balanceContainerRoot: balanceContainerProof.balanceContainerRoot,
proof: proof
});

checkpoint.proofsRemaining--;
checkpoint.beaconChainBalanceBeforeGwei += prevBalanceGwei;
checkpoint.balanceDeltasGwei += balanceDeltaGwei;
exitedBalancesGwei += exitedBalanceGwei;

Expand Down Expand Up @@ -260,6 +261,10 @@ contract EigenPod is Initializable, ReentrancyGuardUpgradeable, EigenPodPausingC
);
}

if (currentCheckpointTimestamp != 0) {
_currentCheckpoint.beaconChainBalanceBeforeGwei += uint64(totalAmountToBeRestakedWei / GWEI_TO_WEI);
}

// Update the EigenPodManager on this pod's new balance
eigenPodManager.recordBeaconChainETHBalanceUpdate(podOwner, int256(totalAmountToBeRestakedWei), 0); // no decrease
}
Expand Down Expand Up @@ -493,8 +498,6 @@ contract EigenPod is Initializable, ReentrancyGuardUpgradeable, EigenPodPausingC
uint64 lastCheckpointedAt = lastCheckpointTimestamp;
if (currentCheckpointTimestamp != 0) {
lastCheckpointedAt = currentCheckpointTimestamp;
_currentCheckpoint.beaconChainBalanceBefore += uint128(restakedBalanceGwei);
_currentCheckpoint.beaconChainBalanceAfter += uint128(restakedBalanceGwei);
}

// Proofs complete - create the validator in state
Expand All @@ -515,11 +518,11 @@ contract EigenPod is Initializable, ReentrancyGuardUpgradeable, EigenPodPausingC
uint64 checkpointTimestamp,
bytes32 balanceContainerRoot,
BeaconChainProofs.BalanceProof calldata proof
) internal returns (int128 balanceDeltaGwei, uint64 exitedBalanceGwei) {
) internal returns (uint64 prevBalanceGwei, int64 balanceDeltaGwei, uint64 exitedBalanceGwei) {
uint40 validatorIndex = uint40(validatorInfo.validatorIndex);

// Verify validator balance against `balanceContainerRoot`
uint64 prevBalanceGwei = validatorInfo.restakedBalanceGwei;
prevBalanceGwei = validatorInfo.restakedBalanceGwei;
uint64 newBalanceGwei = BeaconChainProofs.verifyValidatorBalance({
balanceContainerRoot: balanceContainerRoot,
validatorIndex: validatorIndex,
Expand All @@ -534,10 +537,6 @@ contract EigenPod is Initializable, ReentrancyGuardUpgradeable, EigenPodPausingC
previousAmountGwei: prevBalanceGwei
});

// Update the checkpoint values
_currentCheckpoint.beaconChainBalanceBefore += uint128(prevBalanceGwei);
_currentCheckpoint.beaconChainBalanceAfter += uint128(newBalanceGwei);

emit ValidatorBalanceUpdated(validatorIndex, checkpointTimestamp, newBalanceGwei);
}

Expand All @@ -550,12 +549,12 @@ contract EigenPod is Initializable, ReentrancyGuardUpgradeable, EigenPodPausingC
validatorInfo.status = VALIDATOR_STATUS.WITHDRAWN;
// If we reach this point, `balanceDeltaGwei` should always be negative,
// so this should be a safe conversion
exitedBalanceGwei = uint64(uint128(-balanceDeltaGwei));
exitedBalanceGwei = uint64(-balanceDeltaGwei);

emit ValidatorWithdrawn(checkpointTimestamp, validatorIndex);
}

return (balanceDeltaGwei, exitedBalanceGwei);
return (prevBalanceGwei, balanceDeltaGwei, exitedBalanceGwei);
}

/**
Expand Down Expand Up @@ -607,8 +606,7 @@ contract EigenPod is Initializable, ReentrancyGuardUpgradeable, EigenPodPausingC
proofsRemaining: uint24(activeValidatorCount),
podBalanceGwei: podBalanceGwei,
balanceDeltasGwei: 0,
beaconChainBalanceBefore: 0,
beaconChainBalanceAfter: 0
beaconChainBalanceBeforeGwei: 0
});

// Place checkpoint in storage. If `proofsRemaining` is 0, the checkpoint
Expand Down Expand Up @@ -646,8 +644,8 @@ contract EigenPod is Initializable, ReentrancyGuardUpgradeable, EigenPodPausingC
// Calculate the slashing proportion
uint64 proportionOfOldBalance = 0;
if (totalShareDeltaWei < 0) {
uint256 totalBefore = withdrawableRestakedExecutionLayerGwei + checkpoint.beaconChainBalanceBefore;
proportionOfOldBalance = uint64((totalBefore + uint256(-totalShareDeltaWei)) * WAD / totalBefore);
uint256 totalRestakedBeforeWei = (withdrawableRestakedExecutionLayerGwei + checkpoint.beaconChainBalanceBeforeGwei) * GWEI_TO_WEI;
proportionOfOldBalance = uint64((totalRestakedBeforeWei + uint256(-totalShareDeltaWei)) * WAD / totalRestakedBeforeWei);
}

// Update pod owner's shares
Expand Down Expand Up @@ -675,8 +673,8 @@ contract EigenPod is Initializable, ReentrancyGuardUpgradeable, EigenPodPausingC
}

/// @dev Calculates the delta between two Gwei amounts and returns as an int256
function _calcBalanceDelta(uint64 newAmountGwei, uint64 previousAmountGwei) internal pure returns (int128) {
return int128(uint128(newAmountGwei)) - int128(uint128(previousAmountGwei));
function _calcBalanceDelta(uint64 newAmountGwei, uint64 previousAmountGwei) internal pure returns (int64) {
return int64(newAmountGwei) - int64(previousAmountGwei);
}

/**
Expand Down
7 changes: 5 additions & 2 deletions src/contracts/pods/EigenPodStorage.sol
Original file line number Diff line number Diff line change
Expand Up @@ -68,18 +68,21 @@ abstract contract EigenPodStorage is IEigenPod {
mapping(uint64 => uint64) public checkpointBalanceExitedGwei;

/// @notice The current checkpoint, if there is one active
Checkpoint internal _currentCheckpoint; // TODO: this storage is fucked need split structs
Checkpoint internal _currentCheckpoint;

/// @notice An address with permissions to call `startCheckpoint` and `verifyWithdrawalCredentials`, set
/// by the podOwner. This role exists to allow a podOwner to designate a hot wallet that can call
/// these methods, allowing the podOwner to remain a cold wallet that is only used to manage funds.
/// @dev If this address is NOT set, only the podOwner can call `startCheckpoint` and `verifyWithdrawalCredentials`
address public proofSubmitter;

/// @notice The total balance of the pod before the current checkpoint
uint128 public beaconChainBalanceBeforeCurrentCheckpoint;

Check warning

Code scanning / Slither

State variables that could be declared constant Warning


/**
* @dev This empty reserved space is put in place to allow future versions to add new
* variables without shifting down storage in the inheritance chain.
* See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps
*/
uint256[35] private __gap; // Reduced the gap size by 1 to accommodate the new variable
uint256[35] private __gap;
}

0 comments on commit 560cea6

Please sign in to comment.