⚠️ Work in Progress: This project is under active development and not yet complete.
A toolkit for generating non-membership proofs for Zcash shielded assets as part of the Namada airdrop. This allows Zcash users with unspent shielded notes (Sapling or Orchard) to prove they held funds at a specific snapshot height without revealing their nullifiers.
A non-membership proof is a cryptographic proof that demonstrates a specific element (such as a nullifier) is not present in a given set, without revealing any additional information about the element itself. In the context of Zcash and this toolkit, non-membership proofs allow users to prove that their shielded note's nullifier does not appear in a snapshot of spent nullifiers. This enables users to show they held unspent funds at a particular block height, which is essential for privacy-preserving airdrops.
These proofs are constructed using Merkle trees built from the set of known nullifiers at the snapshot height. By providing a non-membership proof, a user can convince a verifier that their note was not spent (i.e., its nullifier is not in the tree).
- Rust 1.91+ (uses Rust 2024 edition)
- Protobuf compiler (
protoc) - required for building the lightwalletd gRPC bindings
After cloning the repo:
git submodule update --init --recursive
git clone --branch v0.11.0 --single-branch https://github.com/zcash/orchard.git .patched-orchard
git -C .patched-orchard apply "../nix/airdrop-orchard-nullifier.patch"
git clone --branch v0.5.0 --single-branch https://github.com/zcash/sapling-crypto.git .patched-sapling-crypto
git -C .patched-sapling-crypto apply "../nix/airdrop-sapling-nullifier.patch"Note: The patches add support for deriving "hiding nullifiers" - a privacy-preserving nullifier derivation that allows proving non-membership without revealing the actual nullifier.
Submodule updates need to be run manually:
git submodule update --init --recursiveThis workspace uses Nix to enhance the development experience.
nix develop- enter the development environmentnix fmt- format the workspacenix flake check- run checks, like linters and formatters. At the momentcargo clippyis not running with the other linters.
The workspace also uses pre-commit checks. These can be removed if they prove problematic.
- Description: CLI tool for building Zcash airdrop snapshots and generating non-membership proofs. It supports two main commands:
build-airdrop-configuration: Fetches nullifiers from a lightwalletd server or local files and saves them as snapshot files. Also exports a configuration JSON with Merkle tree roots.airdrop-claim: Scans the chain for notes belonging to provided viewing keys, builds Merkle trees from snapshot nullifiers, and generates non-membership proofs for unspent notes.- Run with
--helpto check the usage.
- Description: A utility to convert a Zcash mnemonic to Full Viewing Keys. Outputs the Unified Full Viewing Key in human-readable Bech32 format (e.g.,
uview1...), as well as the individual Orchard and Sapling keys in hex format. Run with--helpto check the usage.
- Description: Core library for generating non-membership proofs for Zcash nullifiers. Provides functionality for:
- Streaming nullifiers from lightwalletd or local files
- Scanning the chain for user notes using Full Viewing Keys
- Building Merkle trees from sorted nullifiers for non-membership proofs
- Deriving standard and hiding nullifiers for Sapling and Orchard notes
Assuming that the project is set up correctly.
After completing the setup steps above, you can build the project. The project provides two binaries, mnemonic-to-fvks and the airdrop. To build them use:
cargo build --releaseThis will produce the optimized mnemonic-to-fvks and airdrop executables in the target/release directory.
For a complete walkthrough of the airdrop claim process, see the Usage Guide.