renderbuffer_manager.cc revision 5821806d5e7f356e8fa4b058a389a808ea183019
15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "gpu/command_buffer/service/renderbuffer_manager.h"
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/logging.h"
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/debug/trace_event.h"
85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/stringprintf.h"
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "gpu/command_buffer/common/gles2_cmd_utils.h"
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "gpu/command_buffer/service/gles2_cmd_decoder.h"
115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "gpu/command_buffer/service/memory_tracking.h"
125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace gpu {
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace gles2 {
155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)RenderbufferManager::RenderbufferManager(
175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    MemoryTracker* memory_tracker,
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    GLint max_renderbuffer_size,
195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    GLint max_samples)
205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : renderbuffer_memory_tracker_(new MemoryTypeTracker(memory_tracker)),
215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      max_renderbuffer_size_(max_renderbuffer_size),
225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      max_samples_(max_samples),
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      num_uncleared_renderbuffers_(0),
245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      mem_represented_(0),
255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      renderbuffer_info_count_(0),
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      have_context_(true) {
275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  UpdateMemRepresented();
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)RenderbufferManager::~RenderbufferManager() {
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK(renderbuffer_infos_.empty());
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // If this triggers, that means something is keeping a reference to
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // a RenderbufferInfo belonging to this.
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  CHECK_EQ(renderbuffer_info_count_, 0u);
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK_EQ(0, num_uncleared_renderbuffers_);
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)size_t RenderbufferManager::RenderbufferInfo::EstimatedSize() {
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return width_ * height_ * samples_ *
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         GLES2Util::RenderbufferBytesPerPixel(internal_format_);
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void RenderbufferManager::RenderbufferInfo::AddToSignature(
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    std::string* signature) const {
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK(signature);
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *signature += base::StringPrintf(
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      "|Renderbuffer|internal_format=%04x|samples=%d|width=%d|height=%d",
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      internal_format_, samples_, width_, height_);
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)RenderbufferManager::RenderbufferInfo::~RenderbufferInfo() {
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (manager_) {
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (manager_->have_context_) {
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      GLuint id = service_id();
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      glDeleteRenderbuffersEXT(1, &id);
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    manager_->StopTracking(this);
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    manager_ = NULL;
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void RenderbufferManager::UpdateMemRepresented() {
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  renderbuffer_memory_tracker_->UpdateMemRepresented(mem_represented_);
665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void RenderbufferManager::Destroy(bool have_context) {
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  have_context_ = have_context;
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  renderbuffer_infos_.clear();
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK_EQ(0u, mem_represented_);
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  UpdateMemRepresented();
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void RenderbufferManager::StartTracking(RenderbufferInfo* /* renderbuffer */) {
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ++renderbuffer_info_count_;
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void RenderbufferManager::StopTracking(RenderbufferInfo* renderbuffer) {
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  --renderbuffer_info_count_;
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!renderbuffer->cleared()) {
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    --num_uncleared_renderbuffers_;
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mem_represented_ -= renderbuffer->EstimatedSize();
855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void RenderbufferManager::SetInfo(
885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RenderbufferInfo* renderbuffer,
895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    GLsizei samples, GLenum internalformat, GLsizei width, GLsizei height) {
905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK(renderbuffer);
915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!renderbuffer->cleared()) {
925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    --num_uncleared_renderbuffers_;
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mem_represented_ -= renderbuffer->EstimatedSize();
955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  renderbuffer->SetInfo(samples, internalformat, width, height);
965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mem_represented_ += renderbuffer->EstimatedSize();
975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  UpdateMemRepresented();
985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!renderbuffer->cleared()) {
995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ++num_uncleared_renderbuffers_;
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void RenderbufferManager::SetCleared(RenderbufferInfo* renderbuffer) {
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK(renderbuffer);
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!renderbuffer->cleared()) {
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    --num_uncleared_renderbuffers_;
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  renderbuffer->set_cleared();
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!renderbuffer->cleared()) {
1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ++num_uncleared_renderbuffers_;
1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void RenderbufferManager::CreateRenderbufferInfo(
1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    GLuint client_id, GLuint service_id) {
1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderbufferInfo::Ref info(new RenderbufferInfo(this, service_id));
1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::pair<RenderbufferInfoMap::iterator, bool> result =
1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      renderbuffer_infos_.insert(std::make_pair(client_id, info));
1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK(result.second);
1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!info->cleared()) {
1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ++num_uncleared_renderbuffers_;
1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)RenderbufferManager::RenderbufferInfo* RenderbufferManager::GetRenderbufferInfo(
1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    GLuint client_id) {
1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderbufferInfoMap::iterator it = renderbuffer_infos_.find(client_id);
1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return it != renderbuffer_infos_.end() ? it->second : NULL;
1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void RenderbufferManager::RemoveRenderbufferInfo(GLuint client_id) {
1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderbufferInfoMap::iterator it = renderbuffer_infos_.find(client_id);
1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (it != renderbuffer_infos_.end()) {
1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RenderbufferInfo* info = it->second;
1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    info->MarkAsDeleted();
1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    renderbuffer_infos_.erase(it);
1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool RenderbufferManager::GetClientId(
1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    GLuint service_id, GLuint* client_id) const {
1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This doesn't need to be fast. It's only used during slow queries.
1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (RenderbufferInfoMap::const_iterator it = renderbuffer_infos_.begin();
1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)       it != renderbuffer_infos_.end(); ++it) {
1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (it->second->service_id() == service_id) {
1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      *client_id = it->first;
1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return true;
1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return false;
1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace gles2
1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace gpu
1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
157