Every captured commit receives deterministic security triage and a separate communication-quality score. Security candidates and broader second-pass signals receive full-patch Ollama analysis.
Message quality measures whether a commit identifies its scope, purpose, rationale, testing, and supporting references. It does not change the security-severity score.
This commit changes how the Lightning networking code handles oversized encrypted messages. Previously, certain conditions would cause the program to crash with a panic. Now the code returns errors instead, which is a defensive improvement…
panic-to-error conversion for oversized message encryption/decryptiondenial-of-service hardening against oversized peer messagesdebug_assert retained to preserve test coverage of invariant violations
This commit simply updates the 'repository' web links in 15 package metadata files from GitHub to a self-hosted Forgejo instance. It does not change any program code, build logic, dependencies, or security behavior. There is no security is…
This commit fixes a bug in the Lightning Dev Kit where, after a disconnection, a node could fail to retransmit a 'splice_locked' message to a peer that was still waiting for transaction signatures. Without this retransmission, the two peer…
Protocol state desynchronization between channel peers after reconnectionMissing retransmission of splice_locked for 0-conf splice channelsPotential channel unusability or stuck splice negotiation
This commit fixes a small accounting bug in how the Lightning wallet estimates the size (and therefore transaction fee) of a special Bitcoin transaction that sweeps funds back to the user after a channel closes. The old code always assumed…
debug assertion failure possible in development/testing buildstransaction weight/fee estimate overestimation up to 3 WUconstant replaced with per-descriptor length computation
This commit changes the project's internal code-review workflow. It stops automatically assigning a human reviewer when a pull request is opened; instead, contributors must manually click a button to request a reviewer after first addressi…
This commit fixes a bug in LDK's Lightning channel reconnection logic after a splice (a way to resize a channel's on-chain funds). If one peer had already received the splice signatures but the other had not, and then they disconnected and…
Protocol-state inconsistency on reconnection after splice signature exchangePotential channel stall/force-close due to quiescence not being exited before commitment updateFuzzer-discovered edge case in Lightning splicing retransmission
This commit adds a new option for Lightning invoice creators to explicitly tell payers not to use multi-path payments (MPP) when paying an invoice. It does not change any enforcement rules; it only changes what feature bits are advertised …
New API surface for feature advertisement controlExplicit documentation that the method does not enforce single-HTLC receipt, shifting enforcement responsibility to callersNo removal or weakening of existing validation logic
This commit adjusts the project's continuous integration (CI) test script to pin an older version of a build-time helper crate called `jobserver` when using older Rust compilers. It is a build compatibility fix, not a security patch, and d…
This commit only adds new test code. It exercises how a newer version of LDK exchanges saved channel data with the older LDK 0.2 release when a channel has a pending splice. There is no change to production logic, no bug fix, and no securi…
This commit removes the 'Option' wrapper from several HTLC amount fields, making them required instead of optional. It is a cleanup/refactoring change that simplifies the code by assuming the amount is always known. The commit message fram…
Removal of Option wrapper for financial amount fieldsSerialization format change from optional to required TLV fieldsLoss of backward compatibility with older serialized monitor/channel state
This commit is a code cleanup inside the project's test suite. It replaces a helper function with several hard-to-read positional arguments (like bare `false` and `None`) with a 'builder' pattern that names each option. This makes the test…
This commit is a feature addition, not a vulnerability fix. It extends rust-lightning's BOLT 12 payment support so that when a wallet pays a BOLT 12 invoice, the paid invoice is saved through retries and restarts and is later exposed in th…
New BOLT 12 payer proof feature: persists paid invoice across retries/restarts and exposes it in Event::PaymentSentPayer signing key re-derived from invoice payer metadata rather than storing extra key materialAdds end-to-end test for proof creation, verification, and bech32 round-trip
This commit is a code cleanup (refactor) in the Lightning Dev Kit library. It moves existing payer key-derivation logic into shared helper functions so that future 'payer proof' features can reuse the same code. The change does not appear …
Refactor only: moves existing key derivation/verification logic into helpers without changing algorithmsAdds new public API `Bolt12Invoice::derive_payer_signing_keys` for payer proof key recoveryNo mention of vulnerability, bug, CVE, security fix, or exploit in commit title/message
This commit changes a CI workflow for the rust-lightning project. It stops trying to push new fuzz test inputs directly to a corpus repository from automated test runs, and instead uploads them as a temporary artifact that a separate sched…
This commit adds partial support in the Lightning Dev Kit node software for receiving and temporarily holding multi-part trampoline payments, then deliberately rejects them once all parts arrive because full outbound forwarding is not yet …
New trampoline forward handling path accumulates MPP parts before rejectingDebug assertion guards first-HTLC failure in MPP mergeTODO comment flags possible MPP inconsistency in next_node_id across trampoline parts
This commit removes a redundant 32-byte shared secret field from an internal data structure used when forwarding trampoline payments in the Lightning Dev Kit. The developers realized the secret was already stored inside each previous hop's…
Removes redundant secret field from in-memory/persisted stateChanges TLV serialization layout for HTLCSource::TrampolineForwardBreaking persistence change acknowledged by commit author
This commit changes the project's automated reviewer-assignment workflow to stop using a long-lived secret token and instead request a short-lived authentication token from the Forgejo CI service. This is a security-hardening improvement: …
Removal of long-lived repository secret from CI workflowAdoption of OIDC-based short-lived token for API authorizationWorkflow runs in pull_request_target context with no code checkout
This commit only adds new fuzz-testing commands to an existing test harness. It lets the fuzzer temporarily block and then re-enable the local node's own signing operations during simulated channel failures. There is no change to productio…
This commit hardens the project's automated build and test scripts by replacing loose version tags like 'actions/checkout@v4' with exact commit hashes served from a specific domain. This prevents a compromised or renamed third-party action…
CI/CD supply-chain hardeningAction reference pinning to immutable commit hashUse of explicit action mirror URL
This commit fixes a logic bug in the Lightning Dev Kit's channel splicing code. Previously, the code wrongly assumed that no unrelated monitor update could be pending when a splice `tx_signatures` message arrived while the channel was quie…
Assertion relaxation in state-machine handling of splice `tx_signatures`Race condition between unrelated HTLC preimage monitor update and splice signature exchangePotential panic or protocol stall due to overly strict debug assertion
Expand any commit for its author, full message, clarity score, changed files, triage signals, analysis, and source link.
AI review queuedVerify Electrum transaction responses before useby Elias Rohrer · 1d131506 · Jun 17, 2026 · 1 fileMessage 90 · StrongTriage 12Details
Commit message · Elias Rohrer
Verify Electrum transaction responses before use
Electrum confirmations must reject transaction_get responses whose body does not compute the requested txid. Otherwise a malicious server can substitute an unrelated transaction and provide matching Merkle data for the substituted body.
Co-Authored-By: HAL 9000
This finding was discovered by Project Loupe
90/100 · StrongMessage clarity
✓ Descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context✓ Explains rationale or failure mode✓ Mentions testing or verification
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedCheck Esplora Merkle leaf risk by base sizeby Elias Rohrer · bc05d9d9 · Jun 17, 2026 · 1 fileMessage 80 · StrongTriage 12Details
Commit message · Elias Rohrer
Check Esplora Merkle leaf risk by base size
Esplora confirmation checks must use the non-witness transaction size for the 64-byte Merkle leaf guard. Witness padding can otherwise raise total_size without changing the serialization hashed into the txid and Merkle tree.
Co-Authored-By: HAL 9000
This finding was discovered by Project Loupe
80/100 · StrongMessage clarity
✓ Descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context✓ Explains rationale or failure mode
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedCheck Electrum Merkle leaf risk by base sizeby Elias Rohrer · 4636d6c9 · Jun 17, 2026 · 2 filesMessage 80 · StrongTriage 12Details
Commit message · Elias Rohrer
Check Electrum Merkle leaf risk by base size
Electrum confirmation checks must reject transactions whose non-witness serialization is 64 bytes, since txids and Merkle leaves are computed from that serialization. Witness padding can otherwise move total_size above 64 without removing the inner-node ambiguity.
Co-Authored-By: HAL 9000
This finding was discovered by Project Loupe
80/100 · StrongMessage clarity
✓ Descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context✓ Explains rationale or failure mode
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedFix underflow in blinded path amt_to_forwardby Valentine Wallace · e560ec17 · Jun 15, 2026 · 1 fileMessage 80 · StrongTriage 0Details
Commit message · Valentine Wallace
Fix underflow in blinded path amt_to_forward
If we have a high (200%+) proportional fee as an intermediate blinded node combined with a low inbound amount, we previously had some code that calculated the outbound amount of the forward that would've underflowed. This would've caused a panic in debug builds and caused us to relay a payment that should've been rejected (due to being unable to cover our high fee) in release builds.
Reported by Project Loupe.
80/100 · StrongMessage clarity
✓ Descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context✓ Explains rationale or failure mode
Why it was queued
second-pass: broader security terminology
AI review queuedClear duplicate monitor-pending RAA on signer resendby Wilmer Paulino · 27223fdd · Jun 15, 2026 · 2 filesMessage 83 · StrongTriage 17Details
Commit message · Wilmer Paulino
Clear duplicate monitor-pending RAA on signer resend
The `chanmon_consistency` fuzz target found a reconnect ordering where `signer_pending_revoke_and_ack` and `monitor_pending_revoke_and_ack` could both describe the same owed `revoke_and_ack`.
The channel first received a `commitment_signed` whose monitor update completed, but the signer could not provide the next point or secret, leaving `signer_pending_revoke_and_ack` set. Later, receiving the peer `revoke_and_ack` freed holding-cell HTLCs and produced a held monitor update. While that monitor update was still blocked, `channel_reestablish` saw the peer one state behind and recorded `monitor_pending_revoke_and_ack`, plus the corresponding monitor-pending `commitment_signed`, so the messages could be replayed once monitor updating was restored.
If the signer unblocked before the held monitor update was released, `signer_maybe_unblocked` generated and sent the already monitor-safe RAA using `signer_pending_revoke_and_ack`. The monitor-pending flag was not cleared at that point, so `monitor_updating_restored` later generated the same RAA again when the held update completed. The peer had already advanced after accepting the signer-unblocked RAA, so it rejected the duplicate secret as not corresponding to its current pubkey and force-closed.
Fix this by clearing `monitor_pending_revoke_and_ack` in the signer-resume path only once a signer-pending RAA is actually being returned.
83/100 · StrongMessage clarity
✓ Specific, descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context✓ Mentions testing or verification
Why it was queued
fuzzing or regression evidencesigning or wallet pathsecond-pass: security-sensitive path
AI review queuedValidate reserved fees on both commitmentsby Leo Nash · 9fe1a362 · May 21, 2026 · 2 filesMessage 80 · StrongTriage 20Details
Commit message · Leo Nash
Validate reserved fees on both commitments
The local and remote commitments may have different dust limits, which can cause each commitment to have a different transaction fee.
Therefore when we reserve commitment transaction fees in `get_available_balances`, we must ensure that we read the maximum of the transaction fees on the local and the remote commitments. Otherwise, we may have not reserved enough fees to ensure that our next proposed channel state update is onside.
80/100 · StrongMessage clarity
✓ Descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context✓ Explains rationale or failure mode
Why it was queued
defensive validationsigning or wallet pathsecond-pass: near security thresholdsecond-pass: security-sensitive path
AI review queuedBreak `get_available_balances` into small helper functionsby Leo Nash · 69d2f08c · May 21, 2026 · 1 fileMessage 50 · ThinTriage 12Details
Commit message · Leo Nash
Break `get_available_balances` into small helper functions
Most diffs here are code moves.
50/100 · ThinMessage clarity
✓ Specific, descriptive subject✓ Names a concrete action or component! No meaningful explanatory body
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedValidate `next_splice_out_maximum_sat` on both commitmentsby Leo Nash · 89e9b75b · May 21, 2026 · 3 filesMessage 73 · AdequateTriage 25Details
Commit message · Leo Nash
Validate `next_splice_out_maximum_sat` on both commitments
Wilmer's fuzzing runs caught a case where an advertised splice out maximum hit the debug assertions in `get_next_splice_out_maximum`. These debug assertions ensure that any adverstised splice out maximum passes the validation of splice contributions.
The core issue is that we only read the local commitment when calculating the splice out maximum, but our splice validation requires that any splice out maximum is covered by the minimum of the holder's balances on the local and the remote commitments.
Therefore, if a HTLC is dust on the local commitment, but non-dust on the remote commitment, and the holder is the funder of the channel, we advertise a splice out maximum that is not covered by the holder's balance on the remote commitment, and fails our validation of splice contributions.
We now read both commitments when calculating the next splice out maximum, which fixes this issue.
73/100 · AdequateMessage clarity
✓ Specific, descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context
Why it was queued
defensive validationfuzzing or regression evidencesigning or wallet pathsecond-pass: near security thresholdsecond-pass: security-sensitive path
AI review queuedDon't check for no-outputs under fee spikes in `get_available_balances`by Leo Nash · 257033fe · May 19, 2026 · 1 fileMessage 73 · AdequateTriage 12Details
Commit message · Leo Nash
Don't check for no-outputs under fee spikes in `get_available_balances`
We only assume fee spikes in legacy channels, and we do not allow `holder_selected_channel_reserve_satoshis` to be set to zero in such channels. It is nonetheless still possible to reach the no-outputs case in a fee spike with solely the counterparty selected reserve set to zero, so we still guard against this case in `get_next_commitment_stats`.
We don't guard against no-outputs under fee spikes `get_available_balances`; in the worst case, the receiver of the HTLC we just sent fails it back.
73/100 · AdequateMessage clarity
✓ Specific, descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedSkip stale fs store artifactsby benthecarman · 9246d868 · May 19, 2026 · 2 filesMessage 68 · AdequateTriage 0Details
Commit message · benthecarman
Skip stale fs store artifacts
The exhaustive filesystem store listing treated leftover temp and trash files as namespace directories after identifying them as non-keys. Skip those artifacts before recursing so migrations can ignore crash leftovers.
68/100 · AdequateMessage clarity
✓ Descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context
Why it was queued
second-pass: broader security terminology
AI review queuedBound sync loops in lightning-transaction-syncby Matt Corallo · 1c7fcb76 · May 15, 2026 · 2 filesMessage 68 · AdequateTriage 12Details
Commit message · Matt Corallo
Bound sync loops in lightning-transaction-sync
If we start syncing from an electrum or esplora server and find that the chain moved during our sync, we reset and start fresh. However, if that happens repeatedly, we probably shouldn't just spin forever. Here we give up after ten attempts and just hope we can sync properly later.
68/100 · AdequateMessage clarity
✓ Descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedMove the calculation of the spiked feerate to `tx_builder`by Leo Nash · e90d524e · May 13, 2026 · 2 filesMessage 73 · AdequateTriage 12Details
Commit message · Leo Nash
Move the calculation of the spiked feerate to `tx_builder`
In the next commit, we will make changes to how the fee spike buffer is calculated which require the real feerate to always be passed to `tx_builder::get_next_commitment_stats`, even in the case where we include a fee spike multiple.
73/100 · AdequateMessage clarity
✓ Specific, descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedDon't trim HTLCs when calculating the fee spike commit tx feeby Leo Nash · deb51aec · May 13, 2026 · 2 filesMessage 73 · AdequateTriage 12Details
Commit message · Leo Nash
Don't trim HTLCs when calculating the fee spike commit tx fee
We previously accounted for HTLC trims at the spiked feerate when calculating the commitment transaction fee including the fee spike multiple.
This only ensured that the funder of the channel could afford the commitment transaction fee for an exact 2x increase in the feerate.
Now, we check that the funder can cover any increase in the feerate between 1x to 2x.
73/100 · AdequateMessage clarity
✓ Specific, descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedDon't trim HTLCs when calculating the reserved commit tx feeby Leo Nash · df624dba · May 12, 2026 · 2 filesMessage 93 · StrongTriage 12Details
Commit message · Leo Nash
Don't trim HTLCs when calculating the reserved commit tx fee
We previously accounted for HTLC trims at the spiked feerate when calculating the reserved commitment transaction fees.
This could cause an underestimate of the real current commitment fee at the current channel feerate. This is because a 2x increase in the feerate could trim enough HTLCs to result in a smaller commitment transaction fee.
Also, the previous code only reserved the fee for an exact 2x increase in the feerate, instead of reserving the fee for any increase in the feerate between 1x to 2x.
Fixes #4563.
93/100 · StrongMessage clarity
✓ Specific, descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context✓ Explains rationale or failure mode✓ Links an issue, advisory, or supporting reference
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedBump transaction sync dev dependenciesby Elias Rohrer · 8882eddc · May 8, 2026 · 2 filesMessage 45 · ThinTriage 12Details
Commit message · Elias Rohrer
Bump transaction sync dev dependencies
45/100 · ThinMessage clarity
✓ Descriptive subject✓ Names a concrete action or component! No meaningful explanatory body
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedBump electrum-client to v0.25by Elias Rohrer · 6f93dead · May 8, 2026 · 1 fileMessage 45 · ThinTriage 12Details
Commit message · Elias Rohrer
Bump electrum-client to v0.25
45/100 · ThinMessage clarity
✓ Descriptive subject✓ Names a concrete action or component! No meaningful explanatory body
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedError if the calculated v2 reserve is greater than the channel valueby Leo Nash · 3835f842 · May 8, 2026 · 3 filesMessage 85 · StrongTriage 20Details
Commit message · Leo Nash
Error if the calculated v2 reserve is greater than the channel value
In 0FC channels, capping the reserve to the total value of the channel allowed a splice initiator to withdraw past their reserve in case the acceptor had no balance in the channel.
This is because the post-splice value of the channel was equal to the initiator's post splice balance. Hence, this post splice balance always matched the reserve, even though the reserve was below the dust limit.
The only thing that prevented the initiator from withdrawing all their balance was the script dust limit check in `interactivetxs::NegotiationContext::receive_tx_add_output`.
In case the splice acceptor had any balance in the channel, or there were HTLCs in the channel, or the channel was not 0FC, the splice initiator's post-splice balance was always below the full channel value. Hence when the reserve was capped at the channel value, the post-splice balance was always below the reserve, and the splice was rejected.
Also, in `validate_splice_contributions`, to determine the `counterparty_selected_channel_reserve`, we now read the holder's dust limit from the context, instead of the current global constant.
85/100 · StrongMessage clarity
✓ Specific, descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context✓ Explains rationale or failure mode
Why it was queued
defensive validationsigning or wallet pathsecond-pass: near security thresholdsecond-pass: security-sensitive path
AI review queuedRename SplicePending and SpliceFailed eventsby Jeffrey Czyz · cc7fb0f5 · May 7, 2026 · 10 filesMessage 68 · AdequateTriage 12Details
Commit message · Jeffrey Czyz
Rename SplicePending and SpliceFailed events
Rename Event::SplicePending to Event::SpliceNegotiated and Event::SpliceFailed to Event::SpliceNegotiationFailed. These names better reflect the per-round semantics: each negotiation attempt resolves to one of these two outcomes, independent of the overall splice lifecycle.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
68/100 · AdequateMessage clarity
✓ Descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedAdd NegotiationFailureReason to SpliceFailed eventby Jeffrey Czyz · f0a8cebb · May 7, 2026 · 5 filesMessage 85 · StrongTriage 0Details
Commit message · Jeffrey Czyz
Add NegotiationFailureReason to SpliceFailed event
Each splice negotiation round can fail for different reasons, but Event::SpliceFailed previously gave no indication of what went wrong. Add a NegotiationFailureReason enum so users can distinguish failures and take appropriate action (e.g., retry with a higher feerate vs. wait for the channel to become usable).
The reason is determined at each channelmanager emission site based on context rather than threaded through channel.rs internals, since the channelmanager knows the triggering context (disconnect, tx_abort, shutdown, etc.) while channel.rs functions like abandon_quiescent_action handle both splice and non-splice quiescent actions.
The one exception is QuiescentError::FailSplice, which carries a reason alongside the SpliceFundingFailed. This is appropriate because FailSplice is already splice-specific, and the channel.rs code that constructs it (e.g., contribution validation, feerate checks) knows the specific failure cause. A with_negotiation_failure_reason method on QuiescentError allows callers to override the default when needed.
Older serializations that lack the reason field default to Unknown via default_value in deserialization. The persistence reload path uses PeerDisconnected since a reload implies the peer connection was lost.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
85/100 · StrongMessage clarity
✓ Specific, descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context✓ Explains rationale or failure mode
Why it was queued
second-pass: broader security terminology
AI review queuedExpose interactive funding candidates on broadcastby Jeffrey Czyz · 0d2ac33e · May 6, 2026 · 6 filesMessage 73 · AdequateTriage 12Details
Commit message · Jeffrey Czyz
Expose interactive funding candidates on broadcast
Replace TransactionType::Splice with TransactionType::InteractiveFunding so downstream consumers can update their own state tracking from the broadcast callback. The local contribution data isn't recoverable from the on-chain transaction, so the broadcast must surface it directly. Each candidate carries the participating channels and their local contributions; the broadcast lists every negotiated candidate — original first, then each RBF replacement — letting downstream reconcile any historical txid, not just the immediate predecessor.
The new variant is structured to be forward-compatible with batches and V2 (dual-funded) channel establishment, neither of which is implemented today. The new types are Writeable/Readable so downstream can persist them directly.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
73/100 · AdequateMessage clarity
✓ Specific, descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedFix signed comparison in `ElectrumClient`by Elias Rohrer · 8b383bb8 · May 5, 2026 · 1 fileMessage 68 · AdequateTriage 12Details
Commit message · Elias Rohrer
Fix signed comparison in `ElectrumClient`
`GetHistoryRes::height` from electrum-client is a *signed* integer. Here we first check for `<= 0` *before* casting to `u32`.
Signed-off-by: Elias Rohrer <dev@tnull.de>
68/100 · AdequateMessage clarity
✓ Descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedAdd `ChannelDetails::next_splice_out_maximum_sat`by Leo Nash · 9bc7b194 · May 5, 2026 · 3 filesMessage 35 · OpaqueTriage 0Details
Commit message · Leo Nash
Add `ChannelDetails::next_splice_out_maximum_sat`
35/100 · OpaqueMessage clarity
✓ Descriptive subject! No meaningful explanatory body
Why it was queued
second-pass: opaque commit message
AI review queuedAdd `test_0reserve_splice`by Leo Nash · b96c2dbe · May 5, 2026 · 2 filesMessage 25 · OpaqueTriage 0Details
Commit message · Leo Nash
Add `test_0reserve_splice`
25/100 · OpaqueMessage clarity
✓ Descriptive subject! Too few words to establish purpose! No meaningful explanatory body
Why it was queued
second-pass: opaque commit message
AI review queuedAlways enforce the 1000sat min channel value in zero-reserve channelsby Leo Nash · be6cf5b8 · May 5, 2026 · 5 filesMessage 85 · StrongTriage 12Details
Commit message · Leo Nash
Always enforce the 1000sat min channel value in zero-reserve channels
We did not enforce this minimum when accepting 0-reserve channels. This is because we depended on the `MIN_THEIR_CHAN_RESERVE_SATOSHIS` constant to guarantee this minimum channel value, but this value is no longer read in 0-reserve channels.
Note that the user's `min_funding_satoshis` value would still be respected in this case.
When splicing 0-reserve channels, we only enforced that the commitment transaction retained at least one output after the splice, which could produce a channel value lower than 1000sats.
Along the way, we also now enforce this 1000sat minimum when splicing reserve-enabled channels. We previously correctly enforced the reserves after the splice, but this could still result in a channel value smaller than 1000sats. This case is now rejected during splice validation.
Note that the user's `min_funding_satoshis` is not respected when validating splice contributions, we leave this for follow-up work.
85/100 · StrongMessage clarity
✓ Specific, descriptive subject✓ Names a concrete action or component✓ Provides detailed explanatory context✓ Explains rationale or failure mode
Why it was queued
signing or wallet pathsecond-pass: security-sensitive path
AI review queuedAdd `AvailableBalances::next_splice_out_maximum_sat`by Leo Nash · 1d28afca · May 5, 2026 · 5 filesMessage 63 · AdequateTriage 12Details
We previously determined this value by subtracting the htlcs, the anchors, and the commitment transaction fee. This ignored the reserve, as well as the at-least-one-output requirement in zero-reserve channels.
This new field now accounts for both of these constraints. It can be seen as the total spliceable balance from the channel.