SignerP256.sol 2.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364
  1. // SPDX-License-Identifier: MIT
  2. // OpenZeppelin Contracts (last updated v5.4.0-rc.1) (utils/cryptography/signers/SignerP256.sol)
  3. pragma solidity ^0.8.20;
  4. import {AbstractSigner} from "./AbstractSigner.sol";
  5. import {P256} from "../P256.sol";
  6. /**
  7. * @dev Implementation of {AbstractSigner} using xref:api:utils/cryptography#P256[P256] signatures.
  8. *
  9. * For {Account} usage, a {_setSigner} function is provided to set the {signer} public key.
  10. * Doing so is easier for a factory, who is likely to use initializable clones of this contract.
  11. *
  12. * Example of usage:
  13. *
  14. * ```solidity
  15. * contract MyAccountP256 is Account, SignerP256, Initializable {
  16. * function initialize(bytes32 qx, bytes32 qy) public initializer {
  17. * _setSigner(qx, qy);
  18. * }
  19. * }
  20. * ```
  21. *
  22. * IMPORTANT: Failing to call {_setSigner} either during construction (if used standalone)
  23. * or during initialization (if used as a clone) may leave the signer either front-runnable or unusable.
  24. */
  25. abstract contract SignerP256 is AbstractSigner {
  26. bytes32 private _qx;
  27. bytes32 private _qy;
  28. error SignerP256InvalidPublicKey(bytes32 qx, bytes32 qy);
  29. constructor(bytes32 qx, bytes32 qy) {
  30. _setSigner(qx, qy);
  31. }
  32. /**
  33. * @dev Sets the signer with a P256 public key. This function should be called during construction
  34. * or through an initializer.
  35. */
  36. function _setSigner(bytes32 qx, bytes32 qy) internal {
  37. if (!P256.isValidPublicKey(qx, qy)) revert SignerP256InvalidPublicKey(qx, qy);
  38. _qx = qx;
  39. _qy = qy;
  40. }
  41. /// @dev Return the signer's P256 public key.
  42. function signer() public view virtual returns (bytes32 qx, bytes32 qy) {
  43. return (_qx, _qy);
  44. }
  45. /// @inheritdoc AbstractSigner
  46. function _rawSignatureValidation(
  47. bytes32 hash,
  48. bytes calldata signature
  49. ) internal view virtual override returns (bool) {
  50. if (signature.length < 0x40) return false;
  51. bytes32 r = bytes32(signature[0x00:0x20]);
  52. bytes32 s = bytes32(signature[0x20:0x40]);
  53. (bytes32 qx, bytes32 qy) = signer();
  54. return P256.verify(hash, r, s, qx, qy);
  55. }
  56. }