1use core::{cmp, i64, mem};
22
23use bitcoin::hashes::hash160;
24use bitcoin::secp256k1::XOnlyPublicKey;
25use bitcoin::util::taproot::{ControlBlock, LeafVersion, TapLeafHash};
26use bitcoin::{LockTime, Sequence};
27use sync::Arc;
28
29use super::context::SigType;
30use crate::prelude::*;
31use crate::util::witness_size;
32use crate::{Miniscript, MiniscriptKey, ScriptContext, Terminal, ToPublicKey};
33
34pub type Preimage32 = [u8; 32];
36pub trait Satisfier<Pk: MiniscriptKey + ToPublicKey> {
41 fn lookup_ecdsa_sig(&self, _: &Pk) -> Option<bitcoin::EcdsaSig> {
43 None
44 }
45
46 fn lookup_tap_key_spend_sig(&self) -> Option<bitcoin::SchnorrSig> {
48 None
49 }
50
51 fn lookup_tap_leaf_script_sig(&self, _: &Pk, _: &TapLeafHash) -> Option<bitcoin::SchnorrSig> {
53 None
54 }
55
56 fn lookup_tap_control_block_map(
58 &self,
59 ) -> Option<&BTreeMap<ControlBlock, (bitcoin::Script, LeafVersion)>> {
60 None
61 }
62
63 fn lookup_raw_pkh_pk(&self, _: &hash160::Hash) -> Option<bitcoin::PublicKey> {
65 None
66 }
67
68 fn lookup_raw_pkh_x_only_pk(&self, _: &hash160::Hash) -> Option<XOnlyPublicKey> {
70 None
71 }
72
73 fn lookup_raw_pkh_ecdsa_sig(
78 &self,
79 _: &hash160::Hash,
80 ) -> Option<(bitcoin::PublicKey, bitcoin::EcdsaSig)> {
81 None
82 }
83
84 fn lookup_raw_pkh_tap_leaf_script_sig(
89 &self,
90 _: &(hash160::Hash, TapLeafHash),
91 ) -> Option<(XOnlyPublicKey, bitcoin::SchnorrSig)> {
92 None
93 }
94
95 fn lookup_sha256(&self, _: &Pk::Sha256) -> Option<Preimage32> {
97 None
98 }
99
100 fn lookup_hash256(&self, _: &Pk::Hash256) -> Option<Preimage32> {
102 None
103 }
104
105 fn lookup_ripemd160(&self, _: &Pk::Ripemd160) -> Option<Preimage32> {
107 None
108 }
109
110 fn lookup_hash160(&self, _: &Pk::Hash160) -> Option<Preimage32> {
112 None
113 }
114
115 fn check_older(&self, _: Sequence) -> bool {
117 false
118 }
119
120 fn check_after(&self, _: LockTime) -> bool {
122 false
123 }
124}
125
126impl<Pk: MiniscriptKey + ToPublicKey> Satisfier<Pk> for () {}
128
129impl<Pk: MiniscriptKey + ToPublicKey> Satisfier<Pk> for Sequence {
130 fn check_older(&self, n: Sequence) -> bool {
131 if !self.is_relative_lock_time() {
132 return false;
133 }
134
135 const SEQUENCE_LOCKTIME_MASK: u32 = 0x0000ffff;
140 const SEQUENCE_LOCKTIME_TYPE_FLAG: u32 = 0x00400000;
141
142 let mask = SEQUENCE_LOCKTIME_MASK | SEQUENCE_LOCKTIME_TYPE_FLAG;
143 let masked_n = n.to_consensus_u32() & mask;
144 let masked_seq = self.to_consensus_u32() & mask;
145 if masked_n < SEQUENCE_LOCKTIME_TYPE_FLAG && masked_seq >= SEQUENCE_LOCKTIME_TYPE_FLAG {
146 false
147 } else {
148 masked_n <= masked_seq
149 }
150 }
151}
152
153impl<Pk: MiniscriptKey + ToPublicKey> Satisfier<Pk> for LockTime {
154 fn check_after(&self, n: LockTime) -> bool {
155 use LockTime::*;
156
157 match (n, *self) {
158 (Blocks(n), Blocks(lock_time)) => n <= lock_time,
159 (Seconds(n), Seconds(lock_time)) => n <= lock_time,
160 _ => false, }
162 }
163}
164impl<Pk: MiniscriptKey + ToPublicKey> Satisfier<Pk> for HashMap<Pk, bitcoin::EcdsaSig> {
165 fn lookup_ecdsa_sig(&self, key: &Pk) -> Option<bitcoin::EcdsaSig> {
166 self.get(key).copied()
167 }
168}
169
170impl<Pk: MiniscriptKey + ToPublicKey> Satisfier<Pk>
171 for HashMap<(Pk, TapLeafHash), bitcoin::SchnorrSig>
172{
173 fn lookup_tap_leaf_script_sig(&self, key: &Pk, h: &TapLeafHash) -> Option<bitcoin::SchnorrSig> {
174 self.get(&(key.clone(), *h)).copied()
179 }
180}
181
182impl<Pk: MiniscriptKey + ToPublicKey> Satisfier<Pk>
183 for HashMap<hash160::Hash, (Pk, bitcoin::EcdsaSig)>
184where
185 Pk: MiniscriptKey + ToPublicKey,
186{
187 fn lookup_ecdsa_sig(&self, key: &Pk) -> Option<bitcoin::EcdsaSig> {
188 self.get(&key.to_pubkeyhash(SigType::Ecdsa)).map(|x| x.1)
189 }
190
191 fn lookup_raw_pkh_pk(&self, pk_hash: &hash160::Hash) -> Option<bitcoin::PublicKey> {
192 self.get(pk_hash).map(|x| x.0.to_public_key())
193 }
194
195 fn lookup_raw_pkh_ecdsa_sig(
196 &self,
197 pk_hash: &hash160::Hash,
198 ) -> Option<(bitcoin::PublicKey, bitcoin::EcdsaSig)> {
199 self.get(pk_hash)
200 .map(|&(ref pk, sig)| (pk.to_public_key(), sig))
201 }
202}
203
204impl<Pk: MiniscriptKey + ToPublicKey> Satisfier<Pk>
205 for HashMap<(hash160::Hash, TapLeafHash), (Pk, bitcoin::SchnorrSig)>
206where
207 Pk: MiniscriptKey + ToPublicKey,
208{
209 fn lookup_tap_leaf_script_sig(&self, key: &Pk, h: &TapLeafHash) -> Option<bitcoin::SchnorrSig> {
210 self.get(&(key.to_pubkeyhash(SigType::Schnorr), *h))
211 .map(|x| x.1)
212 }
213
214 fn lookup_raw_pkh_tap_leaf_script_sig(
215 &self,
216 pk_hash: &(hash160::Hash, TapLeafHash),
217 ) -> Option<(XOnlyPublicKey, bitcoin::SchnorrSig)> {
218 self.get(pk_hash)
219 .map(|&(ref pk, sig)| (pk.to_x_only_pubkey(), sig))
220 }
221}
222
223impl<'a, Pk: MiniscriptKey + ToPublicKey, S: Satisfier<Pk>> Satisfier<Pk> for &'a S {
224 fn lookup_ecdsa_sig(&self, p: &Pk) -> Option<bitcoin::EcdsaSig> {
225 (**self).lookup_ecdsa_sig(p)
226 }
227
228 fn lookup_tap_leaf_script_sig(&self, p: &Pk, h: &TapLeafHash) -> Option<bitcoin::SchnorrSig> {
229 (**self).lookup_tap_leaf_script_sig(p, h)
230 }
231
232 fn lookup_raw_pkh_pk(&self, pkh: &hash160::Hash) -> Option<bitcoin::PublicKey> {
233 (**self).lookup_raw_pkh_pk(pkh)
234 }
235
236 fn lookup_raw_pkh_x_only_pk(&self, pkh: &hash160::Hash) -> Option<XOnlyPublicKey> {
237 (**self).lookup_raw_pkh_x_only_pk(pkh)
238 }
239
240 fn lookup_raw_pkh_ecdsa_sig(
241 &self,
242 pkh: &hash160::Hash,
243 ) -> Option<(bitcoin::PublicKey, bitcoin::EcdsaSig)> {
244 (**self).lookup_raw_pkh_ecdsa_sig(pkh)
245 }
246
247 fn lookup_tap_key_spend_sig(&self) -> Option<bitcoin::SchnorrSig> {
248 (**self).lookup_tap_key_spend_sig()
249 }
250
251 fn lookup_raw_pkh_tap_leaf_script_sig(
252 &self,
253 pkh: &(hash160::Hash, TapLeafHash),
254 ) -> Option<(XOnlyPublicKey, bitcoin::SchnorrSig)> {
255 (**self).lookup_raw_pkh_tap_leaf_script_sig(pkh)
256 }
257
258 fn lookup_tap_control_block_map(
259 &self,
260 ) -> Option<&BTreeMap<ControlBlock, (bitcoin::Script, LeafVersion)>> {
261 (**self).lookup_tap_control_block_map()
262 }
263
264 fn lookup_sha256(&self, h: &Pk::Sha256) -> Option<Preimage32> {
265 (**self).lookup_sha256(h)
266 }
267
268 fn lookup_hash256(&self, h: &Pk::Hash256) -> Option<Preimage32> {
269 (**self).lookup_hash256(h)
270 }
271
272 fn lookup_ripemd160(&self, h: &Pk::Ripemd160) -> Option<Preimage32> {
273 (**self).lookup_ripemd160(h)
274 }
275
276 fn lookup_hash160(&self, h: &Pk::Hash160) -> Option<Preimage32> {
277 (**self).lookup_hash160(h)
278 }
279
280 fn check_older(&self, t: Sequence) -> bool {
281 (**self).check_older(t)
282 }
283
284 fn check_after(&self, n: LockTime) -> bool {
285 (**self).check_after(n)
286 }
287}
288
289impl<'a, Pk: MiniscriptKey + ToPublicKey, S: Satisfier<Pk>> Satisfier<Pk> for &'a mut S {
290 fn lookup_ecdsa_sig(&self, p: &Pk) -> Option<bitcoin::EcdsaSig> {
291 (**self).lookup_ecdsa_sig(p)
292 }
293
294 fn lookup_tap_leaf_script_sig(&self, p: &Pk, h: &TapLeafHash) -> Option<bitcoin::SchnorrSig> {
295 (**self).lookup_tap_leaf_script_sig(p, h)
296 }
297
298 fn lookup_tap_key_spend_sig(&self) -> Option<bitcoin::SchnorrSig> {
299 (**self).lookup_tap_key_spend_sig()
300 }
301
302 fn lookup_raw_pkh_pk(&self, pkh: &hash160::Hash) -> Option<bitcoin::PublicKey> {
303 (**self).lookup_raw_pkh_pk(pkh)
304 }
305
306 fn lookup_raw_pkh_x_only_pk(&self, pkh: &hash160::Hash) -> Option<XOnlyPublicKey> {
307 (**self).lookup_raw_pkh_x_only_pk(pkh)
308 }
309
310 fn lookup_raw_pkh_ecdsa_sig(
311 &self,
312 pkh: &hash160::Hash,
313 ) -> Option<(bitcoin::PublicKey, bitcoin::EcdsaSig)> {
314 (**self).lookup_raw_pkh_ecdsa_sig(pkh)
315 }
316
317 fn lookup_raw_pkh_tap_leaf_script_sig(
318 &self,
319 pkh: &(hash160::Hash, TapLeafHash),
320 ) -> Option<(XOnlyPublicKey, bitcoin::SchnorrSig)> {
321 (**self).lookup_raw_pkh_tap_leaf_script_sig(pkh)
322 }
323
324 fn lookup_tap_control_block_map(
325 &self,
326 ) -> Option<&BTreeMap<ControlBlock, (bitcoin::Script, LeafVersion)>> {
327 (**self).lookup_tap_control_block_map()
328 }
329
330 fn lookup_sha256(&self, h: &Pk::Sha256) -> Option<Preimage32> {
331 (**self).lookup_sha256(h)
332 }
333
334 fn lookup_hash256(&self, h: &Pk::Hash256) -> Option<Preimage32> {
335 (**self).lookup_hash256(h)
336 }
337
338 fn lookup_ripemd160(&self, h: &Pk::Ripemd160) -> Option<Preimage32> {
339 (**self).lookup_ripemd160(h)
340 }
341
342 fn lookup_hash160(&self, h: &Pk::Hash160) -> Option<Preimage32> {
343 (**self).lookup_hash160(h)
344 }
345
346 fn check_older(&self, t: Sequence) -> bool {
347 (**self).check_older(t)
348 }
349
350 fn check_after(&self, n: LockTime) -> bool {
351 (**self).check_after(n)
352 }
353}
354
355macro_rules! impl_tuple_satisfier {
356 ($($ty:ident),*) => {
357 #[allow(non_snake_case)]
358 impl<$($ty,)* Pk> Satisfier<Pk> for ($($ty,)*)
359 where
360 Pk: MiniscriptKey + ToPublicKey,
361 $($ty: Satisfier< Pk>,)*
362 {
363 fn lookup_ecdsa_sig(&self, key: &Pk) -> Option<bitcoin::EcdsaSig> {
364 let &($(ref $ty,)*) = self;
365 $(
366 if let Some(result) = $ty.lookup_ecdsa_sig(key) {
367 return Some(result);
368 }
369 )*
370 None
371 }
372
373 fn lookup_tap_key_spend_sig(&self) -> Option<bitcoin::SchnorrSig> {
374 let &($(ref $ty,)*) = self;
375 $(
376 if let Some(result) = $ty.lookup_tap_key_spend_sig() {
377 return Some(result);
378 }
379 )*
380 None
381 }
382
383 fn lookup_tap_leaf_script_sig(&self, key: &Pk, h: &TapLeafHash) -> Option<bitcoin::SchnorrSig> {
384 let &($(ref $ty,)*) = self;
385 $(
386 if let Some(result) = $ty.lookup_tap_leaf_script_sig(key, h) {
387 return Some(result);
388 }
389 )*
390 None
391 }
392
393 fn lookup_raw_pkh_ecdsa_sig(
394 &self,
395 key_hash: &hash160::Hash,
396 ) -> Option<(bitcoin::PublicKey, bitcoin::EcdsaSig)> {
397 let &($(ref $ty,)*) = self;
398 $(
399 if let Some(result) = $ty.lookup_raw_pkh_ecdsa_sig(key_hash) {
400 return Some(result);
401 }
402 )*
403 None
404 }
405
406 fn lookup_raw_pkh_tap_leaf_script_sig(
407 &self,
408 key_hash: &(hash160::Hash, TapLeafHash),
409 ) -> Option<(XOnlyPublicKey, bitcoin::SchnorrSig)> {
410 let &($(ref $ty,)*) = self;
411 $(
412 if let Some(result) = $ty.lookup_raw_pkh_tap_leaf_script_sig(key_hash) {
413 return Some(result);
414 }
415 )*
416 None
417 }
418
419 fn lookup_raw_pkh_pk(
420 &self,
421 key_hash: &hash160::Hash,
422 ) -> Option<bitcoin::PublicKey> {
423 let &($(ref $ty,)*) = self;
424 $(
425 if let Some(result) = $ty.lookup_raw_pkh_pk(key_hash) {
426 return Some(result);
427 }
428 )*
429 None
430 }
431
432 fn lookup_raw_pkh_x_only_pk(
433 &self,
434 key_hash: &hash160::Hash,
435 ) -> Option<XOnlyPublicKey> {
436 let &($(ref $ty,)*) = self;
437 $(
438 if let Some(result) = $ty.lookup_raw_pkh_x_only_pk(key_hash) {
439 return Some(result);
440 }
441 )*
442 None
443 }
444
445 fn lookup_tap_control_block_map(
446 &self,
447 ) -> Option<&BTreeMap<ControlBlock, (bitcoin::Script, LeafVersion)>> {
448 let &($(ref $ty,)*) = self;
449 $(
450 if let Some(result) = $ty.lookup_tap_control_block_map() {
451 return Some(result);
452 }
453 )*
454 None
455 }
456
457 fn lookup_sha256(&self, h: &Pk::Sha256) -> Option<Preimage32> {
458 let &($(ref $ty,)*) = self;
459 $(
460 if let Some(result) = $ty.lookup_sha256(h) {
461 return Some(result);
462 }
463 )*
464 None
465 }
466
467 fn lookup_hash256(&self, h: &Pk::Hash256) -> Option<Preimage32> {
468 let &($(ref $ty,)*) = self;
469 $(
470 if let Some(result) = $ty.lookup_hash256(h) {
471 return Some(result);
472 }
473 )*
474 None
475 }
476
477 fn lookup_ripemd160(&self, h: &Pk::Ripemd160) -> Option<Preimage32> {
478 let &($(ref $ty,)*) = self;
479 $(
480 if let Some(result) = $ty.lookup_ripemd160(h) {
481 return Some(result);
482 }
483 )*
484 None
485 }
486
487 fn lookup_hash160(&self, h: &Pk::Hash160) -> Option<Preimage32> {
488 let &($(ref $ty,)*) = self;
489 $(
490 if let Some(result) = $ty.lookup_hash160(h) {
491 return Some(result);
492 }
493 )*
494 None
495 }
496
497 fn check_older(&self, n: Sequence) -> bool {
498 let &($(ref $ty,)*) = self;
499 $(
500 if $ty.check_older(n) {
501 return true;
502 }
503 )*
504 false
505 }
506
507 fn check_after(&self, n: LockTime) -> bool {
508 let &($(ref $ty,)*) = self;
509 $(
510 if $ty.check_after(n) {
511 return true;
512 }
513 )*
514 false
515 }
516 }
517 }
518}
519
520impl_tuple_satisfier!(A);
521impl_tuple_satisfier!(A, B);
522impl_tuple_satisfier!(A, B, C);
523impl_tuple_satisfier!(A, B, C, D);
524impl_tuple_satisfier!(A, B, C, D, E);
525impl_tuple_satisfier!(A, B, C, D, E, F);
526impl_tuple_satisfier!(A, B, C, D, E, F, G);
527impl_tuple_satisfier!(A, B, C, D, E, F, G, H);
528
529#[derive(Clone, PartialEq, Eq, Debug)]
531pub enum Witness {
532 Stack(Vec<Vec<u8>>),
534 Unavailable,
537 Impossible,
540}
541
542impl PartialOrd for Witness {
543 fn partial_cmp(&self, other: &Self) -> Option<cmp::Ordering> {
544 Some(self.cmp(other))
545 }
546}
547
548impl Ord for Witness {
549 fn cmp(&self, other: &Self) -> cmp::Ordering {
550 match (self, other) {
551 (&Witness::Stack(ref v1), &Witness::Stack(ref v2)) => {
552 let w1 = witness_size(v1);
553 let w2 = witness_size(v2);
554 w1.cmp(&w2)
555 }
556 (&Witness::Stack(_), _) => cmp::Ordering::Less,
557 (_, &Witness::Stack(_)) => cmp::Ordering::Greater,
558 (&Witness::Impossible, &Witness::Unavailable) => cmp::Ordering::Less,
559 (&Witness::Unavailable, &Witness::Impossible) => cmp::Ordering::Greater,
560 (&Witness::Impossible, &Witness::Impossible) => cmp::Ordering::Equal,
561 (&Witness::Unavailable, &Witness::Unavailable) => cmp::Ordering::Equal,
562 }
563 }
564}
565
566impl Witness {
567 fn signature<Pk: ToPublicKey, S: Satisfier<Pk>, Ctx: ScriptContext>(
569 sat: S,
570 pk: &Pk,
571 leaf_hash: &TapLeafHash,
572 ) -> Self {
573 match Ctx::sig_type() {
574 super::context::SigType::Ecdsa => match sat.lookup_ecdsa_sig(pk) {
575 Some(sig) => Witness::Stack(vec![sig.to_vec()]),
576 None => Witness::Impossible,
578 },
579 super::context::SigType::Schnorr => match sat.lookup_tap_leaf_script_sig(pk, leaf_hash)
580 {
581 Some(sig) => Witness::Stack(vec![sig.to_vec()]),
582 None => Witness::Impossible,
584 },
585 }
586 }
587
588 fn pkh_public_key<Pk: ToPublicKey, S: Satisfier<Pk>, Ctx: ScriptContext>(
590 sat: S,
591 pkh: &hash160::Hash,
592 ) -> Self {
593 match Ctx::sig_type() {
596 SigType::Ecdsa => match sat.lookup_raw_pkh_pk(pkh) {
597 Some(pk) => Witness::Stack(vec![pk.to_bytes()]),
598 None => Witness::Unavailable,
599 },
600 SigType::Schnorr => match sat.lookup_raw_pkh_x_only_pk(pkh) {
601 Some(pk) => Witness::Stack(vec![pk.serialize().to_vec()]),
602 None => Witness::Unavailable,
603 },
604 }
605 }
606
607 fn pkh_signature<Pk: ToPublicKey, S: Satisfier<Pk>, Ctx: ScriptContext>(
609 sat: S,
610 pkh: &hash160::Hash,
611 leaf_hash: &TapLeafHash,
612 ) -> Self {
613 match Ctx::sig_type() {
614 SigType::Ecdsa => match sat.lookup_raw_pkh_ecdsa_sig(pkh) {
615 Some((pk, sig)) => {
616 Witness::Stack(vec![sig.to_vec(), pk.to_public_key().to_bytes()])
617 }
618 None => Witness::Impossible,
619 },
620 SigType::Schnorr => match sat.lookup_raw_pkh_tap_leaf_script_sig(&(*pkh, *leaf_hash)) {
621 Some((pk, sig)) => Witness::Stack(vec![
622 sig.to_vec(),
623 pk.to_x_only_pubkey().serialize().to_vec(),
624 ]),
625 None => Witness::Impossible,
626 },
627 }
628 }
629
630 fn ripemd160_preimage<Pk: ToPublicKey, S: Satisfier<Pk>>(sat: S, h: &Pk::Ripemd160) -> Self {
632 match sat.lookup_ripemd160(h) {
633 Some(pre) => Witness::Stack(vec![pre.to_vec()]),
634 None => Witness::Unavailable,
636 }
637 }
638
639 fn hash160_preimage<Pk: ToPublicKey, S: Satisfier<Pk>>(sat: S, h: &Pk::Hash160) -> Self {
641 match sat.lookup_hash160(h) {
642 Some(pre) => Witness::Stack(vec![pre.to_vec()]),
643 None => Witness::Unavailable,
645 }
646 }
647
648 fn sha256_preimage<Pk: ToPublicKey, S: Satisfier<Pk>>(sat: S, h: &Pk::Sha256) -> Self {
650 match sat.lookup_sha256(h) {
651 Some(pre) => Witness::Stack(vec![pre.to_vec()]),
652 None => Witness::Unavailable,
654 }
655 }
656
657 fn hash256_preimage<Pk: ToPublicKey, S: Satisfier<Pk>>(sat: S, h: &Pk::Hash256) -> Self {
659 match sat.lookup_hash256(h) {
660 Some(pre) => Witness::Stack(vec![pre.to_vec()]),
661 None => Witness::Unavailable,
663 }
664 }
665}
666
667impl Witness {
668 fn hash_dissatisfaction() -> Self {
670 Witness::Stack(vec![vec![0; 32]])
671 }
672
673 fn empty() -> Self {
675 Witness::Stack(vec![])
676 }
677
678 fn push_1() -> Self {
680 Witness::Stack(vec![vec![1]])
681 }
682
683 fn push_0() -> Self {
685 Witness::Stack(vec![vec![]])
686 }
687
688 fn combine(one: Self, two: Self) -> Self {
690 match (one, two) {
691 (Witness::Impossible, _) | (_, Witness::Impossible) => Witness::Impossible,
692 (Witness::Unavailable, _) | (_, Witness::Unavailable) => Witness::Unavailable,
693 (Witness::Stack(mut a), Witness::Stack(b)) => {
694 a.extend(b);
695 Witness::Stack(a)
696 }
697 }
698 }
699}
700
701#[derive(Clone, PartialEq, Eq, Debug)]
703pub struct Satisfaction {
704 pub stack: Witness,
706 pub has_sig: bool,
709}
710
711impl Satisfaction {
712 fn thresh<Pk, Ctx, Sat, F>(
714 k: usize,
715 subs: &[Arc<Miniscript<Pk, Ctx>>],
716 stfr: &Sat,
717 root_has_sig: bool,
718 leaf_hash: &TapLeafHash,
719 min_fn: &mut F,
720 ) -> Self
721 where
722 Pk: MiniscriptKey + ToPublicKey,
723 Ctx: ScriptContext,
724 Sat: Satisfier<Pk>,
725 F: FnMut(Satisfaction, Satisfaction) -> Satisfaction,
726 {
727 let mut sats = subs
728 .iter()
729 .map(|s| {
730 Self::satisfy_helper(
731 &s.node,
732 stfr,
733 root_has_sig,
734 leaf_hash,
735 min_fn,
736 &mut Self::thresh,
737 )
738 })
739 .collect::<Vec<_>>();
740 let mut ret_stack = subs
742 .iter()
743 .map(|s| {
744 Self::dissatisfy_helper(
745 &s.node,
746 stfr,
747 root_has_sig,
748 leaf_hash,
749 min_fn,
750 &mut Self::thresh,
751 )
752 })
753 .collect::<Vec<_>>();
754
755 let mut sat_indices = (0..subs.len()).collect::<Vec<_>>();
759 sat_indices.sort_by_key(|&i| {
760 let stack_weight = match (&sats[i].stack, &ret_stack[i].stack) {
761 (&Witness::Unavailable, _) | (&Witness::Impossible, _) => i64::MAX,
762 (_, &Witness::Unavailable) | (_, &Witness::Impossible) => i64::MIN,
765 (&Witness::Stack(ref s), &Witness::Stack(ref d)) => {
766 witness_size(s) as i64 - witness_size(d) as i64
767 }
768 };
769 let is_impossible = sats[i].stack == Witness::Impossible;
770 (is_impossible, sats[i].has_sig, stack_weight)
775 });
776
777 for i in 0..k {
778 mem::swap(&mut ret_stack[sat_indices[i]], &mut sats[sat_indices[i]]);
779 }
780
781 assert!(k > 0);
787 if sats[sat_indices[k - 1]].stack == Witness::Impossible {
788 Satisfaction {
789 stack: Witness::Impossible,
790 has_sig: false,
793 }
794 }
795 else if k < sat_indices.len()
805 && !sats[sat_indices[k]].has_sig
806 && sats[sat_indices[k]].stack != Witness::Impossible
807 {
808 for sat in &ret_stack {
813 assert!(!sat.has_sig);
814 }
815 Satisfaction {
816 stack: Witness::Unavailable,
817 has_sig: false,
818 }
819 } else {
820 Satisfaction {
822 has_sig: ret_stack.iter().any(|sat| sat.has_sig),
823 stack: ret_stack.into_iter().fold(Witness::empty(), |acc, next| {
824 Witness::combine(next.stack, acc)
825 }),
826 }
827 }
828 }
829
830 fn thresh_mall<Pk, Ctx, Sat, F>(
832 k: usize,
833 subs: &[Arc<Miniscript<Pk, Ctx>>],
834 stfr: &Sat,
835 root_has_sig: bool,
836 leaf_hash: &TapLeafHash,
837 min_fn: &mut F,
838 ) -> Self
839 where
840 Pk: MiniscriptKey + ToPublicKey,
841 Ctx: ScriptContext,
842 Sat: Satisfier<Pk>,
843 F: FnMut(Satisfaction, Satisfaction) -> Satisfaction,
844 {
845 let mut sats = subs
846 .iter()
847 .map(|s| {
848 Self::satisfy_helper(
849 &s.node,
850 stfr,
851 root_has_sig,
852 leaf_hash,
853 min_fn,
854 &mut Self::thresh_mall,
855 )
856 })
857 .collect::<Vec<_>>();
858 let mut ret_stack = subs
860 .iter()
861 .map(|s| {
862 Self::dissatisfy_helper(
863 &s.node,
864 stfr,
865 root_has_sig,
866 leaf_hash,
867 min_fn,
868 &mut Self::thresh_mall,
869 )
870 })
871 .collect::<Vec<_>>();
872
873 let mut sat_indices = (0..subs.len()).collect::<Vec<_>>();
877 sat_indices.sort_by_key(|&i| {
878 match (&sats[i].stack, &ret_stack[i].stack) {
880 (&Witness::Unavailable, _) | (&Witness::Impossible, _) => i64::MAX,
881 (_, &Witness::Unavailable) | (_, &Witness::Impossible) => i64::MIN,
883 (&Witness::Stack(ref s), &Witness::Stack(ref d)) => {
884 witness_size(s) as i64 - witness_size(d) as i64
885 }
886 }
887 });
888
889 for i in 0..k {
891 mem::swap(&mut ret_stack[sat_indices[i]], &mut sats[sat_indices[i]]);
892 }
893
894 Satisfaction {
897 has_sig: ret_stack.iter().any(|sat| sat.has_sig),
898 stack: ret_stack.into_iter().fold(Witness::empty(), |acc, next| {
899 Witness::combine(next.stack, acc)
900 }),
901 }
902 }
903
904 fn minimum(sat1: Self, sat2: Self) -> Self {
905 match (&sat1.stack, &sat2.stack) {
909 (&Witness::Impossible, _) => return sat2,
910 (_, &Witness::Impossible) => return sat1,
911 _ => {}
912 }
913 match (sat1.has_sig, sat2.has_sig) {
914 (false, false) => Satisfaction {
917 stack: Witness::Unavailable,
918 has_sig: false,
919 },
920 (false, true) => Satisfaction {
924 stack: sat1.stack,
925 has_sig: false,
926 },
927 (true, false) => Satisfaction {
928 stack: sat2.stack,
929 has_sig: false,
930 },
931 (true, true) => Satisfaction {
935 stack: cmp::min(sat1.stack, sat2.stack),
936 has_sig: true,
937 },
938 }
939 }
940
941 fn minimum_mall(sat1: Self, sat2: Self) -> Self {
943 match (&sat1.stack, &sat2.stack) {
944 (&Witness::Impossible, _) | (&Witness::Unavailable, _) => return sat2,
947 (_, &Witness::Impossible) | (_, &Witness::Unavailable) => return sat1,
948 _ => {}
949 }
950 Satisfaction {
951 stack: cmp::min(sat1.stack, sat2.stack),
952 has_sig: sat1.has_sig && sat2.has_sig,
955 }
956 }
957
958 fn satisfy_helper<Pk, Ctx, Sat, F, G>(
960 term: &Terminal<Pk, Ctx>,
961 stfr: &Sat,
962 root_has_sig: bool,
963 leaf_hash: &TapLeafHash,
964 min_fn: &mut F,
965 thresh_fn: &mut G,
966 ) -> Self
967 where
968 Pk: MiniscriptKey + ToPublicKey,
969 Ctx: ScriptContext,
970 Sat: Satisfier<Pk>,
971 F: FnMut(Satisfaction, Satisfaction) -> Satisfaction,
972 G: FnMut(
973 usize,
974 &[Arc<Miniscript<Pk, Ctx>>],
975 &Sat,
976 bool,
977 &TapLeafHash,
978 &mut F,
979 ) -> Satisfaction,
980 {
981 match *term {
982 Terminal::PkK(ref pk) => Satisfaction {
983 stack: Witness::signature::<_, _, Ctx>(stfr, pk, leaf_hash),
984 has_sig: true,
985 },
986 Terminal::PkH(ref pk) => {
987 let wit = Witness::signature::<_, _, Ctx>(stfr, pk, leaf_hash);
988 let pk_bytes = match Ctx::sig_type() {
989 SigType::Ecdsa => pk.to_public_key().to_bytes(),
990 SigType::Schnorr => pk.to_x_only_pubkey().serialize().to_vec(),
991 };
992 Satisfaction {
993 stack: Witness::combine(wit, Witness::Stack(vec![pk_bytes])),
994 has_sig: true,
995 }
996 }
997 Terminal::RawPkH(ref pkh) => Satisfaction {
998 stack: Witness::pkh_signature::<_, _, Ctx>(stfr, pkh, leaf_hash),
999 has_sig: true,
1000 },
1001 Terminal::After(t) => Satisfaction {
1002 stack: if stfr.check_after(t.into()) {
1003 Witness::empty()
1004 } else if root_has_sig {
1005 Witness::Impossible
1011 } else {
1012 Witness::Unavailable
1013 },
1014 has_sig: false,
1015 },
1016 Terminal::Older(t) => Satisfaction {
1017 stack: if stfr.check_older(t) {
1018 Witness::empty()
1019 } else if root_has_sig {
1020 Witness::Impossible
1026 } else {
1027 Witness::Unavailable
1028 },
1029
1030 has_sig: false,
1031 },
1032 Terminal::Ripemd160(ref h) => Satisfaction {
1033 stack: Witness::ripemd160_preimage(stfr, h),
1034 has_sig: false,
1035 },
1036 Terminal::Hash160(ref h) => Satisfaction {
1037 stack: Witness::hash160_preimage(stfr, h),
1038 has_sig: false,
1039 },
1040 Terminal::Sha256(ref h) => Satisfaction {
1041 stack: Witness::sha256_preimage(stfr, h),
1042 has_sig: false,
1043 },
1044 Terminal::Hash256(ref h) => Satisfaction {
1045 stack: Witness::hash256_preimage(stfr, h),
1046 has_sig: false,
1047 },
1048 Terminal::True => Satisfaction {
1049 stack: Witness::empty(),
1050 has_sig: false,
1051 },
1052 Terminal::False => Satisfaction {
1053 stack: Witness::Impossible,
1054 has_sig: false,
1055 },
1056 Terminal::Alt(ref sub)
1057 | Terminal::Swap(ref sub)
1058 | Terminal::Check(ref sub)
1059 | Terminal::Verify(ref sub)
1060 | Terminal::NonZero(ref sub)
1061 | Terminal::ZeroNotEqual(ref sub) => {
1062 Self::satisfy_helper(&sub.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn)
1063 }
1064 Terminal::DupIf(ref sub) => {
1065 let sat = Self::satisfy_helper(
1066 &sub.node,
1067 stfr,
1068 root_has_sig,
1069 leaf_hash,
1070 min_fn,
1071 thresh_fn,
1072 );
1073 Satisfaction {
1074 stack: Witness::combine(sat.stack, Witness::push_1()),
1075 has_sig: sat.has_sig,
1076 }
1077 }
1078 Terminal::AndV(ref l, ref r) | Terminal::AndB(ref l, ref r) => {
1079 let l_sat =
1080 Self::satisfy_helper(&l.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1081 let r_sat =
1082 Self::satisfy_helper(&r.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1083 Satisfaction {
1084 stack: Witness::combine(r_sat.stack, l_sat.stack),
1085 has_sig: l_sat.has_sig || r_sat.has_sig,
1086 }
1087 }
1088 Terminal::AndOr(ref a, ref b, ref c) => {
1089 let a_sat =
1090 Self::satisfy_helper(&a.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1091 let a_nsat = Self::dissatisfy_helper(
1092 &a.node,
1093 stfr,
1094 root_has_sig,
1095 leaf_hash,
1096 min_fn,
1097 thresh_fn,
1098 );
1099 let b_sat =
1100 Self::satisfy_helper(&b.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1101 let c_sat =
1102 Self::satisfy_helper(&c.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1103
1104 min_fn(
1105 Satisfaction {
1106 stack: Witness::combine(b_sat.stack, a_sat.stack),
1107 has_sig: a_sat.has_sig || b_sat.has_sig,
1108 },
1109 Satisfaction {
1110 stack: Witness::combine(c_sat.stack, a_nsat.stack),
1111 has_sig: a_nsat.has_sig || c_sat.has_sig,
1112 },
1113 )
1114 }
1115 Terminal::OrB(ref l, ref r) => {
1116 let l_sat =
1117 Self::satisfy_helper(&l.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1118 let r_sat =
1119 Self::satisfy_helper(&r.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1120 let l_nsat = Self::dissatisfy_helper(
1121 &l.node,
1122 stfr,
1123 root_has_sig,
1124 leaf_hash,
1125 min_fn,
1126 thresh_fn,
1127 );
1128 let r_nsat = Self::dissatisfy_helper(
1129 &r.node,
1130 stfr,
1131 root_has_sig,
1132 leaf_hash,
1133 min_fn,
1134 thresh_fn,
1135 );
1136
1137 assert!(!l_nsat.has_sig);
1138 assert!(!r_nsat.has_sig);
1139
1140 min_fn(
1141 Satisfaction {
1142 stack: Witness::combine(r_sat.stack, l_nsat.stack),
1143 has_sig: r_sat.has_sig,
1144 },
1145 Satisfaction {
1146 stack: Witness::combine(r_nsat.stack, l_sat.stack),
1147 has_sig: l_sat.has_sig,
1148 },
1149 )
1150 }
1151 Terminal::OrD(ref l, ref r) | Terminal::OrC(ref l, ref r) => {
1152 let l_sat =
1153 Self::satisfy_helper(&l.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1154 let r_sat =
1155 Self::satisfy_helper(&r.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1156 let l_nsat = Self::dissatisfy_helper(
1157 &l.node,
1158 stfr,
1159 root_has_sig,
1160 leaf_hash,
1161 min_fn,
1162 thresh_fn,
1163 );
1164
1165 assert!(!l_nsat.has_sig);
1166
1167 min_fn(
1168 l_sat,
1169 Satisfaction {
1170 stack: Witness::combine(r_sat.stack, l_nsat.stack),
1171 has_sig: r_sat.has_sig,
1172 },
1173 )
1174 }
1175 Terminal::OrI(ref l, ref r) => {
1176 let l_sat =
1177 Self::satisfy_helper(&l.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1178 let r_sat =
1179 Self::satisfy_helper(&r.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1180 min_fn(
1181 Satisfaction {
1182 stack: Witness::combine(l_sat.stack, Witness::push_1()),
1183 has_sig: l_sat.has_sig,
1184 },
1185 Satisfaction {
1186 stack: Witness::combine(r_sat.stack, Witness::push_0()),
1187 has_sig: r_sat.has_sig,
1188 },
1189 )
1190 }
1191 Terminal::Thresh(k, ref subs) => {
1192 thresh_fn(k, subs, stfr, root_has_sig, leaf_hash, min_fn)
1193 }
1194 Terminal::Multi(k, ref keys) => {
1195 let mut sig_count = 0;
1197 let mut sigs = Vec::with_capacity(k);
1198 for pk in keys {
1199 match Witness::signature::<_, _, Ctx>(stfr, pk, leaf_hash) {
1200 Witness::Stack(sig) => {
1201 sigs.push(sig);
1202 sig_count += 1;
1203 }
1204 Witness::Impossible => {}
1205 Witness::Unavailable => unreachable!(
1206 "Signature satisfaction without witness must be impossible"
1207 ),
1208 }
1209 }
1210
1211 if sig_count < k {
1212 Satisfaction {
1213 stack: Witness::Impossible,
1214 has_sig: false,
1215 }
1216 } else {
1217 for _ in 0..sig_count - k {
1219 let max_idx = sigs
1220 .iter()
1221 .enumerate()
1222 .max_by_key(|&(_, v)| v.len())
1223 .unwrap()
1224 .0;
1225 sigs[max_idx] = vec![];
1226 }
1227
1228 Satisfaction {
1229 stack: sigs.into_iter().fold(Witness::push_0(), |acc, sig| {
1230 Witness::combine(acc, Witness::Stack(sig))
1231 }),
1232 has_sig: true,
1233 }
1234 }
1235 }
1236 Terminal::MultiA(k, ref keys) => {
1237 let mut sig_count = 0;
1239 let mut sigs = vec![vec![vec![]]; keys.len()];
1240 for (i, pk) in keys.iter().rev().enumerate() {
1241 match Witness::signature::<_, _, Ctx>(stfr, pk, leaf_hash) {
1242 Witness::Stack(sig) => {
1243 sigs[i] = sig;
1244 sig_count += 1;
1245 if sig_count == k {
1250 break;
1251 }
1252 }
1253 Witness::Impossible => {}
1254 Witness::Unavailable => unreachable!(
1255 "Signature satisfaction without witness must be impossible"
1256 ),
1257 }
1258 }
1259
1260 if sig_count < k {
1261 Satisfaction {
1262 stack: Witness::Impossible,
1263 has_sig: false,
1264 }
1265 } else {
1266 Satisfaction {
1267 stack: sigs.into_iter().fold(Witness::empty(), |acc, sig| {
1268 Witness::combine(acc, Witness::Stack(sig))
1269 }),
1270 has_sig: true,
1271 }
1272 }
1273 }
1274 }
1275 }
1276
1277 fn dissatisfy_helper<Pk, Ctx, Sat, F, G>(
1279 term: &Terminal<Pk, Ctx>,
1280 stfr: &Sat,
1281 root_has_sig: bool,
1282 leaf_hash: &TapLeafHash,
1283 min_fn: &mut F,
1284 thresh_fn: &mut G,
1285 ) -> Self
1286 where
1287 Pk: MiniscriptKey + ToPublicKey,
1288 Ctx: ScriptContext,
1289 Sat: Satisfier<Pk>,
1290 F: FnMut(Satisfaction, Satisfaction) -> Satisfaction,
1291 G: FnMut(
1292 usize,
1293 &[Arc<Miniscript<Pk, Ctx>>],
1294 &Sat,
1295 bool,
1296 &TapLeafHash,
1297 &mut F,
1298 ) -> Satisfaction,
1299 {
1300 match *term {
1301 Terminal::PkK(..) => Satisfaction {
1302 stack: Witness::push_0(),
1303 has_sig: false,
1304 },
1305 Terminal::PkH(ref pk) => {
1306 let pk_bytes = match Ctx::sig_type() {
1307 SigType::Ecdsa => pk.to_public_key().to_bytes(),
1308 SigType::Schnorr => pk.to_x_only_pubkey().serialize().to_vec(),
1309 };
1310 Satisfaction {
1311 stack: Witness::combine(Witness::push_0(), Witness::Stack(vec![pk_bytes])),
1312 has_sig: false,
1313 }
1314 }
1315 Terminal::RawPkH(ref pkh) => Satisfaction {
1316 stack: Witness::combine(
1317 Witness::push_0(),
1318 Witness::pkh_public_key::<_, _, Ctx>(stfr, pkh),
1319 ),
1320 has_sig: false,
1321 },
1322 Terminal::False => Satisfaction {
1323 stack: Witness::empty(),
1324 has_sig: false,
1325 },
1326 Terminal::True => Satisfaction {
1327 stack: Witness::Impossible,
1328 has_sig: false,
1329 },
1330 Terminal::Older(_) => Satisfaction {
1331 stack: Witness::Impossible,
1332 has_sig: false,
1333 },
1334 Terminal::After(_) => Satisfaction {
1335 stack: Witness::Impossible,
1336 has_sig: false,
1337 },
1338 Terminal::Sha256(_)
1339 | Terminal::Hash256(_)
1340 | Terminal::Ripemd160(_)
1341 | Terminal::Hash160(_) => Satisfaction {
1342 stack: Witness::hash_dissatisfaction(),
1343 has_sig: false,
1344 },
1345 Terminal::Alt(ref sub)
1346 | Terminal::Swap(ref sub)
1347 | Terminal::Check(ref sub)
1348 | Terminal::ZeroNotEqual(ref sub) => {
1349 Self::dissatisfy_helper(&sub.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn)
1350 }
1351 Terminal::DupIf(_) | Terminal::NonZero(_) => Satisfaction {
1352 stack: Witness::push_0(),
1353 has_sig: false,
1354 },
1355 Terminal::Verify(_) => Satisfaction {
1356 stack: Witness::Impossible,
1357 has_sig: false,
1358 },
1359 Terminal::AndV(ref v, ref other) => {
1360 let vsat =
1361 Self::satisfy_helper(&v.node, stfr, root_has_sig, leaf_hash, min_fn, thresh_fn);
1362 let odissat = Self::dissatisfy_helper(
1363 &other.node,
1364 stfr,
1365 root_has_sig,
1366 leaf_hash,
1367 min_fn,
1368 thresh_fn,
1369 );
1370 Satisfaction {
1371 stack: Witness::combine(odissat.stack, vsat.stack),
1372 has_sig: vsat.has_sig || odissat.has_sig,
1373 }
1374 }
1375 Terminal::AndB(ref l, ref r)
1376 | Terminal::OrB(ref l, ref r)
1377 | Terminal::OrD(ref l, ref r)
1378 | Terminal::AndOr(ref l, _, ref r) => {
1379 let lnsat = Self::dissatisfy_helper(
1380 &l.node,
1381 stfr,
1382 root_has_sig,
1383 leaf_hash,
1384 min_fn,
1385 thresh_fn,
1386 );
1387 let rnsat = Self::dissatisfy_helper(
1388 &r.node,
1389 stfr,
1390 root_has_sig,
1391 leaf_hash,
1392 min_fn,
1393 thresh_fn,
1394 );
1395 Satisfaction {
1396 stack: Witness::combine(rnsat.stack, lnsat.stack),
1397 has_sig: rnsat.has_sig || lnsat.has_sig,
1398 }
1399 }
1400 Terminal::OrC(..) => Satisfaction {
1401 stack: Witness::Impossible,
1402 has_sig: false,
1403 },
1404 Terminal::OrI(ref l, ref r) => {
1405 let lnsat = Self::dissatisfy_helper(
1406 &l.node,
1407 stfr,
1408 root_has_sig,
1409 leaf_hash,
1410 min_fn,
1411 thresh_fn,
1412 );
1413 let dissat_1 = Satisfaction {
1414 stack: Witness::combine(lnsat.stack, Witness::push_1()),
1415 has_sig: lnsat.has_sig,
1416 };
1417
1418 let rnsat = Self::dissatisfy_helper(
1419 &r.node,
1420 stfr,
1421 root_has_sig,
1422 leaf_hash,
1423 min_fn,
1424 thresh_fn,
1425 );
1426 let dissat_2 = Satisfaction {
1427 stack: Witness::combine(rnsat.stack, Witness::push_0()),
1428 has_sig: rnsat.has_sig,
1429 };
1430
1431 Satisfaction::minimum_mall(dissat_1, dissat_2)
1433 }
1434 Terminal::Thresh(_, ref subs) => Satisfaction {
1435 stack: subs.iter().fold(Witness::empty(), |acc, sub| {
1436 let nsat = Self::dissatisfy_helper(
1437 &sub.node,
1438 stfr,
1439 root_has_sig,
1440 leaf_hash,
1441 min_fn,
1442 thresh_fn,
1443 );
1444 assert!(!nsat.has_sig);
1445 Witness::combine(nsat.stack, acc)
1446 }),
1447 has_sig: false,
1448 },
1449 Terminal::Multi(k, _) => Satisfaction {
1450 stack: Witness::Stack(vec![vec![]; k + 1]),
1451 has_sig: false,
1452 },
1453 Terminal::MultiA(_, ref pks) => Satisfaction {
1454 stack: Witness::Stack(vec![vec![]; pks.len()]),
1455 has_sig: false,
1456 },
1457 }
1458 }
1459
1460 pub(super) fn satisfy<
1462 Pk: MiniscriptKey + ToPublicKey,
1463 Ctx: ScriptContext,
1464 Sat: Satisfier<Pk>,
1465 >(
1466 term: &Terminal<Pk, Ctx>,
1467 stfr: &Sat,
1468 root_has_sig: bool,
1469 leaf_hash: &TapLeafHash,
1470 ) -> Self {
1471 Self::satisfy_helper(
1472 term,
1473 stfr,
1474 root_has_sig,
1475 leaf_hash,
1476 &mut Satisfaction::minimum,
1477 &mut Satisfaction::thresh,
1478 )
1479 }
1480
1481 pub(super) fn satisfy_mall<
1483 Pk: MiniscriptKey + ToPublicKey,
1484 Ctx: ScriptContext,
1485 Sat: Satisfier<Pk>,
1486 >(
1487 term: &Terminal<Pk, Ctx>,
1488 stfr: &Sat,
1489 root_has_sig: bool,
1490 leaf_hash: &TapLeafHash,
1491 ) -> Self {
1492 Self::satisfy_helper(
1493 term,
1494 stfr,
1495 root_has_sig,
1496 leaf_hash,
1497 &mut Satisfaction::minimum_mall,
1498 &mut Satisfaction::thresh_mall,
1499 )
1500 }
1501}