1

I need to play DRM protected content offline. I two files stored in local storage; a dash file that points to the an mp4 file in the same directory.

The file's key is also stored in a database and retrieved when playback is initiated.

However, after building the DRM session, the following error is thrown:

playerFailed [1.04]
com.google.android.exoplayer2.ExoPlaybackException
    at com.google.android.exoplayer2.mediacodec.MediaCodecRenderer.feedInputBuffer(MediaCodecRenderer.java:691)
    at com.google.android.exoplayer2.mediacodec.MediaCodecRenderer.render(MediaCodecRenderer.java:507)
    at com.google.android.exoplayer2.ExoPlayerImplInternal.doSomeWork(ExoPlayerImplInternal.java:466)
    at com.google.android.exoplayer2.ExoPlayerImplInternal.handleMessage(ExoPlayerImplInternal.java:300)
    at android.os.Handler.dispatchMessage(Handler.java:98)
    at android.os.Looper.loop(Looper.java:148)
    at android.os.HandlerThread.run(HandlerThread.java:61)
    at com.google.android.exoplayer2.util.PriorityHandlerThread.run(PriorityHandlerThread.java:40)
 Caused by: android.media.MediaCodec$CryptoException: Error decrypting data: requested key has not been loaded
    at android.media.MediaCodec.native_queueSecureInputBuffer(Native Method)
    at android.media.MediaCodec.queueSecureInputBuffer(MediaCodec.java:2292)
    at com.google.android.exoplayer2.mediacodec.MediaCodecRenderer.feedInputBuffer(MediaCodecRenderer.java:682)
    at com.google.android.exoplayer2.mediacodec.MediaCodecRenderer.render(MediaCodecRenderer.java:507) 
    at com.google.android.exoplayer2.ExoPlayerImplInternal.doSomeWork(ExoPlayerImplInternal.java:466) 
    at com.google.android.exoplayer2.ExoPlayerImplInternal.handleMessage(ExoPlayerImplInternal.java:300) 
    at android.os.Handler.dispatchMessage(Handler.java:98) 
    at android.os.Looper.loop(Looper.java:148) 
    at android.os.HandlerThread.run(HandlerThread.java:61) 
    at com.google.android.exoplayer2.util.PriorityHandlerThread.run(PriorityHandlerThread.java:40) 

I use this block to check whether a given track has a key or not before requesting for a new one.

private DrmSessionManager<FrameworkMediaCrypto> buildDrmSessionManager(UUID uuid, String licenseURL,
                                                                           Map<String, String> keyRequestProperties) throws UnsupportedDrmException {
        HttpMediaDrmCallback drmCallback = new HttpMediaDrmCallback(licenseURL, buildHttpDataSourceFactory(false), keyRequestProperties);

        defaultDrmSessionManager = new DefaultDrmSessionManager<>(uuid, FrameworkMediaDrm.newInstance(uuid), drmCallback, null, mainHandler, eventLogger);

        if (track != null) {
            DrmKey key = realm.where(DrmKey.class).equalTo("trackId", track.getId()).findFirst();

            Log.e("TrackId", track.getId());

            if (key != null) {
                byte[] offlineKeySetId = Base64.decode(key.getRequestKey(), Base64.DEFAULT);
                defaultDrmSessionManager.setMode(DefaultDrmSessionManager.MODE_QUERY, offlineKeySetId);
                Log.e("Key", key.getRequestKey());

                Log.e(MusicService.class.getSimpleName(), "OfflineKeySet already defined, using the existing one : " + key.getRequestKey());
            } else {
                defaultDrmSessionManager.setMode(DefaultDrmSessionManager.MODE_DOWNLOAD, null);
                Log.e(MusicService.class.getSimpleName(), "Offline key not defined, retrieving a new licence");
            }
        }

        return defaultDrmSessionManager;
    }

For all the offline files I try to play, the key is always available. Why then is it that exoplayer fails to play any of the files?

Alex Kombo
  • 3,256
  • 8
  • 34
  • 67

1 Answers1

0

I figured that I had a key mismatch hence the error. The file played when served with the correct key.

Alex Kombo
  • 3,256
  • 8
  • 34
  • 67
  • i am using exoplayer version 2.9.2.I need offlineKeySetId how to get – Ansal Rabin Dec 29 '18 at 06:48
  • @AnsalRabin I had the same problem with newer versions of Exoplayer. I still haven't figured out how to do it yet. – Alex Kombo Jan 07 '19 at 13:12
  • Hello @AlexKombo can you please share the link to a working example of your project if possible. I am a newbie to android and we have a similar use-case wherein DRM encrypted video from a local USB drive needs to be played on an android TV. Thanks. – Pawan Jain Feb 11 '22 at 06:20
  • @PawanJain, unfortunately, I don't have a working sample. That project was from 4 years ago and Android has changed and improved support for offline media. – Alex Kombo Feb 14 '22 at 13:19
  • Yes Alex, ExoPlayer now directly supports AES encrypted mp4 file - the details are explained here https://stackoverflow.com/questions/38729220/reproducing-encrypted-video-using-exoplayer/64799650#64799650 – Pawan Jain Feb 15 '22 at 06:14
  • @PawanJain I have a similar use case. If you have succeeded, can you point me to any material that can help me? – hardik9850 Oct 17 '22 at 05:33
  • Thanks to Javi, we adapted his Encrypted Video Android Player Code from his repo - https://github.com/Javi/AndroidCbcDecryptingExoplayer – Pawan Jain Oct 18 '22 at 06:50