Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions snapshots/SignatureGateway.Operations.json
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
{
"borrowWithSig": "222144",
"borrowWithSig": "222132",
"repayWithSig": "192513",
"setSelfAsUserPositionManagerWithSig": "75138",
"setUsingAsCollateralWithSig": "85380",
"supplyWithSig": "155914",
"updateUserDynamicConfigWithSig": "63113",
"updateUserRiskPremiumWithSig": "61995",
"updateUserDynamicConfigWithSig": "63101",
"updateUserRiskPremiumWithSig": "62007",
"withdrawWithSig": "135124"
}
2 changes: 1 addition & 1 deletion snapshots/TokenizationSpoke.Operations.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,5 +13,5 @@
"withdraw: on behalf, partial": "119557",
"withdraw: self, full": "94824",
"withdraw: self, partial": "114024",
"withdrawWithSig": "129405"
"withdrawWithSig": "129417"
}
47 changes: 31 additions & 16 deletions src/deployments/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -109,14 +109,17 @@ Hub and spoke labels (provided via `FullDeployInputs.hubLabels` / `spokeLabels`)

Roles are namespaced by contract domain: Hub (100-199), HubConfigurator (200-299), Spoke (300-399), SpokeConfigurator (400-499).

For configurators, initially a single Domain Admin role (HUB_CONFIGURATOR_DOMAIN_ADMIN_ROLE = 200, SPOKE_CONFIGURATOR_DOMAIN_ADMIN_ROLE = 400) holds all target selectors. As more granular roles are introduced, they should be added at the next available ID (201, 202, ... / 401, 402, ...) and the corresponding selectors reassigned from the Domain Admin role to the new granular role:
Each configurator has five granular roles covering the same five concerns, plus a Domain Admin role (200/400) holding the selectors that fall outside them. A role never spans both configurators — a Hub role only holds HubConfigurator selectors and a Spoke role only holds SpokeConfigurator selectors — so Hub and Spoke access is always granted separately. The first two roles are named after the flag they own rather than after pause/freeze, because the Hub has no `paused`/`frozen` flags of its own: the equivalent state lives on the Spoke config the Hub holds for each asset.

- Existing role IDs should never be overwritten or reused for a different purpose.
- New roles are always appended with an incremented ID.
- The Domain Admin role (200/400) only ever has its selector set shrink over time as selectors are divided into more granular roles.
- Addresses holding the Domain Admin role should be granted the new granular role being added to retain their existing access.
| Concern | Hub role | Spoke role | Purpose |
| -------------------- | ------------------------------------- | --------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| Prevent all activity | HUB_CONFIGURATOR_SPOKE_ACTIVE_ROLE | SPOKE_CONFIGURATOR_PAUSE_ROLE | Flips the flag that prevents all activity, in both directions. The Spoke `paused` flag, and the Hub's per-asset Spoke `active` flag which gates every Hub action. |
| Prevent new activity | HUB_CONFIGURATOR_SPOKE_HALTED_ROLE | SPOKE_CONFIGURATOR_FREEZE_ROLE | Flips the flag that prevents new activity, in both directions. The Spoke `frozen` flag, and the Hub's per-asset Spoke `halted` flag which gates the actions that instantly update liquidity. |
| Listing | HUB_CONFIGURATOR_LISTING_ROLE | SPOKE_CONFIGURATOR_LISTING_ROLE | Onboards new assets, Spokes and reserves, and sets the properties fixed at listing time. |
| Emergency | HUB_CONFIGURATOR_EMERGENCY_ROLE | SPOKE_CONFIGURATOR_EMERGENCY_ROLE | The one-directional batch flag actions. Every selector only ever moves a target to a safer state (pause, freeze, deactivate, halt) and cannot revert it, so it can be held by a faster-moving entity than the two-way flag roles above. The Hub's batch cap resets are deliberately excluded — see below. |
| Risk management | HUB_CONFIGURATOR_RISK_MANAGEMENT_ROLE | SPOKE_CONFIGURATOR_RISK_MANAGEMENT_ROLE | The risk parameters of an already listed asset or reserve: caps, interest rates, collateral risk, dynamic configs, liquidation config. |

See `Roles.sol` NatSpec for the full role strategy and evolution guidelines. All roles are labeled on the `AccessManagerEnumerable` during deployment via `AaveV4AccessManagerRolesProcedure.labelAllRoles()`. Each role is labeled with its `Roles.sol` constant name (e.g., role 101 is labeled `"HUB_CONFIGURATOR_ROLE"`). Labels are queryable on-chain via `getLabelOfRole()` and `getRoleOfLabel()`.
See `Roles.sol` NatSpec for the role strategy and the rules for adding new roles. All roles are labeled on the `AccessManagerEnumerable` during deployment via `AaveV4AccessManagerRolesProcedure.labelAllRoles()`. Each role is labeled with its `Roles.sol` constant name (e.g., role 101 is labeled `"HUB_CONFIGURATOR_ROLE"`). Labels are queryable on-chain via `getLabelOfRole()` and `getRoleOfLabel()`.

#### `AccessManager` Role

Expand All @@ -135,11 +138,18 @@ See `Roles.sol` NatSpec for the full role strategy and evolution guidelines. All

#### `HubConfigurator` Roles

| ID | Name | Granted To | Functions |
| --- | ---------------------------------- | -------------------- | ------------------------------------------------ |
| 200 | HUB_CONFIGURATOR_DOMAIN_ADMIN_ROLE | hubConfiguratorAdmin | All 22 HubConfigurator selectors (see Roles.sol) |
| ID | Name | Granted To | Functions |
| --- | ------------------------------------- | -------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------ |
| 200 | HUB_CONFIGURATOR_DOMAIN_ADMIN_ROLE | hubConfiguratorAdmin | updateLiquidityFee, updateFeeReceiver, updateFeeConfig, updateInterestRateStrategy, updateReinvestmentController, resetAssetCaps, resetSpokeCaps |
| 201 | HUB_CONFIGURATOR_SPOKE_ACTIVE_ROLE | hubConfiguratorAdmin | updateSpokeActive |
| 202 | HUB_CONFIGURATOR_SPOKE_HALTED_ROLE | hubConfiguratorAdmin | updateSpokeHalted |
| 203 | HUB_CONFIGURATOR_LISTING_ROLE | hubConfiguratorAdmin | addAsset, addAssetWithDecimals, addSpoke, addSpokeToAssets |
| 204 | HUB_CONFIGURATOR_EMERGENCY_ROLE | hubConfiguratorAdmin | deactivateAsset, haltAsset, deactivateSpoke, haltSpoke |
| 205 | HUB_CONFIGURATOR_RISK_MANAGEMENT_ROLE | hubConfiguratorAdmin | updateSpokeAddCap, updateSpokeDrawCap, updateSpokeCaps, updateSpokeRiskPremiumThreshold, updateInterestRateData |

Domain admin role holds all selectors initially. Granular roles (201+) are carved out as needed.
`resetAssetCaps` and `resetSpokeCaps` stay with the Domain Admin role rather than Emergency. Zeroing caps is as one-directional as a halt, but only risk management can restore them, so it is left to governance rather than to a fast-moving emergency holder.

`grantHubConfiguratorAllRoles` grants all six.

#### `Spoke` Roles (on Spoke contract)

Expand All @@ -151,11 +161,16 @@ Domain admin role holds all selectors initially. Granular roles (201+) are carve

#### `SpokeConfigurator` Roles (on SpokeConfigurator contract)

| ID | Name | Granted To | Functions |
| --- | ------------------------------------ | ---------------------- | -------------------------------------------------- |
| 400 | SPOKE_CONFIGURATOR_DOMAIN_ADMIN_ROLE | spokeConfiguratorAdmin | All 24 SpokeConfigurator selectors (see Roles.sol) |
| ID | Name | Granted To | Functions |
| --- | --------------------------------------- | ---------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 400 | SPOKE_CONFIGURATOR_DOMAIN_ADMIN_ROLE | spokeConfiguratorAdmin | updateReservePriceSource, updatePositionManager |
| 401 | SPOKE_CONFIGURATOR_PAUSE_ROLE | spokeConfiguratorAdmin | updatePaused |
| 402 | SPOKE_CONFIGURATOR_FREEZE_ROLE | spokeConfiguratorAdmin | updateFrozen |
| 403 | SPOKE_CONFIGURATOR_LISTING_ROLE | spokeConfiguratorAdmin | addReserve, updateBorrowable, updateReceiveSharesEnabled |
| 404 | SPOKE_CONFIGURATOR_EMERGENCY_ROLE | spokeConfiguratorAdmin | pauseReserve, pauseAllReserves, freezeReserve, freezeAllReserves |
| 405 | SPOKE_CONFIGURATOR_RISK_MANAGEMENT_ROLE | spokeConfiguratorAdmin | updateCollateralRisk, addCollateralFactor, updateCollateralFactor, addMaxLiquidationBonus, updateMaxLiquidationBonus, addLiquidationFee, updateLiquidationFee, addDynamicReserveConfig, updateDynamicReserveConfig, updateLiquidationTargetHealthFactor, updateHealthFactorForMaxBonus, updateLiquidationBonusFactor, updateLiquidationConfig |

Domain admin role holds all selectors initially. Granular roles (401+) are carved out as needed.
`grantSpokeConfiguratorAllRoles` grants all six.

## Data Flow

Expand Down Expand Up @@ -242,12 +257,12 @@ AaveV4DeployBatchBase.s.sol (Foundry script entry point)
| | AaveV4HubRolesProcedure.grantHubAllRoles() hubAdmin gets roles 101-103
| | AaveV4HubRolesProcedure.grantHubRole() HubConfigurator gets role 101
| | AaveV4HubConfiguratorRolesProcedure.grantHubConfiguratorAllRoles()
| | hubConfiguratorAdmin gets role 200
| | hubConfiguratorAdmin gets roles 200-205
| | _grantSpokeRoles() (if spokeLabels.length > 0)
| | AaveV4SpokeRolesProcedure.grantSpokeAllRoles() spokeAdmin gets roles 301-302
| | AaveV4SpokeRolesProcedure.grantSpokeRole() SpokeConfigurator gets role 301
| | AaveV4SpokeConfiguratorRolesProcedure.grantSpokeConfiguratorAllRoles()
| | spokeConfiguratorAdmin gets role 400
| | spokeConfiguratorAdmin gets roles 400-405
| | AaveV4AccessManagerRolesProcedure.replaceDefaultAdminRole()
| | (if accessManagerAdmin != deployer)
| | grant role 0 to accessManagerAdmin, revoke from deployer
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,14 @@ library AaveV4AccessManagerRolesProcedure {

// HubConfigurator roles
am.labelRole(Roles.HUB_CONFIGURATOR_DOMAIN_ADMIN_ROLE, 'HUB_CONFIGURATOR_DOMAIN_ADMIN_ROLE');
am.labelRole(Roles.HUB_CONFIGURATOR_SPOKE_ACTIVE_ROLE, 'HUB_CONFIGURATOR_SPOKE_ACTIVE_ROLE');
am.labelRole(Roles.HUB_CONFIGURATOR_SPOKE_HALTED_ROLE, 'HUB_CONFIGURATOR_SPOKE_HALTED_ROLE');
am.labelRole(Roles.HUB_CONFIGURATOR_LISTING_ROLE, 'HUB_CONFIGURATOR_LISTING_ROLE');
am.labelRole(Roles.HUB_CONFIGURATOR_EMERGENCY_ROLE, 'HUB_CONFIGURATOR_EMERGENCY_ROLE');
am.labelRole(
Roles.HUB_CONFIGURATOR_RISK_MANAGEMENT_ROLE,
'HUB_CONFIGURATOR_RISK_MANAGEMENT_ROLE'
);

// Spoke roles
am.labelRole(Roles.SPOKE_DOMAIN_ADMIN_ROLE, 'SPOKE_DOMAIN_ADMIN_ROLE');
Expand All @@ -33,6 +41,14 @@ library AaveV4AccessManagerRolesProcedure {
Roles.SPOKE_CONFIGURATOR_DOMAIN_ADMIN_ROLE,
'SPOKE_CONFIGURATOR_DOMAIN_ADMIN_ROLE'
);
am.labelRole(Roles.SPOKE_CONFIGURATOR_PAUSE_ROLE, 'SPOKE_CONFIGURATOR_PAUSE_ROLE');
am.labelRole(Roles.SPOKE_CONFIGURATOR_FREEZE_ROLE, 'SPOKE_CONFIGURATOR_FREEZE_ROLE');
am.labelRole(Roles.SPOKE_CONFIGURATOR_LISTING_ROLE, 'SPOKE_CONFIGURATOR_LISTING_ROLE');
am.labelRole(Roles.SPOKE_CONFIGURATOR_EMERGENCY_ROLE, 'SPOKE_CONFIGURATOR_EMERGENCY_ROLE');
am.labelRole(
Roles.SPOKE_CONFIGURATOR_RISK_MANAGEMENT_ROLE,
'SPOKE_CONFIGURATOR_RISK_MANAGEMENT_ROLE'
);
Comment thread
AlbertoCentonze marked this conversation as resolved.
}

/// @notice Replaces the default admin by granting the role to a new address and revoking it from the old one.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,16 @@ import {Roles} from 'src/deployments/utils/libraries/Roles.sol';
/// @author Aave Labs
/// @notice Procedures for granting and setting up HubConfigurator roles on the AccessManager.
library AaveV4HubConfiguratorRolesProcedure {
/// @notice Grants the HubConfigurator domain admin role (200) to `admin`.
/// @notice Grants every HubConfigurator role (200-205) to `admin`.
/// @param accessManager The address of the AccessManager contract.
/// @param admin The address to receive the HubConfigurator domain admin role.
/// @param admin The address to receive the HubConfigurator roles.
function grantHubConfiguratorAllRoles(address accessManager, address admin) internal {
grantHubConfiguratorRole(accessManager, Roles.HUB_CONFIGURATOR_DOMAIN_ADMIN_ROLE, admin);
grantHubConfiguratorRole(accessManager, Roles.HUB_CONFIGURATOR_SPOKE_ACTIVE_ROLE, admin);
grantHubConfiguratorRole(accessManager, Roles.HUB_CONFIGURATOR_SPOKE_HALTED_ROLE, admin);
grantHubConfiguratorRole(accessManager, Roles.HUB_CONFIGURATOR_LISTING_ROLE, admin);
grantHubConfiguratorRole(accessManager, Roles.HUB_CONFIGURATOR_EMERGENCY_ROLE, admin);
grantHubConfiguratorRole(accessManager, Roles.HUB_CONFIGURATOR_RISK_MANAGEMENT_ROLE, admin);
}

/// @notice Grants a specific HubConfigurator role to the given address.
Expand All @@ -25,7 +30,7 @@ library AaveV4HubConfiguratorRolesProcedure {
IAccessManager(accessManager).grantRole({roleId: role, account: admin, executionDelay: 0});
}

/// @notice Sets up the HubConfigurator domain admin role with all target selectors.
/// @notice Sets up every HubConfigurator role (200-205) with its target selectors.
/// @param accessManager The address of the AccessManager contract.
/// @param hubConfigurator The address of the HubConfigurator contract.
function setupHubConfiguratorAllRoles(address accessManager, address hubConfigurator) internal {
Expand All @@ -35,6 +40,36 @@ library AaveV4HubConfiguratorRolesProcedure {
Roles.HUB_CONFIGURATOR_DOMAIN_ADMIN_ROLE,
Roles.getHubConfiguratorDomainAdminRoleSelectors()
);
setupHubConfiguratorRole(
accessManager,
hubConfigurator,
Roles.HUB_CONFIGURATOR_SPOKE_ACTIVE_ROLE,
Roles.getHubConfiguratorSpokeActiveRoleSelectors()
);
setupHubConfiguratorRole(
accessManager,
hubConfigurator,
Roles.HUB_CONFIGURATOR_SPOKE_HALTED_ROLE,
Roles.getHubConfiguratorSpokeHaltedRoleSelectors()
);
setupHubConfiguratorRole(
accessManager,
hubConfigurator,
Roles.HUB_CONFIGURATOR_LISTING_ROLE,
Roles.getHubConfiguratorListingRoleSelectors()
);
setupHubConfiguratorRole(
accessManager,
hubConfigurator,
Roles.HUB_CONFIGURATOR_EMERGENCY_ROLE,
Roles.getHubConfiguratorEmergencyRoleSelectors()
);
setupHubConfiguratorRole(
accessManager,
hubConfigurator,
Roles.HUB_CONFIGURATOR_RISK_MANAGEMENT_ROLE,
Roles.getHubConfiguratorRiskManagementRoleSelectors()
);
}

/// @notice Sets up a specific HubConfigurator role by assigning function selectors to the target.
Expand Down
Loading
Loading