context_state.cc revision 868fa2fe829687343ffae624259930155e16dbd8
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 3// found in the LICENSE file. 4 5#include "gpu/command_buffer/service/context_state.h" 6 7#include "gpu/command_buffer/common/gles2_cmd_utils.h" 8#include "gpu/command_buffer/service/buffer_manager.h" 9#include "gpu/command_buffer/service/error_state.h" 10#include "gpu/command_buffer/service/framebuffer_manager.h" 11#include "gpu/command_buffer/service/program_manager.h" 12#include "gpu/command_buffer/service/renderbuffer_manager.h" 13#include "ui/gl/gl_bindings.h" 14#include "ui/gl/gl_implementation.h" 15 16namespace gpu { 17namespace gles2 { 18 19namespace { 20 21void EnableDisable(GLenum pname, bool enable) { 22 if (enable) { 23 glEnable(pname); 24 } else { 25 glDisable(pname); 26 } 27} 28 29} // anonymous namespace. 30 31TextureUnit::TextureUnit() 32 : bind_target(GL_TEXTURE_2D) { 33} 34 35TextureUnit::~TextureUnit() { 36} 37 38ContextState::ContextState(FeatureInfo* feature_info, Logger* logger) 39 : active_texture_unit(0), 40 pack_reverse_row_order(false), 41 fbo_binding_for_scissor_workaround_dirty_(false), 42 feature_info_(feature_info), 43 error_state_(ErrorState::Create(logger)) { 44 Initialize(); 45} 46 47ContextState::~ContextState() { 48} 49 50void ContextState::RestoreTextureUnitBindings(GLuint unit) const { 51 DCHECK_LT(unit, texture_units.size()); 52 const TextureUnit& texture_unit = texture_units[unit]; 53 glActiveTexture(GL_TEXTURE0 + unit); 54 GLuint service_id = texture_unit.bound_texture_2d.get() 55 ? texture_unit.bound_texture_2d->service_id() 56 : 0; 57 glBindTexture(GL_TEXTURE_2D, service_id); 58 service_id = texture_unit.bound_texture_cube_map.get() 59 ? texture_unit.bound_texture_cube_map->service_id() 60 : 0; 61 glBindTexture(GL_TEXTURE_CUBE_MAP, service_id); 62 63 if (feature_info_->feature_flags().oes_egl_image_external) { 64 service_id = texture_unit.bound_texture_external_oes.get() 65 ? texture_unit.bound_texture_external_oes->service_id() 66 : 0; 67 glBindTexture(GL_TEXTURE_EXTERNAL_OES, service_id); 68 } 69 70 if (feature_info_->feature_flags().arb_texture_rectangle) { 71 service_id = texture_unit.bound_texture_rectangle_arb.get() 72 ? texture_unit.bound_texture_rectangle_arb->service_id() 73 : 0; 74 glBindTexture(GL_TEXTURE_RECTANGLE_ARB, service_id); 75 } 76} 77 78void ContextState::RestoreBufferBindings() const { 79 if (vertex_attrib_manager.get()) { 80 Buffer* element_array_buffer = 81 vertex_attrib_manager->element_array_buffer(); 82 glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 83 element_array_buffer ? element_array_buffer->service_id() : 0); 84 } 85 glBindBuffer(GL_ARRAY_BUFFER, 86 bound_array_buffer.get() ? bound_array_buffer->service_id() : 0); 87} 88 89void ContextState::RestoreRenderbufferBindings() const { 90 // Restore Bindings 91 glBindRenderbufferEXT( 92 GL_RENDERBUFFER, 93 bound_renderbuffer.get() ? bound_renderbuffer->service_id() : 0); 94} 95 96void ContextState::RestoreProgramBindings() const { 97 glUseProgram(current_program.get() ? current_program->service_id() : 0); 98} 99 100void ContextState::RestoreActiveTexture() const { 101 glActiveTexture(GL_TEXTURE0 + active_texture_unit); 102} 103 104void ContextState::RestoreAllTextureUnitBindings() const { 105 // Restore Texture state. 106 for (size_t ii = 0; ii < texture_units.size(); ++ii) { 107 RestoreTextureUnitBindings(ii); 108 } 109 RestoreActiveTexture(); 110} 111 112void ContextState::RestoreAttribute(GLuint attrib_index) const { 113 const VertexAttrib* attrib = 114 vertex_attrib_manager->GetVertexAttrib(attrib_index); 115 const void* ptr = reinterpret_cast<const void*>(attrib->offset()); 116 Buffer* buffer = attrib->buffer(); 117 glBindBuffer(GL_ARRAY_BUFFER, buffer ? buffer->service_id() : 0); 118 glVertexAttribPointer( 119 attrib_index, attrib->size(), attrib->type(), attrib->normalized(), 120 attrib->gl_stride(), ptr); 121 if (attrib->divisor()) 122 glVertexAttribDivisorANGLE(attrib_index, attrib->divisor()); 123 // Never touch vertex attribute 0's state (in particular, never 124 // disable it) when running on desktop GL because it will never be 125 // re-enabled. 126 if (attrib_index != 0 || 127 gfx::GetGLImplementation() == gfx::kGLImplementationEGLGLES2) { 128 if (attrib->enabled()) { 129 glEnableVertexAttribArray(attrib_index); 130 } else { 131 glDisableVertexAttribArray(attrib_index); 132 } 133 } 134 glVertexAttrib4fv(attrib_index, attrib_values[attrib_index].v); 135} 136 137void ContextState::RestoreGlobalState() const { 138 InitCapabilities(); 139 InitState(); 140} 141 142void ContextState::RestoreState() const { 143 RestoreAllTextureUnitBindings(); 144 145 // Restore Attrib State 146 // TODO: This if should not be needed. RestoreState is getting called 147 // before GLES2Decoder::Initialize which is a bug. 148 if (vertex_attrib_manager.get()) { 149 // TODO(gman): Move this restoration to VertexAttribManager. 150 for (size_t attrib = 0; attrib < vertex_attrib_manager->num_attribs(); 151 ++attrib) { 152 RestoreAttribute(attrib); 153 } 154 } 155 156 RestoreBufferBindings(); 157 RestoreRenderbufferBindings(); 158 RestoreProgramBindings(); 159 RestoreGlobalState(); 160} 161 162ErrorState* ContextState::GetErrorState() { 163 return error_state_.get(); 164} 165 166// Include the auto-generated part of this file. We split this because it means 167// we can easily edit the non-auto generated parts right here in this file 168// instead of having to edit some template or the code generator. 169#include "gpu/command_buffer/service/context_state_impl_autogen.h" 170 171} // namespace gles2 172} // namespace gpu 173 174 175