cdm_adapter.cc revision 0f1bc08d4cfcc34181b0b5cbf065c40f687bf740
1868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)// Copyright 2013 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
58bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#include "media/cdm/ppapi/cdm_adapter.h"
68bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
78bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#include "media/cdm/ppapi/cdm_helpers.h"
80f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)#include "media/cdm/ppapi/supported_cdm_versions.h"
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#if defined(CHECK_DOCUMENT_URL)
1190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include "ppapi/cpp/dev/url_util_dev.h"
1290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include "ppapi/cpp/instance_handle.h"
1390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#endif  // defined(CHECK_DOCUMENT_URL)
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)namespace {
165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool IsMainThread() {
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return pp::Module::Get()->core()->IsMainThread();
195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Posts a task to run |cb| on the main thread. The task is posted even if the
222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// current thread is the main thread.
232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)void PostOnMain(pp::CompletionCallback cb) {
242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  pp::Module::Get()->core()->CallOnMainThread(0, cb, PP_OK);
252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
262a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
272a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Ensures |cb| is called on the main thread, either because the current thread
282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// is the main thread or by posting it to the main thread.
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void CallOnMain(pp::CompletionCallback cb) {
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // TODO(tomfinegan): This is only necessary because PPAPI doesn't allow calls
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // off the main thread yet. Remove this once the change lands.
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (IsMainThread())
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cb.Run(PP_OK);
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  else
352a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    PostOnMain(cb);
365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Configures a cdm::InputBuffer. |subsamples| must exist as long as
395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// |input_buffer| is in use.
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void ConfigureInputBuffer(
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const pp::Buffer_Dev& encrypted_buffer,
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const PP_EncryptedBlockInfo& encrypted_block_info,
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    std::vector<cdm::SubsampleEntry>* subsamples,
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm::InputBuffer* input_buffer) {
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(subsamples);
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(!encrypted_buffer.is_null());
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  input_buffer->data = static_cast<uint8_t*>(encrypted_buffer.data());
492a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  input_buffer->data_size = encrypted_block_info.data_size;
501e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  PP_DCHECK(encrypted_buffer.size() >= input_buffer->data_size);
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  input_buffer->data_offset = encrypted_block_info.data_offset;
522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  PP_DCHECK(encrypted_block_info.key_id_size <=
542a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)            arraysize(encrypted_block_info.key_id));
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  input_buffer->key_id_size = encrypted_block_info.key_id_size;
562a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  input_buffer->key_id = input_buffer->key_id_size > 0 ?
572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      encrypted_block_info.key_id : NULL;
582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  PP_DCHECK(encrypted_block_info.iv_size <= arraysize(encrypted_block_info.iv));
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  input_buffer->iv_size = encrypted_block_info.iv_size;
612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  input_buffer->iv = encrypted_block_info.iv_size > 0 ?
622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      encrypted_block_info.iv : NULL;
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  input_buffer->num_subsamples = encrypted_block_info.num_subsamples;
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (encrypted_block_info.num_subsamples > 0) {
665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    subsamples->reserve(encrypted_block_info.num_subsamples);
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    for (uint32_t i = 0; i < encrypted_block_info.num_subsamples; ++i) {
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      subsamples->push_back(cdm::SubsampleEntry(
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          encrypted_block_info.subsamples[i].clear_bytes,
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          encrypted_block_info.subsamples[i].cipher_bytes));
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    input_buffer->subsamples = &(*subsamples)[0];
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  input_buffer->timestamp = encrypted_block_info.tracking_info.timestamp;
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)PP_DecryptResult CdmStatusToPpDecryptResult(cdm::Status status) {
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  switch (status) {
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case cdm::kSuccess:
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return PP_DECRYPTRESULT_SUCCESS;
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case cdm::kNoKey:
855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return PP_DECRYPTRESULT_DECRYPT_NOKEY;
865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case cdm::kNeedMoreData:
875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return PP_DECRYPTRESULT_NEEDMOREDATA;
885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case cdm::kDecryptError:
895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return PP_DECRYPTRESULT_DECRYPT_ERROR;
905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case cdm::kDecodeError:
915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return PP_DECRYPTRESULT_DECODE_ERROR;
925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    default:
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      PP_NOTREACHED();
945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return PP_DECRYPTRESULT_DECODE_ERROR;
955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)PP_DecryptedFrameFormat CdmVideoFormatToPpDecryptedFrameFormat(
995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm::VideoFormat format) {
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  switch (format) {
1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case cdm::kYv12:
1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return PP_DECRYPTEDFRAMEFORMAT_YV12;
1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case cdm::kI420:
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return PP_DECRYPTEDFRAMEFORMAT_I420;
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    default:
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return PP_DECRYPTEDFRAMEFORMAT_UNKNOWN;
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1101e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)PP_DecryptedSampleFormat CdmAudioFormatToPpDecryptedSampleFormat(
1111e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    cdm::AudioFormat format) {
1121e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  switch (format) {
1131e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    case cdm::kAudioFormatU8:
1141e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      return PP_DECRYPTEDSAMPLEFORMAT_U8;
1151e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    case cdm::kAudioFormatS16:
1161e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      return PP_DECRYPTEDSAMPLEFORMAT_S16;
1171e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    case cdm::kAudioFormatS32:
1181e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      return PP_DECRYPTEDSAMPLEFORMAT_S32;
1191e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    case cdm::kAudioFormatF32:
1201e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      return PP_DECRYPTEDSAMPLEFORMAT_F32;
1211e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    case cdm::kAudioFormatPlanarS16:
1221e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      return PP_DECRYPTEDSAMPLEFORMAT_PLANAR_S16;
1231e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    case cdm::kAudioFormatPlanarF32:
1241e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      return PP_DECRYPTEDSAMPLEFORMAT_PLANAR_F32;
1251e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    default:
1261e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      return PP_DECRYPTEDSAMPLEFORMAT_UNKNOWN;
1271e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  }
1281e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)}
1291e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)cdm::AudioDecoderConfig::AudioCodec PpAudioCodecToCdmAudioCodec(
1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    PP_AudioCodec codec) {
1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  switch (codec) {
1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_AUDIOCODEC_VORBIS:
1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::AudioDecoderConfig::kCodecVorbis;
1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_AUDIOCODEC_AAC:
1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::AudioDecoderConfig::kCodecAac;
1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    default:
1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::AudioDecoderConfig::kUnknownAudioCodec;
1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)cdm::VideoDecoderConfig::VideoCodec PpVideoCodecToCdmVideoCodec(
1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    PP_VideoCodec codec) {
1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  switch (codec) {
1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_VIDEOCODEC_VP8:
1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kCodecVp8;
1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_VIDEOCODEC_H264:
1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kCodecH264;
1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    default:
1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kUnknownVideoCodec;
1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)cdm::VideoDecoderConfig::VideoCodecProfile PpVCProfileToCdmVCProfile(
1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    PP_VideoCodecProfile profile) {
1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  switch (profile) {
1575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_VIDEOCODECPROFILE_VP8_MAIN:
1585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kVp8ProfileMain;
1595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_VIDEOCODECPROFILE_H264_BASELINE:
1605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kH264ProfileBaseline;
1615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_VIDEOCODECPROFILE_H264_MAIN:
1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kH264ProfileMain;
1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_VIDEOCODECPROFILE_H264_EXTENDED:
1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kH264ProfileExtended;
1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_VIDEOCODECPROFILE_H264_HIGH:
1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kH264ProfileHigh;
1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_VIDEOCODECPROFILE_H264_HIGH_10:
1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kH264ProfileHigh10;
1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_VIDEOCODECPROFILE_H264_HIGH_422:
1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kH264ProfileHigh422;
1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_VIDEOCODECPROFILE_H264_HIGH_444_PREDICTIVE:
1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kH264ProfileHigh444Predictive;
1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    default:
1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::VideoDecoderConfig::kUnknownVideoCodecProfile;
1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)cdm::VideoFormat PpDecryptedFrameFormatToCdmVideoFormat(
1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    PP_DecryptedFrameFormat format) {
1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  switch (format) {
1815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_DECRYPTEDFRAMEFORMAT_YV12:
1825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::kYv12;
1835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_DECRYPTEDFRAMEFORMAT_I420:
1845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::kI420;
1855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    default:
1865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::kUnknownVideoFormat;
1875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)cdm::StreamType PpDecryptorStreamTypeToCdmStreamType(
1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    PP_DecryptorStreamType stream_type) {
1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  switch (stream_type) {
1935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_DECRYPTORSTREAMTYPE_AUDIO:
1945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::kStreamTypeAudio;
1955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_DECRYPTORSTREAMTYPE_VIDEO:
1965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return cdm::kStreamTypeVideo;
1975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_NOTREACHED();
2005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return cdm::kStreamTypeVideo;
2015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace
2045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
205ba5b9a6411cb1792fd21f0a078d7a25cd1ceec16Ben Murdochnamespace media {
2065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2078bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)CdmAdapter::CdmAdapter(PP_Instance instance, pp::Module* module)
2085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : pp::Instance(instance),
2095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      pp::ContentDecryptor_Private(this),
2108bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#if defined(OS_CHROMEOS)
2118bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      output_protection_(this),
2128bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      platform_verification_(this),
2138bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      challenge_in_progress_(false),
2148bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      output_link_mask_(0),
2158bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      output_protection_mask_(0),
2168bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      query_output_protection_in_progress_(false),
2178bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#endif
2185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      allocator_(this),
2191e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      cdm_(NULL),
2201e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      deferred_initialize_audio_decoder_(false),
2211e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      deferred_audio_decoder_config_id_(0),
2221e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      deferred_initialize_video_decoder_(false),
2231e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      deferred_video_decoder_config_id_(0) {
2245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  callback_factory_.Initialize(this);
2255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2278bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)CdmAdapter::~CdmAdapter() {}
2282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
2298bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)bool CdmAdapter::CreateCdmInstance(const std::string& key_system) {
2302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  PP_DCHECK(!cdm_);
2318bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  cdm_ = make_linked_ptr(CdmWrapper::Create(
2328bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      key_system.data(), key_system.size(), GetCdmHost, this));
2332a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  return (cdm_ != NULL);
2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2364e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)// No KeyErrors should be reported in this function because they cannot be
2374e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)// bubbled up in the WD EME API. Those errors will be reported during session
2384e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)// creation (aka GenerateKeyRequest).
2398bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::Initialize(const std::string& key_system,
24068043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)                            bool can_challenge_platform) {
2415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(!key_system.empty());
24268043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  PP_DCHECK(key_system_.empty() || (key_system_ == key_system && cdm_));
24368043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)
2444e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  if (!cdm_ && !CreateCdmInstance(key_system))
2454e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)    return;
2464e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)
24768043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  PP_DCHECK(cdm_);
24868043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  key_system_ = key_system;
24968043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)}
25068043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)
2518bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::GenerateKeyRequest(const std::string& type,
25268043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)                                    pp::VarArrayBuffer init_data) {
2534e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  // Initialize() doesn't report an error, so GenerateKeyRequest() can be called
2544e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  // even if Initialize() failed.
2554e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  if (!cdm_) {
2564e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)    SendUnknownKeyError(key_system_, std::string());
2574e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)    return;
2584e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  }
2592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
26090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#if defined(CHECK_DOCUMENT_URL)
26190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  PP_URLComponents_Dev url_components = {};
26290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  pp::Var href = pp::URLUtil_Dev::Get()->GetDocumentURL(
26390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      pp::InstanceHandle(pp_instance()), &url_components);
26490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  PP_DCHECK(href.is_string());
26590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  PP_DCHECK(!href.AsString().empty());
26690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  PP_DCHECK(url_components.host.begin);
26790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  PP_DCHECK(0 < url_components.host.len);
26890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#endif  // defined(CHECK_DOCUMENT_URL)
2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  cdm::Status status = cdm_->GenerateKeyRequest(
2715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      type.data(), type.size(),
2725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      static_cast<const uint8_t*>(init_data.Map()),
2732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      init_data.ByteLength());
2745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(status == cdm::kSuccess || status == cdm::kSessionError);
27568043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  if (status != cdm::kSuccess)
27668043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)    SendUnknownKeyError(key_system_, std::string());
2775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2798bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::AddKey(const std::string& session_id,
2805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        pp::VarArrayBuffer key,
2815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        pp::VarArrayBuffer init_data) {
2824e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  // TODO(jrummell): In EME WD, AddKey() can only be called on valid sessions.
2834e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  // We should be able to DCHECK(cdm_) when addressing http://crbug.com/249976.
2845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!cdm_) {
2852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    SendUnknownKeyError(key_system_, session_id);
2865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
2875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
2885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const uint8_t* key_ptr = static_cast<const uint8_t*>(key.Map());
2901e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  const uint32_t key_size = key.ByteLength();
2915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const uint8_t* init_data_ptr = static_cast<const uint8_t*>(init_data.Map());
2921e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  const uint32_t init_data_size = init_data.ByteLength();
2932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  PP_DCHECK(!init_data_ptr == !init_data_size);
2945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2951e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  if (!key_ptr || !key_size) {
2962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    SendUnknownKeyError(key_system_, session_id);
2975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
2985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
2995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  cdm::Status status = cdm_->AddKey(session_id.data(), session_id.size(),
3015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                    key_ptr, key_size,
3025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                    init_data_ptr, init_data_size);
3035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(status == cdm::kSuccess || status == cdm::kSessionError);
3045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (status != cdm::kSuccess) {
3052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    SendUnknownKeyError(key_system_, session_id);
3065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
3075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
3085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  SendKeyAdded(key_system_, session_id);
3105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3128bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::CancelKeyRequest(const std::string& session_id) {
3134e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  // TODO(jrummell): In EME WD, AddKey() can only be called on valid sessions.
3144e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  // We should be able to DCHECK(cdm_) when addressing http://crbug.com/249976.
3155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!cdm_) {
3162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    SendUnknownKeyError(key_system_, session_id);
3175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
3185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
3195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  cdm::Status status = cdm_->CancelKeyRequest(session_id.data(),
3215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                              session_id.size());
3225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(status == cdm::kSuccess || status == cdm::kSessionError);
3235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (status != cdm::kSuccess)
3242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    SendUnknownKeyError(key_system_, session_id);
3255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Note: In the following decryption/decoding related functions, errors are NOT
3285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// reported via KeyError, but are reported via corresponding PPB calls.
3295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3308bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::Decrypt(pp::Buffer_Dev encrypted_buffer,
3315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         const PP_EncryptedBlockInfo& encrypted_block_info) {
3325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(!encrypted_buffer.is_null());
3335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3342a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // Release a buffer that the caller indicated it is finished with.
3352a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  allocator_.Release(encrypted_block_info.tracking_info.buffer_id);
3362a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
3375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  cdm::Status status = cdm::kDecryptError;
3385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  LinkedDecryptedBlock decrypted_block(new DecryptedBlockImpl());
3395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (cdm_) {
3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm::InputBuffer input_buffer;
3425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    std::vector<cdm::SubsampleEntry> subsamples;
3435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ConfigureInputBuffer(encrypted_buffer, encrypted_block_info, &subsamples,
3445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         &input_buffer);
3455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    status = cdm_->Decrypt(input_buffer, decrypted_block.get());
3462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    PP_DCHECK(status != cdm::kSuccess ||
3472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)              (decrypted_block->DecryptedBuffer() &&
3482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)               decrypted_block->DecryptedBuffer()->Size()));
3495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
3505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  CallOnMain(callback_factory_.NewCallback(
3528bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      &CdmAdapter::DeliverBlock,
3535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      status,
3545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decrypted_block,
3555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      encrypted_block_info.tracking_info));
3565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3588bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::InitializeAudioDecoder(
3595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const PP_AudioDecoderConfig& decoder_config,
3605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    pp::Buffer_Dev extra_data_buffer) {
3611e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  PP_DCHECK(!deferred_initialize_audio_decoder_);
3621e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  PP_DCHECK(deferred_audio_decoder_config_id_ == 0);
3635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  cdm::Status status = cdm::kSessionError;
3645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (cdm_) {
3655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm::AudioDecoderConfig cdm_decoder_config;
3665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_decoder_config.codec =
3675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        PpAudioCodecToCdmAudioCodec(decoder_config.codec);
3685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_decoder_config.channel_count = decoder_config.channel_count;
3695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_decoder_config.bits_per_channel = decoder_config.bits_per_channel;
3705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_decoder_config.samples_per_second = decoder_config.samples_per_second;
3715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_decoder_config.extra_data =
3725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        static_cast<uint8_t*>(extra_data_buffer.data());
3731e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    cdm_decoder_config.extra_data_size = extra_data_buffer.size();
3745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    status = cdm_->InitializeAudioDecoder(cdm_decoder_config);
3755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
3765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3771e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  if (status == cdm::kDeferredInitialization) {
3781e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    deferred_initialize_audio_decoder_ = true;
3791e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    deferred_audio_decoder_config_id_ = decoder_config.request_id;
3801e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    return;
3811e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  }
3821e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
3835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  CallOnMain(callback_factory_.NewCallback(
3848bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      &CdmAdapter::DecoderInitializeDone,
3855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      PP_DECRYPTORSTREAMTYPE_AUDIO,
3865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decoder_config.request_id,
3875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      status == cdm::kSuccess));
3885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3908bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::InitializeVideoDecoder(
3915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const PP_VideoDecoderConfig& decoder_config,
3925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    pp::Buffer_Dev extra_data_buffer) {
3931e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  PP_DCHECK(!deferred_initialize_video_decoder_);
3941e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  PP_DCHECK(deferred_video_decoder_config_id_ == 0);
3955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  cdm::Status status = cdm::kSessionError;
3965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (cdm_) {
3975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm::VideoDecoderConfig cdm_decoder_config;
3985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_decoder_config.codec =
3995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        PpVideoCodecToCdmVideoCodec(decoder_config.codec);
4005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_decoder_config.profile =
4015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        PpVCProfileToCdmVCProfile(decoder_config.profile);
4025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_decoder_config.format =
4035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        PpDecryptedFrameFormatToCdmVideoFormat(decoder_config.format);
4045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_decoder_config.coded_size.width = decoder_config.width;
4055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_decoder_config.coded_size.height = decoder_config.height;
4065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_decoder_config.extra_data =
4075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        static_cast<uint8_t*>(extra_data_buffer.data());
4081e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    cdm_decoder_config.extra_data_size = extra_data_buffer.size();
4095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    status = cdm_->InitializeVideoDecoder(cdm_decoder_config);
4105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
4115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4121e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  if (status == cdm::kDeferredInitialization) {
4131e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    deferred_initialize_video_decoder_ = true;
4141e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    deferred_video_decoder_config_id_ = decoder_config.request_id;
4151e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    return;
4161e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  }
4171e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
4185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  CallOnMain(callback_factory_.NewCallback(
4198bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      &CdmAdapter::DecoderInitializeDone,
4205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      PP_DECRYPTORSTREAMTYPE_VIDEO,
4215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decoder_config.request_id,
4225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      status == cdm::kSuccess));
4235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4258bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::DeinitializeDecoder(PP_DecryptorStreamType decoder_type,
4265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                     uint32_t request_id) {
4274e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  PP_DCHECK(cdm_);  // InitializeXxxxxDecoder should have succeeded.
4285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (cdm_) {
4295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_->DeinitializeDecoder(
4305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        PpDecryptorStreamTypeToCdmStreamType(decoder_type));
4315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
4325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  CallOnMain(callback_factory_.NewCallback(
4348bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      &CdmAdapter::DecoderDeinitializeDone,
4355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decoder_type,
4365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      request_id));
4375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4398bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::ResetDecoder(PP_DecryptorStreamType decoder_type,
4405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              uint32_t request_id) {
4414e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  PP_DCHECK(cdm_);  // InitializeXxxxxDecoder should have succeeded.
4425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (cdm_)
4435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cdm_->ResetDecoder(PpDecryptorStreamTypeToCdmStreamType(decoder_type));
4445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4458bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  CallOnMain(callback_factory_.NewCallback(&CdmAdapter::DecoderResetDone,
4465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                           decoder_type,
4475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                           request_id));
4485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4508bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::DecryptAndDecode(
4515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    PP_DecryptorStreamType decoder_type,
4525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    pp::Buffer_Dev encrypted_buffer,
4535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const PP_EncryptedBlockInfo& encrypted_block_info) {
4544e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  PP_DCHECK(cdm_);  // InitializeXxxxxDecoder should have succeeded.
4552a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // Release a buffer that the caller indicated it is finished with.
4562a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  allocator_.Release(encrypted_block_info.tracking_info.buffer_id);
4572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
4585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  cdm::InputBuffer input_buffer;
4595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::vector<cdm::SubsampleEntry> subsamples;
4605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (cdm_ && !encrypted_buffer.is_null()) {
4615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ConfigureInputBuffer(encrypted_buffer,
4625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         encrypted_block_info,
4635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         &subsamples,
4645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         &input_buffer);
4655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
4665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  cdm::Status status = cdm::kDecodeError;
4685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  switch (decoder_type) {
4705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_DECRYPTORSTREAMTYPE_VIDEO: {
4715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      LinkedVideoFrame video_frame(new VideoFrameImpl());
4725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (cdm_)
4735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        status = cdm_->DecryptAndDecodeFrame(input_buffer, video_frame.get());
4745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      CallOnMain(callback_factory_.NewCallback(
4758bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)          &CdmAdapter::DeliverFrame,
4765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          status,
4775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          video_frame,
4785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          encrypted_block_info.tracking_info));
4795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
4805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
4815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    case PP_DECRYPTORSTREAMTYPE_AUDIO: {
4835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      LinkedAudioFrames audio_frames(new AudioFramesImpl());
4845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (cdm_) {
4855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        status = cdm_->DecryptAndDecodeSamples(input_buffer,
4865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                               audio_frames.get());
4875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
4885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      CallOnMain(callback_factory_.NewCallback(
4898bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)          &CdmAdapter::DeliverSamples,
4905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          status,
4915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          audio_frames,
4925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          encrypted_block_info.tracking_info));
4935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
4945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
4955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    default:
4975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      PP_NOTREACHED();
4985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
4995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
5005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5021e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)cdm::Buffer* CdmAdapter::Allocate(uint32_t capacity) {
5032a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  return allocator_.Allocate(capacity);
5045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5068bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::SetTimer(int64_t delay_ms, void* context) {
5075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // NOTE: doesn't really need to run on the main thread; could just as well run
5085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // on a helper thread if |cdm_| were thread-friendly and care was taken.  We
5095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // only use CallOnMainThread() here to get delayed-execution behavior.
5105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pp::Module::Get()->core()->CallOnMainThread(
5115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      delay_ms,
5128bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      callback_factory_.NewCallback(&CdmAdapter::TimerExpired, context),
5135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      PP_OK);
5145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5168bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::TimerExpired(int32_t result, void* context) {
5175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(result == PP_OK);
5182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  cdm_->TimerExpired(context);
5195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5218bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)double CdmAdapter::GetCurrentWallTimeInSeconds() {
5225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return pp::Module::Get()->core()->GetTime();
5235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5258bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::SendKeyMessage(
5261e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    const char* session_id, uint32_t session_id_length,
5271e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    const char* message, uint32_t message_length,
5281e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    const char* default_url, uint32_t default_url_length) {
5292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  PP_DCHECK(!key_system_.empty());
5302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  PostOnMain(callback_factory_.NewCallback(
5318bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      &CdmAdapter::KeyMessage,
5322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      SessionInfo(key_system_,
5332a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                  std::string(session_id, session_id_length)),
534eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch      std::vector<uint8>(message, message + message_length),
5352a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      std::string(default_url, default_url_length)));
5362a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
5372a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
5388bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::SendKeyError(const char* session_id,
5391e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)                              uint32_t session_id_length,
5402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                              cdm::MediaKeyError error_code,
5412a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                              uint32_t system_code) {
5422a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  SendKeyErrorInternal(key_system_,
5432a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                       std::string(session_id, session_id_length),
5442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                       error_code,
5452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                       system_code);
5462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
5472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
5488bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::GetPrivateData(int32_t* instance,
5498bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)                                GetPrivateInterface* get_interface) {
5502a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  *instance = pp_instance();
5512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  *get_interface = pp::Module::Get()->get_browser_interface();
5522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
5532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
5548bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::SendUnknownKeyError(const std::string& key_system,
5552a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                     const std::string& session_id) {
5562a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  SendKeyErrorInternal(key_system, session_id, cdm::kUnknownError, 0);
5572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
5582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
5598bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::SendKeyAdded(const std::string& key_system,
5602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                              const std::string& session_id) {
5612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  PostOnMain(callback_factory_.NewCallback(
5628bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      &CdmAdapter::KeyAdded,
5632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      SessionInfo(key_system_, session_id)));
5642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
5652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
5668bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::SendKeyErrorInternal(const std::string& key_system,
5672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                      const std::string& session_id,
5682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                      cdm::MediaKeyError error_code,
5692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                      uint32_t system_code) {
5708bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  PostOnMain(callback_factory_.NewCallback(&CdmAdapter::KeyError,
5712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                           SessionInfo(key_system_, session_id),
5722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                           error_code,
5732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                           system_code));
5742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
5752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
5768bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::KeyAdded(int32_t result, const SessionInfo& session_info) {
5775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(result == PP_OK);
5782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  PP_DCHECK(!session_info.key_system.empty());
5792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  pp::ContentDecryptor_Private::KeyAdded(session_info.key_system,
5802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                         session_info.session_id);
5815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5838bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::KeyMessage(int32_t result,
5842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                            const SessionInfo& session_info,
585eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch                            const std::vector<uint8>& message,
5862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                            const std::string& default_url) {
5875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(result == PP_OK);
5882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  PP_DCHECK(!session_info.key_system.empty());
5892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
5902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  pp::VarArrayBuffer message_array_buffer(message.size());
5912a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (message.size() > 0) {
5922a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    memcpy(message_array_buffer.Map(), message.data(), message.size());
5932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  }
5942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
5955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pp::ContentDecryptor_Private::KeyMessage(
5962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      session_info.key_system, session_info.session_id,
5972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      message_array_buffer, default_url);
5985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6008bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::KeyError(int32_t result,
6012a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                          const SessionInfo& session_info,
6022a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                          cdm::MediaKeyError error_code,
6032a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                          uint32_t system_code) {
6045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(result == PP_OK);
6052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  pp::ContentDecryptor_Private::KeyError(
6062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      session_info.key_system, session_info.session_id,
6072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      error_code, system_code);
6085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6108bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::DeliverBlock(int32_t result,
6115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              const cdm::Status& status,
6125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              const LinkedDecryptedBlock& decrypted_block,
6135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              const PP_DecryptTrackingInfo& tracking_info) {
6145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(result == PP_OK);
6155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DecryptedBlockInfo decrypted_block_info;
6165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  decrypted_block_info.tracking_info = tracking_info;
6172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  decrypted_block_info.tracking_info.timestamp = decrypted_block->Timestamp();
6182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  decrypted_block_info.tracking_info.buffer_id = 0;
6192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  decrypted_block_info.data_size = 0;
6205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  decrypted_block_info.result = CdmStatusToPpDecryptResult(status);
6215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pp::Buffer_Dev buffer;
6235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (decrypted_block_info.result == PP_DECRYPTRESULT_SUCCESS) {
6252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    PP_DCHECK(decrypted_block.get() && decrypted_block->DecryptedBuffer());
6262a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    if (!decrypted_block.get() || !decrypted_block->DecryptedBuffer()) {
6275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      PP_NOTREACHED();
6285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decrypted_block_info.result = PP_DECRYPTRESULT_DECRYPT_ERROR;
6295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
6302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      PpbBuffer* ppb_buffer =
6312a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          static_cast<PpbBuffer*>(decrypted_block->DecryptedBuffer());
6322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      buffer = ppb_buffer->buffer_dev();
6332a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      decrypted_block_info.tracking_info.buffer_id = ppb_buffer->buffer_id();
6342a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      decrypted_block_info.data_size = ppb_buffer->Size();
6355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
6365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
6375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pp::ContentDecryptor_Private::DeliverBlock(buffer, decrypted_block_info);
6395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6418bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::DecoderInitializeDone(int32_t result,
6425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                       PP_DecryptorStreamType decoder_type,
6435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                       uint32_t request_id,
6445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                       bool success) {
6455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(result == PP_OK);
6465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pp::ContentDecryptor_Private::DecoderInitializeDone(decoder_type,
6475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                      request_id,
6485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                      success);
6495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6518bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::DecoderDeinitializeDone(int32_t result,
6525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                         PP_DecryptorStreamType decoder_type,
6535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                         uint32_t request_id) {
6545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pp::ContentDecryptor_Private::DecoderDeinitializeDone(decoder_type,
6555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                        request_id);
6565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6588bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::DecoderResetDone(int32_t result,
6595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                  PP_DecryptorStreamType decoder_type,
6605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                  uint32_t request_id) {
6615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pp::ContentDecryptor_Private::DecoderResetDone(decoder_type, request_id);
6625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6648bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::DeliverFrame(
6655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int32_t result,
6665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const cdm::Status& status,
6675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const LinkedVideoFrame& video_frame,
6685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const PP_DecryptTrackingInfo& tracking_info) {
6695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(result == PP_OK);
6705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DecryptedFrameInfo decrypted_frame_info;
6715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  decrypted_frame_info.tracking_info.request_id = tracking_info.request_id;
6722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  decrypted_frame_info.tracking_info.buffer_id = 0;
6735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  decrypted_frame_info.result = CdmStatusToPpDecryptResult(status);
6745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pp::Buffer_Dev buffer;
6765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (decrypted_frame_info.result == PP_DECRYPTRESULT_SUCCESS) {
6782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    if (!IsValidVideoFrame(video_frame)) {
6795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      PP_NOTREACHED();
6805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decrypted_frame_info.result = PP_DECRYPTRESULT_DECODE_ERROR;
6815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
6822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      PpbBuffer* ppb_buffer =
6832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          static_cast<PpbBuffer*>(video_frame->FrameBuffer());
6842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
6852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      buffer = ppb_buffer->buffer_dev();
6862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
6872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      decrypted_frame_info.tracking_info.timestamp = video_frame->Timestamp();
6882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      decrypted_frame_info.tracking_info.buffer_id = ppb_buffer->buffer_id();
6892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      decrypted_frame_info.format =
6902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          CdmVideoFormatToPpDecryptedFrameFormat(video_frame->Format());
6912a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      decrypted_frame_info.width = video_frame->Size().width;
6922a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      decrypted_frame_info.height = video_frame->Size().height;
6935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decrypted_frame_info.plane_offsets[PP_DECRYPTEDFRAMEPLANES_Y] =
6942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          video_frame->PlaneOffset(cdm::VideoFrame::kYPlane);
6955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decrypted_frame_info.plane_offsets[PP_DECRYPTEDFRAMEPLANES_U] =
6962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          video_frame->PlaneOffset(cdm::VideoFrame::kUPlane);
6975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decrypted_frame_info.plane_offsets[PP_DECRYPTEDFRAMEPLANES_V] =
6982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          video_frame->PlaneOffset(cdm::VideoFrame::kVPlane);
6995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decrypted_frame_info.strides[PP_DECRYPTEDFRAMEPLANES_Y] =
7002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          video_frame->Stride(cdm::VideoFrame::kYPlane);
7015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decrypted_frame_info.strides[PP_DECRYPTEDFRAMEPLANES_U] =
7022a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          video_frame->Stride(cdm::VideoFrame::kUPlane);
7035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      decrypted_frame_info.strides[PP_DECRYPTEDFRAMEPLANES_V] =
7042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          video_frame->Stride(cdm::VideoFrame::kVPlane);
7055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
7065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pp::ContentDecryptor_Private::DeliverFrame(buffer, decrypted_frame_info);
7085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
7095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7108bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::DeliverSamples(int32_t result,
7115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                const cdm::Status& status,
7125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                const LinkedAudioFrames& audio_frames,
7135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                const PP_DecryptTrackingInfo& tracking_info) {
7145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PP_DCHECK(result == PP_OK);
7155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7161e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  PP_DecryptedSampleInfo decrypted_sample_info;
7171e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  decrypted_sample_info.tracking_info = tracking_info;
7181e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  decrypted_sample_info.tracking_info.timestamp = 0;
7191e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  decrypted_sample_info.tracking_info.buffer_id = 0;
7201e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  decrypted_sample_info.data_size = 0;
7211e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  decrypted_sample_info.result = CdmStatusToPpDecryptResult(status);
7225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pp::Buffer_Dev buffer;
7245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7251e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  if (decrypted_sample_info.result == PP_DECRYPTRESULT_SUCCESS) {
7262a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    PP_DCHECK(audio_frames.get() && audio_frames->FrameBuffer());
7272a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    if (!audio_frames.get() || !audio_frames->FrameBuffer()) {
7285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      PP_NOTREACHED();
7291e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      decrypted_sample_info.result = PP_DECRYPTRESULT_DECRYPT_ERROR;
7305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
7312a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      PpbBuffer* ppb_buffer =
7322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          static_cast<PpbBuffer*>(audio_frames->FrameBuffer());
7332a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      buffer = ppb_buffer->buffer_dev();
7341e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      decrypted_sample_info.tracking_info.buffer_id = ppb_buffer->buffer_id();
7351e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      decrypted_sample_info.data_size = ppb_buffer->Size();
7361e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      decrypted_sample_info.format =
7371e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)          CdmAudioFormatToPpDecryptedSampleFormat(audio_frames->Format());
7385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
7395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7411e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  pp::ContentDecryptor_Private::DeliverSamples(buffer, decrypted_sample_info);
7425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
7435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7448bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)bool CdmAdapter::IsValidVideoFrame(const LinkedVideoFrame& video_frame) {
7452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (!video_frame.get() ||
7462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      !video_frame->FrameBuffer() ||
7472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      (video_frame->Format() != cdm::kI420 &&
7482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)       video_frame->Format() != cdm::kYv12)) {
7492a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    return false;
7502a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  }
7512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
7522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  PpbBuffer* ppb_buffer = static_cast<PpbBuffer*>(video_frame->FrameBuffer());
7532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
7541e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  for (uint32_t i = 0; i < cdm::VideoFrame::kMaxPlanes; ++i) {
7552a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    int plane_height = (i == cdm::VideoFrame::kYPlane) ?
7562a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        video_frame->Size().height : (video_frame->Size().height + 1) / 2;
7572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    cdm::VideoFrame::VideoPlane plane =
7582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        static_cast<cdm::VideoFrame::VideoPlane>(i);
7592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    if (ppb_buffer->Size() < video_frame->PlaneOffset(plane) +
7602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                             plane_height * video_frame->Stride(plane)) {
7612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      return false;
7622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    }
7632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  }
7642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
7652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  return true;
7662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
7672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
7688bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::SendPlatformChallenge(
7691e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    const char* service_id, uint32_t service_id_length,
7701e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    const char* challenge, uint32_t challenge_length) {
7718bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#if defined(OS_CHROMEOS)
7728bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  PP_DCHECK(!challenge_in_progress_);
7738bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
7748bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // Ensure member variables set by the callback are in a clean state.
7758bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  signed_data_output_ = pp::Var();
7768bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  signed_data_signature_output_ = pp::Var();
7778bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  platform_key_certificate_output_ = pp::Var();
7788bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
7798bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  pp::VarArrayBuffer challenge_var(challenge_length);
7808bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  uint8_t* var_data = static_cast<uint8_t*>(challenge_var.Map());
7818bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  memcpy(var_data, challenge, challenge_length);
7828bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
7838bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  std::string service_id_str(service_id, service_id_length);
7848bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  int32_t result = platform_verification_.ChallengePlatform(
7858bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      pp::Var(service_id_str), challenge_var, &signed_data_output_,
7868bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      &signed_data_signature_output_, &platform_key_certificate_output_,
7878bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      callback_factory_.NewCallback(&CdmAdapter::SendPlatformChallengeDone));
7888bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  challenge_var.Unmap();
7898bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  if (result == PP_OK_COMPLETIONPENDING) {
7908bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    challenge_in_progress_ = true;
7918bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    return;
7928bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  }
7938bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
7948bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // Fall through on error and issue an empty OnPlatformChallengeResponse().
7958bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  PP_DCHECK(result != PP_OK);
7968bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#endif
7978bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
7988bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  cdm::PlatformChallengeResponse response = {};
7998bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  cdm_->OnPlatformChallengeResponse(response);
8008bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)}
8018bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8028bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::EnableOutputProtection(uint32_t desired_protection_mask) {
8038bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#if defined(OS_CHROMEOS)
8048bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  output_protection_.EnableProtection(
8058bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      desired_protection_mask, callback_factory_.NewCallback(
8068bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)          &CdmAdapter::EnableProtectionDone));
8078bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8088bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // Errors are ignored since clients must call QueryOutputProtectionStatus() to
8098bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // inspect the protection status on a regular basis.
8108bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // TODO(dalecurtis): It'd be nice to log a message or non-fatal error here...
8118bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#endif
8128bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)}
8138bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8148bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::QueryOutputProtectionStatus() {
8158bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#if defined(OS_CHROMEOS)
8168bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  PP_DCHECK(!query_output_protection_in_progress_);
8178bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8188bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  output_link_mask_ = output_protection_mask_ = 0;
8198bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  const int32_t result = output_protection_.QueryStatus(
8208bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      &output_link_mask_,
8218bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      &output_protection_mask_,
8228bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      callback_factory_.NewCallback(
8238bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)          &CdmAdapter::QueryOutputProtectionStatusDone));
8248bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  if (result == PP_OK_COMPLETIONPENDING) {
8258bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    query_output_protection_in_progress_ = true;
8268bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    return;
8278bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  }
8288bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8298bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // Fall through on error and issue an empty OnQueryOutputProtectionStatus().
8308bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  PP_DCHECK(result != PP_OK);
8318bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#endif
8328bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8338bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  cdm_->OnQueryOutputProtectionStatus(0, 0);
8348bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)}
8358bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8361e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)void CdmAdapter::OnDeferredInitializationDone(cdm::StreamType stream_type,
8371e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)                                              cdm::Status decoder_status) {
8381e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  switch (stream_type) {
8391e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    case cdm::kStreamTypeAudio:
8401e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      PP_DCHECK(deferred_initialize_audio_decoder_);
8411e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      CallOnMain(
8421e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)          callback_factory_.NewCallback(&CdmAdapter::DecoderInitializeDone,
8431e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)                                        PP_DECRYPTORSTREAMTYPE_AUDIO,
8441e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)                                        deferred_audio_decoder_config_id_,
8451e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)                                        decoder_status == cdm::kSuccess));
8461e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      deferred_initialize_audio_decoder_ = false;
8471e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      deferred_audio_decoder_config_id_ = 0;
8481e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      break;
8491e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    case cdm::kStreamTypeVideo:
8501e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      PP_DCHECK(deferred_initialize_video_decoder_);
8511e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      CallOnMain(
8521e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)          callback_factory_.NewCallback(&CdmAdapter::DecoderInitializeDone,
8531e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)                                        PP_DECRYPTORSTREAMTYPE_VIDEO,
8541e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)                                        deferred_video_decoder_config_id_,
8551e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)                                        decoder_status == cdm::kSuccess));
8561e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      deferred_initialize_video_decoder_ = false;
8571e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      deferred_video_decoder_config_id_ = 0;
8581e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)      break;
8591e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  }
8601e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)}
8611e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
8628bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#if defined(OS_CHROMEOS)
8638bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::SendPlatformChallengeDone(int32_t result) {
8648bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  challenge_in_progress_ = false;
8658bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8668bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  if (result != PP_OK) {
8678bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    cdm::PlatformChallengeResponse response = {};
8688bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    cdm_->OnPlatformChallengeResponse(response);
8698bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    return;
8708bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  }
8718bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8728bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  pp::VarArrayBuffer signed_data_var(signed_data_output_);
8738bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  pp::VarArrayBuffer signed_data_signature_var(signed_data_signature_output_);
8748bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  std::string platform_key_certificate_string =
8758bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      platform_key_certificate_output_.AsString();
8768bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8778bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  cdm::PlatformChallengeResponse response = {
8788bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    static_cast<uint8_t*>(signed_data_var.Map()),
8791e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    signed_data_var.ByteLength(),
8808bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8818bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    static_cast<uint8_t*>(signed_data_signature_var.Map()),
8821e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    signed_data_signature_var.ByteLength(),
8838bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8848bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    reinterpret_cast<const uint8_t*>(platform_key_certificate_string.c_str()),
8851e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    static_cast<uint32_t>(platform_key_certificate_string.length())
8868bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  };
8878bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  cdm_->OnPlatformChallengeResponse(response);
8888bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8898bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  signed_data_var.Unmap();
8908bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  signed_data_signature_var.Unmap();
8918bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)}
8928bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8938bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::EnableProtectionDone(int32_t result) {
8948bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // Does nothing since clients must call QueryOutputProtectionStatus() to
8958bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // inspect the protection status on a regular basis.
8968bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // TODO(dalecurtis): It'd be nice to log a message or non-fatal error here...
8978bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)}
8988bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
8998bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)void CdmAdapter::QueryOutputProtectionStatusDone(int32_t result) {
9008bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  PP_DCHECK(query_output_protection_in_progress_);
9018bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  query_output_protection_in_progress_ = false;
9028bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
9038bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // Return a protection status of none on error.
9048bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  if (result != PP_OK)
9058bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    output_link_mask_ = output_protection_mask_ = 0;
9068bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
9078bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  cdm_->OnQueryOutputProtectionStatus(output_link_mask_,
9088bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)                                      output_protection_mask_);
9098bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)}
9108bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)#endif
9118bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
9122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)void* GetCdmHost(int host_interface_version, void* user_data) {
9132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (!host_interface_version || !user_data)
9142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    return NULL;
9152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
9160f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  COMPILE_ASSERT(cdm::ContentDecryptionModule::Host::kVersion ==
9170f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                 cdm::ContentDecryptionModule_2::Host::kVersion,
9180f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                 update_code_below);
9190f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
9200f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Ensure IsSupportedCdmHostVersion matches implementation of this function.
9210f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Always update this DCHECK when updating this function.
9220f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // If this check fails, update this function and DCHECK or update
9230f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // IsSupportedCdmHostVersion.
9240f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  PP_DCHECK(
9250f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      // Future version is not supported.
9260f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      !IsSupportedCdmHostVersion(
9270f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)          cdm::ContentDecryptionModule::Host::kVersion + 1) &&
9280f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      // Current version is supported.
9290f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      IsSupportedCdmHostVersion(cdm::ContentDecryptionModule::Host::kVersion) &&
9300f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      // Include all previous supported versions here.
9310f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      IsSupportedCdmHostVersion(cdm::Host_1::kVersion) &&
9320f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      // One older than the oldest supported version is not supported.
9330f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      !IsSupportedCdmHostVersion(cdm::Host_1::kVersion - 1));
9340f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  PP_DCHECK(IsSupportedCdmHostVersion(host_interface_version));
9350f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
9368bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  CdmAdapter* cdm_adapter = static_cast<CdmAdapter*>(user_data);
9378bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  switch (host_interface_version) {
9380f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    // The latest CDM host version.
9390f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    case cdm::ContentDecryptionModule::Host::kVersion:
9400f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      return static_cast<cdm::ContentDecryptionModule::Host*>(cdm_adapter);
9410f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    // Older supported version(s) of the CDM host.
9420f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    case cdm::Host_1::kVersion:
9430f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      return static_cast<cdm::Host_1*>(cdm_adapter);
9448bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    default:
9458bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      PP_NOTREACHED();
9468bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      return NULL;
9478bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  }
9482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
9492a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
9505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// This object is the global object representing this plugin library as long
9515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// as it is loaded.
9528bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)class CdmAdapterModule : public pp::Module {
9535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
9548bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  CdmAdapterModule() : pp::Module() {
9555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // This function blocks the renderer thread (PluginInstance::Initialize()).
9565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Move this call to other places if this may be a concern in the future.
9575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    INITIALIZE_CDM_MODULE();
9585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
9598bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  virtual ~CdmAdapterModule() {
9602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    DeinitializeCdmModule();
9615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
9625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  virtual pp::Instance* CreateInstance(PP_Instance instance) {
9648bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    return new CdmAdapter(instance, this);
9655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
9665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
9675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
968ba5b9a6411cb1792fd21f0a078d7a25cd1ceec16Ben Murdoch}  // namespace media
9695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace pp {
9715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Factory function for your specialization of the Module object.
9735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Module* CreateModule() {
9748bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  return new media::CdmAdapterModule();
9755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
9765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace pp
978