aboutsummaryrefslogtreecommitdiff
path: root/src/wallet/rpc/encrypt.cpp
diff options
context:
space:
mode:
authorishaanam <ishaana.misra@gmail.com>2022-10-26 16:59:34 -0400
committerishaanam <ishaana.misra@gmail.com>2023-02-14 23:32:40 -0500
commit493b813e171a389a8b6750b4f2e42e8363a0267e (patch)
treefdb409524347f808ec2bfae547c2f07345d75cc4 /src/wallet/rpc/encrypt.cpp
parent66a86ebabb26a055ca92af846bfa39dbd2f9f722 (diff)
downloadbitcoin-493b813e171a389a8b6750b4f2e42e8363a0267e.tar.xz
wallet: ensure that the passphrase is not deleted from memory when being used to rescan
`m_relock_mutex` is introduced so that the passphrase is not deleted from memory when the timeout provided in `walletpassphrase` is up, but the wallet is still rescanning.
Diffstat (limited to 'src/wallet/rpc/encrypt.cpp')
-rw-r--r--src/wallet/rpc/encrypt.cpp14
1 files changed, 7 insertions, 7 deletions
diff --git a/src/wallet/rpc/encrypt.cpp b/src/wallet/rpc/encrypt.cpp
index 8b818cc4f7..38960bda7b 100644
--- a/src/wallet/rpc/encrypt.cpp
+++ b/src/wallet/rpc/encrypt.cpp
@@ -90,7 +90,7 @@ RPCHelpMan walletpassphrase()
std::weak_ptr<CWallet> weak_wallet = wallet;
pwallet->chain().rpcRunLater(strprintf("lockwallet(%s)", pwallet->GetName()), [weak_wallet, relock_time] {
if (auto shared_wallet = weak_wallet.lock()) {
- LOCK(shared_wallet->cs_wallet);
+ LOCK2(shared_wallet->m_relock_mutex, shared_wallet->cs_wallet);
// Skip if this is not the most recent rpcRunLater callback.
if (shared_wallet->nRelockTime != relock_time) return;
shared_wallet->Lock();
@@ -122,8 +122,6 @@ RPCHelpMan walletpassphrasechange()
std::shared_ptr<CWallet> const pwallet = GetWalletForJSONRPCRequest(request);
if (!pwallet) return UniValue::VNULL;
- LOCK(pwallet->cs_wallet);
-
if (!pwallet->IsCrypted()) {
throw JSONRPCError(RPC_WALLET_WRONG_ENC_STATE, "Error: running with an unencrypted wallet, but walletpassphrasechange was called.");
}
@@ -132,6 +130,8 @@ RPCHelpMan walletpassphrasechange()
throw JSONRPCError(RPC_WALLET_ERROR, "Error: the wallet is currently being used to rescan the blockchain for related transactions. Please call `abortrescan` before changing the passphrase.");
}
+ LOCK2(pwallet->m_relock_mutex, pwallet->cs_wallet);
+
// TODO: get rid of these .c_str() calls by implementing SecureString::operator=(std::string)
// Alternately, find a way to make request.params[0] mlock()'d to begin with.
SecureString strOldWalletPass;
@@ -179,8 +179,6 @@ RPCHelpMan walletlock()
std::shared_ptr<CWallet> const pwallet = GetWalletForJSONRPCRequest(request);
if (!pwallet) return UniValue::VNULL;
- LOCK(pwallet->cs_wallet);
-
if (!pwallet->IsCrypted()) {
throw JSONRPCError(RPC_WALLET_WRONG_ENC_STATE, "Error: running with an unencrypted wallet, but walletlock was called.");
}
@@ -189,6 +187,8 @@ RPCHelpMan walletlock()
throw JSONRPCError(RPC_WALLET_ERROR, "Error: the wallet is currently being used to rescan the blockchain for related transactions. Please call `abortrescan` before locking the wallet.");
}
+ LOCK2(pwallet->m_relock_mutex, pwallet->cs_wallet);
+
pwallet->Lock();
pwallet->nRelockTime = 0;
@@ -227,8 +227,6 @@ RPCHelpMan encryptwallet()
std::shared_ptr<CWallet> const pwallet = GetWalletForJSONRPCRequest(request);
if (!pwallet) return UniValue::VNULL;
- LOCK(pwallet->cs_wallet);
-
if (pwallet->IsWalletFlagSet(WALLET_FLAG_DISABLE_PRIVATE_KEYS)) {
throw JSONRPCError(RPC_WALLET_ENCRYPTION_FAILED, "Error: wallet does not contain private keys, nothing to encrypt.");
}
@@ -241,6 +239,8 @@ RPCHelpMan encryptwallet()
throw JSONRPCError(RPC_WALLET_ERROR, "Error: the wallet is currently being used to rescan the blockchain for related transactions. Please call `abortrescan` before encrypting the wallet.");
}
+ LOCK2(pwallet->m_relock_mutex, pwallet->cs_wallet);
+
// TODO: get rid of this .c_str() by implementing SecureString::operator=(std::string)
// Alternately, find a way to make request.params[0] mlock()'d to begin with.
SecureString strWalletPass;