All relevant types have `Debug` impls, but some of the trait and method
impls were lacking `Debug` bounds on their generic types. This prevented
`Debug` impls being used on the overall partially-constructed `Bundle`
types.
Use derived equality and ordering (which delegate to constant-time
versions) for note::nullifier::Nullifier and tree::MerkleHashOrchard
so that these types can be used as map keys in wallets.
We removed this in zcash/orchard#267 as it did not need to be part of
the public API, but we do still need a way to convert the user-defined
valueBalance type into a `ValueSum` when constructing `bvk`, and this
method is preferable to exposing the `ValueSum` internals.
This enables `InProgress<Unproven, Unauthorized>: Clone`, which allows
the bundle returned by `Builder::build` to be cloned. In pure-Rust
wallets this should not be necessary, but it is required for `zcashd`
due to FFI-crossing.
Callers cannot assume that any specific output corresponds to a specific
Orchard recipient, and must trial-decrypt all outputs to find the ones
belonging to them. This is consistent with higher-layer semantics like
having Unified Addresses as recipients (where the mapping from recipient
to a specific output would become much more complex).
Closeszcash/orchard#203.
Co-authored-by: Daira Hopwood <daira@jacaranda.org>
The MSRV is now 1.54.0, because reddsa 0.2.0 included a fix to its
nightly CI that inadvertently bumped its MSRV.
The `halo2` crate is now the `halo2_proofs` crate, but we're avoiding
the cross-repo crate rename until after `halo2_gadgets` is extracted.
This also brings in the 20% prover performance improvement from
zcash/halo2#447.
The sinsemilla submodules note_commit and commit_ivk are tailored
for input lengths specific to Orchard. They have been moved out of
the gadget folder and into the circuit folder.
This also involves changing the visibility of some getter functions
to be usable outside gadget::sinsemilla.
There is no reason for crate users to be constructing `ValueSum`
directly. We no longer use it to represent `valueBalanceOrchard`,
instead requiring the user to specify their own type.
`PrimeField::from_repr` explicitly leaves the endianness opaque. We
therefore can't use it in places we were using `FieldExt::from_bytes`
(which was specifically little-endian) generically, but the previous
commit replaced it everywhere. We now handle generic contexts on a
case-by-case basis:
- Where we needed to convert bitstrings into field elements, we now use
double-and-add on the field elements directly instead of on bytes.
This is less efficient, but visible correct (and a future change to
the `ff` crate APIs could enable the more efficient version).
- `INV_TWO_POW_K`, which is pre-computed for `pallas::Base`, was being
incorrectly used in a field-generic circuit. We now compute it live.
- `test_zs_and_us` was only used in tests, and hard-coded a field
element encoding length of 32 bytes. It now uses Pallas concretely.
`ak_P` is not allowed to be the identity in the Orchard protocol. We
were enforcing this by construction in most places, except for the
parsing of an Orchard full viewing key.
Closeszcash/orchard#261.
In the previous commit, we fixed a bug where padding was being added to
the state when the sponge was in squeezing mode. But there's no need to
assign a circuit region in which we add constant zeroes to the state :)
Sponge constructions pad the entire input message and then split it into
rate-sized chunks. The previous implementation was using an incorrect
duplex-like hybrid where padding was applied to each chunked input. We
now use an enum to distinguish message and padding words being absorbed
into the sponge.
This also fixes two previous bugs:
- If a `ConstantLength` hash had a length greater than the permutation's
rate but not a multiple of it, no padding would be generated and the
circuit would fail to create proofs.
- If a sponge usage required more output than the permutation's rate,
the squeeze-side permutations would in some cases incorrectly apply
padding, when it should instead use the prior state as-is. We now add
zeroes instead.
This change doesn't alter the Orchard circuit, because it doesn't need
any padding cells, only takes a single field element as output, and
padding is still assigned in the same region as before.
For almost all the sponge constructions defined in the Poseidon paper,
the domain can be defined completely statically. Variable-length hashing
requires knowledge of the message length, but that can be provided to
the fixed padding function in a subsequent commit, and in any case we
can't use variable-length inputs in a circuit.
The `Sponge` struct's API correctly enforces the properties of a sponge:
it can absorb an arbitrary number of elements, and then squeeze an
arbitrary number of elements, but cannot absorb after it has squeezed.
Co-authored-by: ying tong <yingtong@z.cash>
The ECC test chip performs various checks that assume the chip will only
be synthesized with witnesses. This assumption is broken by the chip
printer test, so we fix the assumption here.
In order to make the changeover easier to review, we redefined
`CellValue<F>` to be `AssignedCell<F, F>`. Now we remove that type and
rename throughout the codebase.
As the underlying `Region` methods now return `AssignedCell` instead of
`Cell`, we can simplify all the places where we then constructed a
`CellValue` struct.
We change `CellValue` into a typedef of `AssignedCell` to simplify the
migration in this commit.
The migration from `CellValue` to `AssignedCell` requires several other
changes:
- `<CellValue as Var>::value()` returned `Option<F>`, whereas
`AssignedCell::<F, F>::value()` returns `Option<&F>`. This means we
need to dereference, use `Option::cloned`, or alter functions to take
`&F` arguments.
- `StateWord` in the Poseidon chip has been changed to a newtype around
`AssignedCell` (the chip was written before `CellValue` existed).
This is only used in chip::mul::Config. In a subsequent commit,
this will be configured from mul::Config instead of from
ecc::chip::Config.
This commit does not result in circuit changes.
This is only used in chip::mul::Config. In a subsequent commit,
this will be configured from mul::Config instead of from
ecc::chip::Config.
This commit does not result in circuit changes.
This is only used in chip::mul::Config. In a subsequent commit,
this will be configured from mul::Config instead of from
ecc::chip::Config.
This commit does not result in circuit changes.
We are about to extract the sub-configs from mul::Config and refactor
them. Doing so would have moved their gate definitions past the one gate
that isn't created in a sub-config. Reordering the definitions here will
make the subsequent refactor diffs simpler to review.
We only need is_identity() in tests and can implement it on the
concrete EccPoint type. This method is flagged off by #[cfg(test)].
Co-authored-by: Daira Hopwood <daira@jacaranda.org>
After the previous commit, this is no longer used anywhere. Additionally
it was not enforcing the conversion in the circuit, which could lead to
circuit implementation mistakes.
This is necessary because the blinding factor r can be zero with greater
than negligible probability in an adversarial case, which with incomplete
addition would cause the circuit to compute a commitment that is not on
the curve.