feat(epoch): bound memory during epoch processing (ADR-048) - #101
Conversation
|
Review (coordinator) — not ready to merge yet. Blocking items B1–B3, then re-review. B1 — startup gate throws on an uninitialized store (CI B2 — two statements in the ADR-048 text and this PR body are wrong or premature. B3 — unrelated CI/packaging commits in this PR. Non-blocking
Reference: mainnet validation 448–652 = 205 consecutive exact boundaries on the accepted binaries; last-10 boundaries 46–55 s; footprint 0.98–1.1 GiB (peak 1.5). |
|
Re-review of head
Validation reference: mainnet 448–652 on this lineage's binaries = 205 consecutive exact boundaries (in-process AdaPot 296–621, Koios 322–652); last-10 boundaries 46–55 s; footprint 0.98–1.1 GiB (peak 1.5). Follow-ups tracked separately: #99 (DRep distribution vs DBSync — root cause identified on the issue, fix as its own PR), #100 (post-validation cleanup). PR granularity remains the maintainer's call. |
…ration fix(ledger): match Conway PV9 DRep deregistration semantics
Summary
Implements ADR-048's bounded-memory epoch-boundary design and the accepted follow-up optimizations from #97 and #98.
The change replaces mainnet-sized boundary materialization and random-read hot paths with ordered, bounded processing while preserving ledger ordering, rollback semantics, fail-closed fallbacks, and calculation outputs.
Main changes
utxo_stake_balanceindexexposed through
/api/v1/node/epoch-calc-statusdefault | low-memoryresource profile; individual settingsalways override profile defaults and there is no host-memory auto-detection
Closes #97.
Advances #98.
Related follow-ups: #99 and #100.
Correctness and recovery
A deliberate live Conway crash-after-SNAP drill was completed on a disposable
epoch-532 clone on 2026-08-30. The process was killed after the durable snapshot
write and before COMPLETE; restart resumed at step 3 without repeating rewards
or snapshot, completed with exact AdaPot, and took 2.5 seconds. Evidence:
#97 (comment) and
#101 (comment).
Test evidence
33a79207): core-api 276, ledger-state 308, runtime 1,439 (3 skipped), app 316; 2,339 tests, 0 failures4cce4e40): runtime 1,427, 0 failures15410aa3): ledger-state 318, 0 failures008b7ecdchange is diagnostic logging only; the deployed native artifact was built from that exact commit779c713b:./gradlew test -PskipSigning=true, all modules green in 10m28sLive validation
Preprod
Mainnet to tip
Artifact and runtime:
008b7ecd8d194bfff2d9096bbb9923a283d6c3047f2cb1b3e45d9c8841c67e59df08b7091df2129e71cf4160ab58d9ca79f1b411-Xmx1024m, 64 MiB decoded apply queue, two RocksDB background jobsexit-on-epoch-calc-error=trueResults:
inSync=true, steady state, gap 0, peer RUNNING, runtime not degraded at epoch 6521344850365394442/6156552553301488, exactly equal to KoiosFinal ten boundaries:
One transient raw macOS RSS sample reached 2.007 GiB while physical footprint
remained 1.1 GiB and immediately fell. Both raw RSS and physical footprint are
reported; choosing the formal cross-platform acceptance metric remains an
operator decision.
Review notes
an optional Serial-GC binary experiment, and live Linux 2 GiB validation through
three boundaries; no full sync was restarted for these items
Final rollout decision