OLD | NEW |
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 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 "content/renderer/media/gpu/rtc_video_decoder.h" | 5 #include "content/renderer/media/gpu/rtc_video_decoder.h" |
6 | 6 |
7 #include <utility> | 7 #include <utility> |
8 | 8 |
9 #include "base/bind.h" | 9 #include "base/bind.h" |
10 #include "base/logging.h" | 10 #include "base/logging.h" |
(...skipping 218 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
229 gfx::Size prev_frame_size = frame_size_; | 229 gfx::Size prev_frame_size = frame_size_; |
230 frame_size_ = new_frame_size; | 230 frame_size_ = new_frame_size; |
231 if (!kVDACanHandleMidstreamResize && !prev_frame_size.IsEmpty() && | 231 if (!kVDACanHandleMidstreamResize && !prev_frame_size.IsEmpty() && |
232 prev_frame_size != frame_size_) { | 232 prev_frame_size != frame_size_) { |
233 need_to_reset_for_midstream_resize = true; | 233 need_to_reset_for_midstream_resize = true; |
234 } | 234 } |
235 } else if (IsFirstBufferAfterReset(next_bitstream_buffer_id_, | 235 } else if (IsFirstBufferAfterReset(next_bitstream_buffer_id_, |
236 reset_bitstream_buffer_id_)) { | 236 reset_bitstream_buffer_id_)) { |
237 // TODO(wuchengli): VDA should handle it. Remove this when | 237 // TODO(wuchengli): VDA should handle it. Remove this when |
238 // http://crosbug.com/p/21913 is fixed. | 238 // http://crosbug.com/p/21913 is fixed. |
| 239 |
| 240 // If we're are in an error condition, increase the counter. |
| 241 vda_error_counter_ += vda_error_counter_ ? 1 : 0; |
| 242 |
239 DVLOG(1) << "The first frame should be a key frame. Drop this."; | 243 DVLOG(1) << "The first frame should be a key frame. Drop this."; |
240 return WEBRTC_VIDEO_CODEC_ERROR; | 244 return WEBRTC_VIDEO_CODEC_ERROR; |
241 } | 245 } |
242 | 246 |
243 // Create buffer metadata. | 247 // Create buffer metadata. |
244 BufferData buffer_data(next_bitstream_buffer_id_, | 248 BufferData buffer_data(next_bitstream_buffer_id_, |
245 inputImage._timeStamp, | 249 inputImage._timeStamp, |
246 inputImage._length, | 250 inputImage._length, |
247 gfx::Rect(frame_size_)); | 251 gfx::Rect(frame_size_)); |
248 // Mask against 30 bits, to avoid (undefined) wraparound on signed integer. | 252 // Mask against 30 bits, to avoid (undefined) wraparound on signed integer. |
(...skipping 13 matching lines...) Expand all Loading... |
262 // Better to drop any pending buffers and start afresh to catch up faster. | 266 // Better to drop any pending buffers and start afresh to catch up faster. |
263 DVLOG(1) << "Exceeded maximum pending buffer count, dropping"; | 267 DVLOG(1) << "Exceeded maximum pending buffer count, dropping"; |
264 ClearPendingBuffers(); | 268 ClearPendingBuffers(); |
265 return WEBRTC_VIDEO_CODEC_ERROR; | 269 return WEBRTC_VIDEO_CODEC_ERROR; |
266 } | 270 } |
267 | 271 |
268 if (need_to_reset_for_midstream_resize) { | 272 if (need_to_reset_for_midstream_resize) { |
269 base::AutoUnlock auto_unlock(lock_); | 273 base::AutoUnlock auto_unlock(lock_); |
270 Release(); | 274 Release(); |
271 } | 275 } |
272 | |
273 TryResetVDAErrorCounter_Locked(); | |
274 return WEBRTC_VIDEO_CODEC_OK; | 276 return WEBRTC_VIDEO_CODEC_OK; |
275 } | 277 } |
276 | 278 |
277 SaveToDecodeBuffers_Locked(inputImage, std::move(shm_buffer), buffer_data); | 279 SaveToDecodeBuffers_Locked(inputImage, std::move(shm_buffer), buffer_data); |
278 factories_->GetTaskRunner()->PostTask( | 280 factories_->GetTaskRunner()->PostTask( |
279 FROM_HERE, | 281 FROM_HERE, |
280 base::Bind(&RTCVideoDecoder::RequestBufferDecode, | 282 base::Bind(&RTCVideoDecoder::RequestBufferDecode, |
281 weak_factory_.GetWeakPtr())); | 283 weak_factory_.GetWeakPtr())); |
282 TryResetVDAErrorCounter_Locked(); | |
283 return WEBRTC_VIDEO_CODEC_OK; | 284 return WEBRTC_VIDEO_CODEC_OK; |
284 } | 285 } |
285 | 286 |
286 int32_t RTCVideoDecoder::RegisterDecodeCompleteCallback( | 287 int32_t RTCVideoDecoder::RegisterDecodeCompleteCallback( |
287 webrtc::DecodedImageCallback* callback) { | 288 webrtc::DecodedImageCallback* callback) { |
288 DVLOG(2) << "RegisterDecodeCompleteCallback"; | 289 DVLOG(2) << "RegisterDecodeCompleteCallback"; |
289 DCHECK(callback); | 290 DCHECK(callback); |
290 base::AutoLock auto_lock(lock_); | 291 base::AutoLock auto_lock(lock_); |
291 decode_complete_callback_ = callback; | 292 decode_complete_callback_ = callback; |
292 return WEBRTC_VIDEO_CODEC_OK; | 293 return WEBRTC_VIDEO_CODEC_OK; |
(...skipping 143 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
436 webrtc::kVideoRotation_0); | 437 webrtc::kVideoRotation_0); |
437 | 438 |
438 // Invoke decode callback. WebRTC expects no callback after Release. | 439 // Invoke decode callback. WebRTC expects no callback after Release. |
439 { | 440 { |
440 base::AutoLock auto_lock(lock_); | 441 base::AutoLock auto_lock(lock_); |
441 DCHECK(decode_complete_callback_); | 442 DCHECK(decode_complete_callback_); |
442 if (IsBufferAfterReset(picture.bitstream_buffer_id(), | 443 if (IsBufferAfterReset(picture.bitstream_buffer_id(), |
443 reset_bitstream_buffer_id_)) { | 444 reset_bitstream_buffer_id_)) { |
444 decode_complete_callback_->Decoded(decoded_image); | 445 decode_complete_callback_->Decoded(decoded_image); |
445 } | 446 } |
| 447 // Reset error counter as we successfully decoded a frame. |
| 448 vda_error_counter_ = 0; |
446 } | 449 } |
447 } | 450 } |
448 | 451 |
449 scoped_refptr<media::VideoFrame> RTCVideoDecoder::CreateVideoFrame( | 452 scoped_refptr<media::VideoFrame> RTCVideoDecoder::CreateVideoFrame( |
450 const media::Picture& picture, | 453 const media::Picture& picture, |
451 const media::PictureBuffer& pb, | 454 const media::PictureBuffer& pb, |
452 uint32_t timestamp, | 455 uint32_t timestamp, |
453 const gfx::Rect& visible_rect, | 456 const gfx::Rect& visible_rect, |
454 media::VideoPixelFormat pixel_format) { | 457 media::VideoPixelFormat pixel_format) { |
455 DCHECK(decoder_texture_target_); | 458 DCHECK(decoder_texture_target_); |
(...skipping 426 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
882 DCHECK(factories_->GetTaskRunner()->BelongsToCurrentThread()); | 885 DCHECK(factories_->GetTaskRunner()->BelongsToCurrentThread()); |
883 } | 886 } |
884 | 887 |
885 void RTCVideoDecoder::ClearPendingBuffers() { | 888 void RTCVideoDecoder::ClearPendingBuffers() { |
886 // Delete WebRTC input buffers. | 889 // Delete WebRTC input buffers. |
887 for (const auto& pending_buffer : pending_buffers_) | 890 for (const auto& pending_buffer : pending_buffers_) |
888 delete[] pending_buffer.first._buffer; | 891 delete[] pending_buffer.first._buffer; |
889 pending_buffers_.clear(); | 892 pending_buffers_.clear(); |
890 } | 893 } |
891 | 894 |
892 void RTCVideoDecoder::TryResetVDAErrorCounter_Locked() { | |
893 lock_.AssertAcquired(); | |
894 | |
895 if (vda_error_counter_ == 0) | |
896 return; | |
897 vda_error_counter_ = 0; | |
898 } | |
899 | |
900 } // namespace content | 895 } // namespace content |
OLD | NEW |