// SPDX-License-Identifier: MIT pragma solidity ^0.8.19; contract ReplayPermit { address public signer; mapping(address => uint256) public balances; constructor(address _signer) { signer = _signer; } function claim(uint256 amount, uint8 v, bytes32 r, bytes32 s) external { bytes32 msgHash = keccak256(abi.encodePacked(msg.sender, amount)); address recovered = ecrecover(msgHash, v, r, s); require(recovered == signer, "bad sig"); // no nonce, no deadline, replayable forever balances[msg.sender] += amount; } }