Skip to content

Commit

Permalink
✨ NFT permit helpers
Browse files Browse the repository at this point in the history
✨ NFT permit helpers
  • Loading branch information
z0r0z authored Nov 6, 2022
1 parent 7caf4f2 commit 1beadda
Showing 1 changed file with 59 additions and 2 deletions.
61 changes: 59 additions & 2 deletions src/utils/SelfPermit.sol
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,14 @@ pragma solidity ^0.8.4;

import {Permit} from "./Permit.sol";

/// @notice Signature permit helper for any EIP-2612 or Dai-style token.
/// @author SolDAO (https://github.com/Sol-DAO/solbase/blob/main/src/utils/SelfPermit.sol)
/// @notice Self helper for any EIP-2612, EIP-4494 or Dai-style token permit.
/// @author Solbase (https://github.com/Sol-DAO/solbase/blob/main/src/utils/SelfPermit.sol)
/// @author Modified from Uniswap (https://github.com/Uniswap/v3-periphery/blob/main/contracts/base/SelfPermit.sol)
/// @dev These functions are expected to be embedded in multicall to allow EOAs to approve a contract and call a function
/// that requires an approval in a single transaction.
abstract contract SelfPermit {
/// @dev ERC20.

/// @notice Permits this contract to spend a given EIP-2612 `token` from `msg.sender`.
/// @dev The `owner` is always `msg.sender` and the `spender` is always `address(this)`.
/// @param token The address of the asset spent.
Expand Down Expand Up @@ -46,4 +48,59 @@ abstract contract SelfPermit {
) public virtual {
token.permit(msg.sender, address(this), nonce, deadline, true, v, r, s);
}

/// @dev ERC721.

/// @notice Permits this contract to spend a given EIP-2612-style NFT `tokenID` from `msg.sender`.
/// @dev The `spender` is always `address(this)`.
/// @param token The address of the asset spent.
/// @param tokenId The ID of the token that is being approved for permit.
/// @param deadline The unix timestamp before which permit must be spent.
/// @param v Must produce valid secp256k1 signature from the `msg.sender` along with `r` and `s`.
/// @param r Must produce valid secp256k1 signature from the `msg.sender` along with `v` and `s`.
/// @param s Must produce valid secp256k1 signature from the `msg.sender` along with `r` and `v`.
function selfPermit721(
Permit token,
uint256 tokenId,
uint256 deadline,
uint8 v,
bytes32 r,
bytes32 s
) public virtual {
token.permit(address(this), tokenId, deadline, v, r, s);
}

/// @notice Permits this contract to spend a given EIP-4494 NFT `tokenID`.
/// @dev The `spender` is always `address(this)`.
/// @param token The address of the asset spent.
/// @param tokenId The ID of the token that is being approved for permit.
/// @param deadline The unix timestamp before which permit must be spent.
/// @param sig A traditional or EIP-2098 signature.
function selfPermit721(
Permit token,
uint256 tokenId,
uint256 deadline,
bytes calldata sig
) public virtual {
token.permit(address(this), tokenId, deadline, sig);
}

/// @dev ERC1155.

/// @notice Permits this contract to spend a given EIP-2612-style multitoken.
/// @dev The `owner` is always `msg.sender` and the `operator` is always `address(this)`.
/// @param token The address of the asset spent.
/// @param deadline The unix timestamp before which permit must be spent.
/// @param v Must produce valid secp256k1 signature from the `msg.sender` along with `r` and `s`.
/// @param r Must produce valid secp256k1 signature from the `msg.sender` along with `v` and `s`.
/// @param s Must produce valid secp256k1 signature from the `msg.sender` along with `r` and `v`.
function selfPermit1155(
Permit token,
uint256 deadline,
uint8 v,
bytes32 r,
bytes32 s
) public virtual {
token.permit(msg.sender, address(this), true, deadline, v, r, s);
}
}

0 comments on commit 1beadda

Please sign in to comment.