Skip to content

Commit 588dc64

Browse files
fix: STAA-12 remediation commit i
1 parent bc8cfa0 commit 588dc64

File tree

3 files changed

+44
-2
lines changed

3 files changed

+44
-2
lines changed

src/StartaleSmartAccount.sol

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -323,6 +323,7 @@ contract StartaleSmartAccount is
323323
_tryUninstallPreValidationHook(
324324
_getPreValidationHook(MODULE_TYPE_PREVALIDATION_HOOK_ERC4337), MODULE_TYPE_PREVALIDATION_HOOK_ERC4337
325325
);
326+
_tryUninstallFallbacks();
326327
_initSentinelLists();
327328
}
328329

src/core/ModuleManager.sol

Lines changed: 41 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -328,6 +328,27 @@ abstract contract ModuleManager is AllStorage, EIP712, IModuleManager {
328328
}
329329
}
330330

331+
// Review: if uninstalling selectors also need some data.
332+
function _tryUninstallFallbacks() internal {
333+
AccountStorage storage ds = _getAccountStorage();
334+
uint256 len = ds.fallbackSelectors.length;
335+
336+
for (uint256 i = 0; i < len; i++) {
337+
bytes4 selector = ds.fallbackSelectors[i];
338+
FallbackHandler memory handler = ds.fallbacks[selector];
339+
340+
if (address(handler.handler) == address(0)) continue;
341+
342+
handler.handler.excessivelySafeCall(
343+
gasleft(), 0, 0, abi.encodeWithSelector(IModule.onUninstall.selector, abi.encodePacked(selector))
344+
);
345+
346+
ds.fallbacks[selector] = FallbackHandler(address(0), CallType.wrap(0x00));
347+
}
348+
349+
delete ds.fallbackSelectors;
350+
}
351+
331352
/// @dev Sets the current hook in the storage to the specified address.
332353
/// @param hook The new hook address.
333354
function _setHook(address hook) internal virtual {
@@ -365,9 +386,14 @@ abstract contract ModuleManager is AllStorage, EIP712, IModuleManager {
365386
// This check ensures that we do not overwrite an existing fallback handler, which could lead to unexpected behavior.
366387
require(!_isFallbackHandlerInstalled(selector), FallbackAlreadyInstalledForSelector(selector));
367388

389+
AccountStorage storage ds = _getAccountStorage();
390+
368391
// Store the fallback handler and its call type in the account storage.
369392
// This maps the function selector to the specified fallback handler and call type.
370-
_getAccountStorage().fallbacks[selector] = FallbackHandler(handler, calltype);
393+
ds.fallbacks[selector] = FallbackHandler(handler, calltype);
394+
395+
// Add the selector to the maintained list of fallback selectors
396+
ds.fallbackSelectors.push(selector);
371397

372398
// Invoke the `onInstall` function of the fallback handler with the provided initialization data.
373399
// This step allows the fallback handler to perform any necessary setup or initialization.
@@ -378,7 +404,20 @@ abstract contract ModuleManager is AllStorage, EIP712, IModuleManager {
378404
/// @param fallbackHandler The address of the fallback handler to uninstall.
379405
/// @param data The de-initialization data containing the selector.
380406
function _uninstallFallbackHandler(address fallbackHandler, bytes calldata data) internal virtual {
381-
_getAccountStorage().fallbacks[bytes4(data[0:4])] = FallbackHandler(address(0), CallType.wrap(0x00));
407+
AccountStorage storage ds = _getAccountStorage();
408+
bytes4 selector = bytes4(data[0:4]);
409+
ds.fallbacks[selector] = FallbackHandler(address(0), CallType.wrap(0x00));
410+
411+
// Remove selector from fallbackSelectors via swap-and-pop
412+
uint256 len = ds.fallbackSelectors.length;
413+
for (uint256 i = 0; i < len; i++) {
414+
if (ds.fallbackSelectors[i] == selector) {
415+
ds.fallbackSelectors[i] = ds.fallbackSelectors[len - 1];
416+
ds.fallbackSelectors.pop();
417+
break;
418+
}
419+
}
420+
382421
fallbackHandler.excessivelySafeCall(gasleft(), 0, 0, abi.encodeWithSelector(IModule.onUninstall.selector, data[4:]));
383422
}
384423

src/interfaces/core/IAllStorage.sol

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,8 @@ interface IAllStorage {
1818
SentinelListLib.SentinelList executors;
1919
///< Mapping of selectors to their respective fallback handlers.
2020
mapping(bytes4 => FallbackHandler) fallbacks;
21+
///< List of fallback selectors, initialized upon contract deployment.
22+
bytes4[] fallbackSelectors;
2123
///< Current hook module associated with this account.
2224
IHook hook;
2325
///< Mapping of hooks to requested timelocks.

0 commit comments

Comments
 (0)