The executeMetaTransaction function in NativeMetaTransaction.sol attempts to perform meta-transactions by encoding and calling functions with appended data. Specifically, it appends the userAddress to the functionSignature calldata before calling the target function. However, neither NativeMetaTransaction nor MembershipFactory (which inherits NativeMetaTransaction) have functions that accept this appended userAddress. As a result, function calls made through executeMetaTransaction are likely to fail because the appended data prevents the calldata from matching any function signature in these contracts. This design flaw renders executeMetaTransaction non-functional as intended.
The issue arises in the executeMetaTransaction function, where the contract constructs calldata by appending userAddress to functionSignature:
This approach is problematic because none of the functions in MembershipFactory or NativeMetaTransaction are designed to handle this appended userAddress parameter. When executeMetaTransaction makes the call, the calldata does not match any function signatures, leading to a call failure.
For example, if functionSignature represents a call to joinDAO(address daoMembershipAddress, uint256 tierIndex), appending userAddress results in a signature mismatch, as there is no function defined as joinDAO(address, uint256, address).
The executeMetaTransaction function is effectively unusable, as any attempt to call a function with appended data will fail due to a signature mismatch. This renders the meta-transaction functionality non-functional, preventing users from leveraging gasless transactions or relaying through a meta-transaction relay system.
Manual analysis
Opt for a recommended approach to meta-transactions by avoiding the modification of the calldata structure. Instead, set userAddress as an internal state variable (e.g., _currentMetaTransactionUser) specifically for the duration of the meta-transaction call. This variable can then be referenced by overriding _msgSender() to return the meta-transaction sender address whenever _currentMetaTransactionUser is set. This approach preserves the original function signatures, enabling compatibility with the target contract’s functions and ensuring that the transaction context reflects the original user’s identity.
The contest is live. Earn rewards by submitting a finding.
This is your time to appeal against judgements on your submissions.
Appeals are being carefully reviewed by our judges.