Skip to content

Commit 7e82729

Browse files
Antoine RiardTheBlueMatt
authored andcommitted
Test htlc outputs shared tx claim case
1 parent fe40e9a commit 7e82729

File tree

1 file changed

+66
-0
lines changed

1 file changed

+66
-0
lines changed

src/ln/channelmanager.rs

Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3493,6 +3493,72 @@ mod tests {
34933493
get_announce_close_broadcast_events(&nodes, 0, 1);
34943494
}
34953495

3496+
#[test]
3497+
fn claim_htlc_outputs_shared_tx() {
3498+
// Node revoked old state, htlcs haven't time out yet, claim them in shared justice tx
3499+
3500+
let nodes = create_network(2);
3501+
3502+
// Create some new channel:
3503+
let chan_1 = create_announced_chan_between_nodes(&nodes, 0, 1);
3504+
3505+
// Rebalance the network to generate htlc in the two directions
3506+
send_payment(&nodes[0], &vec!(&nodes[1])[..], 8000000);
3507+
// node[0] is gonna to revoke an old state thus node[1] should be able to claim both offered/received HTLC outputs on top of commitment tx
3508+
let payment_preimage_1 = route_payment(&nodes[0], &vec!(&nodes[1])[..], 3000000).0;
3509+
let _payment_preimage_2 = route_payment(&nodes[1], &vec!(&nodes[0])[..], 3000000).0;
3510+
3511+
// Get the will-be-revoked local txn from node[0]
3512+
let revoked_local_txn = nodes[0].node.channel_state.lock().unwrap().by_id.get(&chan_1.2).unwrap().last_local_commitment_txn.clone();
3513+
3514+
//Revoke the old state
3515+
claim_payment(&nodes[0], &vec!(&nodes[1])[..], payment_preimage_1);
3516+
3517+
{
3518+
let header = BlockHeader { version: 0x20000000, prev_blockhash: Default::default(), merkle_root: Default::default(), time: 42, bits: 42, nonce: 42 };
3519+
3520+
nodes[0].chain_monitor.block_connected_with_filtering(&Block { header, txdata: vec![revoked_local_txn[0].clone()] }, 1);
3521+
3522+
nodes[1].chain_monitor.block_connected_with_filtering(&Block { header, txdata: vec![revoked_local_txn[0].clone()] }, 1);
3523+
let node_txn = nodes[1].tx_broadcaster.txn_broadcasted.lock().unwrap();
3524+
assert_eq!(node_txn.len(), 4);
3525+
3526+
let mut revoked_tx_map = HashMap::new();
3527+
revoked_tx_map.insert(revoked_local_txn[0].txid(), revoked_local_txn[0].clone());
3528+
3529+
assert_eq!(node_txn[0].input.len(), 2);
3530+
node_txn[0].verify(&revoked_tx_map).unwrap();
3531+
3532+
assert_eq!(node_txn[3].input.len(), 2);
3533+
node_txn[3].verify(&revoked_tx_map).unwrap();
3534+
3535+
assert_eq!(node_txn[0].txid(), node_txn[3].txid()); // justice tx is duplicated due to block re-scanning
3536+
3537+
let witness_script_1 = node_txn[0].clone().input[0].witness.pop().unwrap();
3538+
let witness_script_2 = node_txn[0].clone().input[1].witness.pop().unwrap();
3539+
if witness_script_1.len() > 133 {
3540+
assert_eq!(witness_script_1.len(), 138);
3541+
assert_eq!(witness_script_2.len(), 133);
3542+
} else {
3543+
assert_eq!(witness_script_1.len(), 133);
3544+
assert_eq!(witness_script_2.len(), 138);
3545+
}
3546+
3547+
assert_eq!(node_txn[1].input.len(), 1);
3548+
let witness_script = node_txn[1].clone().input[0].witness.pop().unwrap();
3549+
assert_eq!(witness_script.len(), 71); // Spending funding tx unique txoutput, tx broadcasted by ChannelManager
3550+
3551+
assert_eq!(node_txn[2].input.len(), 1);
3552+
let witness_script = node_txn[2].clone().input[0].witness.pop().unwrap();
3553+
assert_eq!(witness_script.len(), 133); //Spending a offered htlc output
3554+
3555+
}
3556+
get_announce_close_broadcast_events(&nodes, 0, 1);
3557+
assert_eq!(nodes[0].node.list_channels().len(), 0);
3558+
assert_eq!(nodes[1].node.list_channels().len(), 0);
3559+
}
3560+
3561+
#[test]
34963562
fn test_htlc_ignore_latest_remote_commitment() {
34973563
// Test that HTLC transactions spending the latest remote commitment transaction are simply
34983564
// ignored if we cannot claim them. This originally tickled an invalid unwrap().

0 commit comments

Comments
 (0)