Skip to content
Bitcoin Roots

v31.1-roots.1 · Commit 6: [PATCH 06/17] feat(wallet): preserve Roots signing and spend controls on v31

src/script/descriptor.cpp

Before: src/script/descriptor.cpp · After: src/script/descriptor.cpp

File metadata
index 19315dd6a30f0409f46810244d94c5367620e7f9..21a250bcbe963d4d826d5860f20419e24bd3bb4d 100644

Download original patch · Release notes

Diff rows 1–66 of 66. Line numbers refer to the original before/after files.

+ Added− RemovedUnmarked lines are context.

Scroll the code area horizontally to read long lines. Before is on the left; after is on the right. Unified view fits narrow screens more easily.

src/script/descriptor.cpp CHANGED
@@ -222,6 +222,24 @@ public:
222
  virtual std::optional<CPubKey> GetRootPubKey() const = 0;
223
  /** Return the extended public key for this PubkeyProvider, if it has one. */
224
  virtual std::optional<CExtPubKey> GetRootExtPubKey() const = 0;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
225
 
226
  /** Make a deep copy of this PubkeyProvider */
227
  virtual std::unique_ptr<PubkeyProvider> Clone() const = 0;
@@ -262,6 +280,11 @@ public:
262
  bool IsRange() const override { return m_provider->IsRange(); }
263
  size_t GetSize() const override { return m_provider->GetSize(); }
264
  bool IsBIP32() const override { return m_provider->IsBIP32(); }
 
 
 
 
 
265
  std::string ToString(StringType type) const override { return "[" + OriginString(type) + "]" + m_provider->ToString(type); }
266
  bool ToPrivateString(const SigningProvider& arg, std::string& ret) const override
267
  {
@@ -331,6 +354,7 @@ public:
331
  bool IsRange() const override { return false; }
332
  size_t GetSize() const override { return m_pubkey.size(); }
333
  bool IsBIP32() const override { return false; }
 
334
  std::string ToString(StringType type) const override { return m_xonly ? HexStr(m_pubkey).substr(2) : HexStr(m_pubkey); }
335
  bool ToPrivateString(const SigningProvider& arg, std::string& ret) const override
336
  {
@@ -762,6 +786,11 @@ public:
762
  }
763
  }
764
 
 
 
 
 
 
765
  // Get RootPubKey and GetRootExtPubKey are used to return the single pubkey underlying the pubkey provider
766
  // to be presented to the user in gethdkeys. As this is a multisig construction, there is no single underlying
767
  // pubkey hence nothing should be returned.
@@ -1007,6 +1036,13 @@ public:
1007
  }
1008
  }
1009
 
 
 
 
 
 
 
 
1010
  std::optional<OutputType> GetOutputType() const override { return std::nullopt; }
1011
 
1012
  std::optional<int64_t> ScriptSize() const override { return {}; }
 
222
  virtual std::optional<CPubKey> GetRootPubKey() const = 0;
223
  /** Return the extended public key for this PubkeyProvider, if it has one. */
224
  virtual std::optional<CExtPubKey> GetRootExtPubKey() const = 0;
225
+ virtual bool IsXOnly() const { return false; }
226
+
227
+ virtual void GetAvailableKeys(int pos, const DescriptorCache& cache, const SigningProvider& provider, std::set<CKeyID>& out) const
228
+ {
229
+ const auto root{GetRootPubKey()};
230
+ const auto ext_root{GetRootExtPubKey()};
231
+ bool available{ext_root && provider.HaveKey(ext_root->pubkey.GetID())};
232
+ if (root) {
233
+ // Constant x-only expressions can represent either public-key parity.
234
+ available |= provider.HaveKey(root->GetID());
235
+ if (IsXOnly()) {
236
+ for (const auto& pubkey : XOnlyPubKey(*root).GetCPubKeys()) available |= provider.HaveKey(pubkey.GetID());
237
+ }
238
+ }
239
+ if (!available) return;
240
+ FlatSigningProvider public_data;
241
+ if (const auto pubkey{GetPubKey(pos, DUMMY_SIGNING_PROVIDER, public_data, &cache)}) out.insert(pubkey->GetID());
242
+ }
243
 
244
  /** Make a deep copy of this PubkeyProvider */
245
  virtual std::unique_ptr<PubkeyProvider> Clone() const = 0;
 
280
  bool IsRange() const override { return m_provider->IsRange(); }
281
  size_t GetSize() const override { return m_provider->GetSize(); }
282
  bool IsBIP32() const override { return m_provider->IsBIP32(); }
283
+ bool IsXOnly() const override { return m_provider->IsXOnly(); }
284
+ void GetAvailableKeys(int pos, const DescriptorCache& cache, const SigningProvider& provider, std::set<CKeyID>& out) const override
285
+ {
286
+ m_provider->GetAvailableKeys(pos, cache, provider, out);
287
+ }
288
  std::string ToString(StringType type) const override { return "[" + OriginString(type) + "]" + m_provider->ToString(type); }
289
  bool ToPrivateString(const SigningProvider& arg, std::string& ret) const override
290
  {
 
354
  bool IsRange() const override { return false; }
355
  size_t GetSize() const override { return m_pubkey.size(); }
356
  bool IsBIP32() const override { return false; }
357
+ bool IsXOnly() const override { return m_xonly; }
358
  std::string ToString(StringType type) const override { return m_xonly ? HexStr(m_pubkey).substr(2) : HexStr(m_pubkey); }
359
  bool ToPrivateString(const SigningProvider& arg, std::string& ret) const override
360
  {
 
786
  }
787
  }
788
 
789
+ void GetAvailableKeys(int pos, const DescriptorCache& cache, const SigningProvider& provider, std::set<CKeyID>& out) const override
790
+ {
791
+ for (const auto& participant : m_participants) participant->GetAvailableKeys(pos, cache, provider, out);
792
+ }
793
+
794
  // Get RootPubKey and GetRootExtPubKey are used to return the single pubkey underlying the pubkey provider
795
  // to be presented to the user in gethdkeys. As this is a multisig construction, there is no single underlying
796
  // pubkey hence nothing should be returned.
 
1036
  }
1037
  }
1038
 
1039
+ // NOLINTNEXTLINE(misc-no-recursion)
1040
+ void GetAvailableKeys(int pos, const DescriptorCache& cache, const SigningProvider& provider, std::set<CKeyID>& out) const final
1041
+ {
1042
+ for (const auto& key : m_pubkey_args) key->GetAvailableKeys(pos, cache, provider, out);
1043
+ for (const auto& descriptor : m_subdescriptor_args) descriptor->GetAvailableKeys(pos, cache, provider, out);
1044
+ }
1045
+
1046
  std::optional<OutputType> GetOutputType() const override { return std::nullopt; }
1047
 
1048
  std::optional<int64_t> ScriptSize() const override { return {}; }