X-Git-Url: http://git.bitcoin.ninja/index.cgi?a=blobdiff_plain;f=lightning%2Fsrc%2Fln%2Fchannelmonitor.rs;h=6bddd302ffc64163e2fb76944bc60df7b76f7764;hb=eff8af21103e43f763cb10ae6a75c1543a2d4068;hp=5241d97d4fe0646bf165ea5b5c74630a1d4d0911;hpb=ddd85fb55023ac7fea1c1a7ae4748b2b795dff61;p=rust-lightning diff --git a/lightning/src/ln/channelmonitor.rs b/lightning/src/ln/channelmonitor.rs index 5241d97d..6bddd302 100644 --- a/lightning/src/ln/channelmonitor.rs +++ b/lightning/src/ln/channelmonitor.rs @@ -19,14 +19,14 @@ use bitcoin::blockdata::opcodes; use bitcoin::consensus::encode; use bitcoin::util::hash::BitcoinHash; -use bitcoin_hashes::Hash; -use bitcoin_hashes::sha256::Hash as Sha256; -use bitcoin_hashes::hash160::Hash as Hash160; -use bitcoin_hashes::sha256d::Hash as Sha256dHash; +use bitcoin::hashes::Hash; +use bitcoin::hashes::sha256::Hash as Sha256; +use bitcoin::hashes::hash160::Hash as Hash160; +use bitcoin::hashes::sha256d::Hash as Sha256dHash; -use secp256k1::{Secp256k1,Signature}; -use secp256k1::key::{SecretKey,PublicKey}; -use secp256k1; +use bitcoin::secp256k1::{Secp256k1,Signature}; +use bitcoin::secp256k1::key::{SecretKey,PublicKey}; +use bitcoin::secp256k1; use ln::msgs::DecodeError; use ln::chan_utils; @@ -442,7 +442,9 @@ pub(crate) enum InputMaterial { preimage: Option, amount: u64, }, - Funding {} + Funding { + funding_redeemscript: Script, + } } impl Writeable for InputMaterial { @@ -469,8 +471,9 @@ impl Writeable for InputMaterial { preimage.write(writer)?; writer.write_all(&byte_utils::be64_to_array(*amount))?; }, - &InputMaterial::Funding {} => { + &InputMaterial::Funding { ref funding_redeemscript } => { writer.write_all(&[3; 1])?; + funding_redeemscript.write(writer)?; } } Ok(()) @@ -517,7 +520,9 @@ impl Readable for InputMaterial { } }, 3 => { - InputMaterial::Funding {} + InputMaterial::Funding { + funding_redeemscript: Readable::read(reader)?, + } } _ => return Err(DecodeError::InvalidValue), }; @@ -1061,8 +1066,8 @@ impl ChannelMonitor { let mut onchain_tx_handler = OnchainTxHandler::new(destination_script.clone(), keys.clone(), their_to_self_delay, logger.clone()); - let local_tx_sequence = initial_local_commitment_tx.without_valid_witness().input[0].sequence as u64; - let local_tx_locktime = initial_local_commitment_tx.without_valid_witness().lock_time as u64; + let local_tx_sequence = initial_local_commitment_tx.unsigned_tx.input[0].sequence as u64; + let local_tx_locktime = initial_local_commitment_tx.unsigned_tx.lock_time as u64; let local_commitment_tx = LocalSignedTx { txid: initial_local_commitment_tx.txid(), revocation_key: initial_local_commitment_tx.local_keys.revocation_key, @@ -1244,8 +1249,8 @@ impl ChannelMonitor { return Err(MonitorUpdateError("A local commitment tx has already been signed, no new local commitment txn can be sent to our counterparty")); } let txid = commitment_tx.txid(); - let sequence = commitment_tx.without_valid_witness().input[0].sequence as u64; - let locktime = commitment_tx.without_valid_witness().lock_time as u64; + let sequence = commitment_tx.unsigned_tx.input[0].sequence as u64; + let locktime = commitment_tx.unsigned_tx.lock_time as u64; let mut new_local_commitment_tx = LocalSignedTx { txid, revocation_key: commitment_tx.local_keys.revocation_key, @@ -1672,8 +1677,18 @@ impl ChannelMonitor { for &(ref htlc, _, _) in local_tx.htlc_outputs.iter() { if let Some(transaction_output_index) = htlc.transaction_output_index { - let preimage = if let Some(preimage) = self.payment_preimages.get(&htlc.payment_hash) { Some(*preimage) } else { None }; - claim_requests.push(ClaimRequest { absolute_timelock: ::std::u32::MAX, aggregable: false, outpoint: BitcoinOutPoint { txid: local_tx.txid, vout: transaction_output_index as u32 }, witness_data: InputMaterial::LocalHTLC { preimage, amount: htlc.amount_msat / 1000 }}); + claim_requests.push(ClaimRequest { absolute_timelock: ::std::u32::MAX, aggregable: false, outpoint: BitcoinOutPoint { txid: local_tx.txid, vout: transaction_output_index as u32 }, + witness_data: InputMaterial::LocalHTLC { + preimage: if !htlc.offered { + if let Some(preimage) = self.payment_preimages.get(&htlc.payment_hash) { + Some(preimage.clone()) + } else { + // We can't build an HTLC-Success transaction without the preimage + continue; + } + } else { None }, + amount: htlc.amount_msat, + }}); watch_outputs.push(commitment_tx.output[transaction_output_index as usize].clone()); } } @@ -1771,13 +1786,19 @@ impl ChannelMonitor { pub fn get_latest_local_commitment_txn(&mut self) -> Vec { log_trace!(self, "Getting signed latest local commitment transaction!"); self.local_tx_signed = true; - if let Some(commitment_tx) = self.onchain_tx_handler.get_fully_signed_local_tx() { + if let Some(commitment_tx) = self.onchain_tx_handler.get_fully_signed_local_tx(&self.funding_redeemscript) { let txid = commitment_tx.txid(); let mut res = vec![commitment_tx]; for htlc in self.current_local_commitment_tx.htlc_outputs.iter() { - if let Some(htlc_index) = htlc.0.transaction_output_index { - let preimage = if let Some(preimage) = self.payment_preimages.get(&htlc.0.payment_hash) { Some(*preimage) } else { None }; - if let Some(htlc_tx) = self.onchain_tx_handler.get_fully_signed_htlc_tx(txid, htlc_index, preimage) { + if let Some(vout) = htlc.0.transaction_output_index { + let preimage = if !htlc.0.offered { + if let Some(preimage) = self.payment_preimages.get(&htlc.0.payment_hash) { Some(preimage.clone()) } else { + // We can't build an HTLC-Success transaction without the preimage + continue; + } + } else { None }; + if let Some(htlc_tx) = self.onchain_tx_handler.get_fully_signed_htlc_tx( + &::bitcoin::OutPoint { txid, vout }, &preimage) { res.push(htlc_tx); } } @@ -1795,13 +1816,19 @@ impl ChannelMonitor { #[cfg(test)] pub fn unsafe_get_latest_local_commitment_txn(&mut self) -> Vec { log_trace!(self, "Getting signed copy of latest local commitment transaction!"); - if let Some(commitment_tx) = self.onchain_tx_handler.get_fully_signed_copy_local_tx() { + if let Some(commitment_tx) = self.onchain_tx_handler.get_fully_signed_copy_local_tx(&self.funding_redeemscript) { let txid = commitment_tx.txid(); let mut res = vec![commitment_tx]; for htlc in self.current_local_commitment_tx.htlc_outputs.iter() { - if let Some(htlc_index) = htlc.0.transaction_output_index { - let preimage = if let Some(preimage) = self.payment_preimages.get(&htlc.0.payment_hash) { Some(*preimage) } else { None }; - if let Some(htlc_tx) = self.onchain_tx_handler.get_fully_signed_htlc_tx(txid, htlc_index, preimage) { + if let Some(vout) = htlc.0.transaction_output_index { + let preimage = if !htlc.0.offered { + if let Some(preimage) = self.payment_preimages.get(&htlc.0.payment_hash) { Some(preimage.clone()) } else { + // We can't build an HTLC-Success transaction without the preimage + continue; + } + } else { None }; + if let Some(htlc_tx) = self.onchain_tx_handler.unsafe_get_fully_signed_htlc_tx( + &::bitcoin::OutPoint { txid, vout }, &preimage) { res.push(htlc_tx); } } @@ -1873,10 +1900,10 @@ impl ChannelMonitor { } let should_broadcast = self.would_broadcast_at_height(height); if should_broadcast { - claimable_outpoints.push(ClaimRequest { absolute_timelock: height, aggregable: false, outpoint: BitcoinOutPoint { txid: self.funding_info.0.txid.clone(), vout: self.funding_info.0.index as u32 }, witness_data: InputMaterial::Funding {}}); + claimable_outpoints.push(ClaimRequest { absolute_timelock: height, aggregable: false, outpoint: BitcoinOutPoint { txid: self.funding_info.0.txid.clone(), vout: self.funding_info.0.index as u32 }, witness_data: InputMaterial::Funding { funding_redeemscript: self.funding_redeemscript.clone() }}); } if should_broadcast { - if let Some(commitment_tx) = self.onchain_tx_handler.get_fully_signed_local_tx() { + if let Some(commitment_tx) = self.onchain_tx_handler.get_fully_signed_local_tx(&self.funding_redeemscript) { let (mut new_outpoints, new_outputs, _) = self.broadcast_by_local_state(&commitment_tx, &self.current_local_commitment_tx); if !new_outputs.is_empty() { watch_outputs.push((self.current_local_commitment_tx.txid.clone(), new_outputs)); @@ -2491,10 +2518,10 @@ mod tests { use bitcoin::blockdata::transaction::{Transaction, TxIn, TxOut, SigHashType}; use bitcoin::blockdata::transaction::OutPoint as BitcoinOutPoint; use bitcoin::util::bip143; - use bitcoin_hashes::Hash; - use bitcoin_hashes::sha256::Hash as Sha256; - use bitcoin_hashes::sha256d::Hash as Sha256dHash; - use bitcoin_hashes::hex::FromHex; + use bitcoin::hashes::Hash; + use bitcoin::hashes::sha256::Hash as Sha256; + use bitcoin::hashes::sha256d::Hash as Sha256dHash; + use bitcoin::hashes::hex::FromHex; use hex; use chain::transaction::OutPoint; use ln::channelmanager::{PaymentPreimage, PaymentHash}; @@ -2503,8 +2530,8 @@ mod tests { use ln::chan_utils; use ln::chan_utils::{HTLCOutputInCommitment, LocalCommitmentTransaction}; use util::test_utils::TestLogger; - use secp256k1::key::{SecretKey,PublicKey}; - use secp256k1::Secp256k1; + use bitcoin::secp256k1::key::{SecretKey,PublicKey}; + use bitcoin::secp256k1::Secp256k1; use rand::{thread_rng,Rng}; use std::sync::Arc; use chain::keysinterface::InMemoryChannelKeys;