Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 "webkit/media/crypto/ppapi_decryptor.h" | 5 #include "webkit/media/crypto/ppapi_decryptor.h" |
| 6 | 6 |
| 7 #include <string> | 7 #include <string> |
| 8 | 8 |
| 9 #include "base/bind.h" | 9 #include "base/bind.h" |
| 10 #include "base/callback_helpers.h" | 10 #include "base/callback_helpers.h" |
| 11 #include "base/location.h" | 11 #include "base/location.h" |
| 12 #include "base/logging.h" | 12 #include "base/logging.h" |
| 13 #include "base/message_loop.h" | 13 #include "base/message_loop.h" |
| 14 #include "base/message_loop_proxy.h" | 14 #include "base/message_loop_proxy.h" |
| 15 #include "media/base/audio_decoder_config.h" | |
| 15 #include "media/base/decoder_buffer.h" | 16 #include "media/base/decoder_buffer.h" |
| 16 #include "media/base/decryptor_client.h" | 17 #include "media/base/decryptor_client.h" |
| 17 #include "media/base/video_decoder_config.h" | 18 #include "media/base/video_decoder_config.h" |
| 18 #include "media/base/video_frame.h" | 19 #include "media/base/video_frame.h" |
| 19 #include "webkit/media/crypto/key_systems.h" | 20 #include "webkit/media/crypto/key_systems.h" |
| 20 #include "webkit/plugins/ppapi/ppapi_plugin_instance.h" | 21 #include "webkit/plugins/ppapi/ppapi_plugin_instance.h" |
| 21 | 22 |
| 22 namespace webkit_media { | 23 namespace webkit_media { |
| 23 | 24 |
| 24 PpapiDecryptor::PpapiDecryptor( | 25 PpapiDecryptor::PpapiDecryptor( |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 66 DCHECK(cdm_plugin_); | 67 DCHECK(cdm_plugin_); |
| 67 | 68 |
| 68 if (!cdm_plugin_->AddKey(session_id, | 69 if (!cdm_plugin_->AddKey(session_id, |
| 69 std::string(reinterpret_cast<const char*>(key), | 70 std::string(reinterpret_cast<const char*>(key), |
| 70 key_length), | 71 key_length), |
| 71 std::string(reinterpret_cast<const char*>(init_data), | 72 std::string(reinterpret_cast<const char*>(init_data), |
| 72 init_data_length))) { | 73 init_data_length))) { |
| 73 ReportFailureToCallPlugin(key_system, session_id); | 74 ReportFailureToCallPlugin(key_system, session_id); |
| 74 } | 75 } |
| 75 | 76 |
| 76 if (!key_added_cb_.is_null()) | 77 if (!audio_key_added_cb_.is_null()) |
| 77 key_added_cb_.Run(); | 78 audio_key_added_cb_.Run(); |
| 79 | |
| 80 if (!video_key_added_cb_.is_null()) | |
| 81 video_key_added_cb_.Run(); | |
| 78 } | 82 } |
| 79 | 83 |
| 80 void PpapiDecryptor::CancelKeyRequest(const std::string& key_system, | 84 void PpapiDecryptor::CancelKeyRequest(const std::string& key_system, |
| 81 const std::string& session_id) { | 85 const std::string& session_id) { |
| 82 DVLOG(2) << "CancelKeyRequest()"; | 86 DVLOG(2) << "CancelKeyRequest()"; |
| 83 DCHECK(render_loop_proxy_->BelongsToCurrentThread()); | 87 DCHECK(render_loop_proxy_->BelongsToCurrentThread()); |
| 84 DCHECK(cdm_plugin_); | 88 DCHECK(cdm_plugin_); |
| 85 | 89 |
| 86 if (!cdm_plugin_->CancelKeyRequest(session_id)) | 90 if (!cdm_plugin_->CancelKeyRequest(session_id)) |
| 87 ReportFailureToCallPlugin(key_system, session_id); | 91 ReportFailureToCallPlugin(key_system, session_id); |
| 88 } | 92 } |
| 89 | 93 |
| 90 // TODO(xhwang): Remove Unretained in the following methods. | 94 // TODO(xhwang): Remove Unretained in the following methods. |
| 91 | 95 |
| 92 void PpapiDecryptor::Decrypt( | 96 void PpapiDecryptor::Decrypt( |
| 97 StreamType stream_type, | |
| 93 const scoped_refptr<media::DecoderBuffer>& encrypted, | 98 const scoped_refptr<media::DecoderBuffer>& encrypted, |
| 94 const DecryptCB& decrypt_cb) { | 99 const DecryptCB& decrypt_cb) { |
| 95 if (!render_loop_proxy_->BelongsToCurrentThread()) { | 100 if (!render_loop_proxy_->BelongsToCurrentThread()) { |
| 96 render_loop_proxy_->PostTask( | 101 render_loop_proxy_->PostTask( |
| 97 FROM_HERE, | 102 FROM_HERE, |
| 98 base::Bind(&PpapiDecryptor::Decrypt, base::Unretained(this), | 103 base::Bind(&PpapiDecryptor::Decrypt, base::Unretained(this), |
| 99 encrypted, decrypt_cb)); | 104 stream_type, encrypted, decrypt_cb)); |
| 100 return; | 105 return; |
| 101 } | 106 } |
| 102 | 107 |
| 103 DVLOG(3) << "Decrypt()"; | 108 DVLOG(3) << "Decrypt() - stream_type: " << stream_type; |
| 104 if (!cdm_plugin_->Decrypt(encrypted, decrypt_cb)) | 109 if (!cdm_plugin_->Decrypt(encrypted, decrypt_cb)) |
| 105 decrypt_cb.Run(kError, NULL); | 110 decrypt_cb.Run(kError, NULL); |
| 106 } | 111 } |
| 107 | 112 |
| 108 void PpapiDecryptor::CancelDecrypt() { | 113 void PpapiDecryptor::CancelDecrypt(StreamType stream_type) { |
| 109 DVLOG(1) << "CancelDecrypt()"; | 114 DVLOG(1) << "CancelDecrypt() - stream_type: " << stream_type; |
| 110 // TODO(xhwang): Implement CancelDecrypt() in PluginInstance and call it here. | 115 // TODO(xhwang): Implement CancelDecrypt() in PluginInstance and call it here. |
| 111 } | 116 } |
| 112 | 117 |
| 118 void PpapiDecryptor::InitializeAudioDecoder( | |
| 119 scoped_ptr<media::AudioDecoderConfig> config, | |
| 120 const DecoderInitCB& init_cb, | |
| 121 const KeyAddedCB& key_added_cb) { | |
| 122 if (!render_loop_proxy_->BelongsToCurrentThread()) { | |
| 123 render_loop_proxy_->PostTask( | |
| 124 FROM_HERE, | |
| 125 base::Bind(&PpapiDecryptor::InitializeAudioDecoder, | |
| 126 base::Unretained(this), base::Passed(&config), | |
| 127 init_cb, key_added_cb)); | |
| 128 return; | |
| 129 } | |
| 130 | |
| 131 DVLOG(2) << "InitializeAudioDecoder()"; | |
| 132 DCHECK(config->is_encrypted()); | |
| 133 DCHECK(config->IsValidConfig()); | |
| 134 | |
| 135 audio_decoder_init_cb_ = init_cb; | |
| 136 // TODO(xhwang): Implement InitializeAudioDecoder() in PluginInstance and call | |
| 137 // it here. | |
| 138 NOTIMPLEMENTED(); | |
| 139 // if (!cdm_plugin_->InitializeAudioDecoder( | |
|
scherkus (not reviewing)
2012/10/18 02:08:36
use #if 0 instead
| |
| 140 // *config, | |
| 141 // base::Bind(&PpapiDecryptor::OnDecoderInitialized, | |
| 142 // base::Unretained(this), kAudio, key_added_cb))) { | |
| 143 base::ResetAndReturn(&audio_decoder_init_cb_).Run(false); | |
| 144 // return; | |
| 145 // } | |
| 146 } | |
| 147 | |
| 113 void PpapiDecryptor::InitializeVideoDecoder( | 148 void PpapiDecryptor::InitializeVideoDecoder( |
| 114 scoped_ptr<media::VideoDecoderConfig> config, | 149 scoped_ptr<media::VideoDecoderConfig> config, |
| 115 const DecoderInitCB& init_cb, | 150 const DecoderInitCB& init_cb, |
| 116 const KeyAddedCB& key_added_cb) { | 151 const KeyAddedCB& key_added_cb) { |
| 117 if (!render_loop_proxy_->BelongsToCurrentThread()) { | 152 if (!render_loop_proxy_->BelongsToCurrentThread()) { |
| 118 render_loop_proxy_->PostTask( | 153 render_loop_proxy_->PostTask( |
| 119 FROM_HERE, | 154 FROM_HERE, |
| 120 base::Bind(&PpapiDecryptor::InitializeVideoDecoder, | 155 base::Bind(&PpapiDecryptor::InitializeVideoDecoder, |
| 121 base::Unretained(this), base::Passed(&config), | 156 base::Unretained(this), base::Passed(&config), |
| 122 init_cb, key_added_cb)); | 157 init_cb, key_added_cb)); |
| 123 return; | 158 return; |
| 124 } | 159 } |
| 125 | 160 |
| 126 DVLOG(2) << "InitializeVideoDecoder()"; | 161 DVLOG(2) << "InitializeVideoDecoder()"; |
| 127 DCHECK(config->is_encrypted()); | 162 DCHECK(config->is_encrypted()); |
| 128 DCHECK(config->IsValidConfig()); | 163 DCHECK(config->IsValidConfig()); |
| 129 | 164 |
| 130 video_decoder_init_cb_ = init_cb; | 165 video_decoder_init_cb_ = init_cb; |
| 131 key_added_cb_ = key_added_cb; | |
| 132 | |
| 133 if (!cdm_plugin_->InitializeVideoDecoder( | 166 if (!cdm_plugin_->InitializeVideoDecoder( |
| 134 *config, | 167 *config, |
| 135 base::Bind(&PpapiDecryptor::OnVideoDecoderInitialized, | 168 base::Bind(&PpapiDecryptor::OnDecoderInitialized, |
| 136 base::Unretained(this)))) { | 169 base::Unretained(this), kVideo, key_added_cb))) { |
| 137 key_added_cb_.Reset(); | |
| 138 base::ResetAndReturn(&video_decoder_init_cb_).Run(false); | 170 base::ResetAndReturn(&video_decoder_init_cb_).Run(false); |
| 139 return; | 171 return; |
| 140 } | 172 } |
| 141 } | 173 } |
| 142 | 174 |
| 175 void PpapiDecryptor::DecryptAndDecodeAudio( | |
| 176 const scoped_refptr<media::DecoderBuffer>& encrypted, | |
| 177 const AudioDecodeCB& audio_decode_cb) { | |
| 178 if (!render_loop_proxy_->BelongsToCurrentThread()) { | |
| 179 render_loop_proxy_->PostTask( | |
| 180 FROM_HERE, | |
| 181 base::Bind(&PpapiDecryptor::DecryptAndDecodeAudio, | |
| 182 base::Unretained(this), encrypted, audio_decode_cb)); | |
| 183 return; | |
| 184 } | |
| 185 | |
| 186 DVLOG(1) << "DecryptAndDecodeAudio()"; | |
| 187 NOTIMPLEMENTED(); | |
| 188 // TODO(xhwang): Enable this once PluginInstance is updated. | |
| 189 // if (!cdm_plugin_->DecryptAndDecodeAudio(encrypted, audio_decode_cb)) | |
|
scherkus (not reviewing)
2012/10/18 02:08:36
use #if 0 instead
| |
| 190 audio_decode_cb.Run(kError, AudioBuffers()); | |
| 191 } | |
| 192 | |
| 143 void PpapiDecryptor::DecryptAndDecodeVideo( | 193 void PpapiDecryptor::DecryptAndDecodeVideo( |
| 144 const scoped_refptr<media::DecoderBuffer>& encrypted, | 194 const scoped_refptr<media::DecoderBuffer>& encrypted, |
| 145 const VideoDecodeCB& video_decode_cb) { | 195 const VideoDecodeCB& video_decode_cb) { |
| 146 if (!render_loop_proxy_->BelongsToCurrentThread()) { | 196 if (!render_loop_proxy_->BelongsToCurrentThread()) { |
| 147 render_loop_proxy_->PostTask( | 197 render_loop_proxy_->PostTask( |
| 148 FROM_HERE, | 198 FROM_HERE, |
| 149 base::Bind(&PpapiDecryptor::DecryptAndDecodeVideo, | 199 base::Bind(&PpapiDecryptor::DecryptAndDecodeVideo, |
| 150 base::Unretained(this), encrypted, video_decode_cb)); | 200 base::Unretained(this), encrypted, video_decode_cb)); |
| 151 return; | 201 return; |
| 152 } | 202 } |
| 153 | 203 |
| 154 DVLOG(3) << "DecryptAndDecodeVideo()"; | 204 DVLOG(3) << "DecryptAndDecodeVideo()"; |
| 155 if (!cdm_plugin_->DecryptAndDecode(encrypted, video_decode_cb)) | 205 if (!cdm_plugin_->DecryptAndDecode(encrypted, video_decode_cb)) |
| 156 video_decode_cb.Run(kError, NULL); | 206 video_decode_cb.Run(kError, NULL); |
| 157 } | 207 } |
| 158 | 208 |
| 159 void PpapiDecryptor::CancelDecryptAndDecodeVideo() { | 209 void PpapiDecryptor::ResetDecoder(StreamType stream_type) { |
| 160 if (!render_loop_proxy_->BelongsToCurrentThread()) { | 210 if (!render_loop_proxy_->BelongsToCurrentThread()) { |
| 161 render_loop_proxy_->PostTask( | 211 render_loop_proxy_->PostTask( |
| 162 FROM_HERE, | 212 FROM_HERE, |
| 163 base::Bind(&PpapiDecryptor::CancelDecryptAndDecodeVideo, | 213 base::Bind(&PpapiDecryptor::ResetDecoder, |
| 164 base::Unretained(this))); | 214 base::Unretained(this), stream_type)); |
| 165 return; | 215 return; |
| 166 } | 216 } |
| 167 | 217 |
| 168 DVLOG(2) << "CancelDecryptAndDecodeVideo()"; | 218 DVLOG(2) << "ResetDecoder() - stream_type: " << stream_type; |
| 219 // TODO(xhwang): Support stream type in PluginInstance. | |
| 169 cdm_plugin_->ResetDecoder(); | 220 cdm_plugin_->ResetDecoder(); |
| 170 } | 221 } |
| 171 | 222 |
| 172 void PpapiDecryptor::StopVideoDecoder() { | 223 void PpapiDecryptor::DeinitializeDecoder(StreamType stream_type) { |
| 173 if (!render_loop_proxy_->BelongsToCurrentThread()) { | 224 if (!render_loop_proxy_->BelongsToCurrentThread()) { |
| 174 render_loop_proxy_->PostTask( | 225 render_loop_proxy_->PostTask( |
| 175 FROM_HERE, | 226 FROM_HERE, |
| 176 base::Bind(&PpapiDecryptor::StopVideoDecoder, base::Unretained(this))); | 227 base::Bind(&PpapiDecryptor::DeinitializeDecoder, |
| 228 base::Unretained(this), stream_type)); | |
| 177 return; | 229 return; |
| 178 } | 230 } |
| 179 | 231 |
| 180 DVLOG(2) << "StopVideoDecoder()"; | 232 DVLOG(2) << "DeinitializeDecoder() - stream_type: " << stream_type; |
| 233 // TODO(xhwang): Support stream type in PluginInstance. | |
| 181 cdm_plugin_->DeinitializeDecoder(); | 234 cdm_plugin_->DeinitializeDecoder(); |
| 182 } | 235 } |
| 183 | 236 |
| 184 void PpapiDecryptor::ReportFailureToCallPlugin(const std::string& key_system, | 237 void PpapiDecryptor::ReportFailureToCallPlugin(const std::string& key_system, |
| 185 const std::string& session_id) { | 238 const std::string& session_id) { |
| 186 DVLOG(1) << "Failed to call plugin."; | 239 DVLOG(1) << "Failed to call plugin."; |
| 187 client_->KeyError(key_system, session_id, kUnknownError, 0); | 240 client_->KeyError(key_system, session_id, kUnknownError, 0); |
| 188 } | 241 } |
| 189 | 242 |
| 190 void PpapiDecryptor::OnVideoDecoderInitialized(bool success) { | 243 void PpapiDecryptor::OnDecoderInitialized(StreamType stream_type, |
| 191 DCHECK(!key_added_cb_.is_null()); | 244 const KeyAddedCB& key_added_cb, |
| 192 DCHECK(!video_decoder_init_cb_.is_null()); | 245 bool success) { |
| 246 DCHECK(!key_added_cb.is_null()); | |
| 193 | 247 |
| 194 if (!success) | 248 switch (stream_type) { |
| 195 key_added_cb_.Reset(); | 249 case kAudio: |
| 250 DCHECK(audio_key_added_cb_.is_null()); | |
| 251 DCHECK(!audio_decoder_init_cb_.is_null()); | |
| 252 if (success) | |
| 253 audio_key_added_cb_ = key_added_cb; | |
| 254 base::ResetAndReturn(&audio_decoder_init_cb_).Run(success); | |
| 255 break; | |
| 196 | 256 |
| 197 base::ResetAndReturn(&video_decoder_init_cb_).Run(success); | 257 case kVideo: |
| 258 DCHECK(video_key_added_cb_.is_null()); | |
| 259 DCHECK(!video_decoder_init_cb_.is_null()); | |
| 260 if (success) | |
| 261 video_key_added_cb_ = key_added_cb; | |
| 262 base::ResetAndReturn(&video_decoder_init_cb_).Run(success); | |
| 263 break; | |
| 264 | |
| 265 default: | |
| 266 NOTREACHED(); | |
| 267 } | |
| 198 } | 268 } |
| 199 | 269 |
| 200 } // namespace webkit_media | 270 } // namespace webkit_media |
| OLD | NEW |