AI-generated analysisPublished automatically and not human-verified. Validated context appears in community notes below.
← Watch feed
Moderate 68 Bitcoin

Check pruned HTLCs were resolved on startup

Public commit record

What the developer wrote

Authored by Valentine Wallace

68/100 · Adequate
Check pruned HTLCs were resolved on startup

In a recent commit, we added support for pruning an inbound HTLC's persisted
onion once the HTLC has been irrevocably forwarded to the outbound edge.

Here, we add a check on startup that those inbound HTLCs were actually handled.
Specifically, we check that the inbound HTLC is either (a) currently present in
the outbound edge or (b) was removed via claim. If neither of those are true,
we infer that the HTLC was removed from the outbound edge via fail and fail the
inbound HTLC backwards.
✓ Descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context
The short version

What changed, and why it matters

This commit fixes a crash-recovery bug in the Lightning Dev Kit (LDK) routing node software. When a forwarding node restarts after a crash, it may have an inbound payment that it already forwarded to the next hop but has not yet resolved backward. Previously, if the outbound HTLC was removed by a failure but the failure signal was lost in the crash, the node could leave the inbound payment stuck or mishandled. The patch adds a startup check: for every inbound HTLC marked 'already forwarded,' it verifies the HTLC is either still present on the outbound channel or was claimed with a known payment preimage. If neither is true, the node now correctly fails the payment backward to the previous hop. This prevents funds from being locked up and ensures honest nodes do not lose money or break protocol consistency after an unclean shutdown.

Recommended action

Treat as a security-relevant correctness fix and include in the next maintenance release. Users running routing nodes should upgrade to avoid HTLC state inconsistency after crashes. Reviewers should verify that the `already_forwarded_htlcs` pruning logic covers all removal paths (claim, fail, holding-cell resolution, closed channels) and that the new `InboundUpdateAdd::Legacy` decode error path cannot be triggered by existing persisted data.

Security signals we found

01

Crash-recovery consistency fix for HTLC forwarding state

02

Prevents stuck or double-handled HTLCs after unclean restart

03

Adds preimage-based verification before replaying backward claims

04

Adds failure fallback for forwarded HTLCs missing from outbound edge and monitors

05

Touches ChannelManager deserialization and ChannelMonitor preimage replay paths

06

Includes regression tests simulating crash with cleared holding cell

Risk score

Why this scored 68/100

Our methodology →
Potential impact 22/30
Exploitability 12/25
Stealth signal 10/15
Affected reach 12/15
Confidence 8/10
Evidence quality 4/5
Human-validated context

Community notes

Notes can correct, qualify, or add evidence to the AI analysis. Every note shown here has been validated by a human moderator.

No validated notes yet.

The AI analysis stands alone for now. Submit a note if you can add evidence or important context.