mirror of
https://github.com/luxfi/consensus.git
synced 2026-09-24 00:26:58 +00:00
The epoch bound admitted any block whose parent it did not track — "an orphan cannot extend finalized history anyway". An orphan only stays one as long as the sender withholds its parent, so a child sent first with a stale epoch was tracked at that epoch, and nothing re-read it when the parent arrived. An untracked-parent block now must also clear the finalized tip's epoch, which no arrival order can lower. The two doors are collapsed onto one predicate. The gossip door open-coded the tracked-parent case only, so the same block it admitted reached the catch-up door and then VM.Accept; epochRegresses is the single site now. This raises the cost but does not close the class: the bound is still evaluated ONCE, at arrival, so a stale epoch above the finalized floor with a withheld-then-delivered parent is still tracked without re-validation. Closing that needs the child's epoch re-checked against its parent when the parent lands, which is a change to WHEN the bound runs. TestEpochOrder_* stay in the tree, failing, as the standing evidence for that work. Co-authored-by: Hanzo Dev <[email protected]>