Changeset View
Changeset View
Standalone View
Standalone View
src/wallet/scriptpubkeyman.cpp
Show First 20 Lines • Show All 1,720 Lines • ▼ Show 20 Lines | for (int32_t i = m_max_cached_index + 1; i < new_range_end; ++i) { | ||||
i, provider, scripts_temp, out_keys, &temp_cache)) { | i, provider, scripts_temp, out_keys, &temp_cache)) { | ||||
return false; | return false; | ||||
} | } | ||||
} | } | ||||
// Add all of the scriptPubKeys to the scriptPubKey set | // Add all of the scriptPubKeys to the scriptPubKey set | ||||
for (const CScript &script : scripts_temp) { | for (const CScript &script : scripts_temp) { | ||||
m_map_script_pub_keys[script] = i; | m_map_script_pub_keys[script] = i; | ||||
} | } | ||||
for (const auto &pk_pair : out_keys.pubkeys) { | |||||
const CPubKey &pubkey = pk_pair.second; | |||||
if (m_map_pubkeys.count(pubkey) != 0) { | |||||
// We don't need to give an error here. | |||||
// It doesn't matter which of many valid indexes the pubkey has, | |||||
// we just need an index where we can derive it and it's private | |||||
// key | |||||
continue; | |||||
} | |||||
m_map_pubkeys[pubkey] = i; | |||||
} | |||||
// Write the cache | // Write the cache | ||||
for (const auto &parent_xpub_pair : | for (const auto &parent_xpub_pair : | ||||
temp_cache.GetCachedParentExtPubKeys()) { | temp_cache.GetCachedParentExtPubKeys()) { | ||||
CExtPubKey xpub; | CExtPubKey xpub; | ||||
if (m_wallet_descriptor.cache.GetCachedParentExtPubKey( | if (m_wallet_descriptor.cache.GetCachedParentExtPubKey( | ||||
parent_xpub_pair.first, xpub)) { | parent_xpub_pair.first, xpub)) { | ||||
if (xpub != parent_xpub_pair.second) { | if (xpub != parent_xpub_pair.second) { | ||||
throw std::runtime_error( | throw std::runtime_error( | ||||
▲ Show 20 Lines • Show All 195 Lines • ▼ Show 20 Lines | unsigned int DescriptorScriptPubKeyMan::GetKeyPoolSize() const { | ||||
return m_wallet_descriptor.range_end - m_wallet_descriptor.next_index; | return m_wallet_descriptor.range_end - m_wallet_descriptor.next_index; | ||||
} | } | ||||
int64_t DescriptorScriptPubKeyMan::GetTimeFirstKey() const { | int64_t DescriptorScriptPubKeyMan::GetTimeFirstKey() const { | ||||
LOCK(cs_desc_man); | LOCK(cs_desc_man); | ||||
return m_wallet_descriptor.creation_time; | return m_wallet_descriptor.creation_time; | ||||
} | } | ||||
std::unique_ptr<FlatSigningProvider> | |||||
DescriptorScriptPubKeyMan::GetSigningProvider(const CScript &script, | |||||
bool include_private) const { | |||||
LOCK(cs_desc_man); | |||||
// Find the index of the script | |||||
auto it = m_map_script_pub_keys.find(script); | |||||
if (it == m_map_script_pub_keys.end()) { | |||||
return nullptr; | |||||
} | |||||
int32_t index = it->second; | |||||
return GetSigningProvider(index, include_private); | |||||
} | |||||
std::unique_ptr<FlatSigningProvider> | |||||
DescriptorScriptPubKeyMan::GetSigningProvider(const CPubKey &pubkey) const { | |||||
LOCK(cs_desc_man); | |||||
// Find index of the pubkey | |||||
auto it = m_map_pubkeys.find(pubkey); | |||||
if (it == m_map_pubkeys.end()) { | |||||
return nullptr; | |||||
} | |||||
int32_t index = it->second; | |||||
// Always try to get the signing provider with private keys. This function | |||||
// should only be called during signing anyways | |||||
return GetSigningProvider(index, true); | |||||
} | |||||
std::unique_ptr<FlatSigningProvider> | |||||
DescriptorScriptPubKeyMan::GetSigningProvider(int32_t index, | |||||
bool include_private) const { | |||||
AssertLockHeld(cs_desc_man); | |||||
// Get the scripts, keys, and key origins for this script | |||||
std::unique_ptr<FlatSigningProvider> out_keys = | |||||
std::make_unique<FlatSigningProvider>(); | |||||
std::vector<CScript> scripts_temp; | |||||
if (!m_wallet_descriptor.descriptor->ExpandFromCache( | |||||
index, m_wallet_descriptor.cache, scripts_temp, *out_keys)) { | |||||
return nullptr; | |||||
} | |||||
if (HavePrivateKeys() && include_private) { | |||||
FlatSigningProvider master_provider; | |||||
master_provider.keys = GetKeys(); | |||||
m_wallet_descriptor.descriptor->ExpandPrivate(index, master_provider, | |||||
*out_keys); | |||||
} | |||||
return out_keys; | |||||
} | |||||
std::unique_ptr<SigningProvider> | std::unique_ptr<SigningProvider> | ||||
DescriptorScriptPubKeyMan::GetSolvingProvider(const CScript &script) const { | DescriptorScriptPubKeyMan::GetSolvingProvider(const CScript &script) const { | ||||
return nullptr; | return GetSigningProvider(script, false); | ||||
} | } | ||||
bool DescriptorScriptPubKeyMan::CanProvide(const CScript &script, | bool DescriptorScriptPubKeyMan::CanProvide(const CScript &script, | ||||
SignatureData &sigdata) { | SignatureData &sigdata) { | ||||
return IsMine(script); | return IsMine(script); | ||||
} | } | ||||
bool DescriptorScriptPubKeyMan::SignTransaction( | bool DescriptorScriptPubKeyMan::SignTransaction( | ||||
▲ Show 20 Lines • Show All 53 Lines • ▼ Show 20 Lines | for (int32_t i = m_wallet_descriptor.range_start; | ||||
if (m_map_script_pub_keys.count(script) != 0) { | if (m_map_script_pub_keys.count(script) != 0) { | ||||
throw std::runtime_error( | throw std::runtime_error( | ||||
strprintf("Error: Already loaded script at index %d as " | strprintf("Error: Already loaded script at index %d as " | ||||
"being at index %d", | "being at index %d", | ||||
i, m_map_script_pub_keys[script])); | i, m_map_script_pub_keys[script])); | ||||
} | } | ||||
m_map_script_pub_keys[script] = i; | m_map_script_pub_keys[script] = i; | ||||
} | } | ||||
for (const auto &pk_pair : out_keys.pubkeys) { | |||||
const CPubKey &pubkey = pk_pair.second; | |||||
if (m_map_pubkeys.count(pubkey) != 0) { | |||||
// We don't need to give an error here. | |||||
// It doesn't matter which of many valid indexes the pubkey has, | |||||
// we just need an index where we can derive it and it's private | |||||
// key | |||||
continue; | |||||
} | |||||
m_map_pubkeys[pubkey] = i; | |||||
} | |||||
m_max_cached_index++; | m_max_cached_index++; | ||||
} | } | ||||
} | } | ||||
bool DescriptorScriptPubKeyMan::AddKey(const CKeyID &key_id, const CKey &key) { | bool DescriptorScriptPubKeyMan::AddKey(const CKeyID &key_id, const CKey &key) { | ||||
LOCK(cs_desc_man); | LOCK(cs_desc_man); | ||||
m_map_keys[key_id] = key; | m_map_keys[key_id] = key; | ||||
return true; | return true; | ||||
Show All 13 Lines |