Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add native registry integration #101

Merged

Conversation

kopy-kat
Copy link

This adds an integration into ERC-7484 natively into the account. Users can use the account as is or with a Registry for higher default security.

@Aboudjem Aboudjem changed the base branch from main to dev June 19, 2024 11:30
@Aboudjem Aboudjem requested review from Aboudjem, livingrockrises and filmakarov and removed request for Aboudjem and livingrockrises June 19, 2024 11:33
@@ -306,6 +320,10 @@ contract Nexus is INexus, EIP712, BaseAccount, ExecutionHelper, ModuleManager, U
return _ACCOUNT_IMPLEMENTATION_ID;
}

function setRegistry(IERC7484 newRegistry, address[] calldata attesters, uint8 threshold) external onlyEntryPointOrSelf {
_configureRegistry(newRegistry, attesters, threshold);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

at which point SA is made to call

function trustAttesters(
uint8 threshold,
address[] memory attesters // deliberately using memory to allow sorting and uniquifying
)

?

That's an optional step with initcode approach we talked about right with specific factory when deploying the account?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes, this could be called during the initialization by the factory (eg see bootstrap) or after an account has been created already

IERC7484 _registry = registry;
if (address(_registry) != address(0)) {
// this will revert if attestations / threshold are not met
_registry.check(module, moduleType);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if we do this everytime through modifier
_checkRegistry

that means, we will always call check() function
and SA should have called trustAttestors before that?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

when could these be used?
function checkN(address module, address[] calldata attesters, uint256 threshold) external view;
function checkN(address module, uint256 moduleType, address[] calldata attesters, uint256 threshold) external view;

if we enshrine this current code

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes thats right, the smart account should've set their trusted attesters before

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

imo it makes more sense to store attesters in the registry since they can then also eg be used by a session key module to check sub-modules on the registry

@@ -76,7 +97,7 @@ contract K1ValidatorFactory is Stakeable {

// Create the validator configuration using the Bootstrap library
BootstrapConfig memory validator = BootstrapLib.createSingleConfig(K1_VALIDATOR, abi.encodePacked(eoaOwner));
bytes memory initData = BOOTSTRAPPER.getInitNexusWithSingleValidatorCalldata(validator);
bytes memory initData = BOOTSTRAPPER.getInitNexusWithSingleValidatorCalldata(validator, REGISTRY, attesters, threshold);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this would set the registry and also add the attesters during bootstrap?
and we can pass 0 addresses for registry, array of address 0 for attesters and threshold also 0.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

correct

error ZeroAddressNotAllowed();

IERC7484 public immutable REGISTRY;
address[] public attesters;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this would maintain attesters here instead of calling trust attesters from the account?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

in this case, the factory has its own attesters but the users account will also call trust attesters if the registry provided is not address(0). so this factory behaves pretty much like the whitelist that was there before but the whitelist is in the registry using the attesters set by the owner of the factory

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

initData in createAccount() allows attesters and threshold to be provided externally. how does it align with attesters and threshold (dynamic cause of ownable) stored in the contract's storage?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So this specific factory will use the factory-native attesters to query the initial modules and then set trustAttesters with the user provided ones and from then on use this

Copy link
Contributor

@livingrockrises livingrockrises left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

review i

abstract contract RegistryAdapter {
event ERC7484RegistryConfigured(IERC7484 indexed registry);

IERC7484 registry;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
IERC7484 registry;
IERC7484 public registry;

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can we also rename to moduleRegistry and add ERC7484 in natspecs

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yeah I havent added natspec yet but happy to add it

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we will do it nw

}

function setThreshold(uint8 newThreshold) external onlyOwner {
threshold = newThreshold;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should check current array size

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is to be removed?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes. I think we can get our questions answered and get started with decided changes / intervene.


/// @title Bootstrap
/// @notice Manages the installation of modules into Nexus smart accounts using delegatecalls.
contract Bootstrap is ModuleManager {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we assume this will be used on all factories and part of Nexus, can we merge the RegistryAdapter into ModuleManager and move the state variable to Storage.sol?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

different contracts are good for separation of concern.

Bootstrap could be is ModuleManager, RegistryAdapter (keeping registry storage in adapter)

or maybe just moving storage to Storage.sol

/// @param executors The configuration array for executor modules.
/// @param hook The configuration for the hook module.
/// @param fallbacks The configuration array for fallback handler modules.
function initNexus(
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is it okay to have two kinds of methods here withRegistry and withoutRegistry
and similarly K1ValidatorFactory and K1ValidatorFactoryWithRegistry

if I use K1ValidatorFactoryWithRegistry with 0 addresses then it would unnecessarily increase gas. we can do comparison benchmark though @Aboudjem

Copy link
Contributor

@livingrockrises livingrockrises left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM. we need to review once again about how storage is managed (the part where RegistryBootstrap is ModuleManager) whereas registry storage is in registry adapter. as we use bootstrap to delegate call to.
@Aboudjem @kopy-kat

Copy link
Contributor

@livingrockrises livingrockrises left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

review ii

error ZeroAddressNotAllowed();

IERC7484 public immutable REGISTRY;
address[] public attesters;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

initData in createAccount() allows attesters and threshold to be provided externally. how does it align with attesters and threshold (dynamic cause of ownable) stored in the contract's storage?

@livingrockrises livingrockrises changed the base branch from dev to feature/native-registry June 24, 2024 07:11
@livingrockrises livingrockrises merged commit 14cfa4b into bcnmy:feature/native-registry Jun 25, 2024
3 of 8 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants