Skip to content

Commit 8b53abe

Browse files
committed
minor improvements
1 parent ad0209a commit 8b53abe

1 file changed

Lines changed: 47 additions & 22 deletions

File tree

src/screens/Home/Home.tsx

Lines changed: 47 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -364,22 +364,26 @@ function Home({ navigation }: Props) {
364364
'[Vault Signing] Received request for chain:',
365365
socketVaultSigningRequest.chain,
366366
);
367-
// Defensively parse fields that may arrive as JSON strings
368-
// (matching the refresh/action path parsing at handleRefresh)
369-
const data = { ...socketVaultSigningRequest };
370-
if (typeof data.recipients === 'string') {
371-
data.recipients = JSON.parse(data.recipients);
372-
}
373-
if (typeof data.inputDetails === 'string') {
374-
data.inputDetails = JSON.parse(data.inputDetails);
375-
}
376-
if (typeof data.allSignerKeys === 'string') {
377-
data.allSignerKeys = JSON.parse(data.allSignerKeys);
378-
}
379-
if (typeof data.allSignerNonces === 'string') {
380-
data.allSignerNonces = JSON.parse(data.allSignerNonces);
367+
try {
368+
// Defensively parse fields that may arrive as JSON strings
369+
// (matching the refresh/action path parsing at handleRefresh)
370+
const data = { ...socketVaultSigningRequest };
371+
if (typeof data.recipients === 'string') {
372+
data.recipients = JSON.parse(data.recipients);
373+
}
374+
if (typeof data.inputDetails === 'string') {
375+
data.inputDetails = JSON.parse(data.inputDetails);
376+
}
377+
if (typeof data.allSignerKeys === 'string') {
378+
data.allSignerKeys = JSON.parse(data.allSignerKeys);
379+
}
380+
if (typeof data.allSignerNonces === 'string') {
381+
data.allSignerNonces = JSON.parse(data.allSignerNonces);
382+
}
383+
setVaultSigningData(data);
384+
} catch {
385+
displayMessage('error', t('home:err_invalid_request'), 5000);
381386
}
382-
setVaultSigningData(data);
383387
}
384388
}, [socketVaultSigningRequest]);
385389

@@ -1247,6 +1251,8 @@ function Home({ navigation }: Props) {
12471251
});
12481252
}
12491253
};
1254+
const nonceReplenishInProgressRef = useRef(false);
1255+
12501256
/**
12511257
* Check enterprise nonce pool and replenish if below threshold.
12521258
* Generates nonces locally, stores private parts in Keychain,
@@ -1258,6 +1264,8 @@ function Home({ navigation }: Props) {
12581264
replenishNeeded?: boolean,
12591265
) => {
12601266
if (!sspWalletKeyInternalIdentity) return;
1267+
if (nonceReplenishInProgressRef.current) return;
1268+
nonceReplenishInProgressRef.current = true;
12611269
try {
12621270
const TARGET_COUNT = 50;
12631271

@@ -1337,6 +1345,8 @@ function Home({ navigation }: Props) {
13371345
} catch (error) {
13381346
// Non-critical — don't block Key functionality
13391347
console.log('[Enterprise Nonces] Key replenish error:', error);
1348+
} finally {
1349+
nonceReplenishInProgressRef.current = false;
13401350
}
13411351
};
13421352

@@ -1670,6 +1680,11 @@ function Home({ navigation }: Props) {
16701680
const handleVaultXpubAction = async () => {
16711681
if (!vaultXpubData) return;
16721682

1683+
// Hoist sensitive vars outside try so they can be cleared in catch
1684+
let pwForEncryption = '';
1685+
let mnemonicPhrase = '';
1686+
let xprivKeyDecrypted = '';
1687+
16731688
try {
16741689
// Get decryption keys from keychain
16751690
const encryptionKey = await Keychain.getGenericPassword({
@@ -1691,14 +1706,13 @@ function Home({ navigation }: Props) {
16911706
const passwordDecryptedString = passwordDecrypted.toString(
16921707
CryptoJS.enc.Utf8,
16931708
);
1694-
let pwForEncryption = encryptionKey.password + passwordDecryptedString;
1709+
pwForEncryption = encryptionKey.password + passwordDecryptedString;
16951710

16961711
// Decrypt mnemonic seed phrase
16971712
const mmm = CryptoJS.AES.decrypt(seedPhrase, pwForEncryption);
1698-
let mnemonicPhrase = mmm.toString(CryptoJS.enc.Utf8);
1713+
mnemonicPhrase = mmm.toString(CryptoJS.enc.Utf8);
16991714

17001715
if (!mnemonicPhrase) {
1701-
pwForEncryption = '';
17021716
throw new Error('Failed to decrypt mnemonic');
17031717
}
17041718

@@ -1725,7 +1739,7 @@ function Home({ navigation }: Props) {
17251739
throw new Error('xprivKey not available');
17261740
}
17271741
const xprivDecrypted = CryptoJS.AES.decrypt(idXprivKey, pwForEncryption);
1728-
let xprivKeyDecrypted = xprivDecrypted.toString(CryptoJS.enc.Utf8);
1742+
xprivKeyDecrypted = xprivDecrypted.toString(CryptoJS.enc.Utf8);
17291743
if (!xprivKeyDecrypted) {
17301744
throw new Error('Failed to decrypt xprivKey');
17311745
}
@@ -1735,8 +1749,6 @@ function Home({ navigation }: Props) {
17351749
0,
17361750
identityChain,
17371751
);
1738-
// Clear decrypted xpriv — no longer needed
1739-
xprivKeyDecrypted = '';
17401752
const xpubMessage = `SSP_VAULT_XPUB:key:${vaultXpub}:${vaultXpubData.chain}:${String(vaultXpubData.orgIndex)}`;
17411753
const keyXpubSignature = signMessage(
17421754
xpubMessage,
@@ -1746,6 +1758,7 @@ function Home({ navigation }: Props) {
17461758

17471759
// Clear sensitive key material
17481760
identityKeypair.privKey = '';
1761+
xprivKeyDecrypted = '';
17491762
mnemonicPhrase = '';
17501763
pwForEncryption = '';
17511764

@@ -1769,6 +1782,10 @@ function Home({ navigation }: Props) {
17691782

17701783
displayMessage('success', t('home:vault_xpub_success'));
17711784
} catch (error) {
1785+
// Clear sensitive key material on error path
1786+
xprivKeyDecrypted = '';
1787+
mnemonicPhrase = '';
1788+
pwForEncryption = '';
17721789
console.error('[Vault Xpub] Error:', error);
17731790
displayMessage('error', t('home:err_vault_xpub_failed'));
17741791
} finally {
@@ -1807,6 +1824,7 @@ function Home({ navigation }: Props) {
18071824
// Hoist sensitive vars outside try so they can be cleared in catch/finally
18081825
let vaultXpriv = '';
18091826
let pwForEncryption = '';
1827+
let mnemonicPhrase = '';
18101828

18111829
try {
18121830
// Get decryption keys from keychain
@@ -1833,7 +1851,7 @@ function Home({ navigation }: Props) {
18331851

18341852
// Decrypt mnemonic seed phrase
18351853
const mmm = CryptoJS.AES.decrypt(seedPhrase, pwForEncryption);
1836-
let mnemonicPhrase = mmm.toString(CryptoJS.enc.Utf8);
1854+
mnemonicPhrase = mmm.toString(CryptoJS.enc.Utf8);
18371855

18381856
if (!mnemonicPhrase) {
18391857
throw new Error('Failed to decrypt mnemonic');
@@ -1973,6 +1991,9 @@ function Home({ navigation }: Props) {
19731991
vaultSigningData.sigOne,
19741992
);
19751993

1994+
// Clear EVM signing keypair private key
1995+
signingKeypair.privKey = '';
1996+
19761997
// Build response with signerContribution + challenge for wallet to forward
19771998
const responsePayload: Record<string, unknown> = {
19781999
signerContribution: vaultSchnorrResult.signerContribution,
@@ -2079,6 +2100,9 @@ function Home({ navigation }: Props) {
20792100
amount,
20802101
witnessScriptBuf,
20812102
);
2103+
2104+
// Clear per-input private key material
2105+
signingKeypair.privKey = '';
20822106
}
20832107

20842108
// Build with both wallet + key sigs (still incomplete if M>1)
@@ -2111,6 +2135,7 @@ function Home({ navigation }: Props) {
21112135
// Clear sensitive key material on error path
21122136
vaultXpriv = '';
21132137
pwForEncryption = '';
2138+
mnemonicPhrase = '';
21142139
console.error('[Vault Signing] Error:', error);
21152140
displayMessage('error', t('home:err_vault_sign_failed'));
21162141
} finally {

0 commit comments

Comments
 (0)