ZIP 2006 — Restricting Transfers into the Orchard Pool
Terminology
The key words "MUST", "MUST NOT", and "SHOULD" in this document are to be interpreted as described in BCP 14 1 when, and only when, they appear in all capitals.
The term "network upgrade" in this document is to be interpreted as described in ZIP 200. 2
The character § is used when referring to sections of the Zcash Protocol Specification. 3
The terms "Orchard protocol", "Orchard pool", "Ironwood pool", "Orchard-pool Action", and "Ironwood-pool Action" are to be interpreted as described in ZIP 229. 4
The expanded receiver of an Orchard-protocol shielded payment address or note is the pair of its diversified base and its diversified transmission key, as defined in § 4.2.3 ‘Orchard Key Components’. 5
Abstract
NU6.3 6 specifies two restrictions intended to limit economic activity within the Orchard pool:
- Value can leave the Orchard pool but cannot enter it.
- Each Orchard-pool Action must send its output to the same expanded receiver as the note that it spends.
So the Orchard pool can still be spent from, including across the turnstile into the Ironwood pool, but cannot be used to transfer value to an address whose spending key the sender does not hold.
This ZIP specifies the enableCrossAddress flag that expresses the second
restriction; the corresponding condition in the Action statement; and the
consensus rules that enforce both restrictions for the Orchard pool.
Motivation
The Orchard Action circuit deployed before NU6.2 had a soundness vulnerability that could have allowed value to be created in the Orchard pool. 7 NU6.3 introduces the Ironwood pool, which uses the Orchard protocol with a corrected circuit. Value moves from the Orchard pool into it subject to the "turnstile" checks on chain value pool balances specified in ZIP 209 8.
For those checks to give the desired balance integrity assurances, newly created shielded value has to be directed into the Ironwood pool, and value in the Orchard pool should only be able to leave it. If users could still pay each other within the Orchard pool, it would remain a working payment pool, and any value created through the vulnerability could circulate in it without ever being checked at the turnstile. Disallowing new value from entering the Orchard pool, and payments between users within it, prevents that, while still letting each holder move their own funds out. It does not prevent users from rebalancing note values within the Orchard pool in order to reduce the information revealed when migrating those funds to the Ironwood pool, as specified in ZIP 318 9.
Privacy Implications
Without the cross-address restriction, unrelated real spends and outputs can share Actions, so the minimum Action count is the maximum of the numbers of real spends and real outputs. Under the restriction, a real spend and a real output can share an Action only if they use the same expanded receiver. When no such pairing is possible, the minimum Action count is instead the sum of those numbers. This increases transaction size and reduces the hiding of transaction arity provided by spend/output pairing. Same-receiver pairing and additional dummy Actions remain possible, so the public Action count does not uniquely determine the numbers of real spends and real outputs. Since the restriction applies to all Orchard-pool Actions, the resulting increase in Action counts is not by itself a wallet-specific fingerprint.
By preventing payments between users within the Orchard pool, this ZIP encourages users to transfer their funds out of that pool. Such transfers reveal the net amount leaving the pool on-chain, regardless of its destination. Transferring a wallet's entire balance at once can therefore reveal that balance, and the amounts and timing of transfers can help link them. The restrictions preserve the ability to rebalance notes within the Orchard pool without crossing the turnstile. ZIP 318 9 specifies amount-selection and timing measures for migration to the Ironwood pool, and ZIP 326 10 describes how to construct the spend and output Actions needed for rebalancing under the cross-address restriction.
Requirements
- After NU6.3 activation, no transaction can increase the Orchard pool's chain value pool balance.
- After NU6.3 activation, an Orchard-pool Action cannot transfer value to an address other than that of the note it spends.
- Holders of Orchard-pool notes can still spend them, including into the Ironwood pool, through the turnstile.
- Holders of Orchard-pool notes can rebalance their values within that pool.
- The restriction is enforced for every Orchard-pool Action mined after NU6.3 activation, whatever the version of the transaction that contains it.
- Signers that treat bit 2 of
flagsOrchardas a reserved zero bit can still produce valid Orchard-pool spends.
Specification
The enableCrossAddress flag
Each Action has a flag , which is set in order to allow the expanded receiver of the Action's output note to differ from the expanded receiver of its input note. The value of is the same for all Actions of a bundle, and is encoded once per bundle in bit 2 of its flags byte:
- In the
flagsIronwoodfield of a version 6 transaction, bit 2 encodesenableCrossAddressfor the Ironwood-pool Actions. 4 - In the
flagsOrchardfield, bit 2 MUST be 0, independent of the transaction version. In a version 5 transaction it is still reserved and MUST be 0. In a version 6 transaction it encodesenableCrossAddress, and MUST be 0.
For blocks before NU6.3 activation, cross-address transfers are always permitted: is taken to be for every Action. From NU6.3 activation, is bit 2 of the flags byte for each pool, so it is for every Orchard-pool Action.
Action statement
For a given Orchard-protocol Action description, let .
From NU6.3 activation, the Action statement gains a primary input , after , and the following condition:
Cross-address restriction: , or and .
The auxiliary input of the Action statement already includes the spent note's expanded receiver and the output note's expanded receiver .
A single circuit, and a single verifying key identified as
OrchardCircuitVersion::PostNu6_3, are used for the Actions of both the
Orchard pool and the Ironwood pool from NU6.3 activation. The pools differ
in the consensus restrictions on the value of ,
not in the circuit.
Consensus rules
The following consensus rules apply from NU6.3 activation to every transaction, whatever its version:
- The verifying key for the proof of an Action description MUST be the one
identified as
OrchardCircuitVersion::PostNu6_3, and the proof MUST be valid for the primary input that includes . - A coinbase transaction MUST NOT contain any Orchard-pool Actions.
- , encoded as the
valueBalanceOrchardfield when it is present, MUST be nonnegative. That is, a transaction can take value from the Orchard pool, but MUST NOT add value to it.
Together with the rule that bit 2 of flagsOrchard is 0, these ensure that
after NU6.3 activation no value enters the Orchard pool, and every
Orchard-pool Action sends its output to the expanded receiver of the note that
it spends.
Requirements on wallets
When an Action with needs a dummy output note, that note MUST be sent to the expanded receiver of the Action's spent note (which may itself be a dummy note), rather than to a random address. Likewise, a dummy spent note paired with an output note that is not a dummy MUST be at the expanded receiver of the output note.
ZIP 326 specifies how wallets spend from, and rebalance notes within, the Orchard pool after NU6.3 activation. 10 In particular, an Action that creates an output note carrying value pairs it with a dummy spent note at the same expanded receiver, and the dummy output note of an Action that spends a real note has a random note ciphertext.
Changes to the Protocol Specification
This section is written as a set of changes relative to version 2026.7.0 of the protocol specification 11. They are applied in version 2026.8.0. 3 Each change applies from NU6.3 activation, and is marked as such in the specification.
§ 4.6 ‘Action Descriptions’
Add:
Let be the pool of this Action description.
Define an expanded receiver as in ZIP 2006, i.e. for a shielded payment address.
Add to the components of an Action description, after , with the description:
is a flag that is set in order to enable the expanded receiver of the output note to be different from the expanded receiver of the input note in this Action.
In the description of the proof, and in the consensus rule requiring it to be valid, append to the primary input, where .
In the note on components that are encoded once for each pool, add to the components listed.
Add the consensus rule:
[NU6.3 onward] MUST be the verifying key identified by
OrchardCircuitVersion::PostNu6_3.
§ 4.8.3 ‘Dummy Notes (Orchard)’
After the steps that construct the spend-related fields for a dummy Orchard-pool input note, add:
[NU6.3 onward] If for the Action, and its output note is not a dummy note, then the first two steps are replaced: and are instead the full viewing key and diversified payment address of the output note's recipient, and the spend authorization signature for the Action is made with the corresponding spend authorizing key.
After the paragraph saying that a dummy Orchard-pool output note is sent to a random shielded payment address, add:
[NU6.3 onward] If for the Action, the dummy output note is instead sent to the expanded receiver of the Action's spent note. If the spent note is not a dummy note, the transmitted note ciphertext of the dummy output note is filled with random bytes rather than being an encryption of its note plaintext. 10
§ 4.18.4 ‘Action Statement (Orchard)’
Append to the primary input:
[NU6.3 onward]
In its encoding, append to the existing nine-element sequence, giving a sequence of type from NU6.3 onward. Qualify the existing nine-element encoding with "[Pre-NU6.3]".
After the "Enable output flag" condition, add:
Cross-address restriction [NU6.3 onward]: , or and .
§ 7.1 ‘Transaction Encoding and Consensus’
In the combined version 5/6 transaction-format table, replace the list in the
Description column for flagsOrchard:
enableSpendsOrchardflag (bit )enableOutputsOrchardflag (bit )- Reserved, zeros (bits ).
with:
enableSpendsflag (bit )enableOutputsflag (bit )- Bit : reserved (v5) or
enableCrossAddress(v6), always- Reserved, zeros (bits ).
In the Description column for flagsIronwood, the version-6-only field added
by ZIP 229 4, replace:
enableSpendsIronwoodflag (bit )enableOutputsIronwoodflag (bit )- Reserved, zeros (bits ).
with:
enableSpendsflag (bit )enableOutputsflag (bit )enableCrossAddressflag (bit )- Reserved, zeros (bits ).
§ 7.1.2 ‘Transaction Consensus Rules’
Add:
[NU6.3 onward] A coinbase transaction MUST NOT have any Orchard-pool Action descriptions.
[NU6.3 onward] MUST be nonnegative.
After the rule that the reserved bits of the flagsOrchard field MUST be
zero, add:
[NU6.3 onward] In a version 6 transaction, bit 2 of
flagsOrchardencodes for the Orchard-pool Actions; it is covered by the preceding rule, and so is .
Changes to ZIPs
ZIP 229
In the Consensus Rules section, replace
Note that the reserved-bit rules above leave bit 2 of
flagsOrchardreserved as 0 (bits 2..7), while bit 2 offlagsIronwoodis theenableCrossAddressbit (reserved bits 3..7); the Orchard pool's cross-address restriction is enforced for its Actions from NU6.3 onward as specified in [ZIP 2006].
with
Note that bit 2 of
flagsOrchardis required to be 0 by the reserved-bit rule above (bits 2..7), independent of the transaction version: in a version 5 transaction it is still reserved, and in a version 6 transaction it encodesenableCrossAddress. Bit 2 offlagsIronwoodis theenableCrossAddressbit (reserved bits 3..7). The Orchard pool's cross-address restriction is enforced for its Actions from NU6.3 onward as specified in [ZIP 2006].
Rationale
Polarity of the flag
The flag is encoded in the enabled sense: bit 2 is 1 when cross-address transfers are enabled, the normal case for the Ironwood pool. With the opposite sense, a post-NU6.3 Orchard-pool spend would have to set bit 2 to 1. Signers that treat bit 2 as a reserved zero bit, such as hardware wallet firmware that has not been upgraded, would then be unable to produce valid Orchard-pool spends. In the enabled sense, the restricted state is bit 2 = 0, which is exactly what such signers already produce.
Within the circuit, the primary input is the negated value . Then a condition of the form " or " is enforced directly by the constraint .
One circuit for both pools
The Orchard pool and the Ironwood pool use the same circuit and verifying
key from NU6.3 activation. They are distinguished by their bundles, note
commitment trees, nullifier sets, and chain value pools, and by the value of
. This avoids a separate circuit for the restricted
pool. It also leaves open the option of enforcing similar restrictions on the
Ironwood pool in future, should there be a reason to. This intentionally
mirrors the design of the enableSpends and enableOutputs flags.
Comparing both coordinates
In the circuit, the points of the expanded receivers are witnessed in affine coordinates, and the condition is enforced coordinate-wise: for each and each coordinate , . Both coordinates are needed.
Restricting value as well as addresses
The cross-address restriction alone does not stop new value from entering the Orchard pool, since an Action can send value to its own spent note's address. The rule that is nonnegative, and the rule that coinbase transactions have no Orchard-pool Actions, close that path.
Deployment
This ZIP was deployed with NU6.3 6, which activated on Mainnet at block height 3428143.
Reference implementation
- The
orchardcrate, version 0.16.0, implements theenableCrossAddressflag, its encoding, and the cross-address restriction in the Action circuit. 12
References
Footnotes
-
Information on BCP 14 — "RFC 2119: Key words for use in RFCs to Indicate Requirement Levels" and "RFC 8174: Ambiguity of Uppercase vs Lowercase in RFC 2119 Key Words" ↩
-
Zcash Protocol Specification, Version 2026.8.0 [NU6.3]. Section 4.2.3: Orchard Key Components ↩
-
ZIP 257: Deployment of the Orchard Temporary Vulnerability Mitigation and NU6.2 Network Upgrade ↩
-
ZIP 326: NU6.3 Consequences for Wallets, section "Spending from and rebalancing within the Orchard pool" ↩ ↩2 ↩3