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

Side by Side Diff: content/renderer/media/rtc_video_decoder.cc

Issue 27420004: Remove threading from RendererGpuVideoAcceleratorFactories (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@dthread
Patch Set: 51676bf4 Initial. Created 7 years, 2 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 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/rtc_video_decoder.h" 5 #include "content/renderer/media/rtc_video_decoder.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/logging.h" 8 #include "base/logging.h"
9 #include "base/memory/ref_counted.h" 9 #include "base/memory/ref_counted.h"
10 #include "base/message_loop/message_loop_proxy.h" 10 #include "base/message_loop/message_loop_proxy.h"
11 #include "base/metrics/histogram.h" 11 #include "base/metrics/histogram.h"
12 #include "base/safe_numerics.h" 12 #include "base/safe_numerics.h"
13 #include "base/stl_util.h" 13 #include "base/stl_util.h"
14 #include "base/synchronization/waitable_event.h"
14 #include "base/task_runner_util.h" 15 #include "base/task_runner_util.h"
15 #include "content/child/child_thread.h" 16 #include "content/child/child_thread.h"
16 #include "content/renderer/media/native_handle_impl.h" 17 #include "content/renderer/media/native_handle_impl.h"
17 #include "media/base/bind_to_loop.h" 18 #include "media/base/bind_to_loop.h"
18 #include "media/filters/gpu_video_accelerator_factories.h" 19 #include "media/filters/gpu_video_accelerator_factories.h"
19 #include "third_party/webrtc/common_video/interface/texture_video_frame.h" 20 #include "third_party/webrtc/common_video/interface/texture_video_frame.h"
20 #include "third_party/webrtc/system_wrappers/interface/ref_count.h" 21 #include "third_party/webrtc/system_wrappers/interface/ref_count.h"
21 22
22 namespace content { 23 namespace content {
23 24
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after
76 : weak_factory_(this), 77 : weak_factory_(this),
77 weak_this_(weak_factory_.GetWeakPtr()), 78 weak_this_(weak_factory_.GetWeakPtr()),
78 factories_(factories), 79 factories_(factories),
79 vda_loop_proxy_(factories->GetMessageLoop()), 80 vda_loop_proxy_(factories->GetMessageLoop()),
80 decoder_texture_target_(0), 81 decoder_texture_target_(0),
81 next_picture_buffer_id_(0), 82 next_picture_buffer_id_(0),
82 state_(UNINITIALIZED), 83 state_(UNINITIALIZED),
83 decode_complete_callback_(NULL), 84 decode_complete_callback_(NULL),
84 num_shm_buffers_(0), 85 num_shm_buffers_(0),
85 next_bitstream_buffer_id_(0), 86 next_bitstream_buffer_id_(0),
86 reset_bitstream_buffer_id_(ID_INVALID) { 87 reset_bitstream_buffer_id_(ID_INVALID) {}
87 DCHECK(!vda_loop_proxy_->BelongsToCurrentThread());
88 base::WaitableEvent message_loop_async_waiter(false, false);
89 // Waiting here is safe. The media thread is stopped in the child thread and
90 // the child thread is blocked when VideoDecoderFactory::CreateVideoDecoder
91 // runs.
92 vda_loop_proxy_->PostTask(FROM_HERE,
93 base::Bind(&RTCVideoDecoder::Initialize,
94 base::Unretained(this),
95 &message_loop_async_waiter));
96 message_loop_async_waiter.Wait();
97 }
98 88
99 RTCVideoDecoder::~RTCVideoDecoder() { 89 RTCVideoDecoder::~RTCVideoDecoder() {
100 DVLOG(2) << "~RTCVideoDecoder"; 90 DVLOG(2) << "~RTCVideoDecoder";
101 DCHECK(vda_loop_proxy_->BelongsToCurrentThread()); 91 DCHECK(vda_loop_proxy_->BelongsToCurrentThread());
102 92
103 DestroyVDA(); 93 DestroyVDA();
104 94
105 // Delete all shared memories. 95 // Delete all shared memories.
106 STLDeleteElements(&available_shm_segments_); 96 STLDeleteElements(&available_shm_segments_);
107 STLDeleteValues(&bitstream_buffers_in_decoder_); 97 STLDeleteValues(&bitstream_buffers_in_decoder_);
(...skipping 19 matching lines...) Expand all
127 media::VideoCodecProfile profile; 117 media::VideoCodecProfile profile;
128 switch (type) { 118 switch (type) {
129 case webrtc::kVideoCodecVP8: 119 case webrtc::kVideoCodecVP8:
130 profile = media::VP8PROFILE_MAIN; 120 profile = media::VP8PROFILE_MAIN;
131 break; 121 break;
132 default: 122 default:
133 DVLOG(2) << "Video codec not supported:" << type; 123 DVLOG(2) << "Video codec not supported:" << type;
134 return decoder.Pass(); 124 return decoder.Pass();
135 } 125 }
136 126
127 base::WaitableEvent waiter(true, false);
137 decoder.reset(new RTCVideoDecoder(factories)); 128 decoder.reset(new RTCVideoDecoder(factories));
138 decoder->vda_ = 129 decoder->vda_loop_proxy_->PostTask(FROM_HERE,
139 factories->CreateVideoDecodeAccelerator(profile, decoder.get()).Pass(); 130 base::Bind(&RTCVideoDecoder::CreateVDA,
131 base::Unretained(decoder.get()),
132 profile,
133 &decoder->vda_,
134 &waiter));
135 waiter.Wait();
140 // vda can be NULL if VP8 is not supported. 136 // vda can be NULL if VP8 is not supported.
141 if (decoder->vda_ != NULL) { 137 if (decoder->vda_ != NULL) {
142 decoder->state_ = INITIALIZED; 138 decoder->state_ = INITIALIZED;
143 } else { 139 } else {
144 factories->GetMessageLoop()->DeleteSoon(FROM_HERE, decoder.release()); 140 factories->GetMessageLoop()->DeleteSoon(FROM_HERE, decoder.release());
145 } 141 }
146 return decoder.Pass(); 142 return decoder.Pass();
147 } 143 }
148 144
149 int32_t RTCVideoDecoder::InitDecode(const webrtc::VideoCodec* codecSettings, 145 int32_t RTCVideoDecoder::InitDecode(const webrtc::VideoCodec* codecSettings,
(...skipping 309 matching lines...) Expand 10 before | Expand all | Expand 10 after
459 LOG(ERROR) << "VDA Error:" << error; 455 LOG(ERROR) << "VDA Error:" << error;
460 UMA_HISTOGRAM_ENUMERATION("Media.RTCVideoDecoderError", 456 UMA_HISTOGRAM_ENUMERATION("Media.RTCVideoDecoderError",
461 error, 457 error,
462 media::VideoDecodeAccelerator::LARGEST_ERROR_ENUM); 458 media::VideoDecodeAccelerator::LARGEST_ERROR_ENUM);
463 DestroyVDA(); 459 DestroyVDA();
464 460
465 base::AutoLock auto_lock(lock_); 461 base::AutoLock auto_lock(lock_);
466 state_ = DECODE_ERROR; 462 state_ = DECODE_ERROR;
467 } 463 }
468 464
469 void RTCVideoDecoder::WillDestroyCurrentMessageLoop() {
470 DVLOG(2) << "WillDestroyCurrentMessageLoop";
471 DCHECK(vda_loop_proxy_->BelongsToCurrentThread());
472 factories_->Abort();
473 weak_factory_.InvalidateWeakPtrs();
474 DestroyVDA();
475 }
476
477 void RTCVideoDecoder::Initialize(base::WaitableEvent* waiter) {
478 DVLOG(2) << "Initialize";
479 DCHECK(vda_loop_proxy_->BelongsToCurrentThread());
480 base::MessageLoop::current()->AddDestructionObserver(this);
481 waiter->Signal();
482 }
483
484 void RTCVideoDecoder::RequestBufferDecode() { 465 void RTCVideoDecoder::RequestBufferDecode() {
485 DCHECK(vda_loop_proxy_->BelongsToCurrentThread()); 466 DCHECK(vda_loop_proxy_->BelongsToCurrentThread());
486 if (!vda_) 467 if (!vda_)
487 return; 468 return;
488 469
489 MovePendingBuffersToDecodeBuffers(); 470 MovePendingBuffersToDecodeBuffers();
490 471
491 while (CanMoreDecodeWorkBeDone()) { 472 while (CanMoreDecodeWorkBeDone()) {
492 // Get a buffer and data from the queue. 473 // Get a buffer and data from the queue.
493 SHMBuffer* shm_buffer = NULL; 474 SHMBuffer* shm_buffer = NULL;
(...skipping 139 matching lines...) Expand 10 before | Expand all | Expand 10 after
633 factories_->DeleteTexture(it->second.texture_id()); 614 factories_->DeleteTexture(it->second.texture_id());
634 dismissed_picture_buffers_.erase(it); 615 dismissed_picture_buffers_.erase(it);
635 return; 616 return;
636 } 617 }
637 618
638 factories_->WaitSyncPoint(sync_point); 619 factories_->WaitSyncPoint(sync_point);
639 620
640 vda_->ReusePictureBuffer(picture_buffer_id); 621 vda_->ReusePictureBuffer(picture_buffer_id);
641 } 622 }
642 623
624 void RTCVideoDecoder::CreateVDA(media::VideoCodecProfile profile,
625 scoped_ptr<media::VideoDecodeAccelerator>* vda,
626 base::WaitableEvent* waiter) {
627 DCHECK(vda_loop_proxy_->BelongsToCurrentThread());
628 *vda = factories_->CreateVideoDecodeAccelerator(profile, this);
wuchengli 2013/10/16 07:43:17 Just use |vda_| here and remove the parameter?
sheu 2013/10/21 05:17:35 Done.
629 waiter->Signal();
630 }
631
643 void RTCVideoDecoder::DestroyTextures() { 632 void RTCVideoDecoder::DestroyTextures() {
644 DCHECK(vda_loop_proxy_->BelongsToCurrentThread()); 633 DCHECK(vda_loop_proxy_->BelongsToCurrentThread());
645 std::map<int32, media::PictureBuffer>::iterator it; 634 std::map<int32, media::PictureBuffer>::iterator it;
646 635
647 for (it = assigned_picture_buffers_.begin(); 636 for (it = assigned_picture_buffers_.begin();
648 it != assigned_picture_buffers_.end(); 637 it != assigned_picture_buffers_.end();
649 ++it) { 638 ++it) {
650 factories_->DeleteTexture(it->second.texture_id()); 639 factories_->DeleteTexture(it->second.texture_id());
651 } 640 }
652 assigned_picture_buffers_.clear(); 641 assigned_picture_buffers_.clear();
(...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after
748 737
749 int32_t RTCVideoDecoder::RecordInitDecodeUMA(int32_t status) { 738 int32_t RTCVideoDecoder::RecordInitDecodeUMA(int32_t status) {
750 // Logging boolean is enough to know if HW decoding has been used. Also, 739 // Logging boolean is enough to know if HW decoding has been used. Also,
751 // InitDecode is less likely to return an error so enum is not used here. 740 // InitDecode is less likely to return an error so enum is not used here.
752 bool sample = (status == WEBRTC_VIDEO_CODEC_OK) ? true : false; 741 bool sample = (status == WEBRTC_VIDEO_CODEC_OK) ? true : false;
753 UMA_HISTOGRAM_BOOLEAN("Media.RTCVideoDecoderInitDecodeStatus", sample); 742 UMA_HISTOGRAM_BOOLEAN("Media.RTCVideoDecoderInitDecodeStatus", sample);
754 return status; 743 return status;
755 } 744 }
756 745
757 } // namespace content 746 } // namespace content
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698