Repository navigation
fix: NativeHLSTextTracks adopts dash.js text tracks a second time (stack overflow / hang with DASH subtitles) - #1856
Conversation
|
Thank you for this pull request, and for the time you've put into Vidstack. Vidstack Player is now in security-only maintenance. Until January 2028, we'll merge priority security fixes into 1.x and nothing else, so we're closing pull requests that don't fix a security issue, and this one won't be merged. The teams behind Vidstack, Plyr, Media Chrome, and Video.js now work on Video.js 10. If this change applies there, we'd love a pull request or issue in videojs/video.js. The migration guide shows where Vidstack concepts live in Video.js 10: React · Web components and other frameworks. Migrating with a coding agent? Paste the prompt from the guide's AI Quickstart section into your agent: React · Web components and other frameworks. If this fixes a security vulnerability, comment here and we'll review it. For a vulnerability that isn't public yet, follow SECURITY.md instead. |
Related:
Fixes #1604 (likely also the unreproduced #1231).
Description:
NativeHLSTextTracksexists to discover text tracks that the native playback engine created (Safari + embedded HLS). It is constructed whenevercanPlayType('application/vnd.apple.mpegurl')is non-empty — which is"maybe"on Chromium/Chrome and Safari (Firefox answers"") — and it adopts every native track that has no<track>element.dash.js creates its text tracks the same way (
addTextTrack(), marked withmanualMode), and the DASH provider already registers those fromTEXT_TRACKS_ADDED. So on Chromium/Safari every DASH subtitle track ends up as twoTextTracks in the model (dash-captions-0and one with id"") bound to the same native track.TextTrackList's single-showing rule then disables one whileNativeTextRenderer#onChangere-derives "showing" from the shared native track — a synchronous flip-flop:With native controls this surfaces as a burst of thousands of
Maximum call stack size exceedederrors (playback recovers); with the default custom layout (<Captions />) the page hangs instead.This PR makes
NativeHLSTextTracksskip native tracks that a JS engine owns (manualModemarker) or that are already referenced by a registeredTextTrack.Ready?
Yes.
Anything Else?
Minimal reproduction, no application code — a static page using the CDN build and a public reference stream:
Open in Chrome →
RangeError: Maximum call stack size exceededin the console;p.textTrackslists the single English subtitle twice. Replacecontrolswith<media-video-layout>→ the page freezes. The same page with an HLS source (oneTextTrackper subtitle) is clean, and so is Firefox (noNativeHLSTextTracksthere becausecanPlayTypereturns"").Verified the fix against the built package (1.15.6 with this change applied to the dist chunks) on a real DASH stream with 12 subtitle languages: Chromium/Chrome go from ~6000 errors to 0 with correct track selection, Firefox unchanged, and the
<Captions />layout no longer hangs and renders cues.Review Process:
manualModeis the intended marker for dash.js-created tracks (it is the same check the DASH provider uses in#onTextTracksAdded).manualModeand are not pre-registered, so they still pass).