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

Side by Side Diff: content/common/gpu/media/v4l2_video_decode_accelerator.cc

Issue 1207043002: Introduce a client minimum picture pool size (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Moved constant to shared header, validate min_picture_size now in resource proxy as well as host co… Created 5 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
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 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 <dlfcn.h> 5 #include <dlfcn.h>
6 #include <errno.h> 6 #include <errno.h>
7 #include <fcntl.h> 7 #include <fcntl.h>
8 #include <linux/videodev2.h> 8 #include <linux/videodev2.h>
9 #include <poll.h> 9 #include <poll.h>
10 #include <sys/eventfd.h> 10 #include <sys/eventfd.h>
(...skipping 304 matching lines...) Expand 10 before | Expand all | Expand 10 after
315 decoder_thread_.message_loop()->PostTask(FROM_HERE, base::Bind( 315 decoder_thread_.message_loop()->PostTask(FROM_HERE, base::Bind(
316 &V4L2VideoDecodeAccelerator::DecodeTask, base::Unretained(this), 316 &V4L2VideoDecodeAccelerator::DecodeTask, base::Unretained(this),
317 bitstream_buffer)); 317 bitstream_buffer));
318 } 318 }
319 319
320 void V4L2VideoDecodeAccelerator::AssignPictureBuffers( 320 void V4L2VideoDecodeAccelerator::AssignPictureBuffers(
321 const std::vector<media::PictureBuffer>& buffers) { 321 const std::vector<media::PictureBuffer>& buffers) {
322 DVLOG(3) << "AssignPictureBuffers(): buffer_count=" << buffers.size(); 322 DVLOG(3) << "AssignPictureBuffers(): buffer_count=" << buffers.size();
323 DCHECK(child_task_runner_->BelongsToCurrentThread()); 323 DCHECK(child_task_runner_->BelongsToCurrentThread());
324 324
325 if (buffers.size() != output_buffer_map_.size()) { 325 const uint32_t req_buffer_count =
326 output_dpb_size_ + kDpbOutputBufferExtraCount;
327
328 if (buffers.size() < req_buffer_count) {
326 LOG(ERROR) << "AssignPictureBuffers(): Failed to provide requested picture" 329 LOG(ERROR) << "AssignPictureBuffers(): Failed to provide requested picture"
327 " buffers. (Got " << buffers.size() 330 " buffers. (Got " << buffers.size()
328 << ", requested " << output_buffer_map_.size() << ")"; 331 << ", requested " << req_buffer_count << ")";
329 NOTIFY_ERROR(INVALID_ARGUMENT); 332 NOTIFY_ERROR(INVALID_ARGUMENT);
330 return; 333 return;
331 } 334 }
332 335
333 if (!make_context_current_.Run()) { 336 if (!make_context_current_.Run()) {
334 LOG(ERROR) << "AssignPictureBuffers(): could not make context current"; 337 LOG(ERROR) << "AssignPictureBuffers(): could not make context current";
335 NOTIFY_ERROR(PLATFORM_FAILURE); 338 NOTIFY_ERROR(PLATFORM_FAILURE);
336 return; 339 return;
337 } 340 }
338 341
339 gfx::ScopedTextureBinder bind_restore(GL_TEXTURE_EXTERNAL_OES, 0); 342 gfx::ScopedTextureBinder bind_restore(GL_TEXTURE_EXTERNAL_OES, 0);
340 343
341 // It's safe to manipulate all the buffer state here, because the decoder 344 // It's safe to manipulate all the buffer state here, because the decoder
342 // thread is waiting on pictures_assigned_. 345 // thread is waiting on pictures_assigned_.
346
347 // Allocate the output buffers.
348 struct v4l2_requestbuffers reqbufs;
349 memset(&reqbufs, 0, sizeof(reqbufs));
350 reqbufs.count = buffers.size();
351 reqbufs.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
352 reqbufs.memory = V4L2_MEMORY_MMAP;
353 IOCTL_OR_ERROR_RETURN(VIDIOC_REQBUFS, &reqbufs);
354
355 if (reqbufs.count != buffers.size()) {
356 DLOG(ERROR) << "Could not allocate enough output buffers";
357 NOTIFY_ERROR(PLATFORM_FAILURE);
358 return;
359 }
360
361 output_buffer_map_.resize(buffers.size());
362
343 DCHECK(free_output_buffers_.empty()); 363 DCHECK(free_output_buffers_.empty());
344 for (size_t i = 0; i < output_buffer_map_.size(); ++i) { 364 for (size_t i = 0; i < output_buffer_map_.size(); ++i) {
345 DCHECK(buffers[i].size() == coded_size_); 365 DCHECK(buffers[i].size() == coded_size_);
346 366
347 OutputRecord& output_record = output_buffer_map_[i]; 367 OutputRecord& output_record = output_buffer_map_[i];
348 DCHECK(!output_record.at_device); 368 DCHECK(!output_record.at_device);
349 DCHECK(!output_record.at_client); 369 DCHECK(!output_record.at_client);
350 DCHECK_EQ(output_record.egl_image, EGL_NO_IMAGE_KHR); 370 DCHECK_EQ(output_record.egl_image, EGL_NO_IMAGE_KHR);
351 DCHECK_EQ(output_record.egl_sync, EGL_NO_SYNC_KHR); 371 DCHECK_EQ(output_record.egl_sync, EGL_NO_SYNC_KHR);
352 DCHECK_EQ(output_record.picture_id, -1); 372 DCHECK_EQ(output_record.picture_id, -1);
(...skipping 1501 matching lines...) Expand 10 before | Expand all | Expand 10 after
1854 1874
1855 // Number of output buffers we need. 1875 // Number of output buffers we need.
1856 struct v4l2_control ctrl; 1876 struct v4l2_control ctrl;
1857 memset(&ctrl, 0, sizeof(ctrl)); 1877 memset(&ctrl, 0, sizeof(ctrl));
1858 ctrl.id = V4L2_CID_MIN_BUFFERS_FOR_CAPTURE; 1878 ctrl.id = V4L2_CID_MIN_BUFFERS_FOR_CAPTURE;
1859 IOCTL_OR_ERROR_RETURN_FALSE(VIDIOC_G_CTRL, &ctrl); 1879 IOCTL_OR_ERROR_RETURN_FALSE(VIDIOC_G_CTRL, &ctrl);
1860 output_dpb_size_ = ctrl.value; 1880 output_dpb_size_ = ctrl.value;
1861 1881
1862 // Output format setup in Initialize(). 1882 // Output format setup in Initialize().
1863 1883
1864 // Allocate the output buffers. 1884 const uint32_t buffer_count = output_dpb_size_ + kDpbOutputBufferExtraCount;
1865 struct v4l2_requestbuffers reqbufs;
1866 memset(&reqbufs, 0, sizeof(reqbufs));
1867 reqbufs.count = output_dpb_size_ + kDpbOutputBufferExtraCount;
1868 reqbufs.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
1869 reqbufs.memory = V4L2_MEMORY_MMAP;
1870 IOCTL_OR_ERROR_RETURN_FALSE(VIDIOC_REQBUFS, &reqbufs);
1871
1872 output_buffer_map_.resize(reqbufs.count);
1873
1874 DVLOG(3) << "CreateOutputBuffers(): ProvidePictureBuffers(): " 1885 DVLOG(3) << "CreateOutputBuffers(): ProvidePictureBuffers(): "
1875 << "buffer_count=" << output_buffer_map_.size() 1886 << "buffer_count=" << buffer_count
1876 << ", coded_size=" << coded_size_.ToString(); 1887 << ", coded_size=" << coded_size_.ToString();
1877 child_task_runner_->PostTask( 1888 child_task_runner_->PostTask(
1878 FROM_HERE, base::Bind(&Client::ProvidePictureBuffers, client_, 1889 FROM_HERE, base::Bind(&Client::ProvidePictureBuffers, client_,
1879 output_buffer_map_.size(), coded_size_, 1890 buffer_count, coded_size_,
1880 device_->GetTextureTarget())); 1891 device_->GetTextureTarget()));
1881 1892
1882 // Wait for the client to call AssignPictureBuffers() on the Child thread. 1893 // Wait for the client to call AssignPictureBuffers() on the Child thread.
1883 // We do this, because if we continue decoding without finishing buffer 1894 // We do this, because if we continue decoding without finishing buffer
1884 // allocation, we may end up Resetting before AssignPictureBuffers arrives, 1895 // allocation, we may end up Resetting before AssignPictureBuffers arrives,
1885 // resulting in unnecessary complications and subtle bugs. 1896 // resulting in unnecessary complications and subtle bugs.
1886 // For example, if the client calls Decode(Input1), Reset(), Decode(Input2) 1897 // For example, if the client calls Decode(Input1), Reset(), Decode(Input2)
1887 // in a sequence, and Decode(Input1) results in us getting here and exiting 1898 // in a sequence, and Decode(Input1) results in us getting here and exiting
1888 // without waiting, we might end up running Reset{,Done}Task() before 1899 // without waiting, we might end up running Reset{,Done}Task() before
1889 // AssignPictureBuffers is scheduled, thus cleaning up and pushing buffers 1900 // AssignPictureBuffers is scheduled, thus cleaning up and pushing buffers
(...skipping 138 matching lines...) Expand 10 before | Expand all | Expand 10 after
2028 2039
2029 void V4L2VideoDecodeAccelerator::PictureCleared() { 2040 void V4L2VideoDecodeAccelerator::PictureCleared() {
2030 DVLOG(3) << "PictureCleared(). clearing count=" << picture_clearing_count_; 2041 DVLOG(3) << "PictureCleared(). clearing count=" << picture_clearing_count_;
2031 DCHECK_EQ(decoder_thread_.message_loop(), base::MessageLoop::current()); 2042 DCHECK_EQ(decoder_thread_.message_loop(), base::MessageLoop::current());
2032 DCHECK_GT(picture_clearing_count_, 0); 2043 DCHECK_GT(picture_clearing_count_, 0);
2033 picture_clearing_count_--; 2044 picture_clearing_count_--;
2034 SendPictureReady(); 2045 SendPictureReady();
2035 } 2046 }
2036 2047
2037 } // namespace content 2048 } // namespace content
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698