Skip to content

lnruntime: Compose native Ark channel state machines - #1191

Open
sputn1ck wants to merge 4 commits into
kon/ark-channel-lifecyclefrom
kon/ark-channel-lnd-runtime
Open

lnruntime: Compose native Ark channel state machines#1191
sputn1ck wants to merge 4 commits into
kon/ark-channel-lifecyclefrom
kon/ark-channel-lnd-runtime

Conversation

@sputn1ck

@sputn1ck sputn1ck commented Aug 24, 2026

Copy link
Copy Markdown
Member

Summary

  • compose lnd's funding, link, invoice, payment, channel-close, and contract-resolution state machines without running a full lnd daemon
  • keep payments fixed to the private client-to-hub leg while retaining lnd's durable channel and payment accounting
  • hand materialization and source unrolling to Wavelength before lnd publishes channel transactions
  • expose a channel as active only after its reserved-SCID link can actually carry HTLCs

This is layer 3 of 5 in the Ark channels stack. It depends on #1190; the next layer is #1192.

Testing

  • go test ./lnruntime
  • go test ./oor ./arkchannel/... ./lnruntime ./waved ./db
  • make build
  • make lint-changed-local

Consume the reviewed lnd fork that exposes external funding and
lifecycle barriers without embedding a second daemon.
Instantiate lnd channel, link, invoice, payment, funding, and close
state machines behind one process-owned runtime.
Expose chain notification and fee boundaries required by the native
channel runtime over the existing wallet backends.
Copilot AI lite review requested due to automatic review settings August 24, 2026 14:37

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 5e0f7c6a9f

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

return
}

case _, ok := <-registration.Reorged:

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Preserve confirmation sequence ordering across reorg channels

When a confirmation, reorg, and reconfirmation are buffered concurrently, the select may receive the newer Confirmed event before the older Reorged event. This branch discards the reorg sequence number, so it cannot reject that stale reorg and can leave the downstream lnd watcher unconfirmed even though the transaction has already reconfirmed. Track the highest shared TxConfirmation.Seq/reorg sequence and suppress older events.

Useful? React with 👍 / 👎.

return
}

case _, ok := <-registration.Reorged:

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Preserve spend sequence ordering across reorg channels

If a spend, its reorg, and a subsequent re-spend are all buffered, this select can forward the newer re-spend first and then forward the stale reorg because the shared sequence value is ignored. The downstream lnd resolver can consequently finish in the unspent state and miss the current spender; compare SpendDetail.Seq with the reorg sequence and discard stale events.

Useful? React with 👍 / 👎.

Comment on lines +139 to +143
if epoch.Height == lastHeight &&
epoch.Hash == lastHash {

continue
}

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Skip block epochs older than the registration snapshot

During a burst of blocks, more than one epoch can be queued after RegisterBlocks but before BestBlock returns. For example, if heights H+1 and H+2 queue while BestBlock reports H+2, the goroutine seeds H+2 and then forwards H+1 followed by H+2 because it only removes exact duplicates, producing a regressing block stream. Ignore queued epochs older than the snapshot while still allowing same-height hash changes for reorg handling.

Useful? React with 👍 / 👎.

Comment on lines +184 to +185
func (n *BackendChainNotifier) Stop() error {
n.started.Store(false)

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Cancel adapter-owned registrations during Stop

When this adapter is stopped while the shared backend remains running, every outstanding confirmation, spend, and block forwarder continues indefinitely because its registration context is rooted at context.Background() and Stop retains no cancellation handles. started also does not prevent new registrations after shutdown. Give the adapter a lifecycle context or track registration cancels so Stop terminates its own workers without stopping the shared backend.

AGENTS.md reference: AGENTS.md:L77-L81

Useful? React with 👍 / 👎.

Copilot stopped reviewing on behalf of sputn1ck due to an error August 24, 2026 14:58
@sputn1ck sputn1ck changed the title kon/ark channel lnd runtime lnruntime: Compose native Ark channel state machines Aug 24, 2026
The durable Ark channel FSM must not expose an active channel until the
native lnd link for its reserved SCID can actually carry HTLCs.
Requiring both the open channel row and switch link removes a race where
the first payment could terminally fail immediately after promotion.
@sputn1ck
sputn1ck force-pushed the kon/ark-channel-lnd-runtime branch from eacb4d1 to 13aac6e Compare August 24, 2026 15:35
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant