@@ -58,6 +58,7 @@ use hmac::{Hmac, Mac};
5858use num_bigint:: BigUint ;
5959use sha2:: Sha512 ;
6060use std:: fmt;
61+ use std:: num:: TryFromIntError ;
6162
6263/// The initial byte in a data-carrying taproot annex
6364pub const TAPROOT_ANNEX_DATA_CARRYING_TAG : u8 = 0 ;
@@ -104,7 +105,7 @@ pub trait Verifier {
104105 script_pubkey : & [ u8 ] ,
105106 amount : Option < i64 > ,
106107 tx_to : & [ u8 ] ,
107- input_index : u32 ,
108+ input_index : usize ,
108109 spent_outputs : & [ TxOut ] ,
109110 ) -> Result < ( ) , Error > ;
110111}
@@ -120,7 +121,7 @@ impl Verifier for DefaultVerifier {
120121 script_pubkey : & [ u8 ] ,
121122 amount : Option < i64 > ,
122123 tx_to : & [ u8 ] ,
123- input_index : u32 ,
124+ input_index : usize ,
124125 spent_outputs : & [ TxOut ] ,
125126 ) -> Result < ( ) , Error > {
126127 let mut outputs = Vec :: new ( ) ;
@@ -141,6 +142,10 @@ impl Verifier for DefaultVerifier {
141142 let tx_to = & bitcoinkernel:: Transaction :: try_from ( tx_to)
142143 . map_err ( |e| Error :: VerificationFailed ( e. to_string ( ) ) ) ?;
143144
145+ let input_index: u32 = input_index
146+ . try_into ( )
147+ . map_err ( |e : TryFromIntError | Error :: VerificationFailed ( e. to_string ( ) ) ) ?;
148+
144149 bitcoinkernel:: verify ( script_pubkey, amount, tx_to, input_index, None , & outputs)
145150 . map_err ( |e| Error :: VerificationFailed ( e. to_string ( ) ) ) ?;
146151
@@ -173,7 +178,7 @@ impl Verifier for DefaultVerifier {
173178/// Returns error if verification fails, key derivation fails, or signing fails
174179pub fn verify_and_sign < V : Verifier > (
175180 verifier : & V ,
176- input_index : u32 ,
181+ input_index : usize ,
177182 emulated_tx_to : & [ u8 ] ,
178183 actual_spent_outputs : & [ TxOut ] ,
179184 aux_rand : & [ u8 ; 32 ] ,
@@ -184,18 +189,18 @@ pub fn verify_and_sign<V: Verifier>(
184189 let mut tx: Transaction = deserialize ( emulated_tx_to) ?;
185190
186191 // Input index must be in bounds
187- if input_index as usize >= tx. input . len ( ) {
192+ if input_index >= tx. input . len ( ) || input_index >= actual_spent_outputs . len ( ) {
188193 return Err ( Error :: InputIndexOutOfBounds ) ;
189194 }
190195
191196 // Get the input amount
192- let amount = actual_spent_outputs[ input_index as usize ]
197+ let amount = actual_spent_outputs[ input_index]
193198 . value
194199 . to_signed ( ) ?
195200 . to_sat ( ) ;
196201
197202 // Must be script path spend
198- let input = tx. input [ input_index as usize ] . clone ( ) ;
203+ let input = tx. input [ input_index] . clone ( ) ;
199204 let ( Some ( control_block) , Some ( tapleaf) ) = (
200205 input. witness . taproot_control_block ( ) ,
201206 input. witness . taproot_leaf_script ( ) ,
@@ -232,7 +237,7 @@ pub fn verify_and_sign<V: Verifier>(
232237
233238 // Actual input scriptPubKey must match expected actual scriptPubKey
234239 let actual_address = Address :: p2tr ( & secp, internal_key, backup_merkle_root, Network :: Bitcoin ) ;
235- if actual_spent_outputs[ input_index as usize ] . script_pubkey != actual_address. script_pubkey ( ) {
240+ if actual_spent_outputs[ input_index] . script_pubkey != actual_address. script_pubkey ( ) {
236241 return Err ( Error :: UnexpectedInput ) ;
237242 }
238243
@@ -256,7 +261,7 @@ pub fn verify_and_sign<V: Verifier>(
256261 let mut sighash_cache = SighashCache :: new ( & tx) ;
257262 let sighash_bytes = sighash_cache
258263 . taproot_signature_hash (
259- input_index as usize ,
264+ input_index,
260265 & Prevouts :: All ( actual_spent_outputs) ,
261266 annex. clone ( ) ,
262267 None ,
@@ -287,7 +292,7 @@ pub fn verify_and_sign<V: Verifier>(
287292 if let Some ( annex) = annex {
288293 witness. push ( annex. as_bytes ( ) ) ;
289294 }
290- tx. input [ input_index as usize ] . witness = witness;
295+ tx. input [ input_index] . witness = witness;
291296
292297 Ok ( tx)
293298}
@@ -538,6 +543,18 @@ mod kernel_tests {
538543 ) ;
539544
540545 assert ! ( matches!( result, Err ( Error :: InputIndexOutOfBounds ) ) ) ;
546+
547+ let result = verify_and_sign (
548+ & DefaultVerifier ,
549+ 0 ,
550+ & serialize ( & create_test_transaction_single_input ( ) ) ,
551+ & [ ] ,
552+ & [ 1u8 ; 32 ] ,
553+ SecretKey :: from_slice ( & [ 1u8 ; 32 ] ) . unwrap ( ) ,
554+ None ,
555+ ) ;
556+
557+ assert ! ( matches!( result, Err ( Error :: InputIndexOutOfBounds ) ) ) ;
541558 }
542559
543560 #[ test]
0 commit comments