aboutsummaryrefslogtreecommitdiff
path: root/src/script
diff options
context:
space:
mode:
Diffstat (limited to 'src/script')
-rw-r--r--src/script/descriptor.cpp46
-rw-r--r--src/script/descriptor.h2
2 files changed, 30 insertions, 18 deletions
diff --git a/src/script/descriptor.cpp b/src/script/descriptor.cpp
index 2d10b5dd0f..dff6429259 100644
--- a/src/script/descriptor.cpp
+++ b/src/script/descriptor.cpp
@@ -191,8 +191,13 @@ public:
/** Get the size of the generated public key(s) in bytes (33 or 65). */
virtual size_t GetSize() const = 0;
+ enum class StringType {
+ PUBLIC,
+ COMPAT // string calculation that mustn't change over time to stay compatible with previous software versions
+ };
+
/** Get the descriptor string form. */
- virtual std::string ToString() const = 0;
+ virtual std::string ToString(StringType type=StringType::PUBLIC) const = 0;
/** Get the descriptor string form including private data (if available in arg). */
virtual bool ToPrivateString(const SigningProvider& arg, std::string& out) const = 0;
@@ -212,9 +217,11 @@ class OriginPubkeyProvider final : public PubkeyProvider
std::unique_ptr<PubkeyProvider> m_provider;
bool m_apostrophe;
- std::string OriginString(bool normalized=false) const
+ std::string OriginString(StringType type, bool normalized=false) const
{
- return HexStr(m_origin.fingerprint) + FormatHDKeypath(m_origin.path, /*apostrophe=*/!normalized && m_apostrophe);
+ // If StringType==COMPAT, always use the apostrophe to stay compatible with previous versions
+ bool use_apostrophe = (!normalized && m_apostrophe) || type == StringType::COMPAT;
+ return HexStr(m_origin.fingerprint) + FormatHDKeypath(m_origin.path, use_apostrophe);
}
public:
@@ -228,12 +235,12 @@ public:
}
bool IsRange() const override { return m_provider->IsRange(); }
size_t GetSize() const override { return m_provider->GetSize(); }
- std::string ToString() const override { return "[" + OriginString() + "]" + m_provider->ToString(); }
+ std::string ToString(StringType type) const override { return "[" + OriginString(type) + "]" + m_provider->ToString(type); }
bool ToPrivateString(const SigningProvider& arg, std::string& ret) const override
{
std::string sub;
if (!m_provider->ToPrivateString(arg, sub)) return false;
- ret = "[" + OriginString() + "]" + std::move(sub);
+ ret = "[" + OriginString(StringType::PUBLIC) + "]" + std::move(sub);
return true;
}
bool ToNormalizedString(const SigningProvider& arg, std::string& ret, const DescriptorCache* cache) const override
@@ -245,9 +252,9 @@ public:
// and append that to our own origin string.
if (sub[0] == '[') {
sub = sub.substr(9);
- ret = "[" + OriginString(/*normalized=*/true) + std::move(sub);
+ ret = "[" + OriginString(StringType::PUBLIC, /*normalized=*/true) + std::move(sub);
} else {
- ret = "[" + OriginString(/*normalized=*/true) + "]" + std::move(sub);
+ ret = "[" + OriginString(StringType::PUBLIC, /*normalized=*/true) + "]" + std::move(sub);
}
return true;
}
@@ -275,7 +282,7 @@ public:
}
bool IsRange() const override { return false; }
size_t GetSize() const override { return m_pubkey.size(); }
- std::string ToString() const override { return m_xonly ? HexStr(m_pubkey).substr(2) : HexStr(m_pubkey); }
+ std::string ToString(StringType type) const override { return m_xonly ? HexStr(m_pubkey).substr(2) : HexStr(m_pubkey); }
bool ToPrivateString(const SigningProvider& arg, std::string& ret) const override
{
CKey key;
@@ -293,7 +300,7 @@ public:
}
bool ToNormalizedString(const SigningProvider& arg, std::string& ret, const DescriptorCache* cache) const override
{
- ret = ToString();
+ ret = ToString(StringType::PUBLIC);
return true;
}
bool GetPrivKey(int pos, const SigningProvider& arg, CKey& key) const override
@@ -421,9 +428,10 @@ public:
return true;
}
- std::string ToString(bool normalized) const
+ std::string ToString(StringType type, bool normalized) const
{
- const bool use_apostrophe = !normalized && m_apostrophe;
+ // If StringType==COMPAT, always use the apostrophe to stay compatible with previous versions
+ const bool use_apostrophe = (!normalized && m_apostrophe) || type == StringType::COMPAT;
std::string ret = EncodeExtPubKey(m_root_extkey) + FormatHDKeypath(m_path, /*apostrophe=*/use_apostrophe);
if (IsRange()) {
ret += "/*";
@@ -431,9 +439,9 @@ public:
}
return ret;
}
- std::string ToString() const override
+ std::string ToString(StringType type=StringType::PUBLIC) const override
{
- return ToString(/*normalized=*/false);
+ return ToString(type, /*normalized=*/false);
}
bool ToPrivateString(const SigningProvider& arg, std::string& out) const override
{
@@ -449,7 +457,7 @@ public:
bool ToNormalizedString(const SigningProvider& arg, std::string& out, const DescriptorCache* cache) const override
{
if (m_derive == DeriveType::HARDENED) {
- out = ToString(/*normalized=*/true);
+ out = ToString(StringType::PUBLIC, /*normalized=*/true);
return true;
}
@@ -556,6 +564,7 @@ public:
PUBLIC,
PRIVATE,
NORMALIZED,
+ COMPAT, // string calculation that mustn't change over time to stay compatible with previous software versions
};
bool IsSolvable() const override
@@ -607,6 +616,9 @@ public:
case StringType::PUBLIC:
tmp = pubkey->ToString();
break;
+ case StringType::COMPAT:
+ tmp = pubkey->ToString(PubkeyProvider::StringType::COMPAT);
+ break;
}
ret += tmp;
}
@@ -617,10 +629,10 @@ public:
return true;
}
- std::string ToString() const final
+ std::string ToString(bool compat_format) const final
{
std::string ret;
- ToStringHelper(nullptr, ret, StringType::PUBLIC);
+ ToStringHelper(nullptr, ret, compat_format ? StringType::COMPAT : StringType::PUBLIC);
return AddChecksum(ret);
}
@@ -1780,7 +1792,7 @@ std::unique_ptr<Descriptor> InferDescriptor(const CScript& script, const Signing
uint256 DescriptorID(const Descriptor& desc)
{
- std::string desc_str = desc.ToString();
+ std::string desc_str = desc.ToString(/*compat_format=*/true);
uint256 id;
CSHA256().Write((unsigned char*)desc_str.data(), desc_str.size()).Finalize(id.begin());
return id;
diff --git a/src/script/descriptor.h b/src/script/descriptor.h
index 0684febf70..c6860c5cf6 100644
--- a/src/script/descriptor.h
+++ b/src/script/descriptor.h
@@ -106,7 +106,7 @@ struct Descriptor {
virtual bool IsSolvable() const = 0;
/** Convert the descriptor back to a string, undoing parsing. */
- virtual std::string ToString() const = 0;
+ virtual std::string ToString(bool compat_format=false) const = 0;
/** Whether this descriptor will return one scriptPubKey or multiple (aka is or is not combo) */
virtual bool IsSingleType() const = 0;