Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

sync: fresh and existing wallets skip trial decryption #1707

Merged
merged 10 commits into from
Sep 3, 2024
Merged
Show file tree
Hide file tree
Changes from 6 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 18 additions & 4 deletions packages/query/src/block-processor.ts
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ interface QueryClientProps {
numeraires: AssetId[];
stakingAssetId: AssetId;
genesisBlock: CompactBlock | undefined;
walletCreationBlockHeight: number;
}

const BLANK_TX_SOURCE = new CommitmentSource({
Expand All @@ -92,6 +93,7 @@ export class BlockProcessor implements BlockProcessorInterface {
private readonly stakingAssetId: AssetId;
private syncPromise: Promise<void> | undefined;
private genesisBlock: CompactBlock | undefined;
private walletCreationBlockHeight: number;
grod220 marked this conversation as resolved.
Show resolved Hide resolved

constructor({
indexedDb,
Expand All @@ -100,13 +102,15 @@ export class BlockProcessor implements BlockProcessorInterface {
numeraires,
stakingAssetId,
genesisBlock,
walletCreationBlockHeight,
}: QueryClientProps) {
this.indexedDb = indexedDb;
this.viewServer = viewServer;
this.querier = querier;
this.numeraires = numeraires;
this.stakingAssetId = stakingAssetId;
this.genesisBlock = genesisBlock;
this.walletCreationBlockHeight = walletCreationBlockHeight;
}

// If sync() is called multiple times concurrently, they'll all wait for
Expand Down Expand Up @@ -171,7 +175,7 @@ export class BlockProcessor implements BlockProcessorInterface {
// begin the chain with local genesis block if provided
if (this.genesisBlock?.height === currentHeight + 1n) {
currentHeight = this.genesisBlock.height;
await this.processBlock(this.genesisBlock, latestKnownBlockHeight);
await this.processBlock(this.genesisBlock, latestKnownBlockHeight, false);
}
}

Expand All @@ -189,7 +193,12 @@ export class BlockProcessor implements BlockProcessorInterface {
throw new Error(`Unexpected block height: ${compactBlock.height} at ${currentHeight}`);
}

await this.processBlock(compactBlock, latestKnownBlockHeight);
// Set the skip_trial_decrypt flag
const skipTrialDecrypt = Boolean(
this.walletCreationBlockHeight && currentHeight < BigInt(this.walletCreationBlockHeight),
grod220 marked this conversation as resolved.
Show resolved Hide resolved
);

await this.processBlock(compactBlock, latestKnownBlockHeight, skipTrialDecrypt);

// We only query Tendermint for the latest known block height once, when
// the block processor starts running. Once we're caught up, though, the
Expand All @@ -203,7 +212,11 @@ export class BlockProcessor implements BlockProcessorInterface {
}

// logic for processing a compact block
private async processBlock(compactBlock: CompactBlock, latestKnownBlockHeight: bigint) {
private async processBlock(
compactBlock: CompactBlock,
latestKnownBlockHeight: bigint,
skipTrialDecrypt: boolean,
) {
TalDerei marked this conversation as resolved.
Show resolved Hide resolved
if (compactBlock.appParametersUpdated) {
await this.indexedDb.saveAppParams(await this.querier.app.appParams());
}
Expand All @@ -225,11 +238,12 @@ export class BlockProcessor implements BlockProcessorInterface {
}
}

// TODO: add logic for determining when to skip trial decryption
TalDerei marked this conversation as resolved.
Show resolved Hide resolved
// wasm view server scan
// - decrypts new notes
// - decrypts new swaps
// - updates idb with advice
const scannerWantsFlush = await this.viewServer.scanBlock(compactBlock);
const scannerWantsFlush = await this.viewServer.scanBlock(compactBlock, skipTrialDecrypt);

// flushing is slow, avoid it until
// - wasm says
Expand Down
2 changes: 1 addition & 1 deletion packages/types/src/block-processor.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { AssetId } from '@penumbra-zone/protobuf/penumbra/core/asset/v1/asset_pb';

export interface BlockProcessorInterface {
sync(): Promise<void>;
sync(isFreshWallet?: boolean, walletCreationBlockHeight?: number): Promise<void>;
TalDerei marked this conversation as resolved.
Show resolved Hide resolved
stop(r?: string): void;
setNumeraires(numeraires: AssetId[]): void;
}
2 changes: 1 addition & 1 deletion packages/types/src/servers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { CompactBlock } from '@penumbra-zone/protobuf/penumbra/core/component/co
import { MerkleRoot } from '@penumbra-zone/protobuf/penumbra/crypto/tct/v1/tct_pb';

export interface ViewServerInterface {
scanBlock(compactBlock: CompactBlock): Promise<boolean>;
scanBlock(compactBlock: CompactBlock, skipTrialDecrypt: boolean): Promise<boolean>;
flushUpdates(): ScanBlockResult;
resetTreeToStored(): Promise<void>;
getSctRoot(): MerkleRoot;
Expand Down
14 changes: 11 additions & 3 deletions packages/wasm/crate/src/view_server.rs
grod220 marked this conversation as resolved.
Show resolved Hide resolved
Original file line number Diff line number Diff line change
Expand Up @@ -113,7 +113,11 @@ impl ViewServer {
/// Use `flush_updates()` to get the scan results
/// Returns: `bool`
#[wasm_bindgen]
pub async fn scan_block(&mut self, compact_block: &[u8]) -> WasmResult<bool> {
pub async fn scan_block(
&mut self,
compact_block: &[u8],
skip_trial_decrypt: bool,
) -> WasmResult<bool> {
grod220 marked this conversation as resolved.
Show resolved Hide resolved
utils::set_panic_hook();

let block = CompactBlock::decode(compact_block)?;
Expand All @@ -125,7 +129,9 @@ impl ViewServer {

match state_payload {
StatePayload::Note { note: payload, .. } => {
match payload.trial_decrypt(&self.fvk) {
match bool::then_some(!skip_trial_decrypt, payload.trial_decrypt(&self.fvk))
TalDerei marked this conversation as resolved.
Show resolved Hide resolved
.flatten()
{
Some(note) => {
let note_position = self.sct.insert(Keep, payload.note_commitment)?;

Expand Down Expand Up @@ -161,7 +167,9 @@ impl ViewServer {
}
}
StatePayload::Swap { swap: payload, .. } => {
match payload.trial_decrypt(&self.fvk) {
match bool::then_some(!skip_trial_decrypt, payload.trial_decrypt(&self.fvk))
.flatten()
{
Some(swap) => {
let swap_position = self.sct.insert(Keep, payload.commitment)?;
let batch_data =
Expand Down
4 changes: 2 additions & 2 deletions packages/wasm/src/view-server.ts
Original file line number Diff line number Diff line change
Expand Up @@ -58,9 +58,9 @@ export class ViewServer implements ViewServerInterface {
// Decrypts blocks with viewing key for notes, swaps, and updates revealed for user
// Makes update to internal state-commitment-tree as a side effect.
// Should extract updates via this.flushUpdates().
async scanBlock(compactBlock: CompactBlock): Promise<boolean> {
async scanBlock(compactBlock: CompactBlock, skipTrialDecrypt: boolean): Promise<boolean> {
const res = compactBlock.toBinary();
return this.wasmViewServer.scan_block(res);
return this.wasmViewServer.scan_block(res, skipTrialDecrypt);
}

// Resets the state of the wasmViewServer to the one set in storage
Expand Down
Loading