Functions allow interaction with services removed from registry
Description
Several functions validate services using only the local _approvedServices[service] mapping without checking the ServiceRegistry, allowing interaction with previously approved services that have been removed from the registry:
function getBalance(address service, address asset) external view returns (uint256) {
! if (!_approvedServices[service]) revert ManagementAccountErrors.ServiceNotApproved(service);
[...]
}
function requestCreditMode(address service, address collateralToken) external onlyOwner {
! if (!_approvedServices[service]) revert ManagementAccountErrors.ServiceNotApproved(service);
[...]
}
function requestCreditModeChange(address newService, address newCollateralToken) external onlyOwner {
! if (!_approvedServices[newService]) revert ManagementAccountErrors.ServiceNotApproved(newService);
[...]
}This creates inconsistent behavior where some functions (like executeServiceAction) properly validate registry membership using _validateRegisteredService, while these functions only check local approval status.
Impact
Accounts can continue interacting with delisted or compromised services through getBalance, requestCreditMode, requestCreditModeChange, and executeModeChange. This undermines the registry's purpose as a centralized control point for managing active services and creates security risks if services are removed due to vulnerabilities or deprecation.
Recommendations
Update these functions to use _validateRegisteredService for proper validation:
function getBalance(address service, address asset) external view returns (uint256) {
- if (!_approvedServices[service]) revert ManagementAccountErrors.ServiceNotApproved(service);
+ _validateRegisteredService(service);
[...]
}
function requestCreditMode(address service, address collateralToken) external onlyOwner {
- if (!_approvedServices[service]) revert ManagementAccountErrors.ServiceNotApproved(service);
+ _validateRegisteredService(service);
[...]
}
function requestCreditModeChange(address newService, address newCollateralToken) external onlyOwner {
- if (!_approvedServices[newService]) revert ManagementAccountErrors.ServiceNotApproved(newService);
+ _validateRegisteredService(newService);
[...]
}
function executeModeChange() external onlyOperator {
+ if (_pendingMode == AccountMode.CREDIT && _pendingCreditService != address(0)) {
+ _validateRegisteredService(_pendingCreditService);
+ }
[...]
}