From d6767834c5d2dfdb144f61f75a26d956dadb6338 Mon Sep 17 00:00:00 2001 From: Jonas Bostoen Date: Mon, 14 Oct 2024 16:19:39 +0200 Subject: [PATCH] feat(contracts): add storage gaps + documentation --- .../src/contracts/BoltChallenger.sol | 17 +++++++++++ .../contracts/BoltEigenLayerMiddleware.sol | 23 +++++++++++++-- bolt-contracts/src/contracts/BoltManager.sol | 18 ++++++++++++ .../src/contracts/BoltParameters.sol | 5 ++++ .../src/contracts/BoltSymbioticMiddleware.sol | 28 +++++++++++++++---- .../src/contracts/BoltValidators.sol | 15 ++++++++++ 6 files changed, 98 insertions(+), 8 deletions(-) diff --git a/bolt-contracts/src/contracts/BoltChallenger.sol b/bolt-contracts/src/contracts/BoltChallenger.sol index 6a88fdc62..c5bd3e6e1 100644 --- a/bolt-contracts/src/contracts/BoltChallenger.sol +++ b/bolt-contracts/src/contracts/BoltChallenger.sol @@ -17,6 +17,11 @@ import {TransactionDecoder} from "../lib/TransactionDecoder.sol"; import {IBoltChallenger} from "../interfaces/IBoltChallenger.sol"; import {IBoltParameters} from "../interfaces/IBoltParameters.sol"; +/// @title Bolt Challenger +/// @notice Contract for managing (creating & resolving) challenges for Bolt inclusion commitments. +/// @dev This contract is upgradeable using the UUPSProxy pattern. Storage layout remains fixed across upgrades +/// with the use of storage gaps. +/// See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps contract BoltChallenger is IBoltChallenger, OwnableUpgradeable, UUPSUpgradeable { using RLPReader for bytes; using RLPReader for RLPReader.RLPItem; @@ -35,6 +40,18 @@ contract BoltChallenger is IBoltChallenger, OwnableUpgradeable, UUPSUpgradeable /// @notice The mapping of challenge IDs to their respective challenges. mapping(bytes32 => Challenge) internal challenges; + // --> Storage layout marker: 3 slots + + /** + * @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 + * This can be validated with the Openzeppelin Foundry Upgrades toolkit. + * + * Total storage slots: 50 + */ + uint256[47] private __gap; + // ========= INITIALIZER ========= /// @notice Initializer diff --git a/bolt-contracts/src/contracts/BoltEigenLayerMiddleware.sol b/bolt-contracts/src/contracts/BoltEigenLayerMiddleware.sol index 00fe01a87..4cb629387 100644 --- a/bolt-contracts/src/contracts/BoltEigenLayerMiddleware.sol +++ b/bolt-contracts/src/contracts/BoltEigenLayerMiddleware.sol @@ -23,6 +23,11 @@ import {AVSDirectoryStorage} from "@eigenlayer/src/contracts/core/AVSDirectorySt import {DelegationManagerStorage} from "@eigenlayer/src/contracts/core/DelegationManagerStorage.sol"; import {StrategyManagerStorage} from "@eigenlayer/src/contracts/core/StrategyManagerStorage.sol"; +/// @title Bolt Manager +/// @notice This contract is responsible for interfacing with the EigenLayer restaking protocol. +/// @dev This contract is upgradeable using the UUPSProxy pattern. Storage layout remains fixed across upgrades +/// with the use of storage gaps. +/// See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps contract BoltEigenLayerMiddleware is IBoltMiddleware, OwnableUpgradeable, UUPSUpgradeable { using EnumerableSet for EnumerableSet.AddressSet; using EnumerableMap for EnumerableMap.AddressToUintMap; @@ -52,12 +57,23 @@ contract BoltEigenLayerMiddleware is IBoltMiddleware, OwnableUpgradeable, UUPSUp /// @notice Address of the EigenLayer Strategy Manager contract. StrategyManagerStorage public STRATEGY_MANAGER; + /// @notice Name hash of the restaking protocol for identifying the instance of `IBoltMiddleware`. + bytes32 public NAME_HASH; + + // --> Storage layout marker: 8 slots + /// @notice Start timestamp of the first epoch. uint48 public START_TIMESTAMP; - // ========= CONSTANTS ========= - /// @notice Name hash of the restaking protocol for identifying the instance of `IBoltMiddleware`. - bytes32 public constant NAME_HASH = keccak256("EIGENLAYER"); + /** + * @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 + * This can be validated with the Openzeppelin Foundry Upgrades toolkit. + * + * Total storage slots: 50 + */ + uint256[42] private __gap; // ========= ERRORS ========= @@ -88,6 +104,7 @@ contract BoltEigenLayerMiddleware is IBoltMiddleware, OwnableUpgradeable, UUPSUp AVS_DIRECTORY = AVSDirectoryStorage(_eigenlayerAVSDirectory); DELEGATION_MANAGER = DelegationManagerStorage(_eigenlayerDelegationManager); STRATEGY_MANAGER = StrategyManagerStorage(_eigenlayerStrategyManager); + NAME_HASH = keccak256("EIGENLAYER"); } function _authorizeUpgrade( diff --git a/bolt-contracts/src/contracts/BoltManager.sol b/bolt-contracts/src/contracts/BoltManager.sol index f1499f2b5..9ade2b10d 100644 --- a/bolt-contracts/src/contracts/BoltManager.sol +++ b/bolt-contracts/src/contracts/BoltManager.sol @@ -14,6 +14,12 @@ import {IBoltParameters} from "../interfaces/IBoltParameters.sol"; import {IBoltMiddleware} from "../interfaces/IBoltMiddleware.sol"; import {IBoltManager} from "../interfaces/IBoltManager.sol"; +/// @title Bolt Manager +/// @notice The Bolt Manager contract is responsible for managing operators & restaking middlewares, and is the +/// entrypoint contract for all Bolt-related queries for off-chain consumers. +/// @dev This contract is upgradeable using the UUPSProxy pattern. Storage layout remains fixed across upgrades +/// with the use of storage gaps. +/// See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps contract BoltManager is IBoltManager, OwnableUpgradeable, UUPSUpgradeable { using EnumerableSet for EnumerableSet.AddressSet; using EnumerableMap for EnumerableMap.OperatorMap; @@ -35,9 +41,21 @@ contract BoltManager is IBoltManager, OwnableUpgradeable, UUPSUpgradeable { /// associated Bolt Middleware contract. EnumerableSet.AddressSet private restakingProtocols; + // --> Storage layout marker: 4 slots + /// @notice Start timestamp of the first epoch. uint48 public START_TIMESTAMP; + /** + * @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 + * This can be validated with the Openzeppelin Foundry Upgrades toolkit. + * + * Total storage slots: 50 + */ + uint256[46] private __gap; + modifier onlyMiddleware() { if (!restakingProtocols.contains(msg.sender)) { revert UnauthorizedMiddleware(); diff --git a/bolt-contracts/src/contracts/BoltParameters.sol b/bolt-contracts/src/contracts/BoltParameters.sol index c9a47c37e..24d12259a 100644 --- a/bolt-contracts/src/contracts/BoltParameters.sol +++ b/bolt-contracts/src/contracts/BoltParameters.sol @@ -4,6 +4,11 @@ pragma solidity 0.8.25; import {OwnableUpgradeable} from "@openzeppelin/contracts-upgradeable/access/OwnableUpgradeable.sol"; import {UUPSUpgradeable} from "@openzeppelin/contracts/proxy/utils/UUPSUpgradeable.sol"; +/// @title Bolt Parameters +/// @notice The BoltParameters contract contains all the parameters for the Bolt protocol. +/// @dev This contract is upgradeable using the UUPSProxy pattern. Storage layout remains fixed across upgrades +/// with the use of storage gaps. +/// See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps contract BoltParameters is OwnableUpgradeable, UUPSUpgradeable { // =========== STORAGE =========== // diff --git a/bolt-contracts/src/contracts/BoltSymbioticMiddleware.sol b/bolt-contracts/src/contracts/BoltSymbioticMiddleware.sol index 5bd12163e..7ba50b639 100644 --- a/bolt-contracts/src/contracts/BoltSymbioticMiddleware.sol +++ b/bolt-contracts/src/contracts/BoltSymbioticMiddleware.sol @@ -23,6 +23,11 @@ import {IBoltParameters} from "../interfaces/IBoltParameters.sol"; import {IBoltMiddleware} from "../interfaces/IBoltMiddleware.sol"; import {IBoltManager} from "../interfaces/IBoltManager.sol"; +/// @title Bolt Symbiotic Middleware +/// @notice This contract is responsible for interfacing with the Symbiotic restaking protocol. +/// @dev This contract is upgradeable using the UUPSProxy pattern. Storage layout remains fixed across upgrades +/// with the use of storage gaps. +/// See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps contract BoltSymbioticMiddleware is IBoltMiddleware, OwnableUpgradeable, UUPSUpgradeable { using EnumerableSet for EnumerableSet.AddressSet; using EnumerableMap for EnumerableMap.AddressToUintMap; @@ -59,15 +64,25 @@ contract BoltSymbioticMiddleware is IBoltMiddleware, OwnableUpgradeable, UUPSUpg /// @notice Start timestamp of the first epoch. uint48 public START_TIMESTAMP; - // ========= CONSTANTS ========= - /// @notice Slasher that can instantly slash operators without veto. - uint256 public constant INSTANT_SLASHER_TYPE = 0; + uint256 public INSTANT_SLASHER_TYPE; /// @notice Slasher that can request a veto before actually slashing operators. - uint256 public constant VETO_SLASHER_TYPE = 1; + uint256 public VETO_SLASHER_TYPE; + + bytes32 public NAME_HASH; + + // --> Storage layout marker: 12 slots - bytes32 public constant NAME_HASH = keccak256("SYMBIOTIC"); + /** + * @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 + * This can be validated with the Openzeppelin Foundry Upgrades toolkit. + * + * Total storage slots: 50 + */ + uint256[38] private __gap; // ========= ERRORS ========= @@ -102,6 +117,9 @@ contract BoltSymbioticMiddleware is IBoltMiddleware, OwnableUpgradeable, UUPSUpg OPERATOR_REGISTRY = _symbioticOperatorRegistry; OPERATOR_NET_OPTIN = _symbioticOperatorNetOptIn; VAULT_REGISTRY = _symbioticVaultRegistry; + INSTANT_SLASHER_TYPE = 0; + VETO_SLASHER_TYPE = 1; + NAME_HASH = keccak256("SYMBIOTIC"); } function _authorizeUpgrade( diff --git a/bolt-contracts/src/contracts/BoltValidators.sol b/bolt-contracts/src/contracts/BoltValidators.sol index 98a77c217..5aadd932e 100644 --- a/bolt-contracts/src/contracts/BoltValidators.sol +++ b/bolt-contracts/src/contracts/BoltValidators.sol @@ -11,6 +11,9 @@ import {IBoltParameters} from "../interfaces/IBoltParameters.sol"; /// @title Bolt Validators /// @notice This contract is responsible for registering validators and managing their configuration +/// @dev This contract is upgradeable using the UUPSProxy pattern. Storage layout remains fixed across upgrades +/// with the use of storage gaps. +/// See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps contract BoltValidators is IBoltValidators, BLSSignatureVerifier, OwnableUpgradeable, UUPSUpgradeable { using BLS12381 for BLS12381.G1Point; @@ -32,11 +35,23 @@ contract BoltValidators is IBoltValidators, BLSSignatureVerifier, OwnableUpgrade /// @dev This is used internally to easily query the pubkey hash of a validator. mapping(uint64 => bytes32) private sequenceNumberToPubkeyHash; + // --> Storage layout marker: 3 slots + /// @notice counter of the next index to be assigned to a validator. /// @dev This incremental index is only used to identify validators in the registry. /// It is not related to the `validatorIndex` assigned by the Beacon Chain. uint64 internal nextValidatorSequenceNumber; + /** + * @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 + * This can be validated with the Openzeppelin Foundry Upgrades toolkit. + * + * Total storage slots: 50 + */ + uint256[47] private __gap; + // ========= EVENTS ========= /// @notice Emitted when a validator is registered