The Zcash ArboretumThe Complete Arboretum PDF

4 Compact blocks (ZIP 307)

This section states the compact block as an abstract message format: the records of a block and of a transaction, the compact outputs, spends and Actions and the fields they omit, the compact variant of trial decryption with the soundness of accepting a plaintext that no tag authenticates, and the placement of notes in the note commitment trees from per-block tree sizes. The service that delivers compact blocks is the subject of “The light-client service” (§5).

4.1 The compact block and the compact transaction

A compact block carries only the data of a block that a wallet needs to detect payments to its addresses, to detect spends of its notes and to maintain the witnesses of its notes (ZIP 307, “Compact Stream Format”); for the transparent pool it carries, on request, the data needed to detect spends of the wallet’s transparent coins.

Remark 4.1 (Normative status of the compact format).

ZIP 307, “Compact Stream Format”, “Output Compression” and “Spend Compression”, specifies the compact format for the Sapling pool only: a compact block of height, block hash and transactions, and a compact transaction of index, transaction identifier, spends and outputs. It names neither the Orchard pool nor the Ironwood pool, nor per-block tree sizes, nor transparent data. ZIP 318 and ZIP 326 address light wallets and specify no compact format. The remainder of the format below (the parent hash of a block, the tree sizes, the compact Actions of both Orchard-protocol pools, the transparent part and pool selection) is designed but unspecified (Definition 1.1). The volume states the format as an abstract message format, not as a serialisation, and states no field number, field width or encoded size. The status of each ZIP cited is that of Table 1.

Definition 4.2 (Compact block).

A compact block of height h is a tuple

𝐶𝐵=(h,𝗁𝖺𝗌𝗁,𝗉𝗋𝖾𝗏𝖧𝖺𝗌𝗁,𝗁𝖽𝗋,𝗏𝗍𝗑,S)

where

  1. 1.

    h∈ℕ is the block height;

  2. 2.

    𝗁𝖺𝗌𝗁 and 𝗉𝗋𝖾𝗏𝖧𝖺𝗌𝗁 are the 32-byte hashes of the block and of its parent block (protocol specification, §“Block Header Encoding and Consensus”);

  3. 3.

    𝗁𝖽𝗋 is either the encoded block header or empty; the abstract format does not guarantee that it is present;

  4. 4.

    𝗏𝗍𝗑=(𝑐𝑡𝑥0,…,𝑐𝑡𝑥m−1) is the sequence of compact transactions (Definition 4.3) of the block, in block order;

  5. 5.

    S=(S𝖲𝖺𝗉𝗅𝗂𝗇𝗀,S𝖮𝗋𝖼𝗁𝖺𝗋𝖽,S𝖨𝗋𝗈𝗇𝗐𝗈𝗈𝖽) gives, for each shielded pool 𝗉𝗈𝗈𝗅, the number S𝗉𝗈𝗈𝗅 of leaves of that pool’s note commitment tree after every transaction of the block has been appended, written S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(h).

Each S𝗉𝗈𝗈𝗅 is an integer in [0,232], where 232 is the leaf capacity of a tree of depth 𝖬𝖾𝗋𝗄𝗅𝖾𝖣𝖾𝗉𝗍𝗁𝖲𝖺𝗉𝗅𝗂𝗇𝗀=𝖬𝖾𝗋𝗄𝗅𝖾𝖣𝖾𝗉𝗍𝗁𝖮𝗋𝖼𝗁𝖺𝗋𝖽=32 (Ironwood Guide, §“The Merkle hash and the tree”, Definition “Note commitment tree”; protocol specification, §“Constants”). The width of any serialisation of S𝗉𝗈𝗈𝗅 lies outside the abstract format.

Definition 4.3 (Compact transaction).

A compact transaction is a tuple

𝑐𝑡𝑥=(i,𝗍𝗑𝗂𝖽,𝑆𝑆𝑝,𝑆𝑂𝑢𝑡,A𝖮𝗋𝖼𝗁𝖺𝗋𝖽,A𝖨𝗋𝗈𝗇𝗐𝗈𝗈𝖽,T)

where

  1. 1.

    i∈ℕ is the index of the transaction in its block;

  2. 2.

    𝗍𝗑𝗂𝖽 is the 32-byte transaction identifier in protocol byte order, the form in which it is computed, not the byte-reversed form used for display (Ironwood Guide, §“Transaction digests and signatures”, Definition “Transaction identifier”; protocol specification, §“Transaction Identifiers”);

  3. 3.

    𝑆𝑆𝑝 and 𝑆𝑂𝑢𝑡 are the sequences of compact Sapling spends and compact Sapling outputs, and A𝖮𝗋𝖼𝗁𝖺𝗋𝖽 and A𝖨𝗋𝗈𝗇𝗐𝗈𝗈𝖽 the sequences of compact Actions of the Orchard pool and of the Ironwood pool (Definition 4.5), each in the order of the transaction’s descriptions, on which note positions depend (§4.4);

  4. 4.

    T is an optional transparent part (O𝗂𝗇,O𝗈𝗎𝗍): O𝗂𝗇 is the sequence of outpoints (𝗍𝗑𝗂𝖽′,n) spent by the transaction’s transparent inputs, in input order, and O𝗈𝗎𝗍 the sequence of pairs (𝗏𝖺𝗅𝗎𝖾,𝗌𝖼𝗋𝗂𝗉𝗍) of its transparent outputs, in output order, with 𝗏𝖺𝗅𝗎𝖾 in zatoshi.

The coinbase transaction of a block is its first transaction and the one whose single transparent input has a null previous outpoint (protocol specification, §“Coinbase Transactions”); it spends no outpoint, its O𝗂𝗇 is empty, and it is recognised by i=0. No fee field is part of the abstract format.

Definition 4.4 (Pool selection).

Let 𝒫⊆{𝗍𝗋𝖺𝗇𝗌𝗉𝖺𝗋𝖾𝗇𝗍,𝖲𝖺𝗉𝗅𝗂𝗇𝗀,𝖮𝗋𝖼𝗁𝖺𝗋𝖽,𝖨𝗋𝗈𝗇𝗐𝗈𝗈𝖽}. The compact block restricted to 𝒫 is obtained from a compact block by keeping, in each compact transaction, only the components of the pools in 𝒫 (𝑆𝑆𝑝 and 𝑆𝑂𝑢𝑡 for Sapling, the sequence A𝗉𝗈𝗈𝗅 for an Orchard-protocol pool, and T only when 𝗍𝗋𝖺𝗇𝗌𝗉𝖺𝗋𝖾𝗇𝗍∈𝒫), and by omitting every compact transaction left with no component. The tuple S is kept whole, and a compact block is returned for every block of a requested range, possibly with empty 𝗏𝗍𝗑. The default is 𝒫={𝖲𝖺𝗉𝗅𝗂𝗇𝗀,𝖮𝗋𝖼𝗁𝖺𝗋𝖽,𝖨𝗋𝗈𝗇𝗐𝗈𝗈𝖽}. The range query of “The query interface” (§5.2) takes 𝒫 as an argument. Pool selection is designed but unspecified (Definition 1.1); ZIP 307 includes by default only the transactions that have Sapling spends or outputs (ZIP 307, “Block header validation”).

For every shielded pool in 𝒫 the restriction keeps every commitment of that pool in its order, since an omitted compact transaction has no component of the pool. The per-pool counts and offsets of Definition 4.11 are therefore the same on a restricted block as on the unrestricted one.

4.2 Compact outputs, spends, and Actions

Definition 4.5 (Compact spend, output, and Action).

Let C𝖾𝗇𝖼 be the note ciphertext of a Sapling output or of an Action: 580 bytes, the encryption of the 564-byte note plaintext followed by the 16-byte tag. Its split at the offsets 52 and 564 is that of the Ironwood Guide, §“Transaction digests and signatures”, Definition “Transaction identifier”.

  1. (a)

    A compact Sapling spend is the 32-byte nullifier 𝗇𝖿 of a Spend description.

  2. (b)

    A compact Sapling output is the triple (𝖼𝗆𝗎,𝖾𝗉𝗁𝖾𝗆𝖾𝗋𝖺𝗅𝖪𝖾𝗒,C𝖾𝗇𝖼[0:52]), a payload of 32+32+52=116 bytes.

  3. (c)

    A compact Action, of the Orchard pool and of the Ironwood pool alike, is the tuple (𝗇𝖿,𝖼𝗆𝗑,𝖾𝗉𝗁𝖾𝗆𝖾𝗋𝖺𝗅𝖪𝖾𝗒,C𝖾𝗇𝖼[0:52]), a payload of 32+32+32+52=148 bytes.

Parts (a) and (b) are specified (ZIP 307, “Output Compression” and “Spend Compression”); part (c) is designed but unspecified (Definition 1.1). The fields are those of the protocol specification, §“Spend Description Encoding and Consensus”, §“Output Description Encoding and Consensus” and §“Action Description Encoding and Consensus”. Only payload sizes are stated; the size of any serialisation lies outside the abstract format.

The nullifier 𝗇𝖿 of a compact Action has two roles. It detects a spend of the note that the Action consumes, and it is the element ρ of the note that the Action creates (Ironwood Guide, §“Nullifier chaining”, Construction “Chaining rule”), an input of 𝖾𝗌𝗄, ψ and 𝗋𝖼𝗆 and hence of the commitment that acceptance recomputes (Definition 4.9). A compact Action without 𝗇𝖿 therefore cannot be accepted.

A compact block omits the memo C𝖾𝗇𝖼[52:564], the tag C𝖾𝗇𝖼[564:580], the outgoing ciphertext C𝗈𝗎𝗍, value commitments, randomised validating keys, anchors, proofs and signatures (ZIP 307, “Output Compression”, “Spend Compression” and “Transaction privacy”). Recovery of a memo or of an outgoing plaintext requires the full transaction, fetched by its identifier (“Leakage of transaction queries”, §8.4).

Proposition 4.6 (Sufficiency of the compact fields).

Let 𝐶𝐵 be a compact block of height h, and let a wallet hold incoming viewing keys and the nullifiers of its notes.

  1. (i)

    Receipt detection, that is compact decryption and acceptance of an output (§4.3), is a function of the key, of h, and of the record (𝖼𝗆𝗎,𝖾𝗉𝗁𝖾𝗆𝖾𝗋𝖺𝗅𝖪𝖾𝗒,C𝖾𝗇𝖼[0:52]) of a Sapling output or (𝗇𝖿,𝖼𝗆𝗑,𝖾𝗉𝗁𝖾𝗆𝖾𝗋𝖺𝗅𝖪𝖾𝗒,C𝖾𝗇𝖼[0:52]) of an Action.

  2. (ii)

    Spend detection is a function of the fields 𝗇𝖿 of 𝑆𝑆𝑝, A𝖮𝗋𝖼𝗁𝖺𝗋𝖽 and A𝖨𝗋𝗈𝗇𝗐𝗈𝗈𝖽.

  3. (iii)

    Note placement is a function of the order of the commitments in 𝗏𝗍𝗑 and of S (§4.4).

No field omitted by the compact block enters (i) to (iii).

Proof.

(i) Trial decryption and acceptance read the ephemeral key, the ciphertext prefix that encrypts the lead byte, diversifier, value and note seed, the commitment, the height through the admissible lead bytes, and, for an Action, 𝗇𝖿 as ρ (Ironwood Guide, §“Trial decryption and note acceptance”, Constructions “Trial decryption” and “Acceptance of an Ironwood-pool output”; ZIP 307, “Scanning for relevant transactions” for Sapling); the memo and the tag enter only the full decryption. (ii) A spend of a note is detected by membership of its nullifier among the published ones (ZIP 307, “Detecting spends”). (iii) The chain appends each pool’s commitments in block, transaction and description order to the least unused leaf (Ironwood Guide, §“The Merkle hash and the tree”, Definition “Note commitment tree”; protocol specification, §“Note Commitment Trees”), so positions follow from that order and a tree size. □

The omitted fields serve the verification of the chain, which the client delegates to the server; that delegation and its assumption are stated in “Architecture and authority” (§5.1).

4.3 Compact trial decryption

Trial decryption and acceptance of full outputs are those of the Ironwood Guide, §“Trial decryption and note acceptance” (Constructions “Trial decryption” and “Acceptance of an Ironwood-pool output”), cited and not re-derived. This subsection states the compact variant.

Definition 4.7 (Compact note plaintext).

The compact note plaintext is the tuple 𝗇𝗉𝖼=(𝗅𝖾𝖺𝖽𝖡𝗒𝗍𝖾,d,v,𝗋𝗌𝖾𝖾𝖽), encoded as

𝗅𝖾𝖺𝖽𝖡𝗒𝗍𝖾⁢‖𝖫𝖤𝖡𝖲𝟤𝖮𝖲𝖯88⁢(d)‖⁢𝖨𝟤𝖫𝖤𝖮𝖲𝖯64⁢(v)∥𝗋𝗌𝖾𝖾𝖽,

of 1+11+8+32=52 bytes: the note plaintext of the Ironwood Guide, §“The note plaintext”, Definition “Note plaintext”, without its memo (protocol specification, §“Note Plaintexts and Memo Fields” and §“Encodings of Note Plaintexts and Memo Fields”). The AEAD encryption is a stream-cipher encryption followed by a tag, so C𝖾𝗇𝖼[0:52] is the encryption of exactly these 52 bytes, which are the contents and the opening of the note commitment (ZIP 307, “Output Compression”).

Construction 4.8 (Compact decryption of an output).

Input: an incoming viewing key 𝗂𝗏𝗄 of the pool’s protocol and a compact output or compact Action with fields 𝖾𝗉𝗁𝖾𝗆𝖾𝗋𝖺𝗅𝖪𝖾𝗒 and c=C𝖾𝗇𝖼[0:52].

  1. 1.

    Compute 𝖾𝗉𝗄:=𝖺𝖻𝗌𝗍⁢(𝖾𝗉𝗁𝖾𝗆𝖾𝗋𝖺𝗅𝖪𝖾𝗒) on the pool’s curve, 𝖺𝖻𝗌𝗍𝕁 on Jubjub for Sapling and 𝖺𝖻𝗌𝗍ℙ on Pallas for either Orchard-protocol pool; return ⊥ if 𝖾𝗉𝗄=⊥.

  2. 2.

    Compute K:=𝖪𝖣𝖥(𝖪𝖠.𝖠𝗀𝗋𝖾𝖾(𝗂𝗏𝗄,𝖾𝗉𝗄),𝖾𝗉𝗁𝖾𝗆𝖾𝗋𝖺𝗅𝖪𝖾𝗒) with the key agreement and key derivation of the pool’s protocol.

  3. 3.

    Compute 𝗇𝗉𝖼:=c⊕KS1⁢(K,096,52), where KS1⁢(K,096,52) is the first 52 bytes of the ChaCha20 keystream under key K and the all-zero nonce 096 of the protocol specification, §“Symmetric Encryption”, starting at block counter 1, the counter from which ChaCha20-Poly1305 encrypts (block 0 yields the Poly1305 key; Crypto Guide, §“The ChaCha20-Poly1305 AEAD”, Construction “ChaCha20-Poly1305”; RFC 8439, §2.8); equivalently, bytes 64 to 115 of the keystream from counter 0.

  4. 4.

    Return 𝗇𝗉𝖼 parsed as a compact note plaintext (Definition 4.7).

The tag is never checked. The result is a candidate, not an accepted note (ZIP 307, “Scanning for relevant transactions”).

Definition 4.9 (Acceptance of a compact candidate).

Let 𝗇𝗉𝖼=(𝗅𝖾𝖺𝖽𝖡𝗒𝗍𝖾,d,v,𝗋𝗌𝖾𝖾𝖽) be the candidate returned by Construction 4.8 under 𝗂𝗏𝗄 for an output of pool 𝗉𝗈𝗈𝗅 in a compact block of height h. Let H𝖢 be the Canopy activation height and 𝖹𝖨𝖯𝟤𝟣𝟤𝖦𝗋𝖺𝖼𝖾𝖯𝖾𝗋𝗂𝗈𝖽=32,256 blocks (protocol specification, §“Constants”). The set of admissible lead bytes is

𝖺𝗅𝗅𝗈𝗐𝖾𝖽𝖫𝖾𝖺𝖽𝖡𝗒𝗍𝖾𝗌𝗉𝗈𝗈𝗅⁢(h):={{𝟶⁢𝚡⁢𝟶𝟷}if ⁢h<H𝖢,{𝟶⁢𝚡⁢𝟶𝟷,𝟶⁢𝚡⁢𝟶𝟸}if ⁢H𝖢≤h<H𝖢+𝖹𝖨𝖯𝟤𝟣𝟤𝖦𝗋𝖺𝖼𝖾𝖯𝖾𝗋𝗂𝗈𝖽,{𝟶⁢𝚡⁢𝟶𝟸}otherwise, if ⁢𝗉𝗈𝗈𝗅≠𝖨𝗋𝗈𝗇𝗐𝗈𝗈𝖽,{𝟶⁢𝚡⁢𝟶𝟹}otherwise

(protocol specification, §“Note Plaintexts and Memo Fields”), so that an Orchard-pool note has lead byte 𝟶⁢𝚡⁢𝟶𝟸 and an Ironwood-pool note 𝟶⁢𝚡⁢𝟶𝟹. The wallet accepts 𝗇𝗉𝖼 if and only if every check passes:

  1. (i)

    𝗅𝖾𝖺𝖽𝖡𝗒𝗍𝖾∈𝖺𝗅𝗅𝗈𝗐𝖾𝖽𝖫𝖾𝖺𝖽𝖡𝗒𝗍𝖾𝗌𝗉𝗈𝗈𝗅⁢(h); for Sapling, moreover, 𝗋𝖼𝗆<r𝕁 and 𝗀𝖽:=𝖣𝗂𝗏𝖾𝗋𝗌𝗂𝖿𝗒𝖧𝖺𝗌𝗁⁢(d)≠⊥, with 𝗋𝖼𝗆:=𝗋𝗌𝖾𝖾𝖽 read as an integer for lead byte 𝟶⁢𝚡⁢𝟶𝟷;

  2. (ii)

    with 𝗉𝗄𝖽:=[𝗂𝗏𝗄]⁢𝗀𝖽, and with ρ:=𝗇𝖿 of the same Action for either Orchard-protocol pool, the note commitment recomputed from (𝗀𝖽,𝗉𝗄𝖽,v,ρ,ψ,𝗋𝖼𝗆), where ψ and 𝗋𝖼𝗆 are derived from 𝗋𝗌𝖾𝖾𝖽 as the pool and the lead byte prescribe (ρ and ψ absent for Sapling), is not ⊥ and extracts to the record’s 𝖼𝗆𝗎 (Sapling) or 𝖼𝗆𝗑 (either Orchard-protocol pool);

  3. (iii)

    for every lead byte other than 𝟶⁢𝚡⁢𝟶𝟷, the field 𝖾𝗉𝗁𝖾𝗆𝖾𝗋𝖺𝗅𝖪𝖾𝗒 equals the encoding of [𝖾𝗌𝗄]⁢𝗀𝖽, with 𝖾𝗌𝗄 re-derived from 𝗋𝗌𝖾𝖾𝖽, and from ρ for either Orchard-protocol pool.

The accepted note is n=((d,𝗉𝗄𝖽),v,ρ,ψ,𝗋𝖼𝗆) without memo, with ρ and ψ absent for a Sapling note. The derivations of ψ, 𝗋𝖼𝗆 and 𝖾𝗌𝗄 are cited and not restated: for Sapling and the Orchard pool to the protocol specification, §“Decryption using an Incoming Viewing Key (Sapling and Orchard)” (ZIP 212, “Changes to the process of sending Sapling or Orchard notes”); for the Ironwood pool to the Ironwood Guide, §“Trial decryption and note acceptance”, Construction “Acceptance of an Ironwood-pool output”, whose checks (i), (ii) with (iv), and (iii) are checks (i), (ii) and (iii) here (ZIP 2005, “Changes to the Protocol Specification”). The method of comparison is not part of the rule.

Check (iii) is a step of the specification’s decryption procedure and of ZIP 307, not an addition (ZIP 212, “Changes to the process of receiving Sapling or Orchard notes”). For an Ironwood-pool note it is made directly after the computation of 𝗀𝖽, in the order of ZIP 2005. Without it a sender could agree the key with one address of a recipient while naming the diversifier of another, and link the two addresses by observing acceptance (Ironwood Guide, §“Trial decryption and note acceptance”, Remark “Role of check (iii)”; ZIP 212, “Motivation”). A Sapling note with lead byte 𝟶⁢𝚡⁢𝟶𝟷, created under the rules before ZIP 212, skips check (iii), since its 𝖾𝗌𝗄 is not derivable from 𝗋𝗌𝖾𝖾𝖽.

For a note n the commitment input is the pair of committed values and trapdoor from which check (ii) computes its commitment: ((𝗀𝖽,𝗉𝗄𝖽,v),𝗋𝖼𝗆) for Sapling and ((𝗀𝖽,𝗉𝗄𝖽,v,ρ,ψ),𝗋𝖼𝗆) for either Orchard-protocol pool. An address of 𝗂𝗏𝗄 is a pair (d,[𝗂𝗏𝗄]⁢𝖣𝗂𝗏𝖾𝗋𝗌𝗂𝖿𝗒𝖧𝖺𝗌𝗁⁢(d)) with 𝖣𝗂𝗏𝖾𝗋𝗌𝗂𝖿𝗒𝖧𝖺𝗌𝗁⁢(d)≠⊥.

Proposition 4.10 (Soundness of compact acceptance).

Let 𝑐𝑚∗ be the commitment, 𝖼𝗆𝗎 or 𝖼𝗆𝗑, that a compact output or compact Action carries.

  1. (a)

    Every note n accepted by Definition 4.9 is an opening of 𝑐𝑚∗. For every efficient sender, which chooses 𝖾𝗉𝗁𝖾𝗆𝖾𝗋𝖺𝗅𝖪𝖾𝗒, C𝖾𝗇𝖼 and the keys under which they are formed, the probability that the wallet accepts n while the sender outputs a note n′ whose commitment input differs from that of n and whose commitment extracts to 𝑐𝑚∗ is negligible, under the binding of the pool’s note commitment scheme. The tag of the AEAD gives no integrity against the sender, who holds K, so its omission loses none.

  2. (b)

    For an output honestly formed for a note n′ whose address is not an address of 𝗂𝗏𝗄, the probability that 𝗂𝗏𝗄 accepts a candidate is negligible under the same assumption.

Whether 𝑐𝑚∗ is the commitment of an output of the best chain is not a property of decryption; it is settled under the assumption of “Architecture and authority” (§5.1).

Proof.

(a) Check (ii) recomputes the commitment of n deterministically from its commitment input and compares it with 𝑐𝑚∗, whatever the ciphertext and whichever key decrypted it, so n opens 𝑐𝑚∗. Consider the algorithm that generates the wallet’s key, runs the sender and the compact decryption and acceptance, and outputs the commitment inputs of n and n′. When the event of (a) occurs it outputs two distinct commitment inputs whose commitments extract to the same 𝑐𝑚∗≠⊥. For either Orchard-protocol pool this is excluded, except with negligible probability, by the argument of the Ironwood Guide, §“Trial decryption and note acceptance”, Proposition “Consistency of accepted notes”, part (c), under Proposition “Hiding and binding of note commitments” (§“Note commitments”). That proof uses neither the integrity of ChaCha20-Poly1305 nor key commitment, so it applies unchanged to a candidate decrypted from the 52-byte prefix; and binding holds for every 𝗋𝖼𝗆, hence also for the trapdoor derivation of the Orchard pool. For Sapling the named assumption is the computational binding of 𝖭𝗈𝗍𝖾𝖢𝗈𝗆𝗆𝗂𝗍𝖲𝖺𝗉𝗅𝗂𝗇𝗀, the security requirement of the protocol specification, §“Windowed Pedersen commitments”, together with the injectivity of 𝖤𝗑𝗍𝗋𝖺𝖼𝗍𝕁(r) on 𝕁(r) (protocol specification, §“Coordinate Extractor for Jubjub”).

(b) Let n be accepted. By check (ii) its address is (d,[𝗂𝗏𝗄]⁢𝗀𝖽) with 𝗀𝖽=𝖣𝗂𝗏𝖾𝗋𝗌𝗂𝖿𝗒𝖧𝖺𝗌𝗁⁢(d)≠⊥, an address of 𝗂𝗏𝗄. Suppose the commitment inputs of n and n′ were equal. Then the diversified base 𝖣𝗂𝗏𝖾𝗋𝗌𝗂𝖿𝗒𝖧𝖺𝗌𝗁⁢(d′) of the address (d′,𝗉𝗄𝖽′) of n′ equals 𝗀𝖽, and 𝗉𝗄𝖽′=[𝗂𝗏𝗄]⁢𝗀𝖽=[𝗂𝗏𝗄]⁢𝖣𝗂𝗏𝖾𝗋𝗌𝗂𝖿𝗒𝖧𝖺𝗌𝗁⁢(d′), so (d′,𝗉𝗄𝖽′) is an address of 𝗂𝗏𝗄, contrary to the hypothesis. The commitment inputs therefore differ, and the honest sender outputs n′, whose commitment extracts to 𝑐𝑚∗; the honest sender is an efficient sender of (a), which bounds the probability. □

4.4 Note positions and tree sizes

For each shielded pool, every note commitment of a block, not only those of the wallet’s notes, is appended to the wallet’s copy of that pool’s note commitment tree in block order, transaction order and description order: 𝖼𝗆𝗑 of each Action of the pool and 𝖼𝗆𝗎 of each Sapling output (ZIP 307, “Creating and updating note witnesses”; Ironwood Guide, §“The Merkle hash and the tree”, Definition “Note commitment tree”; protocol specification, §“Note Commitment Trees”). The leaf of each accepted note is marked for witness retention. The part of the tree a wallet must retain is fixed in “Commitment-tree synchronisation” (§7).

Definition 4.11 (Note position).

Let 𝗉𝗈𝗈𝗅 be a shielded pool, b a block height with compact block 𝐶𝐵, and n𝗉𝗈𝗈𝗅⁢(b) the number of commitments of 𝗉𝗈𝗈𝗅 in 𝐶𝐵. The start size of b is

S𝗌𝗍𝖺𝗋𝗍𝗉𝗈𝗈𝗅⁢(b):={S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(b−1)if the wallet knows it,0otherwise, if ⁢b⁢ lies below the activation of ⁢𝗉𝗈𝗈𝗅,S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(b)−n𝗉𝗈𝗈𝗅⁢(b)otherwise,

the wallet knowing S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(b−1) when it holds the compact block of height b−1 or a tree state of 𝗉𝗈𝗈𝗅 at the end of b−1; in the third case the value is taken from 𝐶𝐵 alone, and the block is rejected if it is negative. For the j-th output o of 𝗉𝗈𝗈𝗅, counted from j=0, of a compact transaction 𝑐𝑡𝑥 of b,

𝗉𝗈𝗌𝗂𝗍𝗂𝗈𝗇⁢(o):=S𝗌𝗍𝖺𝗋𝗍𝗉𝗈𝗈𝗅⁢(b)+𝗈𝖿𝖿⁢(𝑐𝑡𝑥)+j,

where 𝗈𝖿𝖿⁢(𝑐𝑡𝑥) is the number of commitments of 𝗉𝗈𝗈𝗅 in the compact transactions of b before 𝑐𝑡𝑥. Positions are per pool. A block scanned out of order thus places its notes from its own compact block. Note positions are designed but unspecified (Definition 1.1).

For a pool outside the pool set 𝒫 of the query that returned b, the count n𝗉𝗈𝗈𝗅⁢(b) is not served, and neither position nor check is defined.

The position of a note is the leaf index of its commitment (Ironwood Guide, §“The Merkle hash and the tree”, Definition “Note commitment tree”, item 1). Every spend needs it for the authentication path. A Sapling nullifier depends on it, through ρ=𝖬𝗂𝗑𝗂𝗇𝗀𝖯𝖾𝖽𝖾𝗋𝗌𝖾𝗇𝖧𝖺𝗌𝗁⁢(𝖼𝗆,𝗉𝗈𝗌) (protocol specification, §“Computing ρ values and Nullifiers”), while the nullifier of an Orchard-protocol note does not.

Lemma 4.12 (Consistency of tree sizes).

Let the wallet reject a block b unless, for each shielded pool of the pool set 𝒫 of the query that returned b,

S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(b)≥n𝗉𝗈𝗈𝗅⁢(b)andS𝗌𝗍𝖺𝗋𝗍𝗉𝗈𝗈𝗅⁢(b)+n𝗉𝗈𝗈𝗅⁢(b)=S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(b).
  1. (a)

    If every reported size is the true size, no block is rejected, and every position of Definition 4.11 is the leaf index of the commitment in the pool’s tree.

  2. (b)

    A reported S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(b) that is inconsistent with the block’s own commitment count, or with the known end size of b−1, is rejected.

  3. (c)

    A block with n𝗉𝗈𝗈𝗅⁢(b)>0 and reported size 0 is rejected. A size read as zero therefore yields a position only where 0 is consistent with the block, and the check needs no means of telling an absent size from zero.

  4. (d)

    A size that is false but consistent with both conditions is not detected; its exclusion is clause (a) of the server assumption of “Architecture and authority” (§5.1).

Proof.

(a) The chain appends the commitments of a pool in block, transaction and description order, each to the least unused index (Ironwood Guide, §“The Merkle hash and the tree”, Definition “Note commitment tree”). The true start size of b is thus the true end size of b−1, which equals S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(b)−n𝗉𝗈𝗈𝗅⁢(b)≥0, so both conditions hold in every case of the start size; and the j-th commitment of 𝑐𝑡𝑥 lands at index S𝗌𝗍𝖺𝗋𝗍𝗉𝗈𝗈𝗅⁢(b)+𝗈𝖿𝖿⁢(𝑐𝑡𝑥)+j. (b) A size S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(b)<n𝗉𝗈𝗈𝗅⁢(b) fails the first condition. With a known start size, a size that differs from S𝗌𝗍𝖺𝗋𝗍𝗉𝗈𝗈𝗅⁢(b)+n𝗉𝗈𝗈𝗅⁢(b) fails the second. (c) A size 0 with n𝗉𝗈𝗈𝗅⁢(b)>0 fails the first condition. (d) Let the wallet not know the end size of b−1, and let b lie at or above the activation of 𝗉𝗈𝗈𝗅, so that its start size is that of the third case of Definition 4.11. Adding one integer δ≠0 to S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(b) and to the end sizes of all later scanned blocks, such that every shifted size stays in [0,232] and at least the count of its block, preserves both conditions for b, whose start size is computed from its own end size, and for every later block, whose start and end sizes shift by δ together. □

Comparison of the running position with S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(b) identifies the last commitment of 𝗉𝗈𝗈𝗅 in b, at position S𝖾𝗇𝖽𝗉𝗈𝗈𝗅⁢(b)−1. The tree after that commitment, or for n𝗉𝗈𝗈𝗅⁢(b)=0 the tree at the end of b−1, is the tree state at the end of b. Its root is the anchor that a later spend against height b uses (Ironwood Guide, §“Anchors”; protocol specification, §“Transactions and Treestates”), and the wallet records it as a candidate anchor.