@@ -26,26 +26,9 @@ use crate::{
2626 Threshold , ToPublicKey , TranslateErr , Translator ,
2727} ;
2828
29- /// A Taproot Tree representation.
30- // Hidden leaves are not yet supported in descriptor spec. Conceptually, it should
31- // be simple to integrate those here, but it is best to wait on core for the exact syntax.
32- #[ derive( Clone , Ord , PartialOrd , Eq , PartialEq , Hash ) ]
33- pub enum TapTree < Pk : MiniscriptKey > {
34- /// A taproot tree structure
35- Tree {
36- /// Left tree branch.
37- left : Arc < TapTree < Pk > > ,
38- /// Right tree branch.
39- right : Arc < TapTree < Pk > > ,
40- /// Tree height, defined as `1 + max(left_height, right_height)`.
41- height : usize ,
42- } ,
43- /// A taproot leaf denoting a spending condition
44- // A new leaf version would require a new Context, therefore there is no point
45- // in adding a LeafVersion with Leaf type here. All Miniscripts right now
46- // are of Leafversion::default
47- Leaf ( Arc < Miniscript < Pk , Tap > > ) ,
48- }
29+ mod taptree;
30+
31+ pub use self :: taptree:: { TapTree , TapTreeIter , TapTreeIterItem } ;
4932
5033/// A taproot descriptor
5134pub struct Tr < Pk : MiniscriptKey > {
@@ -111,64 +94,6 @@ impl<Pk: MiniscriptKey> hash::Hash for Tr<Pk> {
11194 }
11295}
11396
114- impl < Pk : MiniscriptKey > TapTree < Pk > {
115- /// Creates a `TapTree` by combining `left` and `right` tree nodes.
116- pub fn combine ( left : TapTree < Pk > , right : TapTree < Pk > ) -> Self {
117- let height = 1 + cmp:: max ( left. height ( ) , right. height ( ) ) ;
118- TapTree :: Tree { left : Arc :: new ( left) , right : Arc :: new ( right) , height }
119- }
120-
121- /// Returns the height of this tree.
122- pub fn height ( & self ) -> usize {
123- match * self {
124- TapTree :: Tree { left : _, right : _, height } => height,
125- TapTree :: Leaf ( ..) => 0 ,
126- }
127- }
128-
129- /// Iterates over all miniscripts in DFS walk order compatible with the
130- /// PSBT requirements (BIP 371).
131- pub fn iter ( & self ) -> TapTreeIter < Pk > { TapTreeIter { stack : vec ! [ ( 0 , self ) ] } }
132-
133- // Helper function to translate keys
134- fn translate_helper < T > ( & self , t : & mut T ) -> Result < TapTree < T :: TargetPk > , TranslateErr < T :: Error > >
135- where
136- T : Translator < Pk > ,
137- {
138- let frag = match * self {
139- TapTree :: Tree { ref left, ref right, ref height } => TapTree :: Tree {
140- left : Arc :: new ( left. translate_helper ( t) ?) ,
141- right : Arc :: new ( right. translate_helper ( t) ?) ,
142- height : * height,
143- } ,
144- TapTree :: Leaf ( ref ms) => TapTree :: Leaf ( Arc :: new ( ms. translate_pk ( t) ?) ) ,
145- } ;
146- Ok ( frag)
147- }
148- }
149-
150- impl < Pk : MiniscriptKey > fmt:: Display for TapTree < Pk > {
151- fn fmt ( & self , f : & mut fmt:: Formatter < ' _ > ) -> fmt:: Result {
152- match self {
153- TapTree :: Tree { ref left, ref right, height : _ } => {
154- write ! ( f, "{{{},{}}}" , * left, * right)
155- }
156- TapTree :: Leaf ( ref script) => write ! ( f, "{}" , * script) ,
157- }
158- }
159- }
160-
161- impl < Pk : MiniscriptKey > fmt:: Debug for TapTree < Pk > {
162- fn fmt ( & self , f : & mut fmt:: Formatter < ' _ > ) -> fmt:: Result {
163- match self {
164- TapTree :: Tree { ref left, ref right, height : _ } => {
165- write ! ( f, "{{{:?},{:?}}}" , * left, * right)
166- }
167- TapTree :: Leaf ( ref script) => write ! ( f, "{:?}" , * script) ,
168- }
169- }
170- }
171-
17297impl < Pk : MiniscriptKey > Tr < Pk > {
17398 /// Create a new [`Tr`] descriptor from internal key and [`TapTree`]
17499 pub fn new ( internal_key : Pk , tree : Option < TapTree < Pk > > ) -> Result < Self , Error > {
@@ -194,10 +119,17 @@ impl<Pk: MiniscriptKey> Tr<Pk> {
194119
195120 /// Iterate over all scripts in merkle tree. If there is no script path, the iterator
196121 /// yields [`None`]
197- pub fn iter_scripts ( & self ) -> TapTreeIter < Pk > {
122+ #[ deprecated( since = "TBD" , note = "use `leaves` instead" ) ]
123+ pub fn iter_scripts ( & self ) -> TapTreeIter < Pk > { self . leaves ( ) }
124+
125+ /// Iterates over all the leaves of the tree in depth-first preorder.
126+ ///
127+ /// The yielded elements include the Miniscript for each leave as well as its depth
128+ /// in the tree, which is the data required by PSBT (BIP 371).
129+ pub fn leaves ( & self ) -> TapTreeIter < Pk > {
198130 match self . tree {
199- Some ( ref t) => t. iter ( ) ,
200- None => TapTreeIter { stack : vec ! [ ] } ,
131+ Some ( ref t) => t. leaves ( ) ,
132+ None => TapTreeIter :: empty ( ) ,
201133 }
202134 }
203135
@@ -226,10 +158,10 @@ impl<Pk: MiniscriptKey> Tr<Pk> {
226158 TaprootSpendInfo :: new_key_spend ( & secp, self . internal_key . to_x_only_pubkey ( ) , None )
227159 } else {
228160 let mut builder = TaprootBuilder :: new ( ) ;
229- for ( depth , ms ) in self . iter_scripts ( ) {
230- let script = ms . encode ( ) ;
161+ for leaf in self . leaves ( ) {
162+ let script = leaf . miniscript ( ) . encode ( ) ;
231163 builder = builder
232- . add_leaf ( depth, script)
164+ . add_leaf ( leaf . depth ( ) , script)
233165 . expect ( "Computing spend data on a valid Tree should always succeed" ) ;
234166 }
235167 // Assert builder cannot error here because we have a well formed descriptor
@@ -245,8 +177,8 @@ impl<Pk: MiniscriptKey> Tr<Pk> {
245177
246178 /// Checks whether the descriptor is safe.
247179 pub fn sanity_check ( & self ) -> Result < ( ) , Error > {
248- for ( _depth , ms ) in self . iter_scripts ( ) {
249- ms . sanity_check ( ) ?;
180+ for leaf in self . leaves ( ) {
181+ leaf . miniscript ( ) . sanity_check ( ) ?;
250182 }
251183 Ok ( ( ) )
252184 }
@@ -275,12 +207,12 @@ impl<Pk: MiniscriptKey> Tr<Pk> {
275207 } ;
276208
277209 let wu = tree
278- . iter ( )
279- . filter_map ( |( depth , ms ) | {
280- let script_size = ms . script_size ( ) ;
281- let max_sat_elems = ms . max_satisfaction_witness_elements ( ) . ok ( ) ?;
282- let max_sat_size = ms . max_satisfaction_size ( ) . ok ( ) ?;
283- let control_block_size = control_block_len ( depth) ;
210+ . leaves ( )
211+ . filter_map ( |leaf | {
212+ let script_size = leaf . miniscript ( ) . script_size ( ) ;
213+ let max_sat_elems = leaf . miniscript ( ) . max_satisfaction_witness_elements ( ) . ok ( ) ?;
214+ let max_sat_size = leaf . miniscript ( ) . max_satisfaction_size ( ) . ok ( ) ?;
215+ let control_block_size = control_block_len ( leaf . depth ( ) ) ;
284216
285217 // stack varint difference (+1 for ctrl block, witness script already included)
286218 let stack_varint_diff = varint_len ( max_sat_elems + 1 ) - varint_len ( 0 ) ;
@@ -325,12 +257,12 @@ impl<Pk: MiniscriptKey> Tr<Pk> {
325257 Some ( tree) => tree,
326258 } ;
327259
328- tree. iter ( )
329- . filter_map ( |( depth , ms ) | {
330- let script_size = ms . script_size ( ) ;
331- let max_sat_elems = ms . max_satisfaction_witness_elements ( ) . ok ( ) ?;
332- let max_sat_size = ms . max_satisfaction_size ( ) . ok ( ) ?;
333- let control_block_size = control_block_len ( depth) ;
260+ tree. leaves ( )
261+ . filter_map ( |leaf | {
262+ let script_size = leaf . miniscript ( ) . script_size ( ) ;
263+ let max_sat_elems = leaf . miniscript ( ) . max_satisfaction_witness_elements ( ) . ok ( ) ?;
264+ let max_sat_size = leaf . miniscript ( ) . max_satisfaction_size ( ) . ok ( ) ?;
265+ let control_block_size = control_block_len ( leaf . depth ( ) ) ;
334266 Some (
335267 // scriptSig len byte
336268 4 +
@@ -447,48 +379,6 @@ impl Tr<DefiniteDescriptorKey> {
447379 }
448380}
449381
450- /// Iterator for Taproot structures
451- /// Yields a pair of (depth, miniscript) in a depth first walk
452- /// For example, this tree:
453- /// - N0 -
454- /// / \\
455- /// N1 N2
456- /// / \ / \\
457- /// A B C N3
458- /// / \\
459- /// D E
460- /// would yield (2, A), (2, B), (2,C), (3, D), (3, E).
461- ///
462- #[ derive( Debug , Clone ) ]
463- pub struct TapTreeIter < ' a , Pk : MiniscriptKey > {
464- stack : Vec < ( u8 , & ' a TapTree < Pk > ) > ,
465- }
466-
467- impl < Pk : MiniscriptKey > TapTreeIter < ' _ , Pk > {
468- /// Helper function to return an empty iterator from Descriptor::tap_tree_iter.
469- pub ( super ) fn empty ( ) -> Self { Self { stack : vec ! [ ] } }
470- }
471-
472- impl < ' a , Pk > Iterator for TapTreeIter < ' a , Pk >
473- where
474- Pk : MiniscriptKey + ' a ,
475- {
476- type Item = ( u8 , & ' a Miniscript < Pk , Tap > ) ;
477-
478- fn next ( & mut self ) -> Option < Self :: Item > {
479- while let Some ( ( depth, last) ) = self . stack . pop ( ) {
480- match * last {
481- TapTree :: Tree { ref left, ref right, height : _ } => {
482- self . stack . push ( ( depth + 1 , right) ) ;
483- self . stack . push ( ( depth + 1 , left) ) ;
484- }
485- TapTree :: Leaf ( ref ms) => return Some ( ( depth, ms) ) ,
486- }
487- }
488- None
489- }
490- }
491-
492382impl < Pk : FromStrKey > core:: str:: FromStr for Tr < Pk > {
493383 type Err = Error ;
494384
@@ -597,22 +487,6 @@ impl<Pk: MiniscriptKey> fmt::Display for Tr<Pk> {
597487 }
598488}
599489
600- impl < Pk : MiniscriptKey > Liftable < Pk > for TapTree < Pk > {
601- fn lift ( & self ) -> Result < Policy < Pk > , Error > {
602- fn lift_helper < Pk : MiniscriptKey > ( s : & TapTree < Pk > ) -> Result < Policy < Pk > , Error > {
603- match * s {
604- TapTree :: Tree { ref left, ref right, height : _ } => Ok ( Policy :: Thresh (
605- Threshold :: or ( Arc :: new ( lift_helper ( left) ?) , Arc :: new ( lift_helper ( right) ?) ) ,
606- ) ) ,
607- TapTree :: Leaf ( ref leaf) => leaf. lift ( ) ,
608- }
609- }
610-
611- let pol = lift_helper ( self ) ?;
612- Ok ( pol. normalized ( ) )
613- }
614- }
615-
616490impl < Pk : MiniscriptKey > Liftable < Pk > for Tr < Pk > {
617491 fn lift ( & self ) -> Result < Policy < Pk > , Error > {
618492 match & self . tree {
@@ -628,8 +502,8 @@ impl<Pk: MiniscriptKey> Liftable<Pk> for Tr<Pk> {
628502impl < Pk : MiniscriptKey > ForEachKey < Pk > for Tr < Pk > {
629503 fn for_each_key < ' a , F : FnMut ( & ' a Pk ) -> bool > ( & ' a self , mut pred : F ) -> bool {
630504 let script_keys_res = self
631- . iter_scripts ( )
632- . all ( |( _d , ms ) | ms . for_each_key ( & mut pred) ) ;
505+ . leaves ( )
506+ . all ( |leaf| leaf . miniscript ( ) . for_each_key ( & mut pred) ) ;
633507 script_keys_res && pred ( & self . internal_key )
634508 }
635509}
@@ -673,14 +547,14 @@ where
673547 absolute_timelock : None ,
674548 } ;
675549 let mut min_wit_len = None ;
676- for ( _depth , ms ) in desc. iter_scripts ( ) {
550+ for leaf in desc. leaves ( ) {
677551 let mut satisfaction = if allow_mall {
678- match ms . build_template ( provider) {
552+ match leaf . miniscript ( ) . build_template ( provider) {
679553 s @ Satisfaction { stack : Witness :: Stack ( _) , .. } => s,
680554 _ => continue , // No witness for this script in tr descriptor, look for next one
681555 }
682556 } else {
683- match ms . build_template_mall ( provider) {
557+ match leaf . miniscript ( ) . build_template_mall ( provider) {
684558 s @ Satisfaction { stack : Witness :: Stack ( _) , .. } => s,
685559 _ => continue , // No witness for this script in tr descriptor, look for next one
686560 }
@@ -690,7 +564,7 @@ where
690564 _ => unreachable ! ( ) ,
691565 } ;
692566
693- let leaf_script = ( ms . encode ( ) , LeafVersion :: TapScript ) ;
567+ let leaf_script = ( leaf . compute_script ( ) , LeafVersion :: TapScript ) ;
694568 let control_block = spend_info
695569 . control_block ( & leaf_script)
696570 . expect ( "Control block must exist in script map for every known leaf" ) ;
0 commit comments