@@ -92,6 +92,12 @@ pub struct DescriptorXPub {
92
92
#[ derive( Debug , PartialEq , Clone , Copy ) ]
93
93
pub struct DescriptorKeyParseError ( & ' static str ) ;
94
94
95
+ impl fmt:: Display for DescriptorKeyParseError {
96
+ fn fmt ( & self , f : & mut fmt:: Formatter ) -> fmt:: Result {
97
+ f. write_str ( self . 0 )
98
+ }
99
+ }
100
+
95
101
impl fmt:: Display for DescriptorPublicKey {
96
102
fn fmt ( & self , f : & mut fmt:: Formatter ) -> fmt:: Result {
97
103
match * self {
@@ -239,13 +245,37 @@ impl DescriptorPublicKey {
239
245
) )
240
246
}
241
247
}
248
+
249
+ /// Derives the specified child key if self is a wildcard xpub. Otherwise returns self.
250
+ ///
251
+ /// Panics if given a hardened child number
252
+ pub fn derive ( self , child_number : bip32:: ChildNumber ) -> DescriptorPublicKey {
253
+ debug_assert ! ( child_number. is_normal( ) ) ;
254
+
255
+ match self {
256
+ DescriptorPublicKey :: PubKey ( _) => self ,
257
+ DescriptorPublicKey :: XPub ( xpub) => {
258
+ if xpub. is_wildcard {
259
+ DescriptorPublicKey :: XPub ( DescriptorXPub {
260
+ origin : xpub. origin ,
261
+ xpub : xpub. xpub ,
262
+ derivation_path : xpub. derivation_path . into_child ( child_number) ,
263
+ is_wildcard : false ,
264
+ } )
265
+ } else {
266
+ DescriptorPublicKey :: XPub ( xpub)
267
+ }
268
+ }
269
+ }
270
+ }
242
271
}
243
272
244
273
impl MiniscriptKey for DescriptorPublicKey {
245
- type Hash = hash160:: Hash ;
274
+ // This allows us to be able to derive public keys even for PkH s
275
+ type Hash = Self ;
246
276
247
- fn to_pubkeyhash ( & self ) -> Self :: Hash {
248
- self . to_public_key ( ) . to_pubkeyhash ( )
277
+ fn to_pubkeyhash ( & self ) -> Self {
278
+ self . clone ( )
249
279
}
250
280
}
251
281
@@ -264,7 +294,7 @@ impl ToPublicKey for DescriptorPublicKey {
264
294
}
265
295
266
296
fn hash_to_hash160 ( hash : & Self :: Hash ) -> hash160:: Hash {
267
- * hash
297
+ hash. to_public_key ( ) . to_pubkeyhash ( )
268
298
}
269
299
}
270
300
@@ -627,6 +657,17 @@ impl<Pk: MiniscriptKey + ToPublicKey> Descriptor<Pk> {
627
657
}
628
658
}
629
659
660
+ impl Descriptor < DescriptorPublicKey > {
661
+ /// Derives all wildcard keys in the descriptor using the supplied `child_number`
662
+ pub fn derive ( & self , child_number : bip32:: ChildNumber ) -> Descriptor < DescriptorPublicKey > {
663
+ self . translate_pk (
664
+ |pk| Result :: Ok :: < DescriptorPublicKey , ( ) > ( pk. clone ( ) . derive ( child_number) ) ,
665
+ |pk| Result :: Ok :: < DescriptorPublicKey , ( ) > ( pk. clone ( ) . derive ( child_number) ) ,
666
+ )
667
+ . expect ( "Translation fn can't fail." )
668
+ }
669
+ }
670
+
630
671
impl < Pk > expression:: FromTree for Descriptor < Pk >
631
672
where
632
673
Pk : MiniscriptKey ,
@@ -1413,7 +1454,7 @@ pk(03f28773c2d975288bc7d1d205c3748651b075fbc6610e58cddeeddf8f19405aa8))";
1413
1454
let policy: policy:: concrete:: Policy < DescriptorPublicKey > = descriptor_str. parse ( ) . unwrap ( ) ;
1414
1455
let descriptor = Descriptor :: Sh ( policy. compile ( ) . unwrap ( ) ) ;
1415
1456
let derived_descriptor =
1416
- descriptor. derive ( & [ bip32:: ChildNumber :: from_normal_idx ( 42 ) . unwrap ( ) ] ) ;
1457
+ descriptor. derive ( bip32:: ChildNumber :: from_normal_idx ( 42 ) . unwrap ( ) ) ;
1417
1458
1418
1459
let res_descriptor_str = "thresh(2,\
1419
1460
pk([d34db33f/44'/0'/0']xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL/1/42),\
0 commit comments