Skip to content

channeld: fix channel_ready retransmission after splice via funding_tx_index#9256

Open
nGoline wants to merge 3 commits into
ElementsProject:masterfrom
nGoline:fix-channel-ready-retransmit-after-splice
Open

channeld: fix channel_ready retransmission after splice via funding_tx_index#9256
nGoline wants to merge 3 commits into
ElementsProject:masterfrom
nGoline:fix-channel-ready-retransmit-after-splice

Conversation

@nGoline

@nGoline nGoline commented Jun 24, 2026

Copy link
Copy Markdown
Collaborator

Problem

On reconnect, channeld decides whether to retransmit channel_ready based on whether the peer's channel_reestablish references a splice (is_splice_active). It computed that by comparing the peer's my_current_funding_locked txid against peer->channel->funding.txid.

That comparison is wrong once a splice locks: channel_update_funding() overwrites funding.txid with the splice txid, so afterwards both sides agree on the same txid, the check falls through, and channel_ready is incorrectly retransmitted on reconnect, which can disrupt channels.

This is the problem @ddustin raised reviewing #9079 (comparing against the txid is incorrect, and we should track metadata on the inflight instead), suggesting a funding_tx_index, matching what eclair does.

Fix

Give every funding tx a stable funding_tx_index: 0 for the original funding (including RBF attempts), incrementing by 1 per splice. It is:

  • carried on the channeld inflight and on the channel,
  • threaded through the channeld_init and channeld_add_inflight wire,
  • assigned on splice creation (parent + 1) and copied onto the channel funding when a splice locks,
  • persisted in channel_funding_inflights and channels (two migrations, DEFAULT 0, so existing channels are unaffected).

The reestablish check now resolves the my_current_funding_locked txid to its funding_tx_index (current funding or a pending inflight) and treats > 0 as a splice.

Commits (bisectable)

  1. splice: add tests for funding_tx_index tracking, regression tests (xfail).
  2. splice: track funding_tx_index on inflights and channel funding, the plumbing.
  3. channeld: detect splice on reestablish via funding_tx_index, not txid, the fix.

Tests

  • test_splice_reconnect_after_lock_no_channel_ready: splice, restart, reestablish; asserts the index persists and channel_ready is not retransmitted. It fails on commit 2 (old txid compare) and passes on commit 3, so it genuinely guards the fix.
  • test_splice_funding_tx_index_increments: two sequential splices reach index 2.
  • test_splice_inflight_funding_tx_index: a pending splice inflight carries index 1 and survives a restart.
  • Existing test_reconnect_no_update confirms non-splice channels still retransmit channel_ready.

Risk and plan

The behavioural change is a single line in the reestablish check. The plan is to get the funding_tx_index semantics reviewed properly, and if we don't converge before the v26.09 freeze, revert that one line with a FIXME and keep the plumbing for the follow-up. So this carries low risk.

@ddustin, this implements the funding_tx_index approach you suggested; would appreciate your review of the assignment semantics and whether it matches what you and tbast had in mind.

nGoline added 3 commits June 24, 2026 17:54
Add regression tests that each funding transaction carries a
funding_tx_index (0 for the original funding, +1 per splice), that it is
persisted and reloaded across restart, and that a pending splice inflight
carries its index.

Changelog-None
Give every funding tx a stable index: 0 for the original funding
(including RBF attempts), incrementing by 1 per splice.  Threaded through
the channeld inflight, the channel, the channeld_init and
channeld_add_inflight wire messages, set on splice creation and carried
onto the channel funding when a splice locks, and persisted in the
channel_funding_inflights and channels tables.
is_splice_active compared the peer's my_current_funding_locked txid
against peer->channel->funding.txid, which is wrong: once a splice locks,
funding.txid becomes the splice txid, both sides agree on it, the check
falls through, and channel_ready is incorrectly retransmitted on reconnect.

Resolve the txid to its funding_tx_index (the current channel funding or a
pending splice inflight) and treat > 0 as a splice.

Changelog-Fixed: channeld: correctly detect splice transactions when deciding whether to retransmit `channel_ready` on reconnect.
@nGoline nGoline requested a review from ddustin June 24, 2026 21:50
@nGoline nGoline added the Status::Ready for Review The work has been completed and is now awaiting evaluation or approval. label Jun 24, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Status::Ready for Review The work has been completed and is now awaiting evaluation or approval.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant