Index: components/display_compositor/buffer_queue.cc |
diff --git a/components/display_compositor/buffer_queue.cc b/components/display_compositor/buffer_queue.cc |
deleted file mode 100644 |
index 092ae46771c741ca355acb861fdbc23f57c07db9..0000000000000000000000000000000000000000 |
--- a/components/display_compositor/buffer_queue.cc |
+++ /dev/null |
@@ -1,303 +0,0 @@ |
-// Copyright 2014 The Chromium Authors. All rights reserved. |
-// Use of this source code is governed by a BSD-style license that can be |
-// found in the LICENSE file. |
- |
-#include "components/display_compositor/buffer_queue.h" |
- |
-#include "base/containers/adapters.h" |
-#include "base/memory/ptr_util.h" |
-#include "build/build_config.h" |
-#include "components/display_compositor/gl_helper.h" |
-#include "gpu/GLES2/gl2extchromium.h" |
-#include "gpu/command_buffer/client/gles2_interface.h" |
-#include "gpu/command_buffer/client/gpu_memory_buffer_manager.h" |
-#include "gpu/command_buffer/common/gpu_memory_buffer_support.h" |
-#include "third_party/skia/include/core/SkRect.h" |
-#include "third_party/skia/include/core/SkRegion.h" |
-#include "ui/display/types/display_snapshot.h" |
-#include "ui/gfx/gpu_memory_buffer.h" |
-#include "ui/gfx/skia_util.h" |
- |
-namespace display_compositor { |
- |
-BufferQueue::BufferQueue(gpu::gles2::GLES2Interface* gl, |
- uint32_t texture_target, |
- uint32_t internal_format, |
- gfx::BufferFormat format, |
- GLHelper* gl_helper, |
- gpu::GpuMemoryBufferManager* gpu_memory_buffer_manager, |
- gpu::SurfaceHandle surface_handle) |
- : gl_(gl), |
- fbo_(0), |
- allocated_count_(0), |
- texture_target_(texture_target), |
- internal_format_(internal_format), |
- format_(format), |
- gl_helper_(gl_helper), |
- gpu_memory_buffer_manager_(gpu_memory_buffer_manager), |
- surface_handle_(surface_handle) { |
- DCHECK(gpu::IsImageFormatCompatibleWithGpuMemoryBufferFormat(internal_format, |
- format_)); |
-} |
- |
-BufferQueue::~BufferQueue() { |
- FreeAllSurfaces(); |
- |
- if (fbo_) |
- gl_->DeleteFramebuffers(1, &fbo_); |
-} |
- |
-void BufferQueue::Initialize() { |
- gl_->GenFramebuffers(1, &fbo_); |
-} |
- |
-void BufferQueue::BindFramebuffer() { |
- gl_->BindFramebuffer(GL_FRAMEBUFFER, fbo_); |
- |
- if (!current_surface_) |
- current_surface_ = GetNextSurface(); |
- |
- if (current_surface_) { |
- gl_->FramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, |
- texture_target_, current_surface_->texture, 0); |
- if (current_surface_->stencil) { |
- gl_->FramebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, |
- GL_RENDERBUFFER, current_surface_->stencil); |
- } |
- } |
-} |
- |
-void BufferQueue::CopyBufferDamage(int texture, |
- int source_texture, |
- const gfx::Rect& new_damage, |
- const gfx::Rect& old_damage) { |
- gl_helper_->CopySubBufferDamage(texture_target_, texture, source_texture, |
- SkRegion(gfx::RectToSkIRect(new_damage)), |
- SkRegion(gfx::RectToSkIRect(old_damage))); |
-} |
- |
-void BufferQueue::UpdateBufferDamage(const gfx::Rect& damage) { |
- if (displayed_surface_) |
- displayed_surface_->damage.Union(damage); |
- for (auto& surface : available_surfaces_) |
- surface->damage.Union(damage); |
- for (auto& surface : in_flight_surfaces_) { |
- if (surface) |
- surface->damage.Union(damage); |
- } |
-} |
- |
-void BufferQueue::SwapBuffers(const gfx::Rect& damage) { |
- if (current_surface_) { |
- if (damage != gfx::Rect(size_)) { |
- // Copy damage from the most recently swapped buffer. In the event that |
- // the buffer was destroyed and failed to recreate, pick from the most |
- // recently available buffer. |
- uint32_t texture_id = 0; |
- for (auto& surface : base::Reversed(in_flight_surfaces_)) { |
- if (surface) { |
- texture_id = surface->texture; |
- break; |
- } |
- } |
- if (!texture_id && displayed_surface_) |
- texture_id = displayed_surface_->texture; |
- |
- if (texture_id) { |
- CopyBufferDamage(current_surface_->texture, texture_id, damage, |
- current_surface_->damage); |
- } |
- } |
- current_surface_->damage = gfx::Rect(); |
- } |
- UpdateBufferDamage(damage); |
- in_flight_surfaces_.push_back(std::move(current_surface_)); |
- // Some things reset the framebuffer (CopySubBufferDamage, some GLRenderer |
- // paths), so ensure we restore it here. |
- gl_->BindFramebuffer(GL_FRAMEBUFFER, fbo_); |
-} |
- |
-void BufferQueue::Reshape(const gfx::Size& size, |
- float scale_factor, |
- const gfx::ColorSpace& color_space, |
- bool use_stencil) { |
- if (size == size_ && color_space == color_space_ && |
- use_stencil == use_stencil_) |
- return; |
-#if !defined(OS_MACOSX) |
- // TODO(ccameron): This assert is being hit on Mac try jobs. Determine if that |
- // is cause for concern or if it is benign. |
- // http://crbug.com/524624 |
- DCHECK(!current_surface_); |
-#endif |
- size_ = size; |
- color_space_ = color_space; |
- use_stencil_ = use_stencil; |
- |
- gl_->BindFramebuffer(GL_FRAMEBUFFER, fbo_); |
- gl_->FramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, |
- texture_target_, 0, 0); |
- gl_->FramebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, |
- GL_RENDERBUFFER, 0); |
- |
- FreeAllSurfaces(); |
-} |
- |
-void BufferQueue::RecreateBuffers() { |
- // We need to recreate the buffers, for whatever reason the old ones are not |
- // presentable on the device anymore. |
- // Unused buffers can be freed directly, they will be re-allocated as needed. |
- // Any in flight, current or displayed surface must be replaced. |
- available_surfaces_.clear(); |
- |
- // Recreate all in-flight surfaces and put the recreated copies in the queue. |
- for (auto& surface : in_flight_surfaces_) |
- surface = RecreateBuffer(std::move(surface)); |
- |
- current_surface_ = RecreateBuffer(std::move(current_surface_)); |
- displayed_surface_ = RecreateBuffer(std::move(displayed_surface_)); |
- |
- if (current_surface_) { |
- // If we have a texture bound, we will need to re-bind it. |
- gl_->BindFramebuffer(GL_FRAMEBUFFER, fbo_); |
- gl_->FramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, |
- texture_target_, current_surface_->texture, 0); |
- } |
-} |
- |
-std::unique_ptr<BufferQueue::AllocatedSurface> BufferQueue::RecreateBuffer( |
- std::unique_ptr<AllocatedSurface> surface) { |
- if (!surface) |
- return nullptr; |
- |
- std::unique_ptr<AllocatedSurface> new_surface(GetNextSurface()); |
- if (!new_surface) |
- return nullptr; |
- |
- new_surface->damage = surface->damage; |
- |
- // Copy the entire texture. |
- CopyBufferDamage(new_surface->texture, surface->texture, gfx::Rect(), |
- gfx::Rect(size_)); |
- return new_surface; |
-} |
- |
-void BufferQueue::PageFlipComplete() { |
- // Early out when no surface is in-flight. This can happen when using |
- // overlays and page flipping without changing the primary plane. |
- if (in_flight_surfaces_.empty()) |
- return; |
- if (displayed_surface_) |
- available_surfaces_.push_back(std::move(displayed_surface_)); |
- displayed_surface_ = std::move(in_flight_surfaces_.front()); |
- in_flight_surfaces_.pop_front(); |
-} |
- |
-uint32_t BufferQueue::GetCurrentTextureId() const { |
- // Return current surface texture if bound. |
- if (current_surface_) |
- return current_surface_->texture; |
- |
- // Return in-flight or displayed surface texture if no surface is |
- // currently bound. This can happen when using overlays and surface |
- // damage is empty. Note: |in_flight_surfaces_| entries can be null |
- // as a result of calling FreeAllSurfaces(). |
- if (!in_flight_surfaces_.empty() && in_flight_surfaces_.back()) |
- return in_flight_surfaces_.back()->texture; |
- if (displayed_surface_) |
- return displayed_surface_->texture; |
- |
- return 0; |
-} |
- |
-void BufferQueue::FreeAllSurfaces() { |
- displayed_surface_.reset(); |
- current_surface_.reset(); |
- // This is intentionally not emptied since the swap buffers acks are still |
- // expected to arrive. |
- for (auto& surface : in_flight_surfaces_) |
- surface = nullptr; |
- available_surfaces_.clear(); |
-} |
- |
-void BufferQueue::FreeSurfaceResources(AllocatedSurface* surface) { |
- if (!surface->texture) |
- return; |
- |
- gl_->BindTexture(texture_target_, surface->texture); |
- gl_->ReleaseTexImage2DCHROMIUM(texture_target_, surface->image); |
- gl_->DeleteTextures(1, &surface->texture); |
- gl_->DestroyImageCHROMIUM(surface->image); |
- if (surface->stencil) |
- gl_->DeleteRenderbuffers(1, &surface->stencil); |
- surface->buffer.reset(); |
- allocated_count_--; |
-} |
- |
-std::unique_ptr<BufferQueue::AllocatedSurface> BufferQueue::GetNextSurface() { |
- if (!available_surfaces_.empty()) { |
- std::unique_ptr<AllocatedSurface> surface = |
- std::move(available_surfaces_.back()); |
- available_surfaces_.pop_back(); |
- return surface; |
- } |
- |
- GLuint texture; |
- gl_->GenTextures(1, &texture); |
- |
- GLuint stencil = 0; |
- if (use_stencil_) { |
- gl_->GenRenderbuffers(1, &stencil); |
- gl_->BindRenderbuffer(GL_RENDERBUFFER, stencil); |
- gl_->RenderbufferStorage(GL_RENDERBUFFER, GL_STENCIL_INDEX8, size_.width(), |
- size_.height()); |
- gl_->BindRenderbuffer(GL_RENDERBUFFER, 0); |
- } |
- |
- // We don't want to allow anything more than triple buffering. |
- DCHECK_LT(allocated_count_, 4U); |
- std::unique_ptr<gfx::GpuMemoryBuffer> buffer( |
- gpu_memory_buffer_manager_->CreateGpuMemoryBuffer( |
- size_, format_, gfx::BufferUsage::SCANOUT, surface_handle_)); |
- if (!buffer.get()) { |
- gl_->DeleteTextures(1, &texture); |
- DLOG(ERROR) << "Failed to allocate GPU memory buffer"; |
- return nullptr; |
- } |
- buffer->SetColorSpaceForScanout(color_space_); |
- |
- uint32_t id = |
- gl_->CreateImageCHROMIUM(buffer->AsClientBuffer(), size_.width(), |
- size_.height(), internal_format_); |
- if (!id) { |
- LOG(ERROR) << "Failed to allocate backing image surface"; |
- gl_->DeleteTextures(1, &texture); |
- return nullptr; |
- } |
- |
- allocated_count_++; |
- gl_->BindTexture(texture_target_, texture); |
- gl_->BindTexImage2DCHROMIUM(texture_target_, id); |
- return base::MakeUnique<AllocatedSurface>(this, std::move(buffer), texture, |
- id, stencil, gfx::Rect(size_)); |
-} |
- |
-BufferQueue::AllocatedSurface::AllocatedSurface( |
- BufferQueue* buffer_queue, |
- std::unique_ptr<gfx::GpuMemoryBuffer> buffer, |
- uint32_t texture, |
- uint32_t image, |
- uint32_t stencil, |
- const gfx::Rect& rect) |
- : buffer_queue(buffer_queue), |
- buffer(buffer.release()), |
- texture(texture), |
- image(image), |
- stencil(stencil), |
- damage(rect) {} |
- |
-BufferQueue::AllocatedSurface::~AllocatedSurface() { |
- buffer_queue->FreeSurfaceResources(this); |
-} |
- |
-} // namespace display_compositor |