-
Notifications
You must be signed in to change notification settings - Fork 184
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(world-modules): call with signature supports ERC1271 (#2559)
- Loading branch information
Showing
6 changed files
with
74 additions
and
13 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
17 changes: 17 additions & 0 deletions
17
packages/world-modules/src/modules/callwithsignature/IERC1271.sol
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,17 @@ | ||
// SPDX-License-Identifier: MIT | ||
// OpenZeppelin Contracts (last updated v5.0.0) (interfaces/IERC1271.sol) | ||
|
||
pragma solidity ^0.8.24; | ||
|
||
/** | ||
* @dev Interface of the ERC-1271 standard signature validation method for | ||
* contracts as defined in https://eips.ethereum.org/EIPS/eip-1271[ERC-1271]. | ||
*/ | ||
interface IERC1271 { | ||
/** | ||
* @dev Should return whether the signature provided is valid for the provided data | ||
* @param hash Hash of the data to be signed | ||
* @param signature Signature byte array associated with _data | ||
*/ | ||
function isValidSignature(bytes32 hash, bytes memory signature) external view returns (bytes4 magicValue); | ||
} |
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
50 changes: 50 additions & 0 deletions
50
packages/world-modules/src/modules/callwithsignature/SignatureChecker.sol
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,50 @@ | ||
// SPDX-License-Identifier: MIT | ||
// OpenZeppelin Contracts (last updated v5.0.0) (utils/cryptography/SignatureChecker.sol) | ||
|
||
pragma solidity ^0.8.24; | ||
|
||
import { ECDSA } from "./ECDSA.sol"; | ||
import { IERC1271 } from "./IERC1271.sol"; | ||
|
||
/** | ||
* @dev Signature verification helper that can be used instead of `ECDSA.recover` to seamlessly support both ECDSA | ||
* signatures from externally owned accounts (EOAs) as well as ERC-1271 signatures from smart contract wallets like | ||
* Argent and Safe Wallet (previously Gnosis Safe). | ||
*/ | ||
library SignatureChecker { | ||
/** | ||
* @dev Checks if a signature is valid for a given signer and data hash. If the signer is a smart contract, the | ||
* signature is validated against that smart contract using ERC-1271, otherwise it's validated using `ECDSA.recover`. | ||
* | ||
* NOTE: Unlike ECDSA signatures, contract signatures are revocable, and the outcome of this function can thus | ||
* change through time. It could return true at block N and false at block N+1 (or the opposite). | ||
*/ | ||
function isValidSignatureNow(address signer, bytes32 hash, bytes memory signature) internal view returns (bool) { | ||
if (signer.code.length == 0) { | ||
(address recovered, ECDSA.RecoverError err, ) = ECDSA.tryRecover(hash, signature); | ||
return err == ECDSA.RecoverError.NoError && recovered == signer; | ||
} else { | ||
return isValidERC1271SignatureNow(signer, hash, signature); | ||
} | ||
} | ||
|
||
/** | ||
* @dev Checks if a signature is valid for a given signer and data hash. The signature is validated | ||
* against the signer smart contract using ERC-1271. | ||
* | ||
* NOTE: Unlike ECDSA signatures, contract signatures are revocable, and the outcome of this function can thus | ||
* change through time. It could return true at block N and false at block N+1 (or the opposite). | ||
*/ | ||
function isValidERC1271SignatureNow( | ||
address signer, | ||
bytes32 hash, | ||
bytes memory signature | ||
) internal view returns (bool) { | ||
(bool success, bytes memory result) = signer.staticcall( | ||
abi.encodeCall(IERC1271.isValidSignature, (hash, signature)) | ||
); | ||
return (success && | ||
result.length >= 32 && | ||
abi.decode(result, (bytes32)) == bytes32(IERC1271.isValidSignature.selector)); | ||
} | ||
} |
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