Chromium Code Reviews| OLD | NEW |
|---|---|
| 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 "base/bind.h" | 7 #include "base/bind.h" |
| 8 #include "base/callback_helpers.h" | 8 #include "base/callback_helpers.h" |
| 9 #include "base/cpu.h" | 9 #include "base/cpu.h" |
| 10 #include "base/message_loop.h" | 10 #include "base/message_loop.h" |
| (...skipping 477 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 488 void GpuVideoDecoder::NotifyInitializeDone() { | 488 void GpuVideoDecoder::NotifyInitializeDone() { |
| 489 NOTREACHED() << "GpuVideoDecodeAcceleratorHost::Initialize is synchronous!"; | 489 NOTREACHED() << "GpuVideoDecodeAcceleratorHost::Initialize is synchronous!"; |
| 490 } | 490 } |
| 491 | 491 |
| 492 void GpuVideoDecoder::ProvidePictureBuffers(uint32 count, | 492 void GpuVideoDecoder::ProvidePictureBuffers(uint32 count, |
| 493 const gfx::Size& size, | 493 const gfx::Size& size, |
| 494 uint32 texture_target) { | 494 uint32 texture_target) { |
| 495 DCHECK(gvd_loop_proxy_->BelongsToCurrentThread()); | 495 DCHECK(gvd_loop_proxy_->BelongsToCurrentThread()); |
| 496 | 496 |
| 497 std::vector<uint32> texture_ids; | 497 std::vector<uint32> texture_ids; |
| 498 std::vector<gpu::Mailbox> texture_mailboxes; | |
| 498 decoder_texture_target_ = texture_target; | 499 decoder_texture_target_ = texture_target; |
| 499 if (!factories_->CreateTextures( | 500 // Discards the sync point returned here since PictureReady will imply that |
| 500 count, size, &texture_ids, decoder_texture_target_)) { | 501 // the produce has already happened, and the texture is ready for use. |
| 502 if (!factories_->CreateTextures(count, | |
| 503 size, | |
| 504 &texture_ids, | |
| 505 &texture_mailboxes, | |
| 506 decoder_texture_target_)) { | |
| 501 NotifyError(VideoDecodeAccelerator::PLATFORM_FAILURE); | 507 NotifyError(VideoDecodeAccelerator::PLATFORM_FAILURE); |
| 502 return; | 508 return; |
| 503 } | 509 } |
| 504 DCHECK_EQ(count, texture_ids.size()); | 510 DCHECK_EQ(count, texture_ids.size()); |
| 511 DCHECK_EQ(count, texture_mailboxes.size()); | |
| 505 | 512 |
| 506 if (!vda_) | 513 if (!vda_) |
| 507 return; | 514 return; |
| 508 | 515 |
| 509 std::vector<PictureBuffer> picture_buffers; | 516 std::vector<PictureBuffer> picture_buffers; |
| 510 for (size_t i = 0; i < texture_ids.size(); ++i) { | 517 for (size_t i = 0; i < texture_ids.size(); ++i) { |
| 511 picture_buffers.push_back(PictureBuffer( | 518 picture_buffers.push_back(PictureBuffer( |
| 512 next_picture_buffer_id_++, size, texture_ids[i])); | 519 next_picture_buffer_id_++, size, texture_ids[i], texture_mailboxes[i])); |
| 513 bool inserted = assigned_picture_buffers_.insert(std::make_pair( | 520 bool inserted = assigned_picture_buffers_.insert(std::make_pair( |
| 514 picture_buffers.back().id(), picture_buffers.back())).second; | 521 picture_buffers.back().id(), picture_buffers.back())).second; |
| 515 DCHECK(inserted); | 522 DCHECK(inserted); |
| 516 } | 523 } |
| 517 | 524 |
| 518 available_pictures_ += count; | 525 available_pictures_ += count; |
| 519 | 526 |
| 520 vda_loop_proxy_->PostTask(FROM_HERE, base::Bind( | 527 vda_loop_proxy_->PostTask(FROM_HERE, base::Bind( |
| 521 &VideoDecodeAccelerator::AssignPictureBuffers, weak_vda_, | 528 &VideoDecodeAccelerator::AssignPictureBuffers, weak_vda_, |
| 522 picture_buffers)); | 529 picture_buffers)); |
| (...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 563 } | 570 } |
| 564 const PictureBuffer& pb = it->second; | 571 const PictureBuffer& pb = it->second; |
| 565 | 572 |
| 566 // Update frame's timestamp. | 573 // Update frame's timestamp. |
| 567 base::TimeDelta timestamp; | 574 base::TimeDelta timestamp; |
| 568 gfx::Rect visible_rect; | 575 gfx::Rect visible_rect; |
| 569 gfx::Size natural_size; | 576 gfx::Size natural_size; |
| 570 GetBufferData(picture.bitstream_buffer_id(), ×tamp, &visible_rect, | 577 GetBufferData(picture.bitstream_buffer_id(), ×tamp, &visible_rect, |
| 571 &natural_size); | 578 &natural_size); |
| 572 DCHECK(decoder_texture_target_); | 579 DCHECK(decoder_texture_target_); |
| 580 | |
| 573 scoped_refptr<VideoFrame> frame( | 581 scoped_refptr<VideoFrame> frame( |
| 574 VideoFrame::WrapNativeTexture( | 582 VideoFrame::WrapNativeTexture( |
| 575 pb.texture_id(), decoder_texture_target_, pb.size(), visible_rect, | 583 pb.texture_mailbox(), 0, |
| 584 decoder_texture_target_, | |
| 585 pb.size(), visible_rect, | |
| 576 natural_size, timestamp, | 586 natural_size, timestamp, |
| 577 base::Bind(&Factories::ReadPixels, factories_, pb.texture_id(), | 587 base::Bind(&Factories::ReadPixels, factories_, pb.texture_id(), |
| 578 decoder_texture_target_, | 588 decoder_texture_target_, |
| 579 gfx::Size(visible_rect.width(), visible_rect.height())), | 589 gfx::Size(visible_rect.width(), visible_rect.height())), |
| 580 BindToCurrentLoop(base::Bind( | 590 BindToCurrentLoop(base::Bind( |
| 581 &GpuVideoDecoder::ReusePictureBuffer, weak_this_, | 591 &GpuVideoDecoder::ReusePictureBuffer, weak_this_, |
| 582 picture.picture_buffer_id())))); | 592 picture.picture_buffer_id())), |
| 593 base::Closure())); | |
| 583 CHECK_GT(available_pictures_, 0); | 594 CHECK_GT(available_pictures_, 0); |
| 584 --available_pictures_; | 595 --available_pictures_; |
| 585 bool inserted = | 596 bool inserted = |
| 586 picture_buffers_at_display_.insert(picture.picture_buffer_id()).second; | 597 picture_buffers_at_display_.insert(picture.picture_buffer_id()).second; |
| 587 DCHECK(inserted); | 598 DCHECK(inserted); |
| 588 | 599 |
| 589 EnqueueFrameAndTriggerFrameDelivery(frame); | 600 EnqueueFrameAndTriggerFrameDelivery(frame); |
| 590 } | 601 } |
| 591 | 602 |
| 592 void GpuVideoDecoder::EnqueueFrameAndTriggerFrameDelivery( | 603 void GpuVideoDecoder::EnqueueFrameAndTriggerFrameDelivery( |
| (...skipping 10 matching lines...) Expand all Loading... | |
| 603 else | 614 else |
| 604 DCHECK(!ready_video_frames_.empty()); | 615 DCHECK(!ready_video_frames_.empty()); |
| 605 | 616 |
| 606 if (pending_read_cb_.is_null()) | 617 if (pending_read_cb_.is_null()) |
| 607 return; | 618 return; |
| 608 | 619 |
| 609 base::ResetAndReturn(&pending_read_cb_).Run(kOk, ready_video_frames_.front()); | 620 base::ResetAndReturn(&pending_read_cb_).Run(kOk, ready_video_frames_.front()); |
| 610 ready_video_frames_.pop_front(); | 621 ready_video_frames_.pop_front(); |
| 611 } | 622 } |
| 612 | 623 |
| 613 void GpuVideoDecoder::ReusePictureBuffer(int64 picture_buffer_id) { | 624 void GpuVideoDecoder::ReusePictureBuffer(int64 picture_buffer_id, |
| 625 uint32 sync_point) { | |
| 614 DCHECK(gvd_loop_proxy_->BelongsToCurrentThread()); | 626 DCHECK(gvd_loop_proxy_->BelongsToCurrentThread()); |
| 615 | 627 |
| 616 if (!vda_) | 628 if (!vda_) |
| 617 return; | 629 return; |
| 618 | 630 |
| 619 CHECK(!picture_buffers_at_display_.empty()); | 631 CHECK(!picture_buffers_at_display_.empty()); |
| 620 | 632 |
| 621 size_t num_erased = picture_buffers_at_display_.erase(picture_buffer_id); | 633 size_t num_erased = picture_buffers_at_display_.erase(picture_buffer_id); |
| 622 DCHECK(num_erased); | 634 DCHECK(num_erased); |
| 623 | 635 |
| 624 std::map<int32, PictureBuffer>::iterator it = | 636 std::map<int32, PictureBuffer>::iterator it = |
| 625 assigned_picture_buffers_.find(picture_buffer_id); | 637 assigned_picture_buffers_.find(picture_buffer_id); |
| 626 | 638 |
| 627 if (it == assigned_picture_buffers_.end()) { | 639 if (it == assigned_picture_buffers_.end()) { |
| 628 // This picture was dismissed while in display, so we postponed deletion. | 640 // This picture was dismissed while in display, so we postponed deletion. |
| 629 it = dismissed_picture_buffers_.find(picture_buffer_id); | 641 it = dismissed_picture_buffers_.find(picture_buffer_id); |
| 630 DCHECK(it != dismissed_picture_buffers_.end()); | 642 DCHECK(it != dismissed_picture_buffers_.end()); |
| 631 factories_->DeleteTexture(it->second.texture_id()); | 643 factories_->DeleteTexture(it->second.texture_id()); |
| 632 dismissed_picture_buffers_.erase(it); | 644 dismissed_picture_buffers_.erase(it); |
| 633 return; | 645 return; |
| 634 } | 646 } |
| 635 | 647 |
| 648 factories_->WaitSyncPoint(sync_point); | |
| 649 | |
| 636 ++available_pictures_; | 650 ++available_pictures_; |
| 637 | 651 |
| 652 | |
|
scherkus (not reviewing)
2013/06/17 20:20:37
remove extra blank line
danakj
2013/06/18 00:45:05
oops yep
danakj
2013/06/18 16:54:12
Done.
| |
| 638 vda_loop_proxy_->PostTask(FROM_HERE, base::Bind( | 653 vda_loop_proxy_->PostTask(FROM_HERE, base::Bind( |
| 639 &VideoDecodeAccelerator::ReusePictureBuffer, weak_vda_, | 654 &VideoDecodeAccelerator::ReusePictureBuffer, weak_vda_, |
| 640 picture_buffer_id)); | 655 picture_buffer_id)); |
| 641 } | 656 } |
| 642 | 657 |
| 643 GpuVideoDecoder::SHMBuffer* GpuVideoDecoder::GetSHM(size_t min_size) { | 658 GpuVideoDecoder::SHMBuffer* GpuVideoDecoder::GetSHM(size_t min_size) { |
| 644 DCHECK(gvd_loop_proxy_->BelongsToCurrentThread()); | 659 DCHECK(gvd_loop_proxy_->BelongsToCurrentThread()); |
| 645 if (available_shm_segments_.empty() || | 660 if (available_shm_segments_.empty() || |
| 646 available_shm_segments_.back()->size < min_size) { | 661 available_shm_segments_.back()->size < min_size) { |
| 647 size_t size_to_allocate = std::max(min_size, kSharedMemorySegmentBytes); | 662 size_t size_to_allocate = std::max(min_size, kSharedMemorySegmentBytes); |
| (...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 752 | 767 |
| 753 state_ = kError; | 768 state_ = kError; |
| 754 | 769 |
| 755 if (!pending_read_cb_.is_null()) { | 770 if (!pending_read_cb_.is_null()) { |
| 756 base::ResetAndReturn(&pending_read_cb_).Run(kDecodeError, NULL); | 771 base::ResetAndReturn(&pending_read_cb_).Run(kDecodeError, NULL); |
| 757 return; | 772 return; |
| 758 } | 773 } |
| 759 } | 774 } |
| 760 | 775 |
| 761 } // namespace media | 776 } // namespace media |
| OLD | NEW |