Skip to content

Commit 96c577e

Browse files
committed
lightningd: immediately close without broadcast whenever we close a withheld channel.
There's no funding tx to spend. Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
1 parent 4f93543 commit 96c577e

4 files changed

Lines changed: 39 additions & 8 deletions

File tree

lightningd/channel.c

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1075,21 +1075,31 @@ static void channel_fail_perm(struct channel *channel,
10751075

10761076
channel_set_owner(channel, NULL);
10771077

1078-
if (channel_state_wants_onchain_fail(channel->state))
1078+
if (channel->withheld) {
1079+
channel_set_state(channel,
1080+
channel->state,
1081+
CLOSED,
1082+
reason,
1083+
why);
1084+
} else if (channel_state_wants_onchain_fail(channel->state)) {
10791085
channel_set_state(channel,
10801086
channel->state,
10811087
AWAITING_UNILATERAL,
10821088
reason,
10831089
why);
1090+
}
1091+
1092+
if (channel_state_open_uncommitted(channel->state)) {
1093+
delete_channel(channel, false);
1094+
return;
1095+
}
10841096

10851097
/* Drop non-cooperatively (unilateral) to chain. If we detect
10861098
* the close from the blockchain, then we can observe
10871099
* passively, and not broadcast our own unilateral close, as
10881100
* it doesn't stand a chance anyway. */
10891101
drop_to_chain(ld, channel, false, spent_by);
10901102

1091-
if (channel_state_open_uncommitted(channel->state))
1092-
delete_channel(channel, false);
10931103
}
10941104

10951105
void channel_fail_permanent(struct channel *channel,

lightningd/closing_control.c

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -38,13 +38,18 @@ static void
3838
resolve_one_close_command(struct close_command *cc, bool cooperative,
3939
const struct bitcoin_tx **close_txs)
4040
{
41-
assert(tal_count(close_txs));
4241
struct json_stream *result = json_stream_success(cc->cmd);
43-
const struct bitcoin_tx *close_tx = close_txs[tal_count(close_txs) - 1];
42+
const struct bitcoin_tx *close_tx;
4443

45-
if (command_deprecated_out_ok(cc->cmd, "tx", "v24.11", "v25.12"))
44+
/* Withheld funding channels can have no close_txs! */
45+
if (tal_count(close_txs) != 0)
46+
close_tx = close_txs[tal_count(close_txs) - 1];
47+
else
48+
close_tx = NULL;
49+
50+
if (close_tx && command_deprecated_out_ok(cc->cmd, "tx", "v24.11", "v25.12"))
4651
json_add_tx(result, "tx", close_tx);
47-
if (!invalid_last_tx(close_tx)) {
52+
if (close_tx && !invalid_last_tx(close_tx)) {
4853
struct bitcoin_txid txid;
4954
bitcoin_txid(close_tx, &txid);
5055
if (command_deprecated_out_ok(cc->cmd, "txid", "v24.11", "v25.12"))

lightningd/peer_control.c

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -348,6 +348,17 @@ void drop_to_chain(struct lightningd *ld, struct channel *channel,
348348
struct channel_inflight *inflight;
349349
const char *cmd_id;
350350

351+
/* If we withheld the funding tx, we simply close */
352+
if (channel->withheld) {
353+
log_info(channel->log,
354+
"Withheld channel: not sending a close transaction");
355+
resolve_close_command(ld, channel, cooperative,
356+
tal_arr(tmpctx, const struct bitcoin_tx *, 0));
357+
free_htlcs(ld, channel);
358+
delete_channel(channel, false);
359+
return;
360+
}
361+
351362
/* If we're not already (e.g. close before channel fully open),
352363
* make sure we're watching for the funding spend */
353364
if (!channel->funding_spend_watch) {

plugins/spender/openchannel.c

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1096,17 +1096,22 @@ static void list_awaiting_channels(struct command *init_cmd)
10961096
struct channel_id cid;
10971097
struct command *aux_cmd;
10981098
struct wally_psbt *psbt;
1099+
bool withheld;
10991100

1100-
if (json_scan(tmpctx, buf, t, "{state:%,channel_id:%,funding:{psbt:%}}",
1101+
if (json_scan(tmpctx, buf, t, "{state:%,channel_id:%,funding:{withheld:%,psbt:%}}",
11011102
JSON_SCAN_TAL(tmpctx, json_strdup, &state),
11021103
JSON_SCAN(json_tok_channel_id, &cid),
1104+
JSON_SCAN(json_to_bool, &withheld),
11031105
JSON_SCAN_TAL(tmpctx, json_to_psbt, &psbt)) != NULL)
11041106
continue;
11051107

11061108
if (!streq(state, "CHANNELD_AWAITING_LOCKIN")
11071109
&& !streq(state, "DUALOPEND_AWAITING_LOCKIN"))
11081110
continue;
11091111

1112+
if (withheld)
1113+
continue;
1114+
11101115
/* Don't do this sync, as it can reasonably fail! */
11111116
aux_cmd = aux_command(init_cmd);
11121117
req = jsonrpc_request_start(aux_cmd, "signpsbt",

0 commit comments

Comments
 (0)