multi: Small Determinism Fixups#308
Merged
Merged
Conversation
The payment event heap previously ordered events by execution time alone. When two events are scheduled for the same instant, the BinaryHeap pop order was unspecified, making otherwise-seeded runs non-reproducible. Break ties on the source node's public key. The heap holds at most one event per source at a time, so (execution_time, source) is a total order, and Eq is made consistent with the new Ord. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Two select! loops still polled their branches in tokio's default random order: the payment-failure result send in produce_simulation_results, and the interceptor-result drain in the SimNode HTLC forwarding path. Random branch selection is a source of run-to-run non-determinism. Make both biased so their poll order is fixed. Branch order is unchanged, so behaviour is identical save for the now-deterministic ordering. The shutdown listener already sits first in the failure-send loop, matching the shutdown-first convention used elsewhere. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
send_payment stamped each Payment's dispatch_time with SystemTime::now(), bypassing the simulation clock. Under discrete-event simulation the wall clock does not advance with virtual time, so this both broke virtual-time timestamps and made results non-reproducible. Stamp the dispatch time from the simulation clock once the inter-payment wait has elapsed, and thread it into send_payment as an argument. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
The latency interceptor sampled its forwarding delay from rand::thread_rng(), an unseeded global RNG. That made HTLC latencies non-reproducible even when the simulation was given a fixed seed. Hold a seedable StdRng on the interceptor (behind a mutex, since it is shared across concurrent HTLCs) and seed it from the new_poisson constructor. The CLI threads its fixed seed through when building the interceptor. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
elnosh
approved these changes
Jun 24, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
A few low hanging fruit for improving determinism courtesy of claude.