From 458777c5a2e66187cc3a8ac3e4a7557114886a4e Mon Sep 17 00:00:00 2001 From: Florian Dold Date: Wed, 6 Jan 2021 17:06:19 +0100 Subject: [PATCH] fix tipping planchet derivation --- .../src/crypto/talerCrypto.ts | 4 --- .../crypto/workers/cryptoImplementation.ts | 6 ++--- .../taler-wallet-core/src/operations/tip.ts | 27 ++++++++++++------- 3 files changed, 19 insertions(+), 18 deletions(-) diff --git a/packages/taler-wallet-core/src/crypto/talerCrypto.ts b/packages/taler-wallet-core/src/crypto/talerCrypto.ts index d28f11174..381896858 100644 --- a/packages/taler-wallet-core/src/crypto/talerCrypto.ts +++ b/packages/taler-wallet-core/src/crypto/talerCrypto.ts @@ -340,10 +340,6 @@ export function createEcdheKeyPair(): EcdheKeyPair { return { ecdhePriv, ecdhePub }; } -export function createBlindingKeySecret(): Uint8Array { - return nacl.randomBytes(32); -} - export function hash(d: Uint8Array): Uint8Array { return nacl.hash(d); } diff --git a/packages/taler-wallet-core/src/crypto/workers/cryptoImplementation.ts b/packages/taler-wallet-core/src/crypto/workers/cryptoImplementation.ts index fc8b53eb7..9b703e2c8 100644 --- a/packages/taler-wallet-core/src/crypto/workers/cryptoImplementation.ts +++ b/packages/taler-wallet-core/src/crypto/workers/cryptoImplementation.ts @@ -48,7 +48,6 @@ import { encodeCrock, decodeCrock, createEddsaKeyPair, - createBlindingKeySecret, hash, rsaBlind, eddsaVerify, @@ -199,12 +198,11 @@ export class CryptoImplementation { createTipPlanchet(req: DeriveTipRequest): DerivedTipPlanchet { const fc = setupTipPlanchet(decodeCrock(req.secretSeed), req.planchetIndex); const denomPub = decodeCrock(req.denomPub); - const blindingFactor = createBlindingKeySecret(); const coinPubHash = hash(fc.coinPub); - const ev = rsaBlind(coinPubHash, blindingFactor, denomPub); + const ev = rsaBlind(coinPubHash, fc.bks, denomPub); const tipPlanchet: DerivedTipPlanchet = { - blindingKey: encodeCrock(blindingFactor), + blindingKey: encodeCrock(fc.bks), coinEv: encodeCrock(ev), coinEvHash: encodeCrock(hash(ev)), coinPriv: encodeCrock(fc.coinPriv), diff --git a/packages/taler-wallet-core/src/operations/tip.ts b/packages/taler-wallet-core/src/operations/tip.ts index f683999bc..68b5a2ad0 100644 --- a/packages/taler-wallet-core/src/operations/tip.ts +++ b/packages/taler-wallet-core/src/operations/tip.ts @@ -52,7 +52,7 @@ import { checkDbInvariant, checkLogicInvariant } from "../util/invariants"; import { TalerErrorCode } from "../TalerErrorCode"; import { initRetryInfo, updateRetryInfoTimeout } from "../util/retries"; import { j2s } from "../util/helpers"; -import { DerivedTipPlanchet } from '../types/cryptoTypes'; +import { DerivedTipPlanchet } from "../types/cryptoTypes"; const logger = new Logger("operations/tip.ts"); @@ -95,11 +95,11 @@ export async function prepareTip( const walletTipId = encodeCrock(getRandomBytes(32)); await updateWithdrawalDenoms(ws, tipPickupStatus.exchange_url); - const denoms = await getPossibleWithdrawalDenoms(ws, tipPickupStatus.exchange_url); - const selectedDenoms = await selectWithdrawalDenominations( - amount, - denoms + const denoms = await getPossibleWithdrawalDenoms( + ws, + tipPickupStatus.exchange_url, ); + const selectedDenoms = selectWithdrawalDenominations(amount, denoms); const secretSeed = encodeCrock(getRandomBytes(64)); @@ -213,7 +213,7 @@ async function processTipImpl( const planchets: DerivedTipPlanchet[] = []; // Planchets in the form that the merchant expects const planchetsDetail: TipPlanchetDetail[] = []; - const denomForPlanchet: { [index: number]: DenominationRecord} = []; + const denomForPlanchet: { [index: number]: DenominationRecord } = []; for (const dh of denomsForWithdraw.selectedDenoms) { const denom = await ws.db.get(Stores.denominations, [ @@ -222,11 +222,14 @@ async function processTipImpl( ]); checkDbInvariant(!!denom, "denomination should be in database"); for (let i = 0; i < dh.count; i++) { - const p = await ws.cryptoApi.createTipPlanchet({ + const deriveReq = { denomPub: denom.denomPub, planchetIndex: planchets.length, secretSeed: tipRecord.secretSeed, - }); + }; + logger.trace(`deriving tip planchet: ${j2s(deriveReq)}`) + const p = await ws.cryptoApi.createTipPlanchet(deriveReq); + logger.trace(`derive result: ${j2s(p)}`); denomForPlanchet[planchets.length] = denom; planchets.push(p); planchetsDetail.push({ @@ -242,14 +245,18 @@ async function processTipImpl( ); const req = { planchets: planchetsDetail }; + logger.trace(`sending tip request: ${j2s(req)}`); const merchantResp = await ws.http.postJson(tipStatusUrl.href, req); + logger.trace(`got tip response, status ${merchantResp.status}`); + // Hide transient errors. if ( tipRecord.retryInfo.retryCounter < 5 && - merchantResp.status >= 500 && - merchantResp.status <= 599 + ((merchantResp.status >= 500 && merchantResp.status <= 599) || + merchantResp.status === 424) ) { + logger.trace(`got transient tip error`); const err = makeErrorDetails( TalerErrorCode.WALLET_UNEXPECTED_REQUEST_ERROR, "tip pickup failed (transient)",