zcash_primitives: Add constructor and getter to `zip32::ChainCode`

This commit is contained in:
Jack Grigg 2023-11-21 02:29:43 +00:00
parent 61bb18d97f
commit 45ef8b1604
3 changed files with 24 additions and 16 deletions

View File

@ -74,6 +74,8 @@ and this library adheres to Rust's notion of
- `zcash_primitives::zip32`:
- `ChildIndex::hardened`
- `ChildIndex::index`
- `ChainCode::new`
- `ChainCode::as_bytes`
- `impl From<AccountId> for ChildIndex`
- Test helpers, behind the `test-dependencies` feature flag:
- `zcash_primitives::sapling::prover::mock::{MockSpendProver, MockOutputProver}`

View File

@ -81,14 +81,20 @@ impl ChildIndex {
}
}
/// A BIP-32 chain code
/// A value that is needed, in addition to a spending key, in order to derive descendant
/// keys and addresses of that key.
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub struct ChainCode([u8; 32]);
impl ChainCode {
/// Returns byte representation of the chain code, as required for
/// Constructs a `ChainCode` from the given array.
pub fn new(c: [u8; 32]) -> Self {
Self(c)
}
/// Returns the byte representation of the chain code, as required for
/// [ZIP 32](https://zips.z.cash/zip-0032) encoding.
fn as_bytes(&self) -> &[u8; 32] {
pub fn as_bytes(&self) -> &[u8; 32] {
&self.0
}
}

View File

@ -307,7 +307,7 @@ impl ExtendedSpendingKey {
depth: 0,
parent_fvk_tag: FvkTag::master(),
child_index: KeyIndex::Master,
chain_code: ChainCode(c_m),
chain_code: ChainCode::new(c_m),
expsk: ExpandedSpendingKey::from_spending_key(sk_m),
dk: DiversifierKey::master(sk_m),
}
@ -333,8 +333,8 @@ impl ExtendedSpendingKey {
let child_index = KeyIndex::new(depth, u32::from_le_bytes(ci_bytes))
.ok_or(DecodingError::UnsupportedChildIndex)?;
let mut chain_code = ChainCode([0u8; 32]);
chain_code.0[..].copy_from_slice(&b[9..41]);
let mut c = [0u8; 32];
c[..].copy_from_slice(&b[9..41]);
let expsk = ExpandedSpendingKey::from_bytes(&b[41..137])?;
@ -345,7 +345,7 @@ impl ExtendedSpendingKey {
depth,
parent_fvk_tag,
child_index,
chain_code,
chain_code: ChainCode::new(c),
expsk,
dk,
})
@ -375,7 +375,7 @@ impl ExtendedSpendingKey {
depth,
parent_fvk_tag: FvkTag(tag),
child_index,
chain_code: ChainCode(c),
chain_code: ChainCode::new(c),
expsk,
dk: DiversifierKey(dk),
})
@ -416,7 +416,7 @@ impl ExtendedSpendingKey {
let mut le_i = [0; 4];
LittleEndian::write_u32(&mut le_i, i.index());
prf_expand_vec(
&self.chain_code.0,
self.chain_code.as_bytes(),
&[&[0x11], &self.expsk.to_bytes(), &self.dk.0, &le_i],
)
};
@ -428,7 +428,7 @@ impl ExtendedSpendingKey {
depth: self.depth + 1,
parent_fvk_tag: FvkFingerprint::from(&fvk).tag(),
child_index: KeyIndex::Child(i),
chain_code: ChainCode(c_i),
chain_code: ChainCode::new(c_i),
expsk: {
let mut ask = jubjub::Fr::from_bytes_wide(prf_expand(i_l, &[0x13]).as_array());
let mut nsk = jubjub::Fr::from_bytes_wide(prf_expand(i_l, &[0x14]).as_array());
@ -560,7 +560,7 @@ impl ExtendedFullViewingKey {
depth,
parent_fvk_tag: FvkTag(tag),
child_index,
chain_code: ChainCode(c),
chain_code: ChainCode::new(c),
fvk,
dk: DiversifierKey(dk),
})
@ -570,7 +570,7 @@ impl ExtendedFullViewingKey {
writer.write_u8(self.depth)?;
writer.write_all(&self.parent_fvk_tag.0)?;
writer.write_u32::<LittleEndian>(self.child_index.index())?;
writer.write_all(&self.chain_code.0)?;
writer.write_all(self.chain_code.as_bytes())?;
writer.write_all(&self.fvk.to_bytes())?;
writer.write_all(&self.dk.0)?;
@ -1617,7 +1617,7 @@ mod tests {
assert_eq!(xsk.expsk.ovk.0, tv.ovk);
assert_eq!(xsk.dk.0, tv.dk);
assert_eq!(xsk.chain_code.0, tv.c);
assert_eq!(xsk.chain_code.as_bytes(), &tv.c);
let mut ser = vec![];
xsk.write(&mut ser).unwrap();
@ -1632,7 +1632,7 @@ mod tests {
assert_eq!(internal_xsk.expsk.ovk.0, tv.internal_ovk);
assert_eq!(internal_xsk.dk.0, tv.internal_dk);
assert_eq!(internal_xsk.chain_code.0, tv.c);
assert_eq!(internal_xsk.chain_code.as_bytes(), &tv.c);
let mut ser = vec![];
internal_xsk.write(&mut ser).unwrap();
@ -1645,7 +1645,7 @@ mod tests {
assert_eq!(xfvk.fvk.ovk.0, tv.ovk);
assert_eq!(xfvk.dk.0, tv.dk);
assert_eq!(xfvk.chain_code.0, tv.c);
assert_eq!(xfvk.chain_code.as_bytes(), &tv.c);
assert_eq!(xfvk.fvk.vk.ivk().to_repr().as_ref(), tv.ivk);
@ -1689,7 +1689,7 @@ mod tests {
assert_eq!(internal_xfvk.fvk.ovk.0, tv.internal_ovk);
assert_eq!(internal_xfvk.dk.0, tv.internal_dk);
assert_eq!(internal_xfvk.chain_code.0, tv.c);
assert_eq!(internal_xfvk.chain_code.as_bytes(), &tv.c);
assert_eq!(
internal_xfvk.fvk.vk.ivk().to_repr().as_ref(),