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

Side by Side Diff: media/filters/gpu_video_decoder.cc

Issue 1751323002: Allow multiple texture ids per picture buffer. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 8 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
« no previous file with comments | « media/filters/gpu_video_decoder.h ('k') | media/video/picture.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 "media/filters/gpu_video_decoder.h" 5 #include "media/filters/gpu_video_decoder.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <utility> 8 #include <utility>
9 9
10 #include "base/bind.h" 10 #include "base/bind.h"
(...skipping 249 matching lines...) Expand 10 before | Expand all | Expand 10 after
260 DVLOG_IF(2, !success) << __FUNCTION__ << ": CDM not attached."; 260 DVLOG_IF(2, !success) << __FUNCTION__ << ": CDM not attached.";
261 DCHECK(!init_cb_.is_null()); 261 DCHECK(!init_cb_.is_null());
262 262
263 base::ResetAndReturn(&init_cb_).Run(success); 263 base::ResetAndReturn(&init_cb_).Run(success);
264 } 264 }
265 265
266 void GpuVideoDecoder::DestroyPictureBuffers(PictureBufferMap* buffers) { 266 void GpuVideoDecoder::DestroyPictureBuffers(PictureBufferMap* buffers) {
267 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent(); 267 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent();
268 for (PictureBufferMap::iterator it = buffers->begin(); it != buffers->end(); 268 for (PictureBufferMap::iterator it = buffers->begin(); it != buffers->end();
269 ++it) { 269 ++it) {
270 factories_->DeleteTexture(it->second.texture_id()); 270 for (uint32_t id : it->second.texture_ids())
271 factories_->DeleteTexture(id);
271 } 272 }
272 273
273 buffers->clear(); 274 buffers->clear();
274 } 275 }
275 276
276 void GpuVideoDecoder::DestroyVDA() { 277 void GpuVideoDecoder::DestroyVDA() {
277 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent(); 278 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent();
278 279
279 vda_.reset(); 280 vda_.reset();
280 281
(...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after
400 (!needs_all_picture_buffers_to_decode_ && available_pictures_ > 0) || 401 (!needs_all_picture_buffers_to_decode_ && available_pictures_ > 0) ||
401 available_pictures_ == 402 available_pictures_ ==
402 static_cast<int>(assigned_picture_buffers_.size()); 403 static_cast<int>(assigned_picture_buffers_.size());
403 } 404 }
404 405
405 int GpuVideoDecoder::GetMaxDecodeRequests() const { 406 int GpuVideoDecoder::GetMaxDecodeRequests() const {
406 return kMaxInFlightDecodes; 407 return kMaxInFlightDecodes;
407 } 408 }
408 409
409 void GpuVideoDecoder::ProvidePictureBuffers(uint32_t count, 410 void GpuVideoDecoder::ProvidePictureBuffers(uint32_t count,
411 uint32_t textures_per_buffer,
410 const gfx::Size& size, 412 const gfx::Size& size,
411 uint32_t texture_target) { 413 uint32_t texture_target) {
412 DVLOG(3) << "ProvidePictureBuffers(" << count << ", " 414 DVLOG(3) << "ProvidePictureBuffers(" << count << ", "
413 << size.width() << "x" << size.height() << ")"; 415 << size.width() << "x" << size.height() << ")";
414 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent(); 416 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent();
415 417
416 std::vector<uint32_t> texture_ids; 418 std::vector<uint32_t> texture_ids;
417 std::vector<gpu::Mailbox> texture_mailboxes; 419 std::vector<gpu::Mailbox> texture_mailboxes;
418 decoder_texture_target_ = texture_target; 420 decoder_texture_target_ = texture_target;
419 if (!factories_->CreateTextures(count, 421 if (!factories_->CreateTextures(count * textures_per_buffer, size,
420 size, 422 &texture_ids, &texture_mailboxes,
421 &texture_ids,
422 &texture_mailboxes,
423 decoder_texture_target_)) { 423 decoder_texture_target_)) {
424 NotifyError(VideoDecodeAccelerator::PLATFORM_FAILURE); 424 NotifyError(VideoDecodeAccelerator::PLATFORM_FAILURE);
425 return; 425 return;
426 } 426 }
427 DCHECK_EQ(count, texture_ids.size()); 427 DCHECK_EQ(count * textures_per_buffer, texture_ids.size());
428 DCHECK_EQ(count, texture_mailboxes.size()); 428 DCHECK_EQ(count * textures_per_buffer, texture_mailboxes.size());
429 429
430 if (!vda_) 430 if (!vda_)
431 return; 431 return;
432 432
433 std::vector<PictureBuffer> picture_buffers; 433 std::vector<PictureBuffer> picture_buffers;
434 for (size_t i = 0; i < texture_ids.size(); ++i) { 434 size_t index = 0;
435 picture_buffers.push_back(PictureBuffer( 435 for (size_t i = 0; i < count; ++i) {
436 next_picture_buffer_id_++, size, texture_ids[i], texture_mailboxes[i])); 436 PictureBuffer::TextureIds ids;
437 std::vector<gpu::Mailbox> mailboxes;
438 for (size_t j = 0; j < textures_per_buffer; j++) {
439 ids.push_back(texture_ids[index]);
440 mailboxes.push_back(texture_mailboxes[index]);
441 index++;
442 }
443
444 picture_buffers.push_back(
445 PictureBuffer(next_picture_buffer_id_++, size, ids, mailboxes));
437 bool inserted = assigned_picture_buffers_.insert(std::make_pair( 446 bool inserted = assigned_picture_buffers_.insert(std::make_pair(
438 picture_buffers.back().id(), picture_buffers.back())).second; 447 picture_buffers.back().id(), picture_buffers.back())).second;
439 DCHECK(inserted); 448 DCHECK(inserted);
440 } 449 }
441 450
442 available_pictures_ += count; 451 available_pictures_ += count;
443 452
444 vda_->AssignPictureBuffers(picture_buffers); 453 vda_->AssignPictureBuffers(picture_buffers);
445 } 454 }
446 455
447 void GpuVideoDecoder::DismissPictureBuffer(int32_t id) { 456 void GpuVideoDecoder::DismissPictureBuffer(int32_t id) {
448 DVLOG(3) << "DismissPictureBuffer(" << id << ")"; 457 DVLOG(3) << "DismissPictureBuffer(" << id << ")";
449 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent(); 458 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent();
450 459
451 PictureBufferMap::iterator it = assigned_picture_buffers_.find(id); 460 PictureBufferMap::iterator it = assigned_picture_buffers_.find(id);
452 if (it == assigned_picture_buffers_.end()) { 461 if (it == assigned_picture_buffers_.end()) {
453 NOTREACHED() << "Missing picture buffer: " << id; 462 NOTREACHED() << "Missing picture buffer: " << id;
454 return; 463 return;
455 } 464 }
456 465
457 PictureBuffer buffer_to_dismiss = it->second; 466 PictureBuffer buffer_to_dismiss = it->second;
458 assigned_picture_buffers_.erase(it); 467 assigned_picture_buffers_.erase(it);
459 468
460 if (!picture_buffers_at_display_.count(id)) { 469 if (!picture_buffers_at_display_.count(id)) {
461 // We can delete the texture immediately as it's not being displayed. 470 // We can delete the texture immediately as it's not being displayed.
462 factories_->DeleteTexture(buffer_to_dismiss.texture_id()); 471 for (uint32_t id : buffer_to_dismiss.texture_ids())
472 factories_->DeleteTexture(id);
463 CHECK_GT(available_pictures_, 0); 473 CHECK_GT(available_pictures_, 0);
464 --available_pictures_; 474 --available_pictures_;
465 } 475 }
466 // Not destroying a texture in display in |picture_buffers_at_display_|. 476 // Not destroying a texture in display in |picture_buffers_at_display_|.
467 // Postpone deletion until after it's returned to us. 477 // Postpone deletion until after it's returned to us.
468 } 478 }
469 479
470 void GpuVideoDecoder::PictureReady(const media::Picture& picture) { 480 void GpuVideoDecoder::PictureReady(const media::Picture& picture) {
471 DVLOG(3) << "PictureReady()"; 481 DVLOG(3) << "PictureReady()";
472 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent(); 482 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent();
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
509 << " is larger than coded size " << pb.size().ToString(); 519 << " is larger than coded size " << pb.size().ToString();
510 visible_rect = gfx::Rect(pb.size()); 520 visible_rect = gfx::Rect(pb.size());
511 } 521 }
512 522
513 DCHECK(decoder_texture_target_); 523 DCHECK(decoder_texture_target_);
514 524
515 bool opaque = IsOpaque(config_.format()); 525 bool opaque = IsOpaque(config_.format());
516 526
517 scoped_refptr<VideoFrame> frame(VideoFrame::WrapNativeTexture( 527 scoped_refptr<VideoFrame> frame(VideoFrame::WrapNativeTexture(
518 opaque ? PIXEL_FORMAT_XRGB : PIXEL_FORMAT_ARGB, 528 opaque ? PIXEL_FORMAT_XRGB : PIXEL_FORMAT_ARGB,
519 gpu::MailboxHolder(pb.texture_mailbox(), gpu::SyncToken(), 529 gpu::MailboxHolder(pb.texture_mailbox(0), gpu::SyncToken(),
520 decoder_texture_target_), 530 decoder_texture_target_),
521 BindToCurrentLoop(base::Bind( 531 BindToCurrentLoop(base::Bind(
522 &GpuVideoDecoder::ReleaseMailbox, weak_factory_.GetWeakPtr(), 532 &GpuVideoDecoder::ReleaseMailbox, weak_factory_.GetWeakPtr(),
523 factories_, picture.picture_buffer_id(), pb.texture_id())), 533 factories_, picture.picture_buffer_id(), pb.texture_ids())),
524 pb.size(), visible_rect, natural_size, timestamp)); 534 pb.size(), visible_rect, natural_size, timestamp));
525 if (!frame) { 535 if (!frame) {
526 DLOG(ERROR) << "Create frame failed for: " << picture.picture_buffer_id(); 536 DLOG(ERROR) << "Create frame failed for: " << picture.picture_buffer_id();
527 NotifyError(VideoDecodeAccelerator::PLATFORM_FAILURE); 537 NotifyError(VideoDecodeAccelerator::PLATFORM_FAILURE);
528 return; 538 return;
529 } 539 }
530 if (picture.allow_overlay()) 540 if (picture.allow_overlay())
531 frame->metadata()->SetBoolean(VideoFrameMetadata::ALLOW_OVERLAY, true); 541 frame->metadata()->SetBoolean(VideoFrameMetadata::ALLOW_OVERLAY, true);
532 CHECK_GT(available_pictures_, 0); 542 CHECK_GT(available_pictures_, 0);
533 --available_pictures_; 543 --available_pictures_;
544
534 bool inserted = 545 bool inserted =
535 picture_buffers_at_display_.insert(std::make_pair( 546 picture_buffers_at_display_
536 picture.picture_buffer_id(), 547 .insert(std::make_pair(picture.picture_buffer_id(), pb.texture_ids()))
537 pb.texture_id())).second; 548 .second;
538 DCHECK(inserted); 549 DCHECK(inserted);
539 550
540 DeliverFrame(frame); 551 DeliverFrame(frame);
541 } 552 }
542 553
543 void GpuVideoDecoder::DeliverFrame( 554 void GpuVideoDecoder::DeliverFrame(
544 const scoped_refptr<VideoFrame>& frame) { 555 const scoped_refptr<VideoFrame>& frame) {
545 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent(); 556 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent();
546 557
547 // During a pending vda->Reset(), we don't accumulate frames. Drop it on the 558 // During a pending vda->Reset(), we don't accumulate frames. Drop it on the
548 // floor and return. 559 // floor and return.
549 if (!pending_reset_cb_.is_null()) 560 if (!pending_reset_cb_.is_null())
550 return; 561 return;
551 562
552 output_cb_.Run(frame); 563 output_cb_.Run(frame);
553 } 564 }
554 565
555 // static 566 // static
556 void GpuVideoDecoder::ReleaseMailbox( 567 void GpuVideoDecoder::ReleaseMailbox(
557 base::WeakPtr<GpuVideoDecoder> decoder, 568 base::WeakPtr<GpuVideoDecoder> decoder,
558 media::GpuVideoAcceleratorFactories* factories, 569 media::GpuVideoAcceleratorFactories* factories,
559 int64_t picture_buffer_id, 570 int64_t picture_buffer_id,
560 uint32_t texture_id, 571 PictureBuffer::TextureIds ids,
561 const gpu::SyncToken& release_sync_token) { 572 const gpu::SyncToken& release_sync_token) {
562 DCHECK(factories->GetTaskRunner()->BelongsToCurrentThread()); 573 DCHECK(factories->GetTaskRunner()->BelongsToCurrentThread());
563 factories->WaitSyncToken(release_sync_token); 574 factories->WaitSyncToken(release_sync_token);
564 575
565 if (decoder) { 576 if (decoder) {
566 decoder->ReusePictureBuffer(picture_buffer_id); 577 decoder->ReusePictureBuffer(picture_buffer_id);
567 return; 578 return;
568 } 579 }
569 // It's the last chance to delete the texture after display, 580 // It's the last chance to delete the texture after display,
570 // because GpuVideoDecoder was destructed. 581 // because GpuVideoDecoder was destructed.
571 factories->DeleteTexture(texture_id); 582 for (uint32_t id : ids)
583 factories->DeleteTexture(id);
572 } 584 }
573 585
574 void GpuVideoDecoder::ReusePictureBuffer(int64_t picture_buffer_id) { 586 void GpuVideoDecoder::ReusePictureBuffer(int64_t picture_buffer_id) {
575 DVLOG(3) << "ReusePictureBuffer(" << picture_buffer_id << ")"; 587 DVLOG(3) << "ReusePictureBuffer(" << picture_buffer_id << ")";
576 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent(); 588 DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent();
577 589
578 DCHECK(!picture_buffers_at_display_.empty()); 590 DCHECK(!picture_buffers_at_display_.empty());
579 PictureBufferTextureMap::iterator display_iterator = 591 PictureBufferTextureMap::iterator display_iterator =
580 picture_buffers_at_display_.find(picture_buffer_id); 592 picture_buffers_at_display_.find(picture_buffer_id);
581 uint32_t texture_id = display_iterator->second; 593 PictureBuffer::TextureIds ids = display_iterator->second;
582 DCHECK(display_iterator != picture_buffers_at_display_.end()); 594 DCHECK(display_iterator != picture_buffers_at_display_.end());
583 picture_buffers_at_display_.erase(display_iterator); 595 picture_buffers_at_display_.erase(display_iterator);
584 596
585 if (!assigned_picture_buffers_.count(picture_buffer_id)) { 597 if (!assigned_picture_buffers_.count(picture_buffer_id)) {
586 // This picture was dismissed while in display, so we postponed deletion. 598 // This picture was dismissed while in display, so we postponed deletion.
587 factories_->DeleteTexture(texture_id); 599 for (uint32_t id : ids)
600 factories_->DeleteTexture(id);
588 return; 601 return;
589 } 602 }
590 603
591 ++available_pictures_; 604 ++available_pictures_;
592 605
593 // DestroyVDA() might already have been called. 606 // DestroyVDA() might already have been called.
594 if (vda_) 607 if (vda_)
595 vda_->ReusePictureBuffer(picture_buffer_id); 608 vda_->ReusePictureBuffer(picture_buffer_id);
596 } 609 }
597 610
(...skipping 130 matching lines...) Expand 10 before | Expand all | Expand 10 after
728 } 741 }
729 return false; 742 return false;
730 } 743 }
731 744
732 void GpuVideoDecoder::DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent() 745 void GpuVideoDecoder::DCheckGpuVideoAcceleratorFactoriesTaskRunnerIsCurrent()
733 const { 746 const {
734 DCHECK(factories_->GetTaskRunner()->BelongsToCurrentThread()); 747 DCHECK(factories_->GetTaskRunner()->BelongsToCurrentThread());
735 } 748 }
736 749
737 } // namespace media 750 } // namespace media
OLDNEW
« no previous file with comments | « media/filters/gpu_video_decoder.h ('k') | media/video/picture.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698