From 275e7d3dbddd04792b472a06ff808f748237f8d5 Mon Sep 17 00:00:00 2001 From: ibaker Date: Wed, 26 Feb 2025 07:23:23 -0800 Subject: [PATCH] Rewrite ClearKey UUID to Common PSSH UUID in PSSH box on API < 27 Without this change, content that contains a PSSH box with only the ClearKey UUID is not playable on devices with API < 27. This includes our `sample_fragmented_clearkey.mp4` test content. PiperOrigin-RevId: 731308444 --- .../media3/exoplayer/drm/FrameworkMediaDrm.java | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/drm/FrameworkMediaDrm.java b/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/drm/FrameworkMediaDrm.java index dae849a3d1..7da5ae5535 100644 --- a/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/drm/FrameworkMediaDrm.java +++ b/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/drm/FrameworkMediaDrm.java @@ -42,6 +42,7 @@ import androidx.media3.common.util.UnstableApi; import androidx.media3.common.util.Util; import androidx.media3.exoplayer.analytics.PlayerId; import androidx.media3.extractor.mp4.PsshAtomUtil; +import androidx.media3.extractor.mp4.PsshAtomUtil.PsshAtom; import java.nio.ByteBuffer; import java.nio.ByteOrder; import java.nio.charset.StandardCharsets; @@ -477,8 +478,7 @@ public final class FrameworkMediaDrm implements ExoMediaDrm { } private static UUID adjustUuid(UUID uuid) { - // ClearKey had to be accessed using the Common PSSH UUID prior to API level 27. - return Util.SDK_INT < 27 && C.CLEARKEY_UUID.equals(uuid) ? C.COMMON_PSSH_UUID : uuid; + return cdmRequiresCommonPsshUuid(uuid) ? C.COMMON_PSSH_UUID : uuid; } private static byte[] adjustRequestInitData(UUID uuid, byte[] initData) { @@ -493,6 +493,13 @@ public final class FrameworkMediaDrm implements ExoMediaDrm { PsshAtomUtil.buildPsshAtom( C.PLAYREADY_UUID, addLaUrlAttributeIfMissing(schemeSpecificData)); } + if (cdmRequiresCommonPsshUuid(uuid)) { + PsshAtom psshAtom = PsshAtomUtil.parsePsshAtom(initData); + if (psshAtom != null) { + initData = + PsshAtomUtil.buildPsshAtom(C.COMMON_PSSH_UUID, psshAtom.keyIds, psshAtom.schemeData); + } + } // Prior to API level 21, the Widevine CDM required scheme specific data to be extracted from // the PSSH atom. We also extract the data on API levels 21 and 22 because these API levels @@ -534,6 +541,11 @@ public final class FrameworkMediaDrm implements ExoMediaDrm { return requestData; } + private static boolean cdmRequiresCommonPsshUuid(UUID uuid) { + // ClearKey had to be accessed using the Common PSSH UUID prior to API level 27. + return Util.SDK_INT < 27 && Objects.equals(uuid, C.CLEARKEY_UUID); + } + private static void forceWidevineL3(MediaDrm mediaDrm) { mediaDrm.setPropertyString("securityLevel", "L3"); }