Skip to content

Commit ce90391

Browse files
committed
wallet: Use LegacyDataSPKM when loading
In SetupLegacyScriptPubKeyMan, a base LegacyDataSPKM will be created if the database has the format "bdb_ro" (i.e. the wallet was opened only for migration purposes). All of the loading functions are now called with a LegacyDataSPKM object instead of LegacyScriptPubKeyMan.
1 parent affa517 commit ce90391

File tree

4 files changed

+40
-16
lines changed

4 files changed

+40
-16
lines changed

src/wallet/scriptpubkeyman.h

-1
Original file line numberDiff line numberDiff line change
@@ -492,7 +492,6 @@ class LegacyScriptPubKeyMan : public LegacyDataSPKM
492492

493493
/* Set the HD chain model (chain child index counters) and writes it to the database */
494494
void AddHDChain(const CHDChain& chain);
495-
const CHDChain& GetHDChain() const { return m_hd_chain; }
496495

497496
//! Remove a watch only script from the keystore
498497
bool RemoveWatchOnly(const CScript &dest);

src/wallet/wallet.cpp

+28-5
Original file line numberDiff line numberDiff line change
@@ -3486,6 +3486,16 @@ LegacyScriptPubKeyMan* CWallet::GetLegacyScriptPubKeyMan() const
34863486
return dynamic_cast<LegacyScriptPubKeyMan*>(it->second);
34873487
}
34883488

3489+
LegacyDataSPKM* CWallet::GetLegacyDataSPKM() const
3490+
{
3491+
if (IsWalletFlagSet(WALLET_FLAG_DESCRIPTORS)) {
3492+
return nullptr;
3493+
}
3494+
auto it = m_internal_spk_managers.find(OutputType::LEGACY);
3495+
if (it == m_internal_spk_managers.end()) return nullptr;
3496+
return dynamic_cast<LegacyDataSPKM*>(it->second);
3497+
}
3498+
34893499
LegacyScriptPubKeyMan* CWallet::GetOrCreateLegacyScriptPubKeyMan()
34903500
{
34913501
SetupLegacyScriptPubKeyMan();
@@ -3500,13 +3510,26 @@ void CWallet::AddScriptPubKeyMan(const uint256& id, std::unique_ptr<ScriptPubKey
35003510
FirstKeyTimeChanged(spkm.get(), spkm->GetTimeFirstKey());
35013511
}
35023512

3513+
LegacyDataSPKM* CWallet::GetOrCreateLegacyDataSPKM()
3514+
{
3515+
SetupLegacyScriptPubKeyMan();
3516+
return GetLegacyDataSPKM();
3517+
}
3518+
35033519
void CWallet::SetupLegacyScriptPubKeyMan()
35043520
{
35053521
if (!m_internal_spk_managers.empty() || !m_external_spk_managers.empty() || !m_spk_managers.empty() || IsWalletFlagSet(WALLET_FLAG_DESCRIPTORS)) {
35063522
return;
35073523
}
35083524

3509-
auto spk_manager = std::unique_ptr<ScriptPubKeyMan>(new LegacyScriptPubKeyMan(*this, m_keypool_size));
3525+
std::unique_ptr<ScriptPubKeyMan> spk_manager;
3526+
3527+
// Only create base LegacyDataSPKM if using BERKELEY_RO
3528+
if (m_database->Format() == "bdb_ro") {
3529+
spk_manager = std::unique_ptr<ScriptPubKeyMan>(new LegacyDataSPKM(*this));
3530+
} else {
3531+
spk_manager = std::unique_ptr<ScriptPubKeyMan>(new LegacyScriptPubKeyMan(*this, m_keypool_size));
3532+
}
35103533
for (const auto& type : LEGACY_OUTPUT_TYPES) {
35113534
m_internal_spk_managers[type] = spk_manager.get();
35123535
m_external_spk_managers[type] = spk_manager.get();
@@ -3846,7 +3869,7 @@ std::optional<MigrationData> CWallet::GetDescriptorsForLegacy(bilingual_str& err
38463869
{
38473870
AssertLockHeld(cs_wallet);
38483871

3849-
LegacyScriptPubKeyMan* legacy_spkm = GetLegacyScriptPubKeyMan();
3872+
LegacyDataSPKM* legacy_spkm = GetLegacyDataSPKM();
38503873
assert(legacy_spkm);
38513874

38523875
std::optional<MigrationData> res = legacy_spkm->MigrateToDescriptor();
@@ -3861,7 +3884,7 @@ bool CWallet::ApplyMigrationData(MigrationData& data, bilingual_str& error)
38613884
{
38623885
AssertLockHeld(cs_wallet);
38633886

3864-
LegacyScriptPubKeyMan* legacy_spkm = GetLegacyScriptPubKeyMan();
3887+
LegacyDataSPKM* legacy_spkm = GetLegacyDataSPKM();
38653888
if (!legacy_spkm) {
38663889
error = _("Error: This wallet is already a descriptor wallet");
38673890
return false;
@@ -4187,7 +4210,7 @@ util::Result<MigrationResult> MigrateLegacyToDescriptor(const std::string& walle
41874210

41884211
// If the wallet is still loaded, unload it so that nothing else tries to use it while we're changing it
41894212
if (auto wallet = GetWallet(context, wallet_name)) {
4190-
if (!wallet->GetLegacyScriptPubKeyMan()) {
4213+
if (!wallet->GetLegacyDataSPKM()) {
41914214
return util::Error{_("Error: This wallet is already a descriptor wallet")};
41924215
}
41934216

@@ -4212,7 +4235,7 @@ util::Result<MigrationResult> MigrateLegacyToDescriptor(const std::string& walle
42124235
return util::Error{Untranslated("Wallet loading failed.") + Untranslated(" ") + error};
42134236
}
42144237

4215-
if (!wallet->GetLegacyScriptPubKeyMan()) {
4238+
if (!wallet->GetLegacyDataSPKM()) {
42164239
return util::Error{_("Error: This wallet is already a descriptor wallet")};
42174240
}
42184241
// Unload

src/wallet/wallet.h

+2
Original file line numberDiff line numberDiff line change
@@ -945,6 +945,8 @@ class CWallet final : public WalletStorage, public interfaces::Chain::Notificati
945945
//! Get the LegacyScriptPubKeyMan which is used for all types, internal, and external.
946946
LegacyScriptPubKeyMan* GetLegacyScriptPubKeyMan() const;
947947
LegacyScriptPubKeyMan* GetOrCreateLegacyScriptPubKeyMan();
948+
LegacyDataSPKM* GetLegacyDataSPKM() const;
949+
LegacyDataSPKM* GetOrCreateLegacyDataSPKM();
948950

949951
//! Make a LegacyScriptPubKeyMan and set it for all types, internal, and external.
950952
void SetupLegacyScriptPubKeyMan();

src/wallet/walletdb.cpp

+10-10
Original file line numberDiff line numberDiff line change
@@ -352,7 +352,7 @@ bool LoadKey(CWallet* pwallet, DataStream& ssKey, DataStream& ssValue, std::stri
352352
strErr = "Error reading wallet database: CPrivKey corrupt";
353353
return false;
354354
}
355-
if (!pwallet->GetOrCreateLegacyScriptPubKeyMan()->LoadKey(key, vchPubKey))
355+
if (!pwallet->GetOrCreateLegacyDataSPKM()->LoadKey(key, vchPubKey))
356356
{
357357
strErr = "Error reading wallet database: LegacyScriptPubKeyMan::LoadKey failed";
358358
return false;
@@ -391,7 +391,7 @@ bool LoadCryptedKey(CWallet* pwallet, DataStream& ssKey, DataStream& ssValue, st
391391
}
392392
}
393393

394-
if (!pwallet->GetOrCreateLegacyScriptPubKeyMan()->LoadCryptedKey(vchPubKey, vchPrivKey, checksum_valid))
394+
if (!pwallet->GetOrCreateLegacyDataSPKM()->LoadCryptedKey(vchPubKey, vchPrivKey, checksum_valid))
395395
{
396396
strErr = "Error reading wallet database: LegacyScriptPubKeyMan::LoadCryptedKey failed";
397397
return false;
@@ -438,7 +438,7 @@ bool LoadHDChain(CWallet* pwallet, DataStream& ssValue, std::string& strErr)
438438
try {
439439
CHDChain chain;
440440
ssValue >> chain;
441-
pwallet->GetOrCreateLegacyScriptPubKeyMan()->LoadHDChain(chain);
441+
pwallet->GetOrCreateLegacyDataSPKM()->LoadHDChain(chain);
442442
} catch (const std::exception& e) {
443443
if (strErr.empty()) {
444444
strErr = e.what();
@@ -582,7 +582,7 @@ static DBErrors LoadLegacyWalletRecords(CWallet* pwallet, DatabaseBatch& batch,
582582
key >> hash;
583583
CScript script;
584584
value >> script;
585-
if (!pwallet->GetOrCreateLegacyScriptPubKeyMan()->LoadCScript(script))
585+
if (!pwallet->GetOrCreateLegacyDataSPKM()->LoadCScript(script))
586586
{
587587
strErr = "Error reading wallet database: LegacyScriptPubKeyMan::LoadCScript failed";
588588
return DBErrors::NONCRITICAL_ERROR;
@@ -605,7 +605,7 @@ static DBErrors LoadLegacyWalletRecords(CWallet* pwallet, DatabaseBatch& batch,
605605
key >> vchPubKey;
606606
CKeyMetadata keyMeta;
607607
value >> keyMeta;
608-
pwallet->GetOrCreateLegacyScriptPubKeyMan()->LoadKeyMetadata(vchPubKey.GetID(), keyMeta);
608+
pwallet->GetOrCreateLegacyDataSPKM()->LoadKeyMetadata(vchPubKey.GetID(), keyMeta);
609609

610610
// Extract some CHDChain info from this metadata if it has any
611611
if (keyMeta.nVersion >= CKeyMetadata::VERSION_WITH_HDDATA && !keyMeta.hd_seed_id.IsNull() && keyMeta.hdKeypath.size() > 0) {
@@ -672,7 +672,7 @@ static DBErrors LoadLegacyWalletRecords(CWallet* pwallet, DatabaseBatch& batch,
672672

673673
// Set inactive chains
674674
if (!hd_chains.empty()) {
675-
LegacyScriptPubKeyMan* legacy_spkm = pwallet->GetLegacyScriptPubKeyMan();
675+
LegacyDataSPKM* legacy_spkm = pwallet->GetLegacyDataSPKM();
676676
if (legacy_spkm) {
677677
for (const auto& [hd_seed_id, chain] : hd_chains) {
678678
if (hd_seed_id != legacy_spkm->GetHDChain().seed_id) {
@@ -693,7 +693,7 @@ static DBErrors LoadLegacyWalletRecords(CWallet* pwallet, DatabaseBatch& batch,
693693
uint8_t fYes;
694694
value >> fYes;
695695
if (fYes == '1') {
696-
pwallet->GetOrCreateLegacyScriptPubKeyMan()->LoadWatchOnly(script);
696+
pwallet->GetOrCreateLegacyDataSPKM()->LoadWatchOnly(script);
697697
}
698698
return DBErrors::LOAD_OK;
699699
});
@@ -706,7 +706,7 @@ static DBErrors LoadLegacyWalletRecords(CWallet* pwallet, DatabaseBatch& batch,
706706
key >> script;
707707
CKeyMetadata keyMeta;
708708
value >> keyMeta;
709-
pwallet->GetOrCreateLegacyScriptPubKeyMan()->LoadScriptMetadata(CScriptID(script), keyMeta);
709+
pwallet->GetOrCreateLegacyDataSPKM()->LoadScriptMetadata(CScriptID(script), keyMeta);
710710
return DBErrors::LOAD_OK;
711711
});
712712
result = std::max(result, watch_meta_res.m_result);
@@ -718,7 +718,7 @@ static DBErrors LoadLegacyWalletRecords(CWallet* pwallet, DatabaseBatch& batch,
718718
key >> nIndex;
719719
CKeyPool keypool;
720720
value >> keypool;
721-
pwallet->GetOrCreateLegacyScriptPubKeyMan()->LoadKeyPool(nIndex, keypool);
721+
pwallet->GetOrCreateLegacyDataSPKM()->LoadKeyPool(nIndex, keypool);
722722
return DBErrors::LOAD_OK;
723723
});
724724
result = std::max(result, pool_res.m_result);
@@ -761,7 +761,7 @@ static DBErrors LoadLegacyWalletRecords(CWallet* pwallet, DatabaseBatch& batch,
761761

762762
// nTimeFirstKey is only reliable if all keys have metadata
763763
if (pwallet->IsLegacy() && (key_res.m_records + ckey_res.m_records + watch_script_res.m_records) != (keymeta_res.m_records + watch_meta_res.m_records)) {
764-
auto spk_man = pwallet->GetOrCreateLegacyScriptPubKeyMan();
764+
auto spk_man = pwallet->GetLegacyScriptPubKeyMan();
765765
if (spk_man) {
766766
LOCK(spk_man->cs_KeyStore);
767767
spk_man->UpdateTimeFirstKey(1);

0 commit comments

Comments
 (0)