Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(704)

Side by Side Diff: media/base/android/media_drm_bridge.cc

Issue 962793005: Adds MediaClientAndroid to support embedder/MediaDrmBridge interaction. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: clean up code, implement actual Delegates for Widevine (Android) and Chromecast Created 5 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "media/base/android/media_drm_bridge.h" 5 #include "media/base/android/media_drm_bridge.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 8
9 #include "base/android/build_info.h" 9 #include "base/android/build_info.h"
10 #include "base/android/jni_array.h" 10 #include "base/android/jni_array.h"
11 #include "base/android/jni_string.h" 11 #include "base/android/jni_string.h"
12 #include "base/callback_helpers.h" 12 #include "base/callback_helpers.h"
13 #include "base/containers/hash_tables.h" 13 #include "base/containers/hash_tables.h"
14 #include "base/lazy_instance.h" 14 #include "base/lazy_instance.h"
15 #include "base/location.h" 15 #include "base/location.h"
16 #include "base/logging.h" 16 #include "base/logging.h"
17 #include "base/message_loop/message_loop_proxy.h" 17 #include "base/message_loop/message_loop_proxy.h"
18 #include "base/stl_util.h"
18 #include "base/strings/string_util.h" 19 #include "base/strings/string_util.h"
19 #include "base/sys_byteorder.h" 20 #include "base/sys_byteorder.h"
20 #include "base/sys_info.h" 21 #include "base/sys_info.h"
21 #include "jni/MediaDrmBridge_jni.h" 22 #include "jni/MediaDrmBridge_jni.h"
22 #include "media/base/cdm_key_information.h" 23 #include "media/base/cdm_key_information.h"
23 24
24 #include "widevine_cdm_version.h" // In SHARED_INTERMEDIATE_DIR. 25 #include "widevine_cdm_version.h" // In SHARED_INTERMEDIATE_DIR.
25 26
26 using base::android::AttachCurrentThread; 27 using base::android::AttachCurrentThread;
27 using base::android::ConvertUTF8ToJavaString; 28 using base::android::ConvertUTF8ToJavaString;
28 using base::android::ConvertJavaStringToUTF8; 29 using base::android::ConvertJavaStringToUTF8;
29 using base::android::JavaByteArrayToByteVector; 30 using base::android::JavaByteArrayToByteVector;
30 using base::android::ScopedJavaLocalRef; 31 using base::android::ScopedJavaLocalRef;
31 32
32 namespace media { 33 namespace media {
33 34
34 namespace { 35 namespace {
35 36
36 // DrmBridge supports session expiration event but doesn't provide detailed 37 // DrmBridge supports session expiration event but doesn't provide detailed
37 // status for each key ID, which is required by the EME spec. Use a dummy key ID 38 // status for each key ID, which is required by the EME spec. Use a dummy key ID
38 // here to report session expiration info. 39 // here to report session expiration info.
39 const char kDummyKeyId[] = "Dummy Key Id"; 40 const char kDummyKeyId[] = "Dummy Key Id";
40 41
41 uint32 ReadUint32(const uint8_t* data) {
42 uint32 value = 0;
43 for (int i = 0; i < 4; ++i)
44 value = (value << 8) | data[i];
45 return value;
46 }
47
48 uint64 ReadUint64(const uint8_t* data) {
49 uint64 value = 0;
50 for (int i = 0; i < 8; ++i)
51 value = (value << 8) | data[i];
52 return value;
53 }
54
55 // Returns string session ID from jbyteArray (byte[] in Java). 42 // Returns string session ID from jbyteArray (byte[] in Java).
56 std::string GetSessionId(JNIEnv* env, jbyteArray j_session_id) { 43 std::string GetSessionId(JNIEnv* env, jbyteArray j_session_id) {
57 std::vector<uint8> session_id_vector; 44 std::vector<uint8> session_id_vector;
58 JavaByteArrayToByteVector(env, j_session_id, &session_id_vector); 45 JavaByteArrayToByteVector(env, j_session_id, &session_id_vector);
59 return std::string(session_id_vector.begin(), session_id_vector.end()); 46 return std::string(session_id_vector.begin(), session_id_vector.end());
60 } 47 }
61 48
62 // The structure of an ISO CENC Protection System Specific Header (PSSH) box is
63 // as follows. (See ISO/IEC FDIS 23001-7:2011(E).)
64 // Note: ISO boxes use big-endian values.
65 //
66 // PSSH {
67 // uint32 Size
68 // uint32 Type
69 // uint64 LargeSize # Field is only present if value(Size) == 1.
70 // uint32 VersionAndFlags
71 // uint8[16] SystemId
72 // uint32 DataSize
73 // uint8[DataSize] Data
74 // }
75 const int kBoxHeaderSize = 8; // Box's header contains Size and Type.
76 const int kBoxLargeSizeSize = 8;
77 const int kPsshVersionFlagSize = 4;
78 const int kPsshSystemIdSize = 16;
79 const int kPsshDataSizeSize = 4;
80 const uint32 kTencType = 0x74656e63;
81 const uint32 kPsshType = 0x70737368;
82 const uint8 kWidevineUuid[16] = { 49 const uint8 kWidevineUuid[16] = {
83 0xED, 0xEF, 0x8B, 0xA9, 0x79, 0xD6, 0x4A, 0xCE, 50 0xED, 0xEF, 0x8B, 0xA9, 0x79, 0xD6, 0x4A, 0xCE,
84 0xA3, 0xC8, 0x27, 0xDC, 0xD5, 0x1D, 0x21, 0xED }; 51 0xA3, 0xC8, 0x27, 0xDC, 0xD5, 0x1D, 0x21, 0xED };
85 52
86 typedef std::vector<uint8> UUID; 53 typedef std::vector<uint8> UUID;
87 54
88 // Tries to find a PSSH box whose "SystemId" is |uuid| in |data|, parses the
89 // "Data" of the box and put it in |pssh_data|. Returns true if such a box is
90 // found and successfully parsed. Returns false otherwise.
91 // Notes:
92 // 1, If multiple PSSH boxes are found,the "Data" of the first matching PSSH box
93 // will be set in |pssh_data|.
94 // 2, Only PSSH and TENC boxes are allowed in |data|. TENC boxes are skipped.
95 bool GetPsshData(const uint8* data,
96 int data_size,
97 const UUID& uuid,
98 std::vector<uint8>* pssh_data) {
99 const uint8* cur = data;
100 const uint8* data_end = data + data_size;
101 int bytes_left = data_size;
102
103 while (bytes_left > 0) {
104 const uint8* box_head = cur;
105
106 if (bytes_left < kBoxHeaderSize)
107 return false;
108
109 uint64_t box_size = ReadUint32(cur);
110 uint32 type = ReadUint32(cur + 4);
111 cur += kBoxHeaderSize;
112 bytes_left -= kBoxHeaderSize;
113
114 if (box_size == 1) { // LargeSize is present.
115 if (bytes_left < kBoxLargeSizeSize)
116 return false;
117
118 box_size = ReadUint64(cur);
119 cur += kBoxLargeSizeSize;
120 bytes_left -= kBoxLargeSizeSize;
121 } else if (box_size == 0) {
122 box_size = bytes_left + kBoxHeaderSize;
123 }
124
125 const uint8* box_end = box_head + box_size;
126 if (data_end < box_end)
127 return false;
128
129 if (type == kTencType) {
130 // Skip 'tenc' box.
131 cur = box_end;
132 bytes_left = data_end - cur;
133 continue;
134 } else if (type != kPsshType) {
135 return false;
136 }
137
138 const int kPsshBoxMinimumSize =
139 kPsshVersionFlagSize + kPsshSystemIdSize + kPsshDataSizeSize;
140 if (box_end < cur + kPsshBoxMinimumSize)
141 return false;
142
143 uint32 version_and_flags = ReadUint32(cur);
144 cur += kPsshVersionFlagSize;
145 bytes_left -= kPsshVersionFlagSize;
146 if (version_and_flags != 0)
147 return false;
148
149 DCHECK_GE(bytes_left, kPsshSystemIdSize);
150 if (!std::equal(uuid.begin(), uuid.end(), cur)) {
151 cur = box_end;
152 bytes_left = data_end - cur;
153 continue;
154 }
155
156 cur += kPsshSystemIdSize;
157 bytes_left -= kPsshSystemIdSize;
158
159 uint32 data_size = ReadUint32(cur);
160 cur += kPsshDataSizeSize;
161 bytes_left -= kPsshDataSizeSize;
162
163 if (box_end < cur + data_size)
164 return false;
165
166 pssh_data->assign(cur, cur + data_size);
167 return true;
168 }
169
170 return false;
171 }
172
173 // Convert |init_data_type| to a string supported by MediaDRM. 55 // Convert |init_data_type| to a string supported by MediaDRM.
174 // "audio"/"video" does not matter, so use "video". 56 // "audio"/"video" does not matter, so use "video".
175 std::string ConvertInitDataType(media::EmeInitDataType init_data_type) { 57 std::string ConvertInitDataType(media::EmeInitDataType init_data_type) {
176 // TODO(jrummell): API level >=20 supports "webm" and "cenc", so switch 58 // TODO(jrummell): API level >=20 supports "webm" and "cenc", so switch
177 // to those strings. 59 // to those strings.
178 switch (init_data_type) { 60 switch (init_data_type) {
179 case media::EmeInitDataType::WEBM: 61 case media::EmeInitDataType::WEBM:
180 return "video/webm"; 62 return "video/webm";
181 case media::EmeInitDataType::CENC: 63 case media::EmeInitDataType::CENC:
182 return "video/mp4"; 64 return "video/mp4";
183 default: 65 default:
184 NOTREACHED(); 66 NOTREACHED();
185 return "video/unknown"; 67 return "video/unknown";
186 } 68 }
187 } 69 }
188 70
189 class KeySystemUuidManager { 71 class KeySystemManager {
190 public: 72 public:
191 KeySystemUuidManager(); 73 KeySystemManager();
192 UUID GetUUID(const std::string& key_system); 74 UUID GetUUID(const std::string& key_system);
193 void AddMapping(const std::string& key_system, const UUID& uuid); 75 void AddMapping(const std::string& key_system, const UUID& uuid);
76 void RegisterDelegate(const std::string& key_system,
77 MediaDrmBridge::Delegate* delegate);
78 MediaDrmBridge::Delegate* GetDelegate(const std::string& key_system);
194 std::vector<std::string> GetPlatformKeySystemNames(); 79 std::vector<std::string> GetPlatformKeySystemNames();
195 80
196 private: 81 private:
197 typedef base::hash_map<std::string, UUID> KeySystemUuidMap; 82 typedef base::hash_map<std::string, UUID> KeySystemUuidMap;
83 typedef base::hash_map<std::string, MediaDrmBridge::Delegate*>
84 KeySystemDelegateMap;
198 85
86 KeySystemDelegateMap key_system_delegates_;
199 KeySystemUuidMap key_system_uuid_map_; 87 KeySystemUuidMap key_system_uuid_map_;
200 88
201 DISALLOW_COPY_AND_ASSIGN(KeySystemUuidManager); 89 DISALLOW_COPY_AND_ASSIGN(KeySystemManager);
202 }; 90 };
203 91
204 KeySystemUuidManager::KeySystemUuidManager() { 92 KeySystemManager::KeySystemManager() {
205 // Widevine is always supported in Android. 93 // Widevine is always supported in Android.
206 key_system_uuid_map_[kWidevineKeySystem] = 94 key_system_uuid_map_[kWidevineKeySystem] =
207 UUID(kWidevineUuid, kWidevineUuid + arraysize(kWidevineUuid)); 95 UUID(kWidevineUuid, kWidevineUuid + arraysize(kWidevineUuid));
208 } 96 }
209 97
210 UUID KeySystemUuidManager::GetUUID(const std::string& key_system) { 98 UUID KeySystemManager::GetUUID(const std::string& key_system) {
211 KeySystemUuidMap::iterator it = key_system_uuid_map_.find(key_system); 99 KeySystemUuidMap::iterator it = key_system_uuid_map_.find(key_system);
212 if (it == key_system_uuid_map_.end()) 100 if (it == key_system_uuid_map_.end())
213 return UUID(); 101 return UUID();
214 return it->second; 102 return it->second;
215 } 103 }
216 104
217 void KeySystemUuidManager::AddMapping(const std::string& key_system, 105 void KeySystemManager::AddMapping(const std::string& key_system,
218 const UUID& uuid) { 106 const UUID& uuid) {
219 KeySystemUuidMap::iterator it = key_system_uuid_map_.find(key_system); 107 KeySystemUuidMap::iterator it = key_system_uuid_map_.find(key_system);
220 DCHECK(it == key_system_uuid_map_.end()) 108 DCHECK(it == key_system_uuid_map_.end())
221 << "Shouldn't overwrite an existing key system."; 109 << "Shouldn't overwrite an existing key system.";
222 if (it != key_system_uuid_map_.end()) 110 if (it != key_system_uuid_map_.end())
223 return; 111 return;
224 key_system_uuid_map_[key_system] = uuid; 112 key_system_uuid_map_[key_system] = uuid;
225 } 113 }
226 114
227 std::vector<std::string> KeySystemUuidManager::GetPlatformKeySystemNames() { 115 void KeySystemManager::RegisterDelegate(
116 const std::string& key_system, MediaDrmBridge::Delegate* delegate) {
117 DCHECK(!ContainsKey(key_system_delegates_, key_system))
118 << "Shouldn't overwrite an existing delegate.";
119 key_system_delegates_[key_system] = delegate;
120 }
121
122 MediaDrmBridge::Delegate* KeySystemManager::GetDelegate(
123 const std::string& key_system) {
124 KeySystemDelegateMap::iterator it = key_system_delegates_.find(key_system);
125 if (it == key_system_delegates_.end())
126 return nullptr;
127 return it->second;
128 }
129
130 std::vector<std::string> KeySystemManager::GetPlatformKeySystemNames() {
228 std::vector<std::string> key_systems; 131 std::vector<std::string> key_systems;
229 for (KeySystemUuidMap::iterator it = key_system_uuid_map_.begin(); 132 for (KeySystemUuidMap::iterator it = key_system_uuid_map_.begin();
230 it != key_system_uuid_map_.end(); ++it) { 133 it != key_system_uuid_map_.end(); ++it) {
231 // Rule out the key system handled by Chrome explicitly. 134 // Rule out the key system handled by Chrome explicitly.
232 if (it->first != kWidevineKeySystem) 135 if (it->first != kWidevineKeySystem)
233 key_systems.push_back(it->first); 136 key_systems.push_back(it->first);
234 } 137 }
235 return key_systems; 138 return key_systems;
236 } 139 }
237 140
238 base::LazyInstance<KeySystemUuidManager>::Leaky g_key_system_uuid_manager = 141 base::LazyInstance<KeySystemManager>::Leaky g_key_system_manager =
239 LAZY_INSTANCE_INITIALIZER; 142 LAZY_INSTANCE_INITIALIZER;
240 143
241 // Checks whether |key_system| is supported with |container_mime_type|. Only 144 // Checks whether |key_system| is supported with |container_mime_type|. Only
242 // checks |key_system| support if |container_mime_type| is empty. 145 // checks |key_system| support if |container_mime_type| is empty.
243 // TODO(xhwang): The |container_mime_type| is not the same as contentType in 146 // TODO(xhwang): The |container_mime_type| is not the same as contentType in
244 // the EME spec. Revisit this once the spec issue with initData type is 147 // the EME spec. Revisit this once the spec issue with initData type is
245 // resolved. 148 // resolved.
246 bool IsKeySystemSupportedWithTypeImpl(const std::string& key_system, 149 bool IsKeySystemSupportedWithTypeImpl(const std::string& key_system,
247 const std::string& container_mime_type) { 150 const std::string& container_mime_type) {
248 if (!MediaDrmBridge::IsAvailable()) 151 if (!MediaDrmBridge::IsAvailable())
249 return false; 152 return false;
250 153
251 UUID scheme_uuid = g_key_system_uuid_manager.Get().GetUUID(key_system); 154 UUID scheme_uuid = g_key_system_manager.Get().GetUUID(key_system);
252 if (scheme_uuid.empty()) 155 if (scheme_uuid.empty())
253 return false; 156 return false;
254 157
255 JNIEnv* env = AttachCurrentThread(); 158 JNIEnv* env = AttachCurrentThread();
256 ScopedJavaLocalRef<jbyteArray> j_scheme_uuid = 159 ScopedJavaLocalRef<jbyteArray> j_scheme_uuid =
257 base::android::ToJavaByteArray(env, &scheme_uuid[0], scheme_uuid.size()); 160 base::android::ToJavaByteArray(env, &scheme_uuid[0], scheme_uuid.size());
258 ScopedJavaLocalRef<jstring> j_container_mime_type = 161 ScopedJavaLocalRef<jstring> j_container_mime_type =
259 ConvertUTF8ToJavaString(env, container_mime_type); 162 ConvertUTF8ToJavaString(env, container_mime_type);
260 return Java_MediaDrmBridge_isCryptoSchemeSupported( 163 return Java_MediaDrmBridge_isCryptoSchemeSupported(
261 env, j_scheme_uuid.obj(), j_container_mime_type.obj()); 164 env, j_scheme_uuid.obj(), j_container_mime_type.obj());
(...skipping 25 matching lines...) Expand all
287 } // namespace 190 } // namespace
288 191
289 // Called by Java. 192 // Called by Java.
290 static void AddKeySystemUuidMapping(JNIEnv* env, 193 static void AddKeySystemUuidMapping(JNIEnv* env,
291 jclass clazz, 194 jclass clazz,
292 jstring j_key_system, 195 jstring j_key_system,
293 jobject j_buffer) { 196 jobject j_buffer) {
294 std::string key_system = ConvertJavaStringToUTF8(env, j_key_system); 197 std::string key_system = ConvertJavaStringToUTF8(env, j_key_system);
295 uint8* buffer = static_cast<uint8*>(env->GetDirectBufferAddress(j_buffer)); 198 uint8* buffer = static_cast<uint8*>(env->GetDirectBufferAddress(j_buffer));
296 UUID uuid(buffer, buffer + 16); 199 UUID uuid(buffer, buffer + 16);
297 g_key_system_uuid_manager.Get().AddMapping(key_system, uuid); 200 g_key_system_manager.Get().AddMapping(key_system, uuid);
201 }
202
203 MediaDrmBridge::Delegate::Delegate() {
204 }
205
206 MediaDrmBridge::Delegate::~Delegate() {
207 }
208
209 bool MediaDrmBridge::Delegate::OnCreateSession(
210 const EmeInitDataType init_data_type,
211 const uint8* init_data,
212 int init_data_length,
213 std::vector<uint8>& init_data_out,
214 std::vector<std::string>& optional_parameters_out) {
215 return true;
298 } 216 }
299 217
300 // static 218 // static
301 bool MediaDrmBridge::IsAvailable() { 219 bool MediaDrmBridge::IsAvailable() {
302 if (base::android::BuildInfo::GetInstance()->sdk_int() < 19) 220 if (base::android::BuildInfo::GetInstance()->sdk_int() < 19)
303 return false; 221 return false;
304 222
305 int32 os_major_version = 0; 223 int32 os_major_version = 0;
306 int32 os_minor_version = 0; 224 int32 os_minor_version = 0;
307 int32 os_bugfix_version = 0; 225 int32 os_bugfix_version = 0;
308 base::SysInfo::OperatingSystemVersionNumbers(&os_major_version, 226 base::SysInfo::OperatingSystemVersionNumbers(&os_major_version,
309 &os_minor_version, 227 &os_minor_version,
310 &os_bugfix_version); 228 &os_bugfix_version);
311 if (os_major_version == 4 && os_minor_version == 4 && os_bugfix_version == 0) 229 if (os_major_version == 4 && os_minor_version == 4 && os_bugfix_version == 0)
312 return false; 230 return false;
313 231
314 return true; 232 return true;
315 } 233 }
316 234
317 // TODO(ddorwin): This is specific to Widevine. http://crbug.com/459400 235 // TODO(ddorwin): This is specific to Widevine. http://crbug.com/459400
318 // static 236 // static
319 bool MediaDrmBridge::IsSecureDecoderRequired(SecurityLevel security_level) { 237 bool MediaDrmBridge::IsSecureDecoderRequired(SecurityLevel security_level) {
320 DCHECK(IsAvailable()); 238 DCHECK(IsAvailable());
321 return SECURITY_LEVEL_1 == security_level; 239 return SECURITY_LEVEL_1 == security_level;
322 } 240 }
323 241
324 // static 242 // static
325 std::vector<std::string> MediaDrmBridge::GetPlatformKeySystemNames() { 243 std::vector<std::string> MediaDrmBridge::GetPlatformKeySystemNames() {
326 return g_key_system_uuid_manager.Get().GetPlatformKeySystemNames(); 244 return g_key_system_manager.Get().GetPlatformKeySystemNames();
327 } 245 }
328 246
329 // static 247 // static
330 bool MediaDrmBridge::IsKeySystemSupported(const std::string& key_system) { 248 bool MediaDrmBridge::IsKeySystemSupported(const std::string& key_system) {
331 DCHECK(!key_system.empty()); 249 DCHECK(!key_system.empty());
332 return IsKeySystemSupportedWithTypeImpl(key_system, ""); 250 return IsKeySystemSupportedWithTypeImpl(key_system, "");
333 } 251 }
334 252
335 // static 253 // static
336 bool MediaDrmBridge::IsKeySystemSupportedWithType( 254 bool MediaDrmBridge::IsKeySystemSupportedWithType(
337 const std::string& key_system, 255 const std::string& key_system,
338 const std::string& container_mime_type) { 256 const std::string& container_mime_type) {
339 DCHECK(!key_system.empty() && !container_mime_type.empty()); 257 DCHECK(!key_system.empty() && !container_mime_type.empty());
340 return IsKeySystemSupportedWithTypeImpl(key_system, container_mime_type); 258 return IsKeySystemSupportedWithTypeImpl(key_system, container_mime_type);
341 } 259 }
342 260
261 // static
262 void MediaDrmBridge::RegisterDelegate(const std::string& key_system,
263 Delegate* delegate) {
264 g_key_system_manager.Get().RegisterDelegate(key_system, delegate);
265 }
266
343 bool MediaDrmBridge::RegisterMediaDrmBridge(JNIEnv* env) { 267 bool MediaDrmBridge::RegisterMediaDrmBridge(JNIEnv* env) {
344 return RegisterNativesImpl(env); 268 return RegisterNativesImpl(env);
345 } 269 }
346 270
347 MediaDrmBridge::MediaDrmBridge( 271 MediaDrmBridge::MediaDrmBridge(
348 const std::vector<uint8>& scheme_uuid, 272 const std::vector<uint8>& scheme_uuid,
349 const SessionMessageCB& session_message_cb, 273 const SessionMessageCB& session_message_cb,
350 const SessionClosedCB& session_closed_cb, 274 const SessionClosedCB& session_closed_cb,
351 const LegacySessionErrorCB& legacy_session_error_cb, 275 const LegacySessionErrorCB& legacy_session_error_cb,
352 const SessionKeysChangeCB& session_keys_change_cb) 276 const SessionKeysChangeCB& session_keys_change_cb,
277 Delegate* delegate)
353 : scheme_uuid_(scheme_uuid), 278 : scheme_uuid_(scheme_uuid),
279 delegate_(delegate),
354 session_message_cb_(session_message_cb), 280 session_message_cb_(session_message_cb),
355 session_closed_cb_(session_closed_cb), 281 session_closed_cb_(session_closed_cb),
356 legacy_session_error_cb_(legacy_session_error_cb), 282 legacy_session_error_cb_(legacy_session_error_cb),
357 session_keys_change_cb_(session_keys_change_cb) { 283 session_keys_change_cb_(session_keys_change_cb) {
358 JNIEnv* env = AttachCurrentThread(); 284 JNIEnv* env = AttachCurrentThread();
359 CHECK(env); 285 CHECK(env);
360 286
361 ScopedJavaLocalRef<jbyteArray> j_scheme_uuid = 287 ScopedJavaLocalRef<jbyteArray> j_scheme_uuid =
362 base::android::ToJavaByteArray(env, &scheme_uuid[0], scheme_uuid.size()); 288 base::android::ToJavaByteArray(env, &scheme_uuid[0], scheme_uuid.size());
363 j_media_drm_.Reset(Java_MediaDrmBridge_create( 289 j_media_drm_.Reset(Java_MediaDrmBridge_create(
(...skipping 13 matching lines...) Expand all
377 const std::string& key_system, 303 const std::string& key_system,
378 const SessionMessageCB& session_message_cb, 304 const SessionMessageCB& session_message_cb,
379 const SessionClosedCB& session_closed_cb, 305 const SessionClosedCB& session_closed_cb,
380 const LegacySessionErrorCB& legacy_session_error_cb, 306 const LegacySessionErrorCB& legacy_session_error_cb,
381 const SessionKeysChangeCB& session_keys_change_cb, 307 const SessionKeysChangeCB& session_keys_change_cb,
382 const SessionExpirationUpdateCB& /* session_expiration_update_cb */) { 308 const SessionExpirationUpdateCB& /* session_expiration_update_cb */) {
383 scoped_ptr<MediaDrmBridge> media_drm_bridge; 309 scoped_ptr<MediaDrmBridge> media_drm_bridge;
384 if (!IsAvailable()) 310 if (!IsAvailable())
385 return media_drm_bridge.Pass(); 311 return media_drm_bridge.Pass();
386 312
387 UUID scheme_uuid = g_key_system_uuid_manager.Get().GetUUID(key_system); 313 UUID scheme_uuid = g_key_system_manager.Get().GetUUID(key_system);
388 if (scheme_uuid.empty()) 314 if (scheme_uuid.empty())
389 return media_drm_bridge.Pass(); 315 return media_drm_bridge.Pass();
390 316
317 Delegate* delegate = g_key_system_manager.Get().GetDelegate(key_system);
391 media_drm_bridge.reset( 318 media_drm_bridge.reset(
392 new MediaDrmBridge(scheme_uuid, session_message_cb, session_closed_cb, 319 new MediaDrmBridge(scheme_uuid, session_message_cb, session_closed_cb,
393 legacy_session_error_cb, session_keys_change_cb)); 320 legacy_session_error_cb, session_keys_change_cb,
321 delegate));
394 322
395 if (media_drm_bridge->j_media_drm_.is_null()) 323 if (media_drm_bridge->j_media_drm_.is_null())
396 media_drm_bridge.reset(); 324 media_drm_bridge.reset();
397 325
398 return media_drm_bridge.Pass(); 326 return media_drm_bridge.Pass();
399 } 327 }
400 328
401 // static 329 // static
402 scoped_ptr<MediaDrmBridge> MediaDrmBridge::CreateWithoutSessionSupport( 330 scoped_ptr<MediaDrmBridge> MediaDrmBridge::CreateWithoutSessionSupport(
403 const std::string& key_system) { 331 const std::string& key_system) {
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
443 DVLOG(1) << __FUNCTION__; 371 DVLOG(1) << __FUNCTION__;
444 372
445 if (session_type != media::MediaKeys::TEMPORARY_SESSION) { 373 if (session_type != media::MediaKeys::TEMPORARY_SESSION) {
446 promise->reject(NOT_SUPPORTED_ERROR, 0, 374 promise->reject(NOT_SUPPORTED_ERROR, 0,
447 "Only the temporary session type is supported."); 375 "Only the temporary session type is supported.");
448 return; 376 return;
449 } 377 }
450 378
451 JNIEnv* env = AttachCurrentThread(); 379 JNIEnv* env = AttachCurrentThread();
452 ScopedJavaLocalRef<jbyteArray> j_init_data; 380 ScopedJavaLocalRef<jbyteArray> j_init_data;
381 ScopedJavaLocalRef<jobjectArray> j_optional_parameters;
453 382
454 // Widevine MediaDrm plugin only accepts the "data" part of the PSSH box as 383 if (delegate_) {
xhwang 2015/04/09 22:37:10 Just call g_key_system_manager.Get().GetDelegate(k
gunsch 2015/04/10 00:20:53 Can't right now: MediaDrmBridge doesn't actually t
xhwang 2015/04/10 16:41:13 (3) makes sense to me. MediaDrmBridge only talks U
gunsch 2015/04/11 00:18:16 Done.
455 // the init data when using MP4 container. 384 std::vector<uint8> init_data_from_delegate;
456 if (std::equal(scheme_uuid_.begin(), scheme_uuid_.end(), kWidevineUuid) && 385 std::vector<std::string> optional_parameters_from_delegate;
457 init_data_type == media::EmeInitDataType::CENC) { 386 if (!delegate_->OnCreateSession(init_data_type, init_data, init_data_length,
458 std::vector<uint8> pssh_data; 387 init_data_from_delegate,
459 if (!GetPsshData(init_data, init_data_length, scheme_uuid_, &pssh_data)) { 388 optional_parameters_from_delegate)) {
460 promise->reject(INVALID_ACCESS_ERROR, 0, "Invalid PSSH data."); 389 promise->reject(INVALID_ACCESS_ERROR, 0, "Invalid data.");
461 return;
462 } 390 }
463 j_init_data = 391 if (!init_data_from_delegate.empty()) {
464 base::android::ToJavaByteArray(env, &pssh_data[0], pssh_data.size()); 392 j_init_data = base::android::ToJavaByteArray(
465 } else { 393 env, &init_data_from_delegate[0], init_data_from_delegate.size());
394 }
395 if (!optional_parameters_from_delegate.empty()) {
396 j_optional_parameters = base::android::ToJavaArrayOfStrings(
397 env, optional_parameters_from_delegate);
398 }
399 }
400
401 if (j_init_data.is_null()) {
466 j_init_data = 402 j_init_data =
467 base::android::ToJavaByteArray(env, init_data, init_data_length); 403 base::android::ToJavaByteArray(env, init_data, init_data_length);
468 } 404 }
469 405
470 ScopedJavaLocalRef<jstring> j_mime = 406 ScopedJavaLocalRef<jstring> j_mime =
471 ConvertUTF8ToJavaString(env, ConvertInitDataType(init_data_type)); 407 ConvertUTF8ToJavaString(env, ConvertInitDataType(init_data_type));
472 uint32_t promise_id = cdm_promise_adapter_.SavePromise(promise.Pass()); 408 uint32_t promise_id = cdm_promise_adapter_.SavePromise(promise.Pass());
473 Java_MediaDrmBridge_createSession(env, j_media_drm_.obj(), j_init_data.obj(), 409 Java_MediaDrmBridge_createSession(env, j_media_drm_.obj(), j_init_data.obj(),
474 j_mime.obj(), promise_id); 410 j_mime.obj(), j_optional_parameters.obj(),
411 promise_id);
475 } 412 }
476 413
477 void MediaDrmBridge::LoadSession( 414 void MediaDrmBridge::LoadSession(
478 SessionType session_type, 415 SessionType session_type,
479 const std::string& session_id, 416 const std::string& session_id,
480 scoped_ptr<media::NewSessionCdmPromise> promise) { 417 scoped_ptr<media::NewSessionCdmPromise> promise) {
481 promise->reject(NOT_SUPPORTED_ERROR, 0, "LoadSession() is not supported."); 418 promise->reject(NOT_SUPPORTED_ERROR, 0, "LoadSession() is not supported.");
482 } 419 }
483 420
484 void MediaDrmBridge::UpdateSession( 421 void MediaDrmBridge::UpdateSession(
(...skipping 174 matching lines...) Expand 10 before | Expand all | Expand 10 after
659 JNIEnv* env = AttachCurrentThread(); 596 JNIEnv* env = AttachCurrentThread();
660 Java_MediaDrmBridge_resetDeviceCredentials(env, j_media_drm_.obj()); 597 Java_MediaDrmBridge_resetDeviceCredentials(env, j_media_drm_.obj());
661 } 598 }
662 599
663 void MediaDrmBridge::OnResetDeviceCredentialsCompleted( 600 void MediaDrmBridge::OnResetDeviceCredentialsCompleted(
664 JNIEnv* env, jobject, bool success) { 601 JNIEnv* env, jobject, bool success) {
665 base::ResetAndReturn(&reset_credentials_cb_).Run(success); 602 base::ResetAndReturn(&reset_credentials_cb_).Run(success);
666 } 603 }
667 604
668 } // namespace media 605 } // namespace media
OLDNEW
« media/base/android/media_drm_bridge.h ('K') | « media/base/android/media_drm_bridge.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698