Skip to content
This repository has been archived by the owner on Sep 26, 2023. It is now read-only.

Commit

Permalink
v1.8.0-beta1
Browse files Browse the repository at this point in the history
switch librustzcash to git directly
Add orchard incoming support
  • Loading branch information
adityapk00 committed Jul 29, 2022
1 parent 89a2bab commit 6536876
Show file tree
Hide file tree
Showing 21 changed files with 1,212 additions and 338 deletions.
246 changes: 143 additions & 103 deletions Cargo.lock

Large diffs are not rendered by default.

10 changes: 9 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,12 @@ members = [
]

[profile.release]
debug = false
debug = false

[patch.crates-io]
zcash_address = { git = "https://github.com/zcash/librustzcash", rev = "09567fc280463f5797a77f1d764205be8ad8e64a"}
zcash_primitives = { git = "https://github.com/zcash/librustzcash", rev = "09567fc280463f5797a77f1d764205be8ad8e64a"}
zcash_client_backend = { git = "https://github.com/zcash/librustzcash", rev = "09567fc280463f5797a77f1d764205be8ad8e64a"}
zcash_note_encryption = { git = "https://github.com/zcash/librustzcash", rev = "09567fc280463f5797a77f1d764205be8ad8e64a"}
zcash_encoding = { git = "https://github.com/zcash/librustzcash", rev = "09567fc280463f5797a77f1d764205be8ad8e64a"}
zcash_proofs = { git = "https://github.com/zcash/librustzcash", rev = "09567fc280463f5797a77f1d764205be8ad8e64a"}
2 changes: 1 addition & 1 deletion cli/Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "zecwallet-cli"
version = "1.7.20"
version = "1.8.0-beta1"
edition = "2018"

[dependencies]
Expand Down
2 changes: 1 addition & 1 deletion cli/src/version.rs
Original file line number Diff line number Diff line change
@@ -1 +1 @@
pub const VERSION: &str = "1.7.20";
pub const VERSION: &str = "1.8.0-beta1";
20 changes: 14 additions & 6 deletions lib/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -48,12 +48,20 @@ group = "0.12"

rust-embed = { version = "6.3.0", features = ["debug-embed"] }

zcash_primitives = { git = "https://github.com/adityapk00/librustzcash", rev = "7183acd2fe12ebf201cae5b871166e356273c481", features = ["transparent-inputs"] }
# zcash_primitives = { path = "../../librustzcash/zcash_primitives", features = ["transparent-inputs"] }
zcash_client_backend = { git = "https://github.com/adityapk00/librustzcash", rev = "7183acd2fe12ebf201cae5b871166e356273c481"}
zcash_proofs = { git = "https://github.com/adityapk00/librustzcash", rev = "7183acd2fe12ebf201cae5b871166e356273c481", features = ["multicore"]}
zcash_encoding = { git = "https://github.com/adityapk00/librustzcash", rev = "7183acd2fe12ebf201cae5b871166e356273c481"}
zcash_note_encryption = { git = "https://github.com/adityapk00/librustzcash", rev = "7183acd2fe12ebf201cae5b871166e356273c481", features = ["pre-zip-212"]}
orchard = "0.2.0"
zcash_address = "0.1.0"
zcash_primitives = { version = "0.7.0", features = ["transparent-inputs"] }
zcash_client_backend = "0.5.0"
zcash_proofs = { version = "0.7.1", features = ["multicore"] }
zcash_encoding = "0.1.0"
zcash_note_encryption = { version = "0.1.0", features = ["pre-zip-212"] }


#zcash_primitives = { git = "https://github.com/adityapk00/librustzcash", rev = "7183acd2fe12ebf201cae5b871166e356273c481", features = ["transparent-inputs"] }
#zcash_client_backend = { git = "https://github.com/adityapk00/librustzcash", rev = "7183acd2fe12ebf201cae5b871166e356273c481"}
#zcash_proofs = { git = "https://github.com/adityapk00/librustzcash", rev = "7183acd2fe12ebf201cae5b871166e356273c481", features = ["multicore"]}
#zcash_encoding = { git = "https://github.com/adityapk00/librustzcash", rev = "7183acd2fe12ebf201cae5b871166e356273c481"}
#zcash_note_encryption = { git = "https://github.com/adityapk00/librustzcash", rev = "7183acd2fe12ebf201cae5b871166e356273c481", features = ["pre-zip-212"]}

[dev-dependencies]
portpicker = "0.1.1"
Expand Down
22 changes: 16 additions & 6 deletions lib/proto/compact_formats.proto
Original file line number Diff line number Diff line change
Expand Up @@ -37,20 +37,30 @@ message CompactTx {
// valueBalance + (sum(vPubNew) - sum(vPubOld) - sum(tOut))
uint32 fee = 3;

repeated CompactSpend spends = 4; // inputs
repeated CompactOutput outputs = 5; // outputs
repeated CompactSaplingSpend spends = 4; // inputs
repeated CompactSaplingOutput outputs = 5; // outputs
repeated CompactOrchardAction actions = 6;
}

// CompactSpend is a Sapling Spend Description as described in 7.3 of the Zcash
// CompactSaplingSpend is a Sapling Spend Description as described in 7.3 of the Zcash
// protocol specification.
message CompactSpend {
message CompactSaplingSpend {
bytes nf = 1; // nullifier (see the Zcash protocol specification)
}

// output is a Sapling Output Description as described in section 7.4 of the
// Zcash protocol spec. Total size is 948.
message CompactOutput {
message CompactSaplingOutput {
bytes cmu = 1; // note commitment u-coordinate
bytes epk = 2; // ephemeral public key
bytes ciphertext = 3; // ciphertext and zkproof
bytes ciphertext = 3; // first 52 bytes of ciphertext
}

// https://github.com/zcash/zips/blob/main/zip-0225.rst#orchard-action-description-orchardaction
// (but not all fields are needed)
message CompactOrchardAction {
bytes nullifier = 1; // [32] The nullifier of the input note
bytes cmx = 2; // [32] The x-coordinate of the note commitment for the output note
bytes ephemeralKey = 3; // [32] An encoding of an ephemeral Pallas public key
bytes ciphertext = 4; // [52] The note plaintext component of the encCiphertext field
}
20 changes: 12 additions & 8 deletions lib/proto/service.proto
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,8 @@ message TxFilter {
}

// RawTransaction contains the complete transaction data. It also optionally includes
// the block height in which the transaction was included.
// the block height in which the transaction was included, or, when returned
// by GetMempoolStream(), the latest block height.
message RawTransaction {
bytes data = 1; // exact data returned by Zcash 'getrawtransaction'
uint64 height = 2; // height that the transaction was mined (or -1)
Expand Down Expand Up @@ -109,11 +110,12 @@ message Exclude {

// The TreeState is derived from the Zcash z_gettreestate rpc.
message TreeState {
string network = 1; // "main" or "test"
uint64 height = 2;
string hash = 3; // block id
uint32 time = 4; // Unix epoch time when the block was mined
string tree = 5; // sapling commitment tree state
string network = 1; // "main" or "test"
uint64 height = 2; // block height
string hash = 3; // block id
uint32 time = 4; // Unix epoch time when the block was mined
string tree = 5; // sapling commitment tree state
string orchardTree = 6; // orchard commitment tree state
}

// Results are sorted by height, which makes it easy to issue another
Expand Down Expand Up @@ -163,7 +165,7 @@ service CompactTxStreamer {
rpc GetBlock(BlockID) returns (CompactBlock) {}
// Return a list of consecutive compact blocks
rpc GetBlockRange(BlockRange) returns (stream CompactBlock) {}

// Get the historical and current prices
rpc GetZECPrice(PriceRequest) returns (PriceResponse) {}
rpc GetCurrentZECPrice(Empty) returns (PriceResponse) {}
Expand All @@ -178,7 +180,7 @@ service CompactTxStreamer {

// Legacy API that is used as a fallback for t-Address support, if the server is running the old version (lwdv2)
rpc GetAddressTxids(TransparentAddressBlockFilter) returns (stream RawTransaction) {}

rpc GetTaddressBalance(AddressList) returns (Balance) {}
rpc GetTaddressBalanceStream(stream Address) returns (Balance) {}

Expand All @@ -193,6 +195,8 @@ service CompactTxStreamer {
// in the exclude list that don't exist in the mempool are ignored.
rpc GetMempoolTx(Exclude) returns (stream CompactTx) {}

// Return a stream of current Mempool transactions. This will keep the output stream open while
// there are mempool transactions. It will close the returned stream when a new block is mined.
rpc GetMempoolStream(Empty) returns (stream RawTransaction) {}

// GetTreeState returns the note commitment tree state corresponding to the given block.
Expand Down
39 changes: 35 additions & 4 deletions lib/src/blaze/fetch_full_tx.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,9 @@ use crate::{

use futures::{stream::FuturesUnordered, StreamExt};
use log::info;
use orchard::note_encryption::OrchardDomain;
use zcash_note_encryption::try_note_decryption;

use std::{
collections::HashSet,
convert::{TryFrom, TryInto},
Expand Down Expand Up @@ -291,9 +294,9 @@ impl<P: consensus::Parameters + Send + Sync + 'static> FetchFullTxns<P> {
.collect();

let extfvks = Arc::new(keys.read().await.get_all_extfvks());
let ivks: Vec<_> = extfvks.iter().map(|k| k.fvk.vk.ivk()).collect();
let s_ivks: Vec<_> = extfvks.iter().map(|k| k.fvk.vk.ivk()).collect();

// Step 4: Scan shielded sapling outputs to see if anyone of them is us, and if it is, extract the memo. Note that if this
// Step 4a: Scan shielded sapling outputs to see if anyone of them is us, and if it is, extract the memo. Note that if this
// is invoked by a transparent transaction, and we have not seen this Tx from the trial_decryptions processor, the Note
// might not exist, and the memo updating might be a No-Op. That's Ok, the memo will get updated when this Tx is scanned
// a second time by the Full Tx Fetcher
Expand All @@ -302,7 +305,7 @@ impl<P: consensus::Parameters + Send + Sync + 'static> FetchFullTxns<P> {
if let Some(s_bundle) = tx.sapling_bundle() {
for output in s_bundle.shielded_outputs.iter() {
// Search all of our keys
for (i, ivk) in ivks.iter().enumerate() {
for (i, ivk) in s_ivks.iter().enumerate() {
let (note, to, memo_bytes) =
match try_sapling_note_decryption(&config.get_params(), height, &ivk, output) {
Some(ret) => ret,
Expand All @@ -322,7 +325,7 @@ impl<P: consensus::Parameters + Send + Sync + 'static> FetchFullTxns<P> {
}

let memo = memo_bytes.clone().try_into().unwrap_or(Memo::Future(memo_bytes));
wallet_txns.write().await.add_memo_to_note(&tx.txid(), note, memo);
wallet_txns.write().await.add_memo_to_s_note(&tx.txid(), note, memo);
}

// Also scan the output to see if it can be decoded with our OutgoingViewKey
Expand Down Expand Up @@ -371,6 +374,34 @@ impl<P: consensus::Parameters + Send + Sync + 'static> FetchFullTxns<P> {
}
}

// Step 4b: Scan the orchard part of the bundle to see if there are any memos
let o_ivks = keys.read().await.get_all_orchard_ivks();
if let Some(o_bundle) = tx.orchard_bundle() {
// let orchard_actions = o_bundle
// .actions()
// .into_iter()
// .map(|oa| (OrchardDomain::for_action(oa), oa))
// .collect::<Vec<_>>();

// let decrypts = try_note_decryption(o_ivks.as_ref(), orchard_actions.as_ref());
for oa in o_bundle.actions() {
for (ivk_num, ivk) in o_ivks.iter().enumerate() {
if let Some((note, _address, memo_bytes)) =
try_note_decryption(&OrchardDomain::for_action(oa), ivk, oa)
{
if let Ok(memo) = Memo::from_bytes(&memo_bytes) {
wallet_txns.write().await.add_memo_to_o_note(
&tx.txid(),
&keys.read().await.okeys[ivk_num].fvk(),
note,
memo,
);
}
}
}
}
}

// Step 5. Process t-address outputs
// If this Tx in outgoing, i.e., we recieved sent some money in this Tx, then we need to grab all transparent outputs
// that don't belong to us as the outgoing metadata
Expand Down
50 changes: 40 additions & 10 deletions lib/src/blaze/test_utils.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
use std::{convert::TryInto, sync::Arc};

use crate::{
compact_formats::{CompactBlock, CompactOutput, CompactSpend, CompactTx},
compact_formats::{CompactBlock, CompactSaplingOutput, CompactSaplingSpend, CompactTx},
lightclient::{
faketx::{clone_transactiondata, new_transactiondata},
test_server::TestServerData,
Expand Down Expand Up @@ -138,12 +138,12 @@ impl FakeTransaction {
let enc_ciphertext = encryptor.encrypt_note_plaintext();

// Create a fake CompactBlock containing the note
let mut cout = CompactOutput::default();
let mut cout = CompactSaplingOutput::default();
cout.cmu = cmu;
cout.epk = epk;
cout.ciphertext = enc_ciphertext[..52].to_vec();

let mut sapling_bundle = if self.td.sapling_bundle.is_some() {
let mut sapling_bundle = if self.td.sapling_bundle().is_some() {
self.td.sapling_bundle().unwrap().clone()
} else {
sapling::Bundle {
Expand All @@ -156,7 +156,17 @@ impl FakeTransaction {
}
};
sapling_bundle.shielded_outputs.push(od);
self.td.sapling_bundle = Some(sapling_bundle);

self.td = TransactionData::from_parts(
self.td.version(),
self.td.consensus_branch_id(),
self.td.lock_time(),
self.td.expiry_height(),
self.td.transparent_bundle().cloned(),
self.td.sprout_bundle().cloned(),
Some(sapling_bundle),
self.td.orchard_bundle().cloned(),
);

self.ctx.outputs.push(cout);

Expand All @@ -166,7 +176,7 @@ impl FakeTransaction {
pub fn add_tx_spending(&mut self, nf: &Nullifier, value: u64, ovk: &OutgoingViewingKey, to: &PaymentAddress) {
let _ = self.add_sapling_output(value, Some(ovk.clone()), to);

let mut cs = CompactSpend::default();
let mut cs = CompactSaplingSpend::default();
cs.nf = nf.to_vec();
self.ctx.spends.push(cs);

Expand Down Expand Up @@ -206,7 +216,17 @@ impl FakeTransaction {
value: Amount::from_u64(value).unwrap(),
script_pubkey: TransparentAddress::PublicKey(taddr_bytes.try_into().unwrap()).script(),
});
self.td.transparent_bundle = Some(t_bundle);

self.td = TransactionData::from_parts(
self.td.version(),
self.td.consensus_branch_id(),
self.td.lock_time(),
self.td.expiry_height(),
Some(t_bundle),
self.td.sprout_bundle().cloned(),
self.td.sapling_bundle().cloned(),
self.td.orchard_bundle().cloned(),
);

self.taddrs_involved.push(taddr)
}
Expand All @@ -228,7 +248,17 @@ impl FakeTransaction {
script_sig: Script { 0: vec![] },
sequence: 0,
});
self.td.transparent_bundle = Some(t_bundle);

self.td = TransactionData::from_parts(
self.td.version(),
self.td.consensus_branch_id(),
self.td.lock_time(),
self.td.expiry_height(),
Some(t_bundle),
self.td.sprout_bundle().cloned(),
self.td.sapling_bundle().cloned(),
self.td.orchard_bundle().cloned(),
);

self.taddrs_involved.push(taddr);
}
Expand Down Expand Up @@ -289,7 +319,7 @@ impl FakeCompactBlock {
};

// Create a fake CompactBlock containing the note
let mut cout = CompactOutput::default();
let mut cout = CompactSaplingOutput::default();
cout.cmu = note.cmu().to_bytes().to_vec();
cout.epk = [0u8; 32].to_vec();
cout.ciphertext = [0u8; 52].to_vec();
Expand Down Expand Up @@ -349,7 +379,7 @@ impl FakeCompactBlockList {

if let Some(s_bundle) = tx.sapling_bundle() {
for out in &s_bundle.shielded_outputs {
let mut cout = CompactOutput::default();
let mut cout = CompactSaplingOutput::default();
cout.cmu = out.cmu.to_repr().to_vec();
cout.epk = out.ephemeral_key.0.to_vec();
cout.ciphertext = out.enc_ciphertext[..52].to_vec();
Expand All @@ -358,7 +388,7 @@ impl FakeCompactBlockList {
}

for spend in &s_bundle.shielded_spends {
let mut cs = CompactSpend::default();
let mut cs = CompactSaplingSpend::default();
cs.nf = spend.nullifier.to_vec();

ctx.spends.push(cs);
Expand Down
Loading

0 comments on commit 6536876

Please sign in to comment.