Dash-Industry-Forum / DASH-IF-IOP

DASH-IF Interoperability Points issue tracker and document source code
31 stars 7 forks source link

Simplifying representation of multi-key encrypted video tracks #400

Open technogeek00 opened 3 years ago

technogeek00 commented 3 years ago

In order to present premium video content across a wide ecosystem devices it is becoming increasingly necessary to utilize an extensive set of encryption keys to maintain robust security of content distribution.

To illustrate this let me use a practical example of encryption key assignment for an encode that tops out at UltraHD + HDR:

Dynamic Range Encoding Encryption Key
SDR 270p A
SDR 360p A
SDR 480p A
SDR 720p (Low) B
SDR 720p (High) B
SDR 1080p (Low) C
SDR 1080p (High) C
SDR 1440p (Low) D
SDR 1440p (High) D
SDR 2160p (Low) D
SDR 2160p (High) D
HDR 270p E
HDR 360p E
HDR 480p E
HDR 720p (Low) F
HDR 720p (High) F
HDR 1080p (Low) G
HDR 1080p (High) G
HDR 1440p (Low) H
HDR 1440p (High) H
HDR 2160p (Low) H
HDR 2160p (High) H

Due to the varying security environments that different resolutions of video will be distributable in and contractual requirements dictating explicit key separations, you end up with needing 8 keys to represents 2 encoding ladders.

When representing this in DASH, we currently have the following constraint (IOP v4.3 7.7.1 ISO BMFF Content Protection Constraints):

There SHALL be identical values of default_KID in the Track Encryption Box (‘tenc’) of all Representation referenced by one Adaptation Set. Different Adaptation Sets may have equal or different values of default_KID.

This means a multi-key encrypted video asset like the example above would require 8 Adaptation Sets where the 4 for SDR and 4 for HDR are signalled to be cross-adaptable (integer values equal for AdaptationSet@segmentAlignment or AdaptationSet@subsegmentAlignment). Here is a partial illustration of this phenomenon with the SDR Adaptation Sets, HDR and audio omitted for size:

<Period id="content-0" start="PT0.0S" duration="PT...S">
    <BaseURL serviceLocation="source1">https://stream.example.com/...</BaseURL>
    <AdaptationSet id="1" mimeType="video/mp4" segmentAlignment="1" bitstreamSwitching="true">
        <Role schemeIdUri="urn:mpeg:dash:role:2011" value="main"/>
        <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="2f284c6574025af887eaebf782b398d6"/>
        <ContentProtection schemeIdUri="urn:uuid:edef8ba9-79d6-4ace-a3c8-27dcd51d21ed">
            <cenc:pssh><!-- Widevine PSSH for KID 2f284c6574025af887eaebf782b398d6--></cenc:pssh>
        </ContentProtection>
        <ContentProtection schemeIdUri="urn:uuid:9a04f079-9840-4286-ab92-e65be0885f95">
            <cenc:pssh><!-- PlayReady PSSH for KID 2f284c6574025af887eaebf782b398d6--></cenc:pssh>
        </ContentProtection>
        <Representation id="sdr-486" codecs="hev1.2.4.L90.90" bandwidth="1329996" startWithSAP="1" width="864" height="486" frameRate="24000/1001">
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-270" codecs="hev1.2.4.L63.90" bandwidth="585402" startWithSAP="1" width="480" height="270" frameRate="24000/1001">
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-360" codecs="hev1.2.4.L63.90" bandwidth="881592" startWithSAP="1" width="640" height="360" frameRate="24000/1001">
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
    </AdaptationSet>
    <AdaptationSet id="2" mimeType="video/mp4" segmentAlignment="1" bitstreamSwitching="true">
        <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="01e0ab6b0de541a4bc2637af6a5bfeb9"/>
        <ContentProtection schemeIdUri="urn:uuid:edef8ba9-79d6-4ace-a3c8-27dcd51d21ed">
            <cenc:pssh><!-- Widevine PSSH for KID 01e0ab6b0de541a4bc2637af6a5bfeb9--></cenc:pssh>
        </ContentProtection>
        <ContentProtection schemeIdUri="urn:uuid:9a04f079-9840-4286-ab92-e65be0885f95">
            <cenc:pssh><!-- PlayReady PSSH for KID 01e0ab6b0de541a4bc2637af6a5bfeb9--></cenc:pssh>
        </ContentProtection>
        <Representation id="sdr-720-low" codecs="hev1.2.4.L93.90" bandwidth="2323628" startWithSAP="1" width="1280" height="720" frameRate="24000/1001">
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-720-high" codecs="hev1.2.4.L93.90" bandwidth="3169544" startWithSAP="1" width="1280" height="720" frameRate="24000/1001">
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
    </AdaptationSet>
    <AdaptationSet id="3" mimeType="video/mp4" segmentAlignment="1" bitstreamSwitching="true">
        <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="c9fa435f49d840c789277e3bf67580a6"/>
        <ContentProtection schemeIdUri="urn:uuid:edef8ba9-79d6-4ace-a3c8-27dcd51d21ed">
            <cenc:pssh><!-- Widevine PSSH for KID c9fa435f49d840c789277e3bf67580a6--></cenc:pssh>
        </ContentProtection>
        <ContentProtection schemeIdUri="urn:uuid:9a04f079-9840-4286-ab92-e65be0885f95">
            <cenc:pssh><!-- PlayReady PSSH for KID c9fa435f49d840c789277e3bf67580a6--></cenc:pssh>
        </ContentProtection>
        <Representation id="sdr-1080-low" codecs="hev1.2.4.L120.90" bandwidth="4851328" startWithSAP="1" width="1920" height="1080" frameRate="24000/1001">
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-1080-high" codecs="hev1.2.4.L123.90" bandwidth="6544077" startWithSAP="1" width="1920" height="1080" frameRate="24000/1001">
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
    </AdaptationSet>
    <AdaptationSet id="4" mimeType="video/mp4" segmentAlignment="1" bitstreamSwitching="true">
        <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="68eabb0ea41f4a2ba1c6c7f16be33099"/>
        <ContentProtection schemeIdUri="urn:uuid:edef8ba9-79d6-4ace-a3c8-27dcd51d21ed">
            <cenc:pssh><!-- Widevine PSSH for KID 68eabb0ea41f4a2ba1c6c7f16be33099--></cenc:pssh>
        </ContentProtection>
        <ContentProtection schemeIdUri="urn:uuid:9a04f079-9840-4286-ab92-e65be0885f95">
            <cenc:pssh><!-- PlayReady PSSH for KID 68eabb0ea41f4a2ba1c6c7f16be33099--></cenc:pssh>
        </ContentProtection>
        <Representation id="sdr-1440-low" codecs="hev1.2.4.L150.90" bandwidth="8129748" startWithSAP="1" width="2560" height="1440" frameRate="24000/1001">
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-1440-high" codecs="hev1.2.4.L150.90" bandwidth="10188933" startWithSAP="1" width="2560" height="1440" frameRate="24000/1001">
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-2160-low" codecs="hev1.2.4.L150.90" bandwidth="14798065" startWithSAP="1" width="3840" height="2160" frameRate="24000/1001">
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-2160-high" codecs="hev1.2.4.L153.90" bandwidth="20306583" startWithSAP="1" width="3840" height="2160" frameRate="24000/1001">
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
    </AdaptationSet>
    <!-- Omitted 4 HDR Adaptation Sets and various audio Adaptation Sets -->
</Period>

Even using SegmentBase this is a verbose manifest, if someone were to use SegmentTimeline the repeating of the timeline would exponentiate the size here. While the DASH AMD1 mechanism for compressing ContentProtection usage can be utilized, it does not address the Adaptation Set structure verbosity. During playout the expectation would be for the player to consider the Adaptation Sets as a fully adaptable range and we would prefer to optimize the key acquisition flow to fetch all keys immediately and dynamically remove from adaptation consideration Representations that the CDM cannot support protection of.

After researching options for awhile, we could not find a solid reason for this restriction to continue existing as multi-key support across CDMs is fairly widespread and the fraction of devices that cannot will properly fallback to challenges based on the ISOBMFF signalled KID for the segments. Therefore we would like to propose the following changes to the DASH-IF guidelines, but we think similar restriction reductions may be needed in the DASH CMAF Profile as well:

We believe these changes will allow for players to optimize their start-up flows, while having in-manifest signalling of encryption key KIDs in order to properly communicate with the system CDM and blacklist representations the CDM has determined it cannot provide protection for.

Utilizing this proposal the above example would be simplified to the following:

<Period id="content-0" start="PT0.0S" duration="PT...S">
    <BaseURL serviceLocation="source1">https://stream.example.com/...</BaseURL>
    <AdaptationSet id="1" mimeType="video/mp4" segmentAlignment="true" bitstreamSwitching="true">
        <Role schemeIdUri="urn:mpeg:dash:role:2011" value="main"/>
        <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="2f284c6574025af887eaebf782b398d6 01e0ab6b0de541a4bc2637af6a5bfeb9 c9fa435f49d840c789277e3bf67580a6 68eabb0ea41f4a2ba1c6c7f16be33099"/>
        <SupplementalProperty schemeIdUri="https://dashif.org/identifiers/content_protection/least_restrictive_key" value="2f284c6574025af887eaebf782b398d6" />
        <ContentProtection schemeIdUri="urn:uuid:edef8ba9-79d6-4ace-a3c8-27dcd51d21ed">
            <cenc:pssh><!-- Widevine PSSH for all KIDs--></cenc:pssh>
        </ContentProtection>
        <ContentProtection schemeIdUri="urn:uuid:9a04f079-9840-4286-ab92-e65be0885f95">
            <cenc:pssh><!-- PlayReady PSSH for all KIDs--></cenc:pssh>
        </ContentProtection>
        <Representation id="sdr-486" codecs="hev1.2.4.L90.90" bandwidth="1329996" startWithSAP="1" width="864" height="486" frameRate="24000/1001">
            <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="2f284c6574025af887eaebf782b398d6"/>
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-270" codecs="hev1.2.4.L63.90" bandwidth="585402" startWithSAP="1" width="480" height="270" frameRate="24000/1001">
            <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="2f284c6574025af887eaebf782b398d6"/>
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-360" codecs="hev1.2.4.L63.90" bandwidth="881592" startWithSAP="1" width="640" height="360" frameRate="24000/1001">
            <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="2f284c6574025af887eaebf782b398d6"/>
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-720-low" codecs="hev1.2.4.L93.90" bandwidth="2323628" startWithSAP="1" width="1280" height="720" frameRate="24000/1001">
            <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="01e0ab6b0de541a4bc2637af6a5bfeb9"/>
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-720-high" codecs="hev1.2.4.L93.90" bandwidth="3169544" startWithSAP="1" width="1280" height="720" frameRate="24000/1001">
            <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="01e0ab6b0de541a4bc2637af6a5bfeb9"/>
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-1080-low" codecs="hev1.2.4.L120.90" bandwidth="4851328" startWithSAP="1" width="1920" height="1080" frameRate="24000/1001">
            <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="c9fa435f49d840c789277e3bf67580a6"/>
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-1080-high" codecs="hev1.2.4.L123.90" bandwidth="6544077" startWithSAP="1" width="1920" height="1080" frameRate="24000/1001">
            <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="c9fa435f49d840c789277e3bf67580a6"/>
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-1440-low" codecs="hev1.2.4.L150.90" bandwidth="8129748" startWithSAP="1" width="2560" height="1440" frameRate="24000/1001">
            <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="68eabb0ea41f4a2ba1c6c7f16be33099"/>
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-1440-high" codecs="hev1.2.4.L150.90" bandwidth="10188933" startWithSAP="1" width="2560" height="1440" frameRate="24000/1001">
            <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="68eabb0ea41f4a2ba1c6c7f16be33099"/>
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-2160-low" codecs="hev1.2.4.L150.90" bandwidth="14798065" startWithSAP="1" width="3840" height="2160" frameRate="24000/1001">
            <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="68eabb0ea41f4a2ba1c6c7f16be33099"/>
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
        <Representation id="sdr-2160-high" codecs="hev1.2.4.L153.90" bandwidth="20306583" startWithSAP="1" width="3840" height="2160" frameRate="24000/1001">
            <ContentProtection schemeIdUri="urn:mpeg:dash:mp4protection:2011" value="cenc" cenc:default_KID="68eabb0ea41f4a2ba1c6c7f16be33099"/>
            <BaseURL>...</BaseURL>
            <SegmentBase indexRange="..." indexRangeExact="true">
                <Initialization range="..."/>
            </SegmentBase>
        </Representation>
    </AdaptationSet>
    <!-- Omitted HDR Adaptation Set and various audio Adaptation Sets -->
</Period>
haudiobe commented 2 years ago

@lpiron @technogeek00 is this still relevant?

lpiron commented 2 years ago

This is one of the bugs we need to address in the next version of Part 6. Still relevant.

technogeek00 commented 2 years ago

Yes just unfortunately I've not had the time to move the proposal forward.

RufaelDev commented 10 months ago

@lpiron @haudiobe maybe good to bring this up again in IOP, we need to know if this optimization is worth (potentially) breaking backward compatiblity, as far as I know adaptation set switching support is also limited.

yueming198306 commented 2 weeks ago

Hi, I recently start working on multi key feature on DASH and came across this ticket. Is there any progress on multi key support? Will v6 include it?