Refactor/Cleanup

Spam filter + GPU
This commit is contained in:
Hanh 2022-09-04 19:19:49 +08:00
parent 48c5f45259
commit fd47863277
14 changed files with 166 additions and 151 deletions

View File

@ -1,6 +1,7 @@
// Account creation
use crate::coinconfig::CoinConfig;
use crate::db::AccountData;
use crate::key2::decode_key;
use crate::taddr::{derive_taddr, derive_tkeys};
use crate::transaction::retrieve_tx_info;
@ -36,7 +37,7 @@ pub fn new_account(
pub fn new_sub_account(name: &str, index: Option<u32>, count: u32) -> anyhow::Result<()> {
let c = CoinConfig::get_active();
let db = c.db()?;
let (seed, _) = db.get_seed(c.id_account)?;
let AccountData { seed, .. } = db.get_account_info(c.id_account)?;
let seed = seed.ok_or_else(|| anyhow!("Account has no seed"))?;
let index = index.unwrap_or_else(|| db.next_account_id(&seed).unwrap());
drop(db);
@ -61,7 +62,7 @@ fn new_account_with_key(coin: u8, name: &str, key: &str, index: u32) -> anyhow::
pub fn import_transparent_key(coin: u8, id_account: u32, path: &str) -> anyhow::Result<()> {
let c = CoinConfig::get(coin);
let db = c.db()?;
let (seed, _) = db.get_seed(c.id_account)?;
let AccountData { seed, .. } = db.get_account_info(c.id_account)?;
let seed = seed.ok_or_else(|| anyhow!("Account has no seed"))?;
let (sk, addr) = derive_tkeys(c.chain.network(), &seed, path)?;
db.store_transparent_key(id_account, &sk, &addr)?;
@ -79,10 +80,10 @@ pub fn import_transparent_secret_key(coin: u8, id_account: u32, sk: &str) -> any
pub fn new_diversified_address() -> anyhow::Result<String> {
let c = CoinConfig::get_active();
let db = c.db()?;
let ivk = db.get_ivk(c.id_account)?;
let AccountData { fvk, .. } = db.get_account_info(c.id_account)?;
let fvk = decode_extended_full_viewing_key(
c.chain.network().hrp_sapling_extended_full_viewing_key(),
&ivk,
&fvk,
)?
.unwrap();
let mut diversifier_index = db.get_diversifier(c.id_account)?;
@ -122,20 +123,20 @@ pub async fn scan_transparent_accounts(gap_limit: usize) -> anyhow::Result<()> {
pub fn get_backup(account: u32) -> anyhow::Result<String> {
let c = CoinConfig::get_active();
let (seed, sk, ivk) = c.db()?.get_backup(account)?;
let AccountData { seed, sk, fvk, .. } = c.db()?.get_account_info(account)?;
if let Some(seed) = seed {
return Ok(seed);
}
if let Some(sk) = sk {
return Ok(sk);
}
Ok(ivk)
Ok(fvk)
}
pub fn get_sk(account: u32) -> anyhow::Result<String> {
let c = CoinConfig::get_active();
let sk = c.db()?.get_sk(account)?;
Ok(sk)
let AccountData { sk, .. } = c.db()?.get_account_info(account)?;
Ok(sk.unwrap_or(String::new()))
}
pub fn reset_db(coin: u8) -> anyhow::Result<()> {
@ -184,7 +185,7 @@ pub fn derive_keys(
) -> anyhow::Result<KeyPack> {
let c = CoinConfig::get(coin);
let db = c.db()?;
let (seed, _) = db.get_seed(id_account)?;
let AccountData { seed, .. } = db.get_account_info(id_account)?;
let seed = seed.unwrap();
derive_zip32(c.chain.network(), &seed, account, external, address)
}

View File

@ -2,6 +2,7 @@ use crate::api::payment::{build_sign_send_multi_payment, RecipientMemo};
use crate::api::sync::get_latest_height;
use crate::coinconfig::CoinConfig;
use crate::contact::{serialize_contacts, Contact};
use crate::db::AccountData;
use zcash_primitives::memo::Memo;
pub fn store_contact(id: u32, name: &str, address: &str, dirty: bool) -> anyhow::Result<()> {
@ -26,7 +27,7 @@ pub async fn commit_unsaved_contacts(anchor_offset: u32) -> anyhow::Result<Strin
pub async fn save_contacts_tx(memos: &[Memo], anchor_offset: u32) -> anyhow::Result<String> {
let c = CoinConfig::get_active();
let last_height = get_latest_height().await?;
let address = c.db()?.get_address(c.id_account)?;
let AccountData { address, .. } = c.db()?.get_account_info(c.id_account)?;
let recipients: Vec<_> = memos
.iter()
.map(|m| RecipientMemo {

View File

@ -534,7 +534,7 @@ pub unsafe extern "C" fn parse_payment_uri(uri: *mut c_char) -> *mut c_char {
#[no_mangle]
pub unsafe extern "C" fn generate_random_enc_key() -> *mut c_char {
to_c_str(log_string(crate::key2::generate_random_enc_key()))
to_c_str(log_string(crate::key::generate_random_enc_key()))
}
#[no_mangle]

View File

@ -2,11 +2,12 @@ use zcash_client_backend::encoding::decode_extended_full_viewing_key;
use zcash_primitives::consensus::Parameters;
use crate::coinconfig::CoinConfig;
use crate::db::AccountData;
use crate::get_latest_height;
pub async fn scan() -> anyhow::Result<i64> {
let c = CoinConfig::get_active();
let ivk = c.db()?.get_ivk(c.id_account)?;
let AccountData { fvk, .. } = c.db()?.get_account_info(c.id_account)?;
let mut client = c.connect_lwd().await?;
let height = get_latest_height(&mut client).await?;
let mut mempool = c.mempool.lock().unwrap();
@ -17,7 +18,7 @@ pub async fn scan() -> anyhow::Result<i64> {
}
let fvk = decode_extended_full_viewing_key(
c.chain.network().hrp_sapling_extended_full_viewing_key(),
&ivk,
&fvk,
)?
.unwrap();
mempool

View File

@ -1,3 +1,4 @@
use anyhow::anyhow;
use std::str::FromStr;
use secp256k1::SecretKey;
@ -12,7 +13,7 @@ use zcash_client_backend::encoding::{
use zcash_primitives::consensus::Parameters;
use zcash_primitives::transaction::builder::Progress;
use crate::db::ZMessage;
use crate::db::{AccountData, ZMessage};
use crate::taddr::get_utxos;
use serde::Deserialize;
use zcash_primitives::memo::Memo;
@ -29,7 +30,7 @@ async fn prepare_multi_payment(
let c = CoinConfig::get_active();
let mut tx_builder = TxBuilder::new(c.coin_type, last_height);
let fvk = c.db()?.get_ivk(c.id_account)?;
let AccountData { fvk, .. } = c.db()?.get_account_info(c.id_account)?;
let fvk = decode_extended_full_viewing_key(
c.chain.network().hrp_sapling_extended_full_viewing_key(),
&fvk,
@ -62,7 +63,8 @@ fn sign(tx: &Tx, progress_callback: PaymentProgressCallback) -> anyhow::Result<V
let c = CoinConfig::get_active();
let prover = get_prover();
let db = c.db()?;
let zsk = db.get_sk(c.id_account)?;
let AccountData { sk: zsk, .. } = db.get_account_info(c.id_account)?;
let zsk = zsk.ok_or(anyhow!("Cannot sign without secret key"))?;
let tsk = db
.get_tsk(c.id_account)?
.map(|tsk| SecretKey::from_str(&tsk).unwrap());
@ -122,7 +124,7 @@ pub async fn shield_taddr() -> anyhow::Result<String> {
pub fn parse_recipients(recipients: &str) -> anyhow::Result<Vec<RecipientMemo>> {
let c = CoinConfig::get_active();
let address = c.db()?.get_address(c.id_account)?;
let AccountData { address, .. } = c.db()?.get_account_info(c.id_account)?;
let recipients: Vec<Recipient> = serde_json::from_str(recipients)?;
let recipient_memos: Vec<_> = recipients
.iter()

View File

@ -2,11 +2,13 @@
use crate::coinconfig::CoinConfig;
use crate::scan::AMProgressCallback;
use crate::{BlockId, CTree, CompactTxStreamerClient, DbAdapter};
use crate::{BlockId, CTree, CompactTxStreamerClient, DbAdapter, AccountData};
use std::sync::Arc;
use tokio::sync::Mutex;
use tonic::transport::Channel;
use tonic::Request;
use zcash_primitives::sapling::Note;
use crate::db::PlainNote;
const DEFAULT_CHUNK_SIZE: u32 = 100_000;
@ -90,7 +92,6 @@ pub async fn skip_to_last_height(coin: u8) -> anyhow::Result<()> {
pub async fn rewind_to_height(height: u32) -> anyhow::Result<u32> {
let c = CoinConfig::get_active();
let mut client = c.connect_lwd().await?;
let height = c.db()?.trim_to_height(height, false)?;
Ok(height)
}
@ -129,3 +130,10 @@ pub async fn get_block_by_time(time: u32) -> anyhow::Result<u32> {
let date_time = crate::chain::get_block_by_time(c.chain.network(), &mut client, time).await?;
Ok(date_time)
}
pub fn trial_decrypt(height: u32, cmu: &[u8], epk: &[u8], ciphertext: &[u8]) -> anyhow::Result<Option<Note>> {
let c = CoinConfig::get_active();
let AccountData { fvk, .. } = c.db().unwrap().get_account_info(c.id_account)?;
let note = crate::scan::trial_decrypt_one(c.chain.network(), height, &fvk, cmu, epk, ciphertext)?;
Ok(note)
}

135
src/db.rs
View File

@ -214,7 +214,7 @@ impl DbAdapter {
.query_row(
"SELECT 1 from blocks WHERE height = ?1",
params![height],
|row| Ok(()),
|_| Ok(()),
)
.map_err(wrap_query_no_rows("trim_to_height: height not found"))?;
height
@ -644,97 +644,6 @@ impl DbAdapter {
Ok(contacts)
}
pub fn get_backup(
&self,
account: u32,
) -> anyhow::Result<(Option<String>, Option<String>, String)> {
log::debug!("+get_backup");
let (seed, sk, ivk) = self
.connection
.query_row(
"SELECT seed, sk, ivk FROM accounts WHERE id_account = ?1",
params![account],
|row| {
let seed: Option<String> = row.get(0)?;
let sk: Option<String> = row.get(1)?;
let ivk: String = row.get(2)?;
Ok((seed, sk, ivk))
},
)
.map_err(wrap_query_no_rows("get_backup"))?;
log::debug!("-get_backup");
Ok((seed, sk, ivk))
}
pub fn get_seed(&self, account: u32) -> anyhow::Result<(Option<String>, u32)> {
log::info!("+get_seed");
let (seed, index) = self
.connection
.query_row(
"SELECT seed, aindex FROM accounts WHERE id_account = ?1",
params![account],
|row| {
let sk: Option<String> = row.get(0)?;
let index: u32 = row.get(1)?;
Ok((sk, index))
},
)
.map_err(wrap_query_no_rows("get_seed"))?;
log::info!("-get_seed");
Ok((seed, index))
}
pub fn get_sk(&self, account: u32) -> anyhow::Result<String> {
log::info!("+get_sk");
let sk = self
.connection
.query_row(
"SELECT sk FROM accounts WHERE id_account = ?1",
params![account],
|row| {
let sk: String = row.get(0)?;
Ok(sk)
},
)
.map_err(wrap_query_no_rows("get_sk"))?;
log::info!("-get_sk");
Ok(sk)
}
pub fn get_ivk(&self, account: u32) -> anyhow::Result<String> {
log::debug!("+get_ivk");
let ivk = self
.connection
.query_row(
"SELECT ivk FROM accounts WHERE id_account = ?1",
params![account],
|row| {
let ivk: String = row.get(0)?;
Ok(ivk)
},
)
.map_err(wrap_query_no_rows("get_ivk"))?;
log::debug!("-get_ivk");
Ok(ivk)
}
pub fn get_address(&self, account: u32) -> anyhow::Result<String> {
log::debug!("+get_address");
let address = self
.connection
.query_row(
"SELECT address FROM accounts WHERE id_account = ?1",
params![account],
|row| {
let address: String = row.get(0)?;
Ok(address)
},
)
.map_err(wrap_query_no_rows("get_address"))?;
log::debug!("-get_address");
Ok(address)
}
pub fn get_diversifier(&self, account: u32) -> anyhow::Result<DiversifierIndex> {
let diversifier_index = self
.connection
@ -753,6 +662,33 @@ impl DbAdapter {
Ok(DiversifierIndex(diversifier_index))
}
pub fn get_account_info(&self, account: u32) -> anyhow::Result<AccountData> {
let account_data = self
.connection
.query_row(
"SELECT name, seed, sk, ivk, address, aindex FROM accounts WHERE id_account = ?1",
params![account],
|row| {
let name: String = row.get(0)?;
let seed: Option<String> = row.get(1)?;
let sk: Option<String> = row.get(2)?;
let fvk: String = row.get(3)?;
let address: String = row.get(4)?;
let aindex: u32 = row.get(5)?;
Ok(AccountData {
name,
seed,
sk,
fvk,
address,
aindex,
})
},
)
.map_err(wrap_query_no_rows("get_account_info"))?;
Ok(account_data)
}
pub fn store_diversifier(
&self,
account: u32,
@ -798,9 +734,9 @@ impl DbAdapter {
}
pub fn create_taddr(&self, account: u32) -> anyhow::Result<()> {
let (seed, index) = self.get_seed(account)?;
let AccountData { seed, aindex, .. } = self.get_account_info(account)?;
if let Some(seed) = seed {
let bip44_path = format!("m/44'/{}'/0'/0/{}", self.network().coin_type(), index);
let bip44_path = format!("m/44'/{}'/0'/0/{}", self.network().coin_type(), aindex);
let (sk, address) = derive_tkeys(self.network(), &seed, &bip44_path)?;
self.connection.execute(
"INSERT INTO taddrs(account, sk, address) VALUES (?1, ?2, ?3) \
@ -1181,7 +1117,7 @@ pub struct AccountRec {
}
#[serde_as]
#[derive(Clone, Serialize, Deserialize)]
#[derive(Clone, Serialize, Deserialize, Debug)]
pub struct PlainNote {
pub height: u32,
pub value: u64,
@ -1273,3 +1209,12 @@ mod tests {
println!("{}", balance);
}
}
pub struct AccountData {
pub name: String,
pub seed: Option<String>,
pub sk: Option<String>,
pub fvk: String,
pub address: String,
pub aindex: u32,
}

View File

@ -1,3 +1,4 @@
use std::convert::TryInto;
use crate::chain::{DecryptedBlock, DecryptedNote, Nf};
use crate::db::AccountViewKey;
use crate::CompactBlock;
@ -119,16 +120,16 @@ fn collect_decrypted_notes(
for db in decrypted_blocks {
let b = &db.compact_block;
let mut decrypted_notes = vec![];
let mut position_in_block = 0;
let domain = SaplingDomain::for_height(*network, BlockHeight::from_u32(b.height as u32));
for (tx_index, tx) in b.vtx.iter().enumerate() {
for (output_index, co) in tx.outputs.iter().enumerate() {
let plaintext = &output_buffer[i * buffer_stride + 64..i * buffer_stride + 116];
let plaintext = &output_buffer[i * buffer_stride + 32..i * buffer_stride + 84];
// version and amount must be in range - 21 million ZEC is less than 0x0008 0000 0000 0000
if plaintext[0] <= 2 && plaintext[18] < 0x08 && plaintext[19] == 0 {
if let Some((note, pa)) =
domain.parse_note_plaintext_without_memo_ivk(&ivk, plaintext)
{
let position_in_block = usize::from_le_bytes(plaintext[52..60].try_into().unwrap());
let cmu = note.cmu().to_bytes();
if &cmu == co.cmu.as_slice() {
log::info!("Note {} {}", account, u64::from(note.value));
@ -148,7 +149,6 @@ fn collect_decrypted_notes(
}
}
i += 1;
position_in_block += 1;
}
}
db.notes.extend(decrypted_notes);

View File

@ -16,7 +16,7 @@ use zcash_primitives::consensus::Network;
use zcash_primitives::sapling::SaplingIvk;
const THREADS_PER_BLOCK: usize = 256usize;
const BUFFER_SIZE: usize = 128usize;
const BUFFER_SIZE: usize = 96usize;
lazy_static! {
pub static ref CUDA_CONTEXT: Mutex<Option<CudaContext>> = Mutex::new(CudaContext::new().ok());
@ -159,15 +159,20 @@ impl CudaProcessor {
let decrypted_blocks = collect_nf(blocks)?;
let mut data_buffer = vec![0u8; n * BUFFER_SIZE];
let mut i = 0;
for db in decrypted_blocks.iter() {
let mut i = 0;
let mut position_in_block = 0;
let b = &db.compact_block;
for tx in b.vtx.iter() {
for co in tx.outputs.iter() {
if co.epk.is_empty() { break } // skip decryption
data_buffer[i * BUFFER_SIZE..i * BUFFER_SIZE + 32].copy_from_slice(&co.epk);
data_buffer[i * BUFFER_SIZE + 64..i * BUFFER_SIZE + 116]
data_buffer[i * BUFFER_SIZE + 32..i * BUFFER_SIZE + 84]
.copy_from_slice(&co.ciphertext);
data_buffer[i * BUFFER_SIZE + 84..i * BUFFER_SIZE + 92]
.copy_from_slice(&usize::to_le_bytes(position_in_block));
i += 1;
position_in_block += 1;
}
}
}

View File

@ -1,8 +1,5 @@
use crate::coinconfig::CoinConfig;
use bech32::{ToBase32, Variant};
use bip39::{Language, Mnemonic, Seed};
use rand::rngs::OsRng;
use rand::RngCore;
use zcash_client_backend::address::RecipientAddress;
use zcash_client_backend::encoding::{
decode_extended_full_viewing_key, decode_extended_spending_key,
@ -98,10 +95,3 @@ fn derive_address(network: &Network, fvk: &ExtendedFullViewingKey) -> anyhow::Re
let address = encode_payment_address(network.hrp_sapling_payment_address(), &payment_address);
Ok(address)
}
pub fn generate_random_enc_key() -> anyhow::Result<String> {
let mut key = [0u8; 32];
OsRng.fill_bytes(&mut key);
let key = bech32::encode("zwk", key.to_base32(), Variant::Bech32)?;
Ok(key)
}

View File

@ -71,7 +71,7 @@ pub use crate::coinconfig::{
init_coin, set_active, set_active_account, set_coin_lwd_url, CoinConfig,
};
pub use crate::commitment::{CTree, Witness};
pub use crate::db::{AccountInfo, AccountRec, DbAdapter, TxRec};
pub use crate::db::{AccountInfo, AccountRec, AccountData, DbAdapter, TxRec};
pub use crate::fountain::{put_drop, FountainCodes, RaptorQDrops};
pub use crate::hash::{pedersen_hash, Hash, GENERATORS_EXP};
pub use crate::key::{generate_random_enc_key, KeyHelpers};

View File

@ -15,10 +15,7 @@ use std::sync::Mutex;
use thiserror::Error;
use warp_api_ffi::api::payment::{Recipient, RecipientMemo};
use warp_api_ffi::api::payment_uri::PaymentURI;
use warp_api_ffi::{
derive_zip32, get_best_server, AccountInfo, AccountRec, CoinConfig, KeyPack, RaptorQDrops, Tx,
TxRec,
};
use warp_api_ffi::{derive_zip32, get_best_server, AccountInfo, AccountRec, CoinConfig, KeyPack, RaptorQDrops, Tx, TxRec, AccountData};
lazy_static! {
static ref SYNC_CANCELED: Mutex<bool> = Mutex::new(false);
@ -26,6 +23,8 @@ lazy_static! {
#[derive(Error, Debug)]
pub enum Error {
#[error(transparent)]
Hex(#[from] hex::FromHexError),
#[error(transparent)]
Reqwest(#[from] reqwest::Error),
#[error(transparent)]
@ -69,6 +68,9 @@ async fn main() -> anyhow::Result<()> {
let yec: HashMap<String, String> = figment.extract_inner("yec")?;
init(1, yec)?;
warp_api_ffi::set_active_account(0, 1);
warp_api_ffi::set_active(0);
let _ = rocket
.mount(
"/",
@ -95,6 +97,7 @@ async fn main() -> anyhow::Result<()> {
merge_data,
derive_keys,
instant_sync,
trial_decrypt,
],
)
.attach(AdHoc::config::<Config>())
@ -169,7 +172,7 @@ pub async fn get_latest_height() -> Result<Json<Heights>, Error> {
pub fn get_address() -> Result<String, Error> {
let c = CoinConfig::get_active();
let db = c.db()?;
let address = db.get_address(c.id_account)?;
let AccountData { address, .. } = db.get_account_info(c.id_account)?;
Ok(address)
}
@ -180,7 +183,7 @@ pub fn get_backup(config: &State<Config>) -> Result<Json<Backup>, Error> {
} else {
let c = CoinConfig::get_active();
let db = c.db()?;
let (seed, sk, fvk) = db.get_backup(c.id_account)?;
let AccountData { seed, sk, fvk, .. } = db.get_account_info(c.id_account)?;
Ok(Json(Backup { seed, sk, fvk }))
}
}
@ -207,7 +210,8 @@ pub async fn create_offline_tx(payment: Json<Payment>) -> Result<Json<Tx>, Error
let latest = warp_api_ffi::api::sync::get_latest_height().await?;
let from = {
let db = c.db()?;
db.get_address(c.id_account)?
let AccountData { address, .. } = db.get_account_info(c.id_account)?;
address
};
let recipients: Vec<_> = payment
.recipients
@ -244,7 +248,8 @@ pub async fn pay(payment: Json<Payment>, config: &State<Config>) -> Result<Strin
let latest = warp_api_ffi::api::sync::get_latest_height().await?;
let from = {
let db = c.db()?;
db.get_address(c.id_account)?
let AccountData { address, .. } = db.get_account_info(c.id_account)?;
address
};
let recipients: Vec<_> = payment
.recipients
@ -323,12 +328,22 @@ pub fn derive_keys(
Ok(Json(result))
}
#[post("/trial_decrypt?<height>&<cmu>&<epk>&<ciphertext>")]
pub async fn trial_decrypt(height: u32, cmu: String, epk: String, ciphertext: String) -> Result<String, Error> {
let epk = hex::decode(&epk)?;
let cmu = hex::decode(&cmu)?;
let ciphertext = hex::decode(&ciphertext)?;
let note = warp_api_ffi::api::sync::trial_decrypt(height, &cmu, &epk, &ciphertext)?;
log::info!("{:?}", note);
Ok(note.is_some().to_string())
}
#[post("/instant_sync")]
pub async fn instant_sync() -> Result<(), Error> {
let c = CoinConfig::get_active();
let fvk = {
let db = c.db()?;
let (_, _, fvk) = db.get_backup(c.id_account)?;
let AccountData { fvk, .. } = db.get_account_info(c.id_account)?;
fvk
};
let client = reqwest::Client::new();

View File

@ -1,12 +1,10 @@
use crate::builder::BlockProcessor;
use crate::chain::{DecryptedBlock, Nf, NfRef, TRIAL_DECRYPTIONS};
use crate::db::{DbAdapter, ReceivedNote};
use crate::db::{AccountViewKey, DbAdapter, PlainNote, ReceivedNote};
use std::cmp::Ordering;
use crate::transaction::retrieve_tx_info;
use crate::{
connect_lightwalletd, download_chain, get_latest_height, CompactBlock, DecryptNode, Witness,
};
use crate::{connect_lightwalletd, download_chain, get_latest_height, CompactBlock, DecryptNode, Witness, CompactTx, CompactSaplingOutput};
use ff::PrimeField;
use lazy_static::lazy_static;
@ -14,12 +12,15 @@ use std::collections::HashMap;
use std::panic;
use std::sync::Arc;
use std::time::Instant;
use anyhow::anyhow;
use tokio::runtime::{Builder, Runtime};
use tokio::sync::mpsc;
use tokio::sync::Mutex;
use zcash_client_backend::encoding::decode_extended_full_viewing_key;
use zcash_primitives::consensus::{Network, Parameters};
use zcash_params::coin::{get_coin_chain, CoinType};
use zcash_primitives::sapling::Node;
use zcash_primitives::sapling::{Node, Note};
pub struct Blocks(pub Vec<CompactBlock>);
@ -66,7 +67,7 @@ pub async fn sync_async(
let mut client = connect_lightwalletd(&ld_url).await?;
let (start_height, prev_hash, vks) = {
let mut db = DbAdapter::new(coin_type, &db_path)?;
let db = DbAdapter::new(coin_type, &db_path)?;
let height = db.get_db_height()?;
let hash = db.get_db_hash(height)?;
let vks = db.get_fvks()?;
@ -357,3 +358,45 @@ pub async fn latest_height(ld_url: &str) -> anyhow::Result<u32> {
let height = get_latest_height(&mut client).await?;
Ok(height)
}
#[allow(dead_code)]
// test function
pub fn trial_decrypt_one(network: &Network, height: u32, fvk: &str, cmu: &[u8], epk: &[u8], ciphertext: &[u8]) -> anyhow::Result<Option<Note>> {
let mut vks = HashMap::new();
let fvk = decode_extended_full_viewing_key(network.hrp_sapling_extended_full_viewing_key(), &fvk)?.ok_or(anyhow!("Invalid FVK"))?;
let ivk = fvk.fvk.vk.ivk();
vks.insert(0, AccountViewKey {
fvk,
ivk,
viewonly: false
});
let dn = DecryptNode::new(vks);
let block = vec![CompactBlock {
proto_version: 0, // don't care about most of these fields
height: height as u64,
hash: vec![],
prev_hash: vec![],
time: 0,
header: vec![],
vtx: vec![
CompactTx {
index: 0,
hash: vec![],
fee: 0,
spends: vec![],
actions: vec![],
outputs: vec![
CompactSaplingOutput {
cmu: cmu.to_vec(),
epk: epk.to_vec(),
ciphertext: ciphertext.to_vec(),
}
],
}
]
}];
let decrypted_block = dn.decrypt_blocks(network, block);
let decrypted_block = decrypted_block.first().unwrap();
let note = decrypted_block.notes.first().map(|dn| dn.note.clone());
Ok(note)
}

View File

@ -1,4 +1,5 @@
use crate::coinconfig::CoinConfig;
use crate::db::AccountData;
use crate::{AddressList, CompactTxStreamerClient, GetAddressUtxosArg, GetAddressUtxosReply};
use anyhow::anyhow;
use base58check::FromBase58Check;
@ -52,17 +53,20 @@ pub async fn scan_transparent_accounts(
let c = CoinConfig::get_active();
let mut addresses = vec![];
let db = c.db()?;
let (seed, mut index) = db.get_seed(c.id_account)?;
let account_data = db.get_account_info(c.id_account)?;
let AccountData {
seed, mut aindex, ..
} = account_data;
if let Some(seed) = seed {
let mut gap = 0;
while gap < gap_limit {
let bip44_path = format!("m/44'/{}'/0'/0/{}", network.coin_type(), index);
log::info!("{} {}", index, bip44_path);
let bip44_path = format!("m/44'/{}'/0'/0/{}", network.coin_type(), aindex);
log::info!("{} {}", aindex, bip44_path);
let (_, address) = derive_tkeys(network, &seed, &bip44_path)?;
let balance = get_taddr_balance(client, &address).await?;
if balance > 0 {
addresses.push(TBalance {
index,
index: aindex,
address,
balance,
});
@ -70,7 +74,7 @@ pub async fn scan_transparent_accounts(
} else {
gap += 1;
}
index += 1;
aindex += 1;
}
}
db.store_t_scan(&addresses)?;