@@ -6501,8 +6501,7 @@ fn get_v2_channel_reserve_satoshis(channel_value_satoshis: u64, dust_limit_satos
65016501fn check_splice_contribution_sufficient(
65026502 contribution: &SpliceContribution, is_initiator: bool, funding_feerate: FeeRate,
65036503) -> Result<SignedAmount, String> {
6504- let contribution_amount = contribution.value();
6505- if contribution_amount < SignedAmount::ZERO {
6504+ if contribution.inputs().is_empty() {
65066505 let estimated_fee = Amount::from_sat(estimate_v2_funding_transaction_fee(
65076506 contribution.inputs(),
65086507 contribution.outputs(),
@@ -6511,20 +6510,25 @@ fn check_splice_contribution_sufficient(
65116510 funding_feerate.to_sat_per_kwu() as u32,
65126511 ));
65136512
6513+ let contribution_amount = contribution.net_value();
65146514 contribution_amount
65156515 .checked_sub(
65166516 estimated_fee.to_signed().expect("fees should never exceed Amount::MAX_MONEY"),
65176517 )
6518- .ok_or(format!("Our {contribution_amount} contribution plus the fee estimate exceeds the total bitcoin supply"))
6518+ .ok_or(format!(
6519+ "{estimated_fee} splice-out amount plus {} fee estimate exceeds the total bitcoin supply",
6520+ contribution_amount.unsigned_abs(),
6521+ ))
65196522 } else {
65206523 check_v2_funding_inputs_sufficient(
6521- contribution_amount.to_sat (),
6524+ contribution.value_added (),
65226525 contribution.inputs(),
6526+ contribution.outputs(),
65236527 is_initiator,
65246528 true,
65256529 funding_feerate.to_sat_per_kwu() as u32,
65266530 )
6527- .map(|_| contribution_amount )
6531+ .map(|_| contribution.net_value() )
65286532 }
65296533}
65306534
@@ -6583,16 +6587,16 @@ fn estimate_v2_funding_transaction_fee(
65836587/// Returns estimated (partial) fees as additional information
65846588#[rustfmt::skip]
65856589fn check_v2_funding_inputs_sufficient(
6586- contribution_amount: i64 , funding_inputs: &[FundingTxInput], is_initiator: bool ,
6587- is_splice: bool, funding_feerate_sat_per_1000_weight: u32,
6588- ) -> Result<u64 , String> {
6589- let estimated_fee = estimate_v2_funding_transaction_fee(
6590- funding_inputs, &[] , is_initiator, is_splice, funding_feerate_sat_per_1000_weight,
6591- );
6592-
6593- let mut total_input_sats = 0u64 ;
6590+ contributed_input_value: Amount , funding_inputs: &[FundingTxInput], outputs: &[TxOut] ,
6591+ is_initiator: bool, is_splice: bool, funding_feerate_sat_per_1000_weight: u32,
6592+ ) -> Result<Amount , String> {
6593+ let estimated_fee = Amount::from_sat( estimate_v2_funding_transaction_fee(
6594+ funding_inputs, outputs , is_initiator, is_splice, funding_feerate_sat_per_1000_weight,
6595+ )) ;
6596+
6597+ let mut total_input_value = Amount::ZERO ;
65946598 for FundingTxInput { utxo, .. } in funding_inputs.iter() {
6595- total_input_sats = total_input_sats .checked_add(utxo.output.value.to_sat() )
6599+ total_input_value = total_input_value .checked_add(utxo.output.value)
65966600 .ok_or("Sum of input values is greater than the total bitcoin supply")?;
65976601 }
65986602
@@ -6607,13 +6611,11 @@ fn check_v2_funding_inputs_sufficient(
66076611 // TODO(splicing): refine check including the fact wether a change will be added or not.
66086612 // Can be done once dual funding preparation is included.
66096613
6610- let minimal_input_amount_needed = contribution_amount.checked_add(estimated_fee as i64)
6611- .ok_or(format!("Our {contribution_amount} contribution plus the fee estimate exceeds the total bitcoin supply"))?;
6612- if i64::try_from(total_input_sats).map_err(|_| "Sum of input values is greater than the total bitcoin supply")?
6613- < minimal_input_amount_needed
6614- {
6614+ let minimal_input_amount_needed = contributed_input_value.checked_add(estimated_fee)
6615+ .ok_or(format!("{contributed_input_value} contribution plus {estimated_fee} fee estimate exceeds the total bitcoin supply"))?;
6616+ if total_input_value < minimal_input_amount_needed {
66156617 Err(format!(
6616- "Total input amount {total_input_sats } is lower than needed for contribution {contribution_amount }, considering fees of {estimated_fee}. Need more inputs.",
6618+ "Total input amount {total_input_value } is lower than needed for splice-in contribution {contributed_input_value }, considering fees of {estimated_fee}. Need more inputs.",
66176619 ))
66186620 } else {
66196621 Ok(estimated_fee)
@@ -6679,7 +6681,7 @@ impl FundingNegotiationContext {
66796681 };
66806682
66816683 // Optionally add change output
6682- let change_value_opt = if self.our_funding_contribution > SignedAmount::ZERO {
6684+ let change_value_opt = if ! self.our_funding_inputs.is_empty() {
66836685 match calculate_change_output_value(
66846686 &self,
66856687 self.shared_funding_input.is_some(),
@@ -12070,7 +12072,7 @@ where
1207012072 });
1207112073 }
1207212074
12073- let our_funding_contribution = contribution.value ();
12075+ let our_funding_contribution = contribution.net_value ();
1207412076 if our_funding_contribution == SignedAmount::ZERO {
1207512077 return Err(APIError::APIMisuseError {
1207612078 err: format!(
@@ -18525,6 +18527,13 @@ mod tests {
1852518527 FundingTxInput::new_p2wpkh(prevtx, 0).unwrap()
1852618528 }
1852718529
18530+ fn funding_output_sats(output_value_sats: u64) -> TxOut {
18531+ TxOut {
18532+ value: Amount::from_sat(output_value_sats),
18533+ script_pubkey: ScriptBuf::new_p2wpkh(&WPubkeyHash::all_zeros()),
18534+ }
18535+ }
18536+
1852818537 #[test]
1852918538 #[rustfmt::skip]
1853018539 fn test_check_v2_funding_inputs_sufficient() {
@@ -18535,16 +18544,83 @@ mod tests {
1853518544 let expected_fee = if cfg!(feature = "grind_signatures") { 2278 } else { 2284 };
1853618545 assert_eq!(
1853718546 check_v2_funding_inputs_sufficient(
18538- 220_000,
18547+ Amount::from_sat(220_000),
18548+ &[
18549+ funding_input_sats(200_000),
18550+ funding_input_sats(100_000),
18551+ ],
18552+ &[],
18553+ true,
18554+ true,
18555+ 2000,
18556+ ).unwrap(),
18557+ Amount::from_sat(expected_fee),
18558+ );
18559+ }
18560+
18561+ // Net splice-in
18562+ {
18563+ let expected_fee = if cfg!(feature = "grind_signatures") { 2526 } else { 2532 };
18564+ assert_eq!(
18565+ check_v2_funding_inputs_sufficient(
18566+ Amount::from_sat(220_000),
18567+ &[
18568+ funding_input_sats(200_000),
18569+ funding_input_sats(100_000),
18570+ ],
18571+ &[
18572+ funding_output_sats(200_000),
18573+ ],
18574+ true,
18575+ true,
18576+ 2000,
18577+ ).unwrap(),
18578+ Amount::from_sat(expected_fee),
18579+ );
18580+ }
18581+
18582+ // Net splice-out
18583+ {
18584+ let expected_fee = if cfg!(feature = "grind_signatures") { 2526 } else { 2532 };
18585+ assert_eq!(
18586+ check_v2_funding_inputs_sufficient(
18587+ Amount::from_sat(220_000),
1853918588 &[
1854018589 funding_input_sats(200_000),
1854118590 funding_input_sats(100_000),
1854218591 ],
18592+ &[
18593+ funding_output_sats(400_000),
18594+ ],
1854318595 true,
1854418596 true,
1854518597 2000,
1854618598 ).unwrap(),
18547- expected_fee,
18599+ Amount::from_sat(expected_fee),
18600+ );
18601+ }
18602+
18603+ // Net splice-out, inputs insufficient to cover fees
18604+ {
18605+ let expected_fee = if cfg!(feature = "grind_signatures") { 113670 } else { 113940 };
18606+ assert_eq!(
18607+ check_v2_funding_inputs_sufficient(
18608+ Amount::from_sat(220_000),
18609+ &[
18610+ funding_input_sats(200_000),
18611+ funding_input_sats(100_000),
18612+ ],
18613+ &[
18614+ funding_output_sats(400_000),
18615+ ],
18616+ true,
18617+ true,
18618+ 90000,
18619+ ),
18620+ Err(format!(
18621+ "Total input amount 0.00300000 BTC is lower than needed for splice-in contribution 0.00220000 BTC, considering fees of {}. Need more inputs.",
18622+ Amount::from_sat(expected_fee),
18623+ )),
1854818624 );
1854918625 }
1855018626
@@ -18553,17 +18629,18 @@ mod tests {
1855318629 let expected_fee = if cfg!(feature = "grind_signatures") { 1736 } else { 1740 };
1855418630 assert_eq!(
1855518631 check_v2_funding_inputs_sufficient(
18556- 220_000,
18632+ Amount::from_sat( 220_000) ,
1855718633 &[
1855818634 funding_input_sats(100_000),
1855918635 ],
18636+ &[],
1856018637 true,
1856118638 true,
1856218639 2000,
1856318640 ),
1856418641 Err(format!(
18565- "Total input amount 100000 is lower than needed for contribution 220000 , considering fees of {}. Need more inputs.",
18566- expected_fee,
18642+ "Total input amount 0.00100000 BTC is lower than needed for splice-in contribution 0.00220000 BTC , considering fees of {}. Need more inputs.",
18643+ Amount::from_sat( expected_fee) ,
1856718644 )),
1856818645 );
1856918646 }
@@ -18573,16 +18650,17 @@ mod tests {
1857318650 let expected_fee = if cfg!(feature = "grind_signatures") { 2278 } else { 2284 };
1857418651 assert_eq!(
1857518652 check_v2_funding_inputs_sufficient(
18576- (300_000 - expected_fee - 20) as i64 ,
18653+ Amount::from_sat (300_000 - expected_fee - 20),
1857718654 &[
1857818655 funding_input_sats(200_000),
1857918656 funding_input_sats(100_000),
1858018657 ],
18658+ &[],
1858118659 true,
1858218660 true,
1858318661 2000,
1858418662 ).unwrap(),
18585- expected_fee,
18663+ Amount::from_sat( expected_fee) ,
1858618664 );
1858718665 }
1858818666
@@ -18591,18 +18669,19 @@ mod tests {
1859118669 let expected_fee = if cfg!(feature = "grind_signatures") { 2506 } else { 2513 };
1859218670 assert_eq!(
1859318671 check_v2_funding_inputs_sufficient(
18594- 298032,
18672+ Amount::from_sat( 298032) ,
1859518673 &[
1859618674 funding_input_sats(200_000),
1859718675 funding_input_sats(100_000),
1859818676 ],
18677+ &[],
1859918678 true,
1860018679 true,
1860118680 2200,
1860218681 ),
1860318682 Err(format!(
18604- "Total input amount 300000 is lower than needed for contribution 298032 , considering fees of {}. Need more inputs.",
18605- expected_fee
18683+ "Total input amount 0.00300000 BTC is lower than needed for splice-in contribution 0.00298032 BTC , considering fees of {}. Need more inputs.",
18684+ Amount::from_sat( expected_fee),
1860618685 )),
1860718686 );
1860818687 }
@@ -18612,16 +18691,17 @@ mod tests {
1861218691 let expected_fee = if cfg!(feature = "grind_signatures") { 1084 } else { 1088 };
1861318692 assert_eq!(
1861418693 check_v2_funding_inputs_sufficient(
18615- (300_000 - expected_fee - 20) as i64 ,
18694+ Amount::from_sat (300_000 - expected_fee - 20),
1861618695 &[
1861718696 funding_input_sats(200_000),
1861818697 funding_input_sats(100_000),
1861918698 ],
18699+ &[],
1862018700 false,
1862118701 false,
1862218702 2000,
1862318703 ).unwrap(),
18624- expected_fee,
18704+ Amount::from_sat( expected_fee) ,
1862518705 );
1862618706 }
1862718707 }
0 commit comments