-
Notifications
You must be signed in to change notification settings - Fork 38
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
17 changed files
with
401 additions
and
104 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
63183 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
39356 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
188347 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
84168 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
60080 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,104 @@ | ||
// SPDX-License-Identifier: UNLICENSED | ||
// !! THIS FILE WAS AUTOGENERATED BY abi-to-sol v0.8.0. SEE SOURCE BELOW. !! | ||
pragma solidity ^0.8.20; | ||
|
||
interface ILightAccount { | ||
error ArrayLengthMismatch(); | ||
error ECDSAInvalidSignature(); | ||
error ECDSAInvalidSignatureLength(uint256 length); | ||
error ECDSAInvalidSignatureS(bytes32 s); | ||
error InvalidInitialization(); | ||
error InvalidOwner(address owner); | ||
error InvalidSignatureType(); | ||
error NotAuthorized(address caller); | ||
error NotInitializing(); | ||
error UnauthorizedCallContext(); | ||
error UpgradeFailed(); | ||
error ZeroAddressNotAllowed(); | ||
|
||
event Initialized(uint64 version); | ||
event LightAccountInitialized(address indexed entryPoint, address indexed owner); | ||
event OwnershipTransferred(address indexed previousOwner, address indexed newOwner); | ||
event Upgraded(address indexed implementation); | ||
|
||
function addDeposit() external payable; | ||
|
||
function eip712Domain() | ||
external | ||
view | ||
returns ( | ||
bytes1 fields, | ||
string memory name, | ||
string memory version, | ||
uint256 chainId, | ||
address verifyingContract, | ||
bytes32 salt, | ||
uint256[] memory extensions | ||
); | ||
|
||
function entryPoint() external view returns (address); | ||
|
||
function execute(address dest, uint256 value, bytes memory func) external; | ||
|
||
function executeBatch(address[] memory dest, bytes[] memory func) external; | ||
|
||
function executeBatch(address[] memory dest, uint256[] memory value, bytes[] memory func) external; | ||
|
||
function getDeposit() external view returns (uint256); | ||
|
||
function getMessageHash(bytes memory message) external view returns (bytes32); | ||
|
||
function getNonce() external view returns (uint256); | ||
|
||
function initialize(address owner_) external; | ||
|
||
function isValidSignature(bytes32 hash, bytes memory signature) external view returns (bytes4); | ||
|
||
function onERC1155BatchReceived(address, address, uint256[] memory, uint256[] memory, bytes memory) | ||
external | ||
pure | ||
returns (bytes4); | ||
|
||
function onERC1155Received(address, address, uint256, uint256, bytes memory) external pure returns (bytes4); | ||
|
||
function onERC721Received(address, address, uint256, bytes memory) external pure returns (bytes4); | ||
|
||
function owner() external view returns (address); | ||
|
||
function proxiableUUID() external view returns (bytes32); | ||
|
||
function supportsInterface(bytes4 interfaceId) external view returns (bool); | ||
|
||
function transferOwnership(address newOwner) external; | ||
|
||
function upgradeToAndCall(address newImplementation, bytes memory data) external payable; | ||
|
||
function validateUserOp(PackedUserOperation memory userOp, bytes32 userOpHash, uint256 missingAccountFunds) | ||
external | ||
returns (uint256 validationData); | ||
|
||
function withdrawDepositTo(address withdrawAddress, uint256 amount) external; | ||
|
||
receive() external payable; | ||
} | ||
|
||
struct PackedUserOperation { | ||
address sender; | ||
uint256 nonce; | ||
bytes initCode; | ||
bytes callData; | ||
bytes32 accountGasLimits; | ||
uint256 preVerificationGas; | ||
bytes32 gasFees; | ||
bytes paymasterAndData; | ||
bytes signature; | ||
} | ||
|
||
// THIS FILE WAS AUTOGENERATED FROM THE FOLLOWING ABI JSON: | ||
/* | ||
[{"inputs":[{"internalType":"contract | ||
IEntryPoint","name":"entryPoint_","type":"address"}],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[],"name":"ArrayLengthMismatch","type":"error"},{"inputs":[],"name":"ECDSAInvalidSignature","type":"error"},{"inputs":[{"internalType":"uint256","name":"length","type":"uint256"}],"name":"ECDSAInvalidSignatureLength","type":"error"},{"inputs":[{"internalType":"bytes32","name":"s","type":"bytes32"}],"name":"ECDSAInvalidSignatureS","type":"error"},{"inputs":[],"name":"InvalidInitialization","type":"error"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"InvalidOwner","type":"error"},{"inputs":[],"name":"InvalidSignatureType","type":"error"},{"inputs":[{"internalType":"address","name":"caller","type":"address"}],"name":"NotAuthorized","type":"error"},{"inputs":[],"name":"NotInitializing","type":"error"},{"inputs":[],"name":"UnauthorizedCallContext","type":"error"},{"inputs":[],"name":"UpgradeFailed","type":"error"},{"inputs":[],"name":"ZeroAddressNotAllowed","type":"error"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint64","name":"version","type":"uint64"}],"name":"Initialized","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"contract | ||
IEntryPoint","name":"entryPoint","type":"address"},{"indexed":true,"internalType":"address","name":"owner","type":"address"}],"name":"LightAccountInitialized","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"previousOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferred","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"implementation","type":"address"}],"name":"Upgraded","type":"event"},{"inputs":[],"name":"addDeposit","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"eip712Domain","outputs":[{"internalType":"bytes1","name":"fields","type":"bytes1"},{"internalType":"string","name":"name","type":"string"},{"internalType":"string","name":"version","type":"string"},{"internalType":"uint256","name":"chainId","type":"uint256"},{"internalType":"address","name":"verifyingContract","type":"address"},{"internalType":"bytes32","name":"salt","type":"bytes32"},{"internalType":"uint256[]","name":"extensions","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"entryPoint","outputs":[{"internalType":"contract | ||
IEntryPoint","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"dest","type":"address"},{"internalType":"uint256","name":"value","type":"uint256"},{"internalType":"bytes","name":"func","type":"bytes"}],"name":"execute","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address[]","name":"dest","type":"address[]"},{"internalType":"bytes[]","name":"func","type":"bytes[]"}],"name":"executeBatch","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address[]","name":"dest","type":"address[]"},{"internalType":"uint256[]","name":"value","type":"uint256[]"},{"internalType":"bytes[]","name":"func","type":"bytes[]"}],"name":"executeBatch","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"getDeposit","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes","name":"message","type":"bytes"}],"name":"getMessageHash","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getNonce","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner_","type":"address"}],"name":"initialize","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"hash","type":"bytes32"},{"internalType":"bytes","name":"signature","type":"bytes"}],"name":"isValidSignature","outputs":[{"internalType":"bytes4","name":"","type":"bytes4"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"address","name":"","type":"address"},{"internalType":"uint256[]","name":"","type":"uint256[]"},{"internalType":"uint256[]","name":"","type":"uint256[]"},{"internalType":"bytes","name":"","type":"bytes"}],"name":"onERC1155BatchReceived","outputs":[{"internalType":"bytes4","name":"","type":"bytes4"}],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"address","name":"","type":"address"},{"internalType":"uint256","name":"","type":"uint256"},{"internalType":"uint256","name":"","type":"uint256"},{"internalType":"bytes","name":"","type":"bytes"}],"name":"onERC1155Received","outputs":[{"internalType":"bytes4","name":"","type":"bytes4"}],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"address","name":"","type":"address"},{"internalType":"uint256","name":"","type":"uint256"},{"internalType":"bytes","name":"","type":"bytes"}],"name":"onERC721Received","outputs":[{"internalType":"bytes4","name":"","type":"bytes4"}],"stateMutability":"pure","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"proxiableUUID","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes4","name":"interfaceId","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newImplementation","type":"address"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"upgradeToAndCall","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"components":[{"internalType":"address","name":"sender","type":"address"},{"internalType":"uint256","name":"nonce","type":"uint256"},{"internalType":"bytes","name":"initCode","type":"bytes"},{"internalType":"bytes","name":"callData","type":"bytes"},{"internalType":"bytes32","name":"accountGasLimits","type":"bytes32"},{"internalType":"uint256","name":"preVerificationGas","type":"uint256"},{"internalType":"bytes32","name":"gasFees","type":"bytes32"},{"internalType":"bytes","name":"paymasterAndData","type":"bytes"},{"internalType":"bytes","name":"signature","type":"bytes"}],"internalType":"struct | ||
PackedUserOperation","name":"userOp","type":"tuple"},{"internalType":"bytes32","name":"userOpHash","type":"bytes32"},{"internalType":"uint256","name":"missingAccountFunds","type":"uint256"}],"name":"validateUserOp","outputs":[{"internalType":"uint256","name":"validationData","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address | ||
payable","name":"withdrawAddress","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"withdrawDepositTo","outputs":[],"stateMutability":"nonpayable","type":"function"},{"stateMutability":"payable","type":"receive"}]*/ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,59 @@ | ||
// SPDX-License-Identifier: UNLICENSED | ||
pragma solidity ^0.8.26; | ||
|
||
import {EntryPoint} from "@eth-infinitism/account-abstraction/core/EntryPoint.sol"; | ||
import {IEntryPoint} from "@eth-infinitism/account-abstraction/interfaces/IEntryPoint.sol"; | ||
import {GasSnapshot} from "forge-gas-snapshot/GasSnapshot.sol"; | ||
|
||
import {AccountFactory} from "../../src/account/AccountFactory.sol"; | ||
import {ModularAccount} from "../../src/account/ModularAccount.sol"; | ||
import {SemiModularAccount} from "../../src/account/SemiModularAccount.sol"; | ||
|
||
import {ModuleEntity, ModuleEntityLib} from "../../src/helpers/ModuleEntityLib.sol"; | ||
import {SingleSignerValidationModule} from "../../src/modules/validation/SingleSignerValidationModule.sol"; | ||
|
||
import {MockERC20} from "../../test/mocks/MockERC20.sol"; | ||
|
||
import {ModuleSignatureUtils} from "../../test/utils/ModuleSignatureUtils.sol"; | ||
import {OptimizedTest} from "../../test/utils/OptimizedTest.sol"; | ||
|
||
abstract contract ModularAccountBenchmarkBase is GasSnapshot, OptimizedTest, ModuleSignatureUtils { | ||
EntryPoint public entryPoint; | ||
|
||
AccountFactory public factory; | ||
ModularAccount public accountImpl; | ||
SemiModularAccount public semiModularImpl; | ||
SingleSignerValidationModule public singleSignerValidationModule; | ||
|
||
ModularAccount public account1; | ||
|
||
address public owner1; | ||
uint256 public owner1Key; | ||
|
||
address public recipient; | ||
MockERC20 public mockErc20; | ||
|
||
ModuleEntity public signerValidation; | ||
|
||
constructor() { | ||
(owner1, owner1Key) = makeAddrAndKey("owner1"); | ||
|
||
recipient = makeAddr("recipient"); | ||
vm.deal(recipient, 1 wei); | ||
|
||
entryPoint = _deployEntryPoint070(); | ||
accountImpl = _deployModularAccount(IEntryPoint(entryPoint)); | ||
semiModularImpl = _deploySemiModularAccount(IEntryPoint(entryPoint)); | ||
singleSignerValidationModule = _deploySingleSignerValidationModule(); | ||
mockErc20 = new MockERC20(); | ||
|
||
factory = new AccountFactory( | ||
entryPoint, accountImpl, semiModularImpl, address(singleSignerValidationModule), address(this) | ||
); | ||
} | ||
|
||
function _deployAccount1() internal { | ||
account1 = factory.createAccount(owner1, 0, 0); | ||
signerValidation = ModuleEntityLib.pack(address(singleSignerValidationModule), 0); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,66 @@ | ||
// SPDX-License-Identifier: UNLICENSED | ||
pragma solidity ^0.8.26; | ||
|
||
import {VmSafe} from "forge-std/src/Vm.sol"; | ||
import {console} from "forge-std/src/console.sol"; | ||
|
||
import {ModularAccount} from "../../src/account/ModularAccount.sol"; | ||
|
||
import {ModularAccountBenchmarkBase} from "./BenchmarkBase.sol"; | ||
|
||
contract ModularAccountRuntimeTest is ModularAccountBenchmarkBase { | ||
function test_modularAccountGas_runtimeAccountCreation() public { | ||
uint256 salt = 0; | ||
uint32 entityId = 0; | ||
|
||
factory.createAccount(owner1, salt, entityId); | ||
|
||
VmSafe.Gas memory gas = vm.lastCallGas(); | ||
|
||
console.log("Runtime: account creation: "); | ||
console.log("gasTotalUsed: %d", gas.gasTotalUsed); | ||
|
||
snap("ModularAccount_Runtime_AccountCreation", gas.gasTotalUsed); | ||
} | ||
|
||
function test_modularAccountGas_runtimeNativeTransfer() public { | ||
_deployAccount1(); | ||
|
||
vm.deal(address(account1), 1 ether); | ||
|
||
vm.prank(owner1); | ||
account1.executeWithAuthorization( | ||
abi.encodeCall(ModularAccount.execute, (recipient, 0.1 ether, "")), | ||
_encodeSignature(signerValidation, GLOBAL_VALIDATION, "") | ||
); | ||
|
||
VmSafe.Gas memory gas = vm.lastCallGas(); | ||
|
||
console.log("Runtime: native transfer: "); | ||
console.log("gasTotalUsed: %d", gas.gasTotalUsed); | ||
|
||
snap("ModularAccount_Runtime_NativeTransfer", gas.gasTotalUsed); | ||
} | ||
|
||
function test_modularAccountGas_runtimeErc20Transfer() public { | ||
_deployAccount1(); | ||
|
||
mockErc20.mint(address(account1), 100 ether); | ||
|
||
vm.prank(owner1); | ||
account1.executeWithAuthorization( | ||
abi.encodeCall( | ||
ModularAccount.execute, | ||
(address(mockErc20), 0, abi.encodeWithSelector(mockErc20.transfer.selector, recipient, 10 ether)) | ||
), | ||
_encodeSignature(signerValidation, GLOBAL_VALIDATION, "") | ||
); | ||
|
||
VmSafe.Gas memory gas = vm.lastCallGas(); | ||
|
||
console.log("Runtime: erc20 transfer: "); | ||
console.log("gasTotalUsed: %d", gas.gasTotalUsed); | ||
|
||
snap("ModularAccount_Runtime_Erc20Transfer", gas.gasTotalUsed); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.