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

Side by Side Diff: chrome/renderer/gpu_video_decoder_host.cc

Issue 3020077: Revert 55405 - Special thanks for in-ming cheng's MFT hardware decodering cod... (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src/
Patch Set: Created 10 years, 4 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 | Annotate | Revision Log
« no previous file with comments | « chrome/renderer/gpu_video_decoder_host.h ('k') | chrome/renderer/gpu_video_service_host.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "chrome/renderer/gpu_video_decoder_host.h"
6
7 #include "chrome/common/gpu_messages.h"
8 #include "chrome/renderer/gpu_video_service_host.h"
9 #include "chrome/renderer/render_thread.h"
10
11 void GpuVideoDecoderHost::OnChannelError() {
12 channel_host_.release();
13 }
14
15 void GpuVideoDecoderHost::OnMessageReceived(const IPC::Message& msg) {
16 IPC_BEGIN_MESSAGE_MAP(GpuVideoDecoderHost, msg)
17 IPC_MESSAGE_HANDLER(GpuVideoDecoderHostMsg_InitializeACK,
18 OnInitializeDone)
19 IPC_MESSAGE_HANDLER(GpuVideoDecoderHostMsg_DestroyACK,
20 OnUninitializeDone)
21 IPC_MESSAGE_HANDLER(GpuVideoDecoderHostMsg_FlushACK,
22 OnFlushDone)
23 IPC_MESSAGE_HANDLER(GpuVideoDecoderHostMsg_EmptyThisBufferACK,
24 OnEmptyThisBufferACK)
25 IPC_MESSAGE_HANDLER(GpuVideoDecoderHostMsg_EmptyThisBufferDone,
26 OnEmptyThisBufferDone)
27 IPC_MESSAGE_HANDLER(GpuVideoDecoderHostMsg_FillThisBufferDone,
28 OnFillThisBufferDone)
29 IPC_MESSAGE_UNHANDLED_ERROR()
30 IPC_END_MESSAGE_MAP()
31 }
32
33 bool GpuVideoDecoderHost::Initialize(const GpuVideoDecoderInitParam& param) {
34 DCHECK_EQ(state_, kStateUninitialized);
35
36 init_param_ = param;
37 if (!channel_host_->Send(
38 new GpuVideoDecoderMsg_Initialize(route_id(), param))) {
39 LOG(ERROR) << "GpuVideoDecoderMsg_Initialize failed";
40 return false;
41 }
42 return true;
43 }
44
45 bool GpuVideoDecoderHost::Uninitialize() {
46 if (!channel_host_->Send(new GpuVideoDecoderMsg_Destroy(route_id()))) {
47 LOG(ERROR) << "GpuVideoDecoderMsg_Destroy failed";
48 return false;
49 }
50 return true;
51 }
52
53 void GpuVideoDecoderHost::EmptyThisBuffer(scoped_refptr<Buffer> buffer) {
54 DCHECK_NE(state_, kStateUninitialized);
55 DCHECK_NE(state_, kStateFlushing);
56
57 // We never own input buffers, therefore when client in flush state, it
58 // never call us with EmptyThisBuffer.
59 if (state_ != kStateNormal)
60 return;
61
62 input_buffer_queue_.push_back(buffer);
63 SendInputBufferToGpu();
64 }
65
66 void GpuVideoDecoderHost::FillThisBuffer(scoped_refptr<VideoFrame> frame) {
67 DCHECK_NE(state_, kStateUninitialized);
68
69 // Depends on who provides buffer. client could return buffer to
70 // us while flushing.
71 if (state_ == kStateError)
72 return;
73
74 GpuVideoDecoderOutputBufferParam param;
75 if (!channel_host_->Send(
76 new GpuVideoDecoderMsg_FillThisBuffer(route_id(), param))) {
77 LOG(ERROR) << "GpuVideoDecoderMsg_FillThisBuffer failed";
78 }
79 }
80
81 bool GpuVideoDecoderHost::Flush() {
82 state_ = kStateFlushing;
83 if (!channel_host_->Send(new GpuVideoDecoderMsg_Flush(route_id()))) {
84 LOG(ERROR) << "GpuVideoDecoderMsg_Flush failed";
85 return false;
86 }
87 input_buffer_queue_.clear();
88 // TODO(jiesun): because GpuVideoDeocder/GpuVideoDecoder are asynchronously.
89 // We need a way to make flush logic more clear. but I think ring buffer
90 // should make the busy flag obsolete, therefore I will leave it for now.
91 input_buffer_busy_ = false;
92 return true;
93 }
94
95 void GpuVideoDecoderHost::OnInitializeDone(
96 const GpuVideoDecoderInitDoneParam& param) {
97 done_param_ = param;
98 bool success = false;
99
100 do {
101 if (!param.success_)
102 break;
103
104 if (!base::SharedMemory::IsHandleValid(param.input_buffer_handle_))
105 break;
106 input_transfer_buffer_.reset(
107 new base::SharedMemory(param.input_buffer_handle_, false));
108 if (!input_transfer_buffer_->Map(param.input_buffer_size_))
109 break;
110
111 if (!base::SharedMemory::IsHandleValid(param.output_buffer_handle_))
112 break;
113 output_transfer_buffer_.reset(
114 new base::SharedMemory(param.output_buffer_handle_, false));
115 if (!output_transfer_buffer_->Map(param.output_buffer_size_))
116 break;
117
118 success = true;
119 } while (0);
120
121 state_ = success ? kStateNormal : kStateError;
122 event_handler_->OnInitializeDone(success, param);
123 }
124
125 void GpuVideoDecoderHost::OnUninitializeDone() {
126 input_transfer_buffer_.reset();
127 output_transfer_buffer_.reset();
128
129 event_handler_->OnUninitializeDone();
130 }
131
132 void GpuVideoDecoderHost::OnFlushDone() {
133 state_ = kStateNormal;
134 event_handler_->OnFlushDone();
135 }
136
137 void GpuVideoDecoderHost::OnEmptyThisBufferDone() {
138 scoped_refptr<Buffer> buffer;
139 event_handler_->OnEmptyBufferDone(buffer);
140 }
141
142 void GpuVideoDecoderHost::OnFillThisBufferDone(
143 const GpuVideoDecoderOutputBufferParam& param) {
144 scoped_refptr<VideoFrame> frame;
145
146 if (param.flags_ & GpuVideoDecoderOutputBufferParam::kFlagsEndOfStream) {
147 VideoFrame::CreateEmptyFrame(&frame);
148 } else {
149 VideoFrame::CreateFrame(VideoFrame::YV12,
150 init_param_.width_,
151 init_param_.height_,
152 base::TimeDelta::FromMicroseconds(param.timestamp_),
153 base::TimeDelta::FromMicroseconds(param.duration_),
154 &frame);
155
156 uint8* src = static_cast<uint8*>(output_transfer_buffer_->memory());
157 uint8* data0 = frame->data(0);
158 uint8* data1 = frame->data(1);
159 uint8* data2 = frame->data(2);
160 int32 size = init_param_.width_ * init_param_.height_;
161 memcpy(data0, src, size);
162 memcpy(data1, src + size, size / 4);
163 memcpy(data2, src + size + size / 4, size / 4);
164 }
165
166 event_handler_->OnFillBufferDone(frame);
167 if (!channel_host_->Send(
168 new GpuVideoDecoderMsg_FillThisBufferDoneACK(route_id()))) {
169 LOG(ERROR) << "GpuVideoDecoderMsg_FillThisBufferDoneACK failed";
170 }
171 }
172
173 void GpuVideoDecoderHost::OnEmptyThisBufferACK() {
174 input_buffer_busy_ = false;
175 SendInputBufferToGpu();
176 }
177
178 void GpuVideoDecoderHost::SendInputBufferToGpu() {
179 if (input_buffer_busy_) return;
180 if (input_buffer_queue_.empty()) return;
181
182 input_buffer_busy_ = true;
183
184 scoped_refptr<Buffer> buffer;
185 buffer = input_buffer_queue_.front();
186 input_buffer_queue_.pop_front();
187
188 // Send input data to GPU process.
189 GpuVideoDecoderInputBufferParam param;
190 param.offset_ = 0;
191 param.size_ = buffer->GetDataSize();
192 param.timestamp_ = buffer->GetTimestamp().InMicroseconds();
193 memcpy(input_transfer_buffer_->memory(), buffer->GetData(), param.size_);
194 if (!channel_host_->Send(
195 new GpuVideoDecoderMsg_EmptyThisBuffer(route_id(), param))) {
196 LOG(ERROR) << "GpuVideoDecoderMsg_EmptyThisBuffer failed";
197 }
198 }
199
OLDNEW
« no previous file with comments | « chrome/renderer/gpu_video_decoder_host.h ('k') | chrome/renderer/gpu_video_service_host.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698