Skip to content

Commit 685314e

Browse files
authored
Update erc-8289.md
1 parent 92dce05 commit 685314e

1 file changed

Lines changed: 16 additions & 16 deletions

File tree

ERCS/erc-8289.md

Lines changed: 16 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ created: 2026-06-16
1212

1313
## Abstract
1414

15-
This document defines [ERC-8289](./eip-8289.md), a **private-by-default fungible token** for the EVM: the privacy version of [ERC-20](./eip-20.md). Under the hood it uses the Orchard shielded-pool model from the Zcash Protocol Specification (https://zips.z.cash/protocol/protocol.pdf). It keeps the [ERC-20](./eip-20.md) full method surface, but several methods are **private** (holder-only, off-chain) rather than public on-chain reads, and `transfer` / `approve` / `transferFrom` all appear on-chain as the same `transfer` operation. See [Interface Overview](#interface-overview).
15+
This document defines [ERC-8289](./eip-8289.md), a **private-by-default fungible token** for the EVM: the privacy version of [ERC-20](./eip-20.md). Under the hood it uses the Orchard shielded-pool model from the Zcash Protocol Specification. It keeps the [ERC-20](./eip-20.md) full method surface, but several methods are **private** (holder-only, off-chain) rather than public on-chain reads, and `transfer` / `approve` / `transferFrom` all appear on-chain as the same `transfer` operation. See [Interface Overview](#interface-overview).
1616

1717
## Motivation
1818

@@ -28,7 +28,7 @@ The key words **MUST**, **MUST NOT**, **SHOULD**, **MAY** are interpreted per RF
2828

2929
### Underlying Protocol
3030

31-
Value is held in shielded notes, not account balances. The note format, nullifiers, commitment tree, note encryption, and action/bundle structure follow the **Orchard shielded pool** in the Zcash Protocol Specification (https://zips.z.cash/protocol/protocol.pdf), adapted here as a per-asset EVM contract verified with Groth16. Field-level formats not repeated below are normative in the [Reference Implementation](#reference-implementation).
31+
Value is held in shielded notes, not account balances. The note format, nullifiers, commitment tree, note encryption, and action/bundle structure follow the **Orchard shielded pool** in the Zcash Protocol Specification, adapted here as a per-asset EVM contract verified with Groth16. Field-level formats not repeated below are normative in the [Reference Implementation](#reference-implementation).
3232

3333
### Interface Overview
3434

@@ -38,9 +38,9 @@ This section lists **all interfaces** in one place and marks whether each corres
3838
|---|---|---|---|---|
3939
| `name()` / `symbol()` / `decimals()` | yes | on-chain | public | Identical to [ERC-20](./eip-20.md) |
4040
| `totalSupply()` | yes | on-chain | public | Public counter (`mint``burn`) |
41-
| `balanceOf(addr)` | yes | off-chain | **private** | Scan Orchard notes (Zcash Protocol Specification, https://zips.z.cash/protocol/protocol.pdf) with viewing key; holder-only |
41+
| `balanceOf(addr)` | yes | off-chain | **private** | Scan Orchard notes (Zcash Protocol Specification) with viewing key; holder-only |
4242
| `transfer(PrivacyCall)` | yes | on-chain | private (parties + amount) | Orchard action bundle |
43-
| `approve(spender, N)` | yes | off-chain | private (relationship hidden) | ZIP-32 subaccount (https://zips.z.cash/zip-0032); fund + deliver key; on-chain submits as `transfer(PrivacyCall)` |
43+
| `approve(spender, N)` | yes | off-chain | private (relationship hidden) | ZIP-32 subaccount; fund + deliver key; on-chain submits as `transfer(PrivacyCall)` |
4444
| `allowance(owner, spender)` | yes | off-chain | **private** | Scan subaccount remaining balance |
4545
| `transferFrom(from, to, amount)` | yes | off-chain | private (relationship hidden) | Spender spends subaccount; on-chain submits as `transfer(PrivacyCall)` |
4646
| `mint(amount, PrivacyCall)` | extension | on-chain | amount public; recipient private | Issuer-only; Orchard action + `totalSupply` increase |
@@ -129,7 +129,7 @@ Conformance:
129129

130130
### Call Format
131131

132-
Every value-changing operation submits a `PrivacyCall` encoding one or more **Orchard actions** (Zcash Protocol Specification, https://zips.z.cash/protocol/protocol.pdf):
132+
Every value-changing operation submits a `PrivacyCall` encoding one or more **Orchard actions** (Zcash Protocol Specification):
133133

134134
- `actions` = `abi.encode(BundleAction[])`.
135135
- `bindingSig` = Schnorr binding signature `[Rx, Ry, s]` proving value conservation.
@@ -165,7 +165,7 @@ Without the `pubFields` ↔ calldata equality checks, a valid proof could be rep
165165

166166
The bundle-level `bindingSig` MUST be verified over all action nullifiers, commitments, and the operation's `valueBalance` before any state mutation (see Method Semantics for encodings).
167167

168-
Note encryption and key derivation follow the Orchard note format in the Zcash Protocol Specification (https://zips.z.cash/protocol/protocol.pdf); exact encodings are in the [Reference Implementation](#reference-implementation).
168+
Note encryption and key derivation follow the Orchard note format in the Zcash Protocol Specification; exact encodings are in the [Reference Implementation](#reference-implementation).
169169

170170
### Method Semantics
171171

@@ -175,11 +175,11 @@ Identical to [ERC-20](./eip-20.md): public on-chain views.
175175

176176
#### `transfer(PrivacyCall) → bool`
177177

178-
Spends input Orchard notes (Zcash Protocol Specification, https://zips.z.cash/protocol/protocol.pdf) and creates output notes in a value-conserving action bundle (`valueBalance == 0`). Sender, recipient, and amount MUST remain private. Returns `true` on success; emits `NoteAdded` / `NoteConfirmed`, not `Transfer(from,to,value)`.
178+
Spends input Orchard notes (Zcash Protocol Specification) and creates output notes in a value-conserving action bundle (`valueBalance == 0`). Sender, recipient, and amount MUST remain private. Returns `true` on success; emits `NoteAdded` / `NoteConfirmed`, not `Transfer(from,to,value)`.
179179

180180
#### `mint(amount, PrivacyCall)` / `burn(amount, PrivacyCall)`
181181

182-
Same Orchard action verification path as `transfer` (Zcash Protocol Specification, https://zips.z.cash/protocol/protocol.pdf), with public `totalSupply` accounting:
182+
Same Orchard action verification path as `transfer` (Zcash Protocol Specification), with public `totalSupply` accounting:
183183

184184
- `mint`: `totalSupply += amount` (`onlyIssuer`); `amount` public, recipient private. Mint MUST use the same anchor / nullifier / spend-auth path as `transfer` (no output-only branch). The circuit MUST constrain the consumed input to `v = 0` so the action represents net inflow; the contract does not read note value directly.
185185
- `burn`: `totalSupply -= amount`; any holder MAY burn own notes; `amount` public, burner private.
@@ -192,11 +192,11 @@ Same Orchard action verification path as `transfer` (Zcash Protocol Specificatio
192192

193193
#### `balanceOf` (off-chain, private)
194194

195-
Only the holder can compute their balance by scanning `NoteAdded` events, trial-decrypting Orchard notes (Zcash Protocol Specification, https://zips.z.cash/protocol/protocol.pdf) with their viewing key, and excluding spent nullifiers. There is no on-chain `balanceOf` and no way to query a third party's balance.
195+
Only the holder can compute their balance by scanning `NoteAdded` events, trial-decrypting Orchard notes (Zcash Protocol Specification) with their viewing key, and excluding spent nullifiers. There is no on-chain `balanceOf` and no way to query a third party's balance.
196196

197197
#### `approve` / `allowance` / `transferFrom` (off-chain semantics; on-chain = `transfer`)
198198

199-
Approved spending is built on ZIP-32 hierarchical accounts (https://zips.z.cash/zip-0032): each **EOA spender** receives a dedicated subaccount (`account_S`) with its own spending and viewing keys, cryptographically isolated from the owner's main account and from every other spender. This ERC maps [ERC-20](./eip-20.md) `approve` / `transferFrom` onto it as follows:
199+
Approved spending is built on ZIP-32 hierarchical accounts: each **EOA spender** receives a dedicated subaccount (`account_S`) with its own spending and viewing keys, cryptographically isolated from the owner's main account and from every other spender. This ERC maps [ERC-20](./eip-20.md) `approve` / `transferFrom` onto it as follows:
200200

201201
1. **`approve(spender, N)`** — Owner derives an unused ZIP-32 subaccount, funds it with `N` via `transfer(PrivacyCall)`, and delivers that subaccount's spending key to the spender (encrypted off-chain). On-chain: one `transfer`.
202202
2. **`allowance(owner, spender)`** — Remaining balance of that subaccount, scanned with the subaccount viewing key. No on-chain mapping.
@@ -207,7 +207,7 @@ The allowance ceiling is enforced by the subaccount's actual note balance, not a
207207

208208
### Execution Requirements
209209

210-
The on-chain state machine follows the Orchard shielded pool (Zcash Protocol Specification, https://zips.z.cash/protocol/protocol.pdf). Implementations MUST:
210+
The on-chain state machine follows the Orchard shielded pool (Zcash Protocol Specification). Implementations MUST:
211211

212212
- Maintain a nullifier set; the same `nf` MUST NOT be spent twice.
213213
- Maintain an append-only commitment tree; historical roots queryable via `isValidAnchor`.
@@ -220,10 +220,10 @@ The on-chain state machine follows the Orchard shielded pool (Zcash Protocol Spe
220220

221221
## Rationale
222222

223-
- **Orchard ZK-UTXO model.** Notes, nullifiers, and the commitment tree follow the Zcash Protocol Specification (https://zips.z.cash/protocol/protocol.pdf); this ERC defines the private token interface and per-asset deployment on EVM.
223+
- **Orchard ZK-UTXO model.** Notes, nullifiers, and the commitment tree follow the Zcash Protocol Specification; this ERC defines the private token interface and per-asset deployment on EVM.
224224
- **Private [ERC-20](./eip-20.md), not a different asset.** Same method surface; privacy changes openness (public view vs private query vs indistinguishable transfer), not user intent.
225225
- **One on-chain operation for all movement.** Collapsing `transfer` / `approve` / `transferFrom` removes approval metadata [ERC-20](./eip-20.md) unavoidably leaks.
226-
- **Approved spending via ZIP-32 subaccounts** (https://zips.z.cash/zip-0032). Each EOA spender gets an isolated hierarchical account instead of an on-chain `allowance` mapping; see Method Semantics.
226+
- **Approved spending via ZIP-32 subaccounts**. Each EOA spender gets an isolated hierarchical account instead of an on-chain `allowance` mapping; see Method Semantics.
227227
- **No `approve(contract)`.** A contract has no private key; placing a spending key on-chain would expose it to everyone. Programmable private spending (predicate-authorized notes, MPC custody) is future work, not part of this ERC.
228228
- **Wallet behavior is out of scope of the on-chain ABI.** Subaccount layout, encrypted key delivery, and note scanning are wallet/SDK responsibilities; a conformant reference is provided in the [Reference Implementation](#reference-implementation).
229229

@@ -244,16 +244,16 @@ The [Reference Implementation](#reference-implementation) repository includes:
244244

245245
### Code
246246

247-
Reference implementation: GitHub repository PERC20Labs/pERC20_ (https://github.com/PERC20Labs/pERC20_).
247+
Reference implementation: GitHub repository PERC20Labs/pERC20_.
248248

249249
- Normative asset contract: `contracts/ptoken/PERC20.sol`.
250250
- Cryptographic and wallet formats (key derivation, `perc1` addresses, note encryption, nullifiers, approved-spending packaging): reference libraries and SDK in the same repository.
251251

252252
### Related Standards and Protocols
253253

254254
- [EIP-20](./eip-20.md): Token Standard — the public fungible token interface that this ERC maps to.
255-
- Zcash Protocol Specification (https://zips.z.cash/protocol/protocol.pdf): Orchard shielded pool — note commitments, nullifiers, note encryption, and action structure adapted here for EVM Groth16 verification.
256-
- ZIP-32 (https://zips.z.cash/zip-0032): Shielded Hierarchical Deterministic Wallets — hierarchical account derivation used for per-spender subaccounts in `approve` / `transferFrom`.
255+
- Zcash Protocol Specification: Orchard shielded pool — note commitments, nullifiers, note encryption, and action structure adapted here for EVM Groth16 verification.
256+
- ZIP-32: Shielded Hierarchical Deterministic Wallets — hierarchical account derivation used for per-spender subaccounts in `approve` / `transferFrom`.
257257

258258
## Security Considerations
259259

0 commit comments

Comments
 (0)