Skip to content

AetherEngine 5.20.0

Choose a tag to compare

@superuser404notfound superuser404notfound released this 23 Jul 03:26

Fixed

A #168-rerouted live session that loses its ingest now recovers in-engine instead of cycling through the doomed native mount (#199)

When the live-ingest loopback session behind the #168 reroute (HEVC-in-MPEG-TS masters that AVPlayer plays audio-only) lost its source mid-session, the pump exit delegated straight to a host retune. A host that answers by re-tuning the same URL relanded on the native bypass, which deterministically builds no video track for that master, so the session re-ran the whole reroute dance (native mount, ~4 s carriage-watchdog grace, reroute, loopback rejoin) roughly every 13 s. The trigger class is real beyond test-beds: MEDIA-SEQUENCE resets from encoder restarts, CDN gaps that outlive the refresh-retry budget, and upstream ENDLIST all funneled into the same teardown.

Three layers, from source to session:

  • MEDIA-SEQUENCE reset rejoin. The ingest playlist tracker treats three consecutive refreshes whose whole window sits behind the cursor as an axis reset and rejoins at the new edge under an EXT-X-DISCONTINUITY seam, instead of starving the reader into its ingestStalled terminal. Isolated stale-CDN-edge regressions do not trip it, and regressions never feed the stall counter.
  • Reroute verdict memory. Masters whose video-carriage watchdog fired are remembered (bounded to 32 entries, 6 h expiry, exact-URL keyed). A later load() of the same URL under the same gates (live, ingest fallback enabled) routes straight onto the live-ingest loopback, skipping the doomed native mount and its watchdog grace entirely. Survives stop()/load() seams, so zap-away-and-back stays cheap.
  • In-session reopen for engine-created ingest readers. eof/readError/keyframeStarvation pump exits on an engine-created HLSLiveIngestReader session now rebuild a fresh reader through the existing bounded live-reopen machinery (fresh demuxer over the new reader, continuation segment indices, discontinuity seam) instead of tearing the player session down. Only an exhausted reopen budget (attempt cap or barren cycles) halts production and surfaces liveSourceReset, so hosts keep their last-resort retune signal. Host-provided custom readers (disc, SMB) and demuxed-audio companion sessions keep the immediate host-retune contract.

New public surface (hence the minor bump): HLSVideoEngine.CustomSourceReopenFactory. Behavior of LoadOptions.nativeRemoteHLSIngestFallback is unchanged; hosts that opted out of the #168 fallback are never silently rerouted by the verdict memory either.

Covered by Issue199RerouteRecoveryTests, extended HLSPlaylistTrackerTests, and the reopenable-semantics update in LiveProductionHaltTests.

Acknowledgements

Thanks to @kskchaitanya1993 for the deep-window field trace on #189/#199 that separated this defect from the live-edge holdback fix and pinned the ~13 s cycle end to end.