simplicity/policy/
sighash.rs

1// SPDX-License-Identifier: CC0-1.0
2
3use std::borrow::Borrow;
4use std::ops::Deref;
5
6use hashes::sha256;
7
8use crate::jet::elements::ElementsUtxo;
9use crate::Cmr;
10
11pub struct SighashCache<T: Deref<Target = elements::Transaction>> {
12    tx: T,
13    fallback: elements::sighash::SighashCache<T>,
14}
15
16impl<T: Deref<Target = elements::Transaction> + Clone> SighashCache<T> {
17    pub fn new(tx: T) -> Self {
18        Self {
19            tx: tx.clone(),
20            fallback: elements::sighash::SighashCache::new(tx),
21        }
22    }
23
24    pub fn taproot_key_spend_signature_hash<O>(
25        &mut self,
26        input_index: usize,
27        prevouts: &elements::sighash::Prevouts<O>,
28        sighash_type: elements::sighash::SchnorrSighashType,
29        genesis_hash: elements::BlockHash,
30    ) -> Result<elements::taproot::TapSighashHash, elements::sighash::Error>
31    where
32        O: Borrow<elements::TxOut>,
33    {
34        self.fallback.taproot_key_spend_signature_hash(
35            input_index,
36            prevouts,
37            sighash_type,
38            genesis_hash,
39        )
40    }
41
42    pub fn taproot_script_spend_signature_hash<S, O>(
43        &mut self,
44        input_index: usize,
45        prevouts: &elements::sighash::Prevouts<O>,
46        leaf_hash: S,
47        sighash_type: elements::sighash::SchnorrSighashType,
48        genesis_hash: elements::BlockHash,
49    ) -> Result<elements::taproot::TapSighashHash, elements::sighash::Error>
50    where
51        S: Into<elements::taproot::TapLeafHash>,
52        O: Borrow<elements::TxOut>,
53    {
54        self.fallback.taproot_script_spend_signature_hash(
55            input_index,
56            prevouts,
57            leaf_hash,
58            sighash_type,
59            genesis_hash,
60        )
61    }
62
63    pub fn simplicity_spend_signature_hash<O>(
64        &mut self,
65        input_index: usize,
66        prevouts: &elements::sighash::Prevouts<O>,
67        script_cmr: Cmr,
68        control_block: elements::taproot::ControlBlock,
69        genesis_hash: elements::BlockHash,
70    ) -> Result<sha256::Hash, elements::sighash::Error>
71    where
72        O: Borrow<elements::TxOut>,
73    {
74        let all = match prevouts {
75            elements::sighash::Prevouts::All(prevouts) => *prevouts,
76            _ => return Err(elements::sighash::Error::PrevoutKind),
77        };
78        let utxos: Vec<_> = all
79            .iter()
80            .map(|o| ElementsUtxo::from(O::borrow(o).clone()))
81            .collect();
82
83        let simplicity_env = crate::jet::elements::ElementsEnv::new(
84            self.tx.clone(),
85            utxos,
86            input_index as u32,
87            script_cmr,
88            control_block,
89            None,
90            genesis_hash,
91        );
92        let simplicity_sighash = simplicity_env.c_tx_env().sighash_all();
93
94        Ok(simplicity_sighash)
95    }
96}