feat(tracks): probe HDR10 tracks for HDR10+ SEI before selection

Relabel HEVC HDR10 tracks whose first fragment carries ST 2094-40 SEI as HDR10P, for dl, the REST API and remote sessions. Config key hdr10plus_probe (default true).
This commit is contained in:
imSp4rky
2026-10-17 18:58:48 -06:00
parent 338adc5ff0
commit 811e0a19c0
11 changed files with 484 additions and 22 deletions
+31
View File
@@ -370,6 +370,37 @@ dual_multi_mode: strict
Regional variants of the same base language (e.g. `en-US` and `en-GB`) collapse to a single
language in both modes, so they never trigger `{dual}` on their own.
## `hdr10plus_probe`
- **Type:** `bool`  ·  **Default:** `true`
Find the HDR10+ tracks that a service labels as HDR10. Before unshackle lists or selects tracks, it
reads the first fragment of HEVC HDR10 tracks from DASH, HLS fMP4 and one-file sources. A track
whose first frame carries HDR10+ (SMPTE ST 2094-40) metadata becomes `HDR10P`. Then `-r HDR10P`,
`--list` and [`--generate-dv`](../../guide/downloading.md#dolby-vision-from-hdr10) use it.
When two HDR10 tracks have the same resolution, they can be an HDR10 encode and an HDR10+ encode
side by side, so unshackle probes every track. When each track has its own resolution, unshackle
probes the two highest and the two lowest bitrates first:
| Result | Action |
|--------|--------|
| All four carry HDR10+ | Every HDR10 track of the title becomes `HDR10P`. |
| Some carry HDR10+ | The title has HDR10 and HDR10+ encodes side by side, so unshackle probes every track. |
| None carry HDR10+ | Every track stays `HDR10`. |
A probe that fails, or a fragment whose metadata is encrypted, keeps the label from the service.
unshackle does not probe ISM tracks. Each probe makes one to three small requests: the 64 KiB
fragment, plus the playlist of an HLS track or the header of a one-file track. The probes run in
parallel, with no more at a time than `--workers` (or `dl.workers`) sets for a track download.
```yaml
hdr10plus_probe: true
```
A remote server probes its tracks before it sends them, so the setting on the server applies to
remote downloads and to the REST API.
## `generate_dv_mode`
- **Type:** `str`  ·  **Default:** `v29`
+1 -1
View File
@@ -31,7 +31,7 @@ Where the file lives, how unshackle discovers it, and how to edit it:
|------|------|
| [Directories](directories.md) | `directories`, `filenames`, `services_repo_force` |
| [Services & authentication](services.md) | `services`, `credentials`, `firefox_cookies`, `remote_services`, `serve` |
| [Download & processing](download.md) | `dl`, `continue_downloads`, `merge_segments`, `subtitle`, `audio`, `muxing`, `language_tags`, `dual_multi_mode`, `generate_dv_mode` |
| [Download & processing](download.md) | `dl`, `continue_downloads`, `merge_segments`, `subtitle`, `audio`, `muxing`, `language_tags`, `dual_multi_mode`, `generate_dv_mode`, `hdr10plus_probe` |
| [Output & naming](output.md) | `output_template`, `tag`, `tag_rules`, `tag_group_name`, `tag_imdb_tmdb`, `chapter_fallback_name`, `unicode_filenames` |
| [DRM & CDM](drm.md) | `cdm`, `remote_cdm`, `decryption` |
| [Network & proxy](network.md) | `network`, `headers`, `proxy_providers` |