Skip to content

Latest commit

 

History

History
84 lines (60 loc) · 3.52 KB

eip.md

File metadata and controls

84 lines (60 loc) · 3.52 KB
eip title description author discussions-to status type category created requires
<to be assigned>
ERC-721 zk-Provable Token Extension
An extension to the ERC-721 standard to introduce private stealth addresses
Anton Wahrstätter (@Nerolation)
Idea
Standards Track
ERC
2022-08-10
EIP 165, 721

Abstract

This specification defines an extension to the ERC-721 standard. The extension adds standardized stealth addresses to the ERC-721 standard to enable users private token ownership.

Motivation

A standard interface for private ERC-721 tokens that enables users to recieve tokens without letting other users know.

Using Stealth Addresses that are generated from a shared secret between the sender and the receiver, the recipients of transfers are obfuscated.

Specification

The key words “MUST”, “MUST NOT”, “REQUIRED”, “SHALL”, “SHALL NOT”, “SHOULD”, “SHOULD NOT”, “RECOMMENDED”, “MAY”, and “OPTIONAL” in this document are to be interpreted as described in RFC 2119.

Every ERC0000 compliant contract MUST implement the ERC-721 (0x80ac58cd) and ERC165 (0x01ffc9a7 TBD) interfaces:

// SPDX-License-Identifier: CC0-1.0
pragma solidity ^0.8.6;
...
interface ERC0001 /* is ERC721, ERC165 */ {

    /// @notice Broadcasts event with a ``Shared Secret``.
    /// @dev Emits event with private transfer information `S`. 
    ///  S is generated by the sender an represents the public key to the private key `s`.
    ///  s is a user-generated secret (MUST NOT be the senders account private key).
    ///  The sender broadcasts S for every transfer. Users can use S to check if they were
    ///  the recipients of a respective transfer.
    /// @param publishableData The public key to the sender's secret
    event PrivateTransfer(bytes publishableData)
}
    

Stealth Address Generation

 Sender Keypair    --> (s,S) | S = s * G // s represents a sender-generated secret
 Recipient Keypair --> (p,P) | P = p * G
 
    
 For transfering:
    sharedSecret    = s*P
    stealthAddress  = pubtoaddr(P + (G * keccak(sharedSecret))) # // ``to`` value
    publishableData = G * s = S                                   // ``publishableData`` value

    
 For receiving:
    forall publishableData `S` do:
        if pubtoaddr(P + (G * keccak(S * p))) has token:
            store_key(p + keccak(S * p))
    

Rationale

EIP- emerged from the need of having privacy-preserving ways for interacting with non-fungible tokens (NFTs). NFTs can reveal sensitive private information about the owner. While users might want to prove the ownership of a NFT-concert ticket, they might not want to reveal personal account-related information at the same time. The standardization of stealth address generation for NFTs represents a significant step for privacy. Privacy-preserving solutions require standards to gain adoption, therefore it is critical to focus on generalisable ways of implement ownership-proofs into related contracts.

TBD This extension standardizes the method to create and look-up Stealth Addresses.

Backwards Compatibility

EIP--- is not backwards compatibly with basic ERC-721 contracts. EIP--- implements the EIP-165 standard.

Reference Implementation

You can find an implementation of this standard in assets/eip.sol.

Security Considerations

TBD

Copyright

Copyright and related rights waived via CC0.