@@ -1031,6 +1031,70 @@ def test_rbf_reconnect_tx_sigs(node_factory, bitcoind, chainparams):
10311031 assert l1_funding_txid == l2_funding_txid
10321032
10331033
1034+ @unittest .skipIf (TEST_NETWORK != 'regtest' , 'elementsd doesnt yet support PSBT features we need' )
1035+ @pytest .mark .openchannel ('v2' )
1036+ def test_rbf_to_chain_before_commit (node_factory , bitcoind , chainparams ):
1037+ disconnects = ['=WIRE_TX_ADD_INPUT' , # Initial funding succeeds
1038+ '=WIRE_COMMITMENT_SIGNED' ,
1039+ '-WIRE_COMMITMENT_SIGNED' ]
1040+ l1 , l2 = node_factory .get_nodes (2 ,
1041+ opts = [{'disconnect' : disconnects ,
1042+ 'may_reconnect' : True ,
1043+ 'dev-no-reconnect' : None },
1044+ {'may_reconnect' : True ,
1045+ 'dev-no-reconnect' : None ,
1046+ 'allow_broken_log' : True }])
1047+
1048+ l1 .rpc .connect (l2 .info ['id' ], 'localhost' , l2 .port )
1049+ amount = 2 ** 24
1050+ chan_amount = 100000
1051+ bitcoind .rpc .sendtoaddress (l1 .rpc .newaddr ()['bech32' ], amount / 10 ** 8 + 0.01 )
1052+ bitcoind .generate_block (1 )
1053+ # Wait for it to arrive.
1054+ wait_for (lambda : len (l1 .rpc .listfunds ()['outputs' ]) > 0 )
1055+
1056+ res = l1 .rpc .fundchannel (l2 .info ['id' ], chan_amount )
1057+ chan_id = res ['channel_id' ]
1058+ vins = bitcoind .rpc .decoderawtransaction (res ['tx' ])['vin' ]
1059+ assert (only_one (vins ))
1060+ prev_utxos = ["{}:{}" .format (vins [0 ]['txid' ], vins [0 ]['vout' ])]
1061+
1062+ # Check that we're waiting for lockin
1063+ l1 .daemon .wait_for_log (' to DUALOPEND_AWAITING_LOCKIN' )
1064+
1065+ # rbf the lease with a higher amount
1066+ rate = int (find_next_feerate (l1 , l2 )[:- 5 ])
1067+ # We 4x the feerate to beat the min-relay fee
1068+ next_feerate = '{}perkw' .format (rate * 4 )
1069+
1070+ # Initiate an RBF
1071+ startweight = 42 + 172 # base weight, funding output
1072+ initpsbt = l1 .rpc .utxopsbt (chan_amount , next_feerate , startweight ,
1073+ prev_utxos , reservedok = True ,
1074+ min_witness_weight = 110 ,
1075+ excess_as_change = True )
1076+
1077+ # Peers try RBF, break on initial COMMITMENT_SIGNED
1078+ bump = l1 .rpc .openchannel_bump (chan_id , chan_amount , initpsbt ['psbt' ])
1079+ with pytest .raises (RpcError ):
1080+ l1 .rpc .openchannel_update (chan_id , bump ['psbt' ])
1081+ wait_for (lambda : l1 .rpc .getpeer (l2 .info ['id' ])['connected' ] is False )
1082+
1083+ # We don't have the commtiments yet, there's no scratch_txid
1084+ inflights = only_one (l1 .rpc .listpeerchannels ()['channels' ])['inflight' ]
1085+ assert len (inflights ) == 2
1086+ assert 'scratch_txid' not in inflights [1 ]
1087+
1088+ # Close the channel!
1089+ l1 .rpc .close (chan_id , 1 )
1090+ l1 .daemon .wait_for_logs (['Broadcasting txid {}' .format (inflights [0 ]['scratch_txid' ]),
1091+ 'sendrawtx exit 0' ])
1092+
1093+ wait_for (lambda : inflights [0 ]['scratch_txid' ] in bitcoind .rpc .getrawmempool ())
1094+ assert inflights [0 ]['funding_txid' ] in bitcoind .rpc .getrawmempool ()
1095+ assert inflights [1 ]['funding_txid' ] not in bitcoind .rpc .getrawmempool ()
1096+
1097+
10341098@unittest .skipIf (TEST_NETWORK != 'regtest' , 'elementsd doesnt yet support PSBT features we need' )
10351099@pytest .mark .openchannel ('v2' )
10361100def test_rbf_no_overlap (node_factory , bitcoind , chainparams ):
0 commit comments