mirror of
https://github.com/bitcoin/bitcoin.git
synced 2025-11-12 15:09:59 +01:00
Add option to disable private keys during internal wallet creation
This commit is contained in:
@@ -164,6 +164,7 @@ const CWalletTx* CWallet::GetWalletTx(const uint256& hash) const
|
||||
|
||||
CPubKey CWallet::GenerateNewKey(WalletBatch &batch, bool internal)
|
||||
{
|
||||
assert(!IsWalletFlagSet(WALLET_FLAG_DISABLE_PRIVATE_KEYS));
|
||||
AssertLockHeld(cs_wallet); // mapKeyMetadata
|
||||
bool fCompressed = CanSupportFeature(FEATURE_COMPRPUBKEY); // default to compressed public keys if we want 0.6.0 wallets
|
||||
|
||||
@@ -1465,6 +1466,7 @@ CAmount CWallet::GetChange(const CTransaction& tx) const
|
||||
|
||||
CPubKey CWallet::GenerateNewSeed()
|
||||
{
|
||||
assert(!IsWalletFlagSet(WALLET_FLAG_DISABLE_PRIVATE_KEYS));
|
||||
CKey key;
|
||||
key.MakeNewKey(true);
|
||||
return DeriveNewSeed(key);
|
||||
@@ -1539,13 +1541,19 @@ bool CWallet::IsWalletFlagSet(uint64_t flag)
|
||||
return (m_wallet_flags & flag);
|
||||
}
|
||||
|
||||
void CWallet::SetWalletFlags(uint64_t overwriteFlags, bool memonly)
|
||||
bool CWallet::SetWalletFlags(uint64_t overwriteFlags, bool memonly)
|
||||
{
|
||||
LOCK(cs_wallet);
|
||||
m_wallet_flags = overwriteFlags;
|
||||
if (((overwriteFlags & g_known_wallet_flags) >> 32) ^ (overwriteFlags >> 32)) {
|
||||
// contains unknown non-tolerable wallet flags
|
||||
return false;
|
||||
}
|
||||
if (!memonly && !WalletBatch(*database).WriteWalletFlags(m_wallet_flags)) {
|
||||
throw std::runtime_error(std::string(__func__) + ": writing wallet flags failed");
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
int64_t CWalletTx::GetTxTime() const
|
||||
@@ -2793,6 +2801,10 @@ bool CWallet::CreateTransaction(const std::vector<CRecipient>& vecSend, CTransac
|
||||
// post-backup change.
|
||||
|
||||
// Reserve a new key pair from key pool
|
||||
if (IsWalletFlagSet(WALLET_FLAG_DISABLE_PRIVATE_KEYS)) {
|
||||
strFailReason = _("Can't generate a change-address key. Private keys are disabled for this wallet.");
|
||||
return false;
|
||||
}
|
||||
CPubKey vchPubKey;
|
||||
bool ret;
|
||||
ret = reservekey.GetReservedKey(vchPubKey, true);
|
||||
@@ -3193,7 +3205,7 @@ DBErrors CWallet::LoadWallet(bool& fFirstRunRet)
|
||||
{
|
||||
LOCK(cs_KeyStore);
|
||||
// This wallet is in its first run if all of these are empty
|
||||
fFirstRunRet = mapKeys.empty() && mapCryptedKeys.empty() && mapWatchKeys.empty() && setWatchOnly.empty() && mapScripts.empty();
|
||||
fFirstRunRet = mapKeys.empty() && mapCryptedKeys.empty() && mapWatchKeys.empty() && setWatchOnly.empty() && mapScripts.empty() && !IsWalletFlagSet(WALLET_FLAG_DISABLE_PRIVATE_KEYS);
|
||||
}
|
||||
|
||||
if (nLoadWalletRet != DBErrors::LOAD_OK)
|
||||
@@ -3317,6 +3329,9 @@ const std::string& CWallet::GetLabelName(const CScript& scriptPubKey) const
|
||||
*/
|
||||
bool CWallet::NewKeyPool()
|
||||
{
|
||||
if (IsWalletFlagSet(WALLET_FLAG_DISABLE_PRIVATE_KEYS)) {
|
||||
return false;
|
||||
}
|
||||
{
|
||||
LOCK(cs_wallet);
|
||||
WalletBatch batch(*database);
|
||||
@@ -3375,6 +3390,9 @@ void CWallet::LoadKeyPool(int64_t nIndex, const CKeyPool &keypool)
|
||||
|
||||
bool CWallet::TopUpKeyPool(unsigned int kpSize)
|
||||
{
|
||||
if (IsWalletFlagSet(WALLET_FLAG_DISABLE_PRIVATE_KEYS)) {
|
||||
return false;
|
||||
}
|
||||
{
|
||||
LOCK(cs_wallet);
|
||||
|
||||
@@ -3499,6 +3517,10 @@ void CWallet::ReturnKey(int64_t nIndex, bool fInternal, const CPubKey& pubkey)
|
||||
|
||||
bool CWallet::GetKeyFromPool(CPubKey& result, bool internal)
|
||||
{
|
||||
if (IsWalletFlagSet(WALLET_FLAG_DISABLE_PRIVATE_KEYS)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
CKeyPool keypool;
|
||||
{
|
||||
LOCK(cs_wallet);
|
||||
@@ -4038,7 +4060,7 @@ bool CWallet::Verify(std::string wallet_file, bool salvage_wallet, std::string&
|
||||
return WalletBatch::VerifyDatabaseFile(wallet_path, warning_string, error_string);
|
||||
}
|
||||
|
||||
std::shared_ptr<CWallet> CWallet::CreateWalletFromFile(const std::string& name, const fs::path& path)
|
||||
std::shared_ptr<CWallet> CWallet::CreateWalletFromFile(const std::string& name, const fs::path& path, uint64_t wallet_creation_flags)
|
||||
{
|
||||
const std::string& walletFile = name;
|
||||
|
||||
@@ -4163,18 +4185,33 @@ std::shared_ptr<CWallet> CWallet::CreateWalletFromFile(const std::string& name,
|
||||
}
|
||||
walletInstance->SetMinVersion(FEATURE_LATEST);
|
||||
|
||||
// generate a new seed
|
||||
CPubKey seed = walletInstance->GenerateNewSeed();
|
||||
if (!walletInstance->SetHDSeed(seed))
|
||||
throw std::runtime_error(std::string(__func__) + ": Storing HD seed failed");
|
||||
if ((wallet_creation_flags & WALLET_FLAG_DISABLE_PRIVATE_KEYS)) {
|
||||
//selective allow to set flags
|
||||
walletInstance->SetWalletFlag(WALLET_FLAG_DISABLE_PRIVATE_KEYS);
|
||||
} else {
|
||||
// generate a new seed
|
||||
CPubKey seed = walletInstance->GenerateNewSeed();
|
||||
if (!walletInstance->SetHDSeed(seed)) {
|
||||
throw std::runtime_error(std::string(__func__) + ": Storing HD seed failed");
|
||||
}
|
||||
}
|
||||
|
||||
// Top up the keypool
|
||||
if (!walletInstance->TopUpKeyPool()) {
|
||||
if (!walletInstance->IsWalletFlagSet(WALLET_FLAG_DISABLE_PRIVATE_KEYS) && !walletInstance->TopUpKeyPool()) {
|
||||
InitError(_("Unable to generate initial keys") += "\n");
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
walletInstance->ChainStateFlushed(chainActive.GetLocator());
|
||||
} else if (wallet_creation_flags & WALLET_FLAG_DISABLE_PRIVATE_KEYS) {
|
||||
// Make it impossible to disable private keys after creation
|
||||
InitError(strprintf(_("Error loading %s: Private keys can only be disabled during creation"), walletFile));
|
||||
return NULL;
|
||||
} else if (walletInstance->IsWalletFlagSet(WALLET_FLAG_DISABLE_PRIVATE_KEYS)) {
|
||||
LOCK(walletInstance->cs_KeyStore);
|
||||
if (!walletInstance->mapKeys.empty() || !walletInstance->mapCryptedKeys.empty()) {
|
||||
InitWarning(strprintf(_("Warning: Private keys detected in wallet {%s} with disabled private keys"), walletFile));
|
||||
}
|
||||
} else if (gArgs.IsArgSet("-usehd")) {
|
||||
bool useHD = gArgs.GetBoolArg("-usehd", true);
|
||||
if (walletInstance->IsHDEnabled() && !useHD) {
|
||||
|
||||
Reference in New Issue
Block a user