| Index: gpu/command_buffer/service/gles2_cmd_decoder.cc
|
| diff --git a/gpu/command_buffer/service/gles2_cmd_decoder.cc b/gpu/command_buffer/service/gles2_cmd_decoder.cc
|
| index eb7c6df43d3b747f9b178afe332f1e75b1657e13..f31effa2b14cceefa1611f579a3ce151bda3f578 100644
|
| --- a/gpu/command_buffer/service/gles2_cmd_decoder.cc
|
| +++ b/gpu/command_buffer/service/gles2_cmd_decoder.cc
|
| @@ -566,6 +566,18 @@ class GLES2DecoderImpl : public base::SupportsWeakPtr<GLES2DecoderImpl>,
|
| (type == GL_SAMPLER_EXTERNAL_OES ? bound_texture_external_oes :
|
| bound_texture_cube_map);
|
| }
|
| +
|
| + void Unbind(TextureManager::TextureInfo* texture) {
|
| + if (bound_texture_2d == texture) {
|
| + bound_texture_2d = NULL;
|
| + }
|
| + if (bound_texture_cube_map == texture) {
|
| + bound_texture_cube_map = NULL;
|
| + }
|
| + if (bound_texture_external_oes == texture) {
|
| + bound_texture_external_oes = NULL;
|
| + }
|
| + }
|
| };
|
|
|
| // Initialize or re-initialize the shader translator.
|
| @@ -623,7 +635,7 @@ class GLES2DecoderImpl : public base::SupportsWeakPtr<GLES2DecoderImpl>,
|
| TextureManager::TextureInfo* GetTextureInfo(GLuint client_id) {
|
| TextureManager::TextureInfo* info =
|
| texture_manager()->GetTextureInfo(client_id);
|
| - return (info && !info->IsDeleted()) ? info : NULL;
|
| + return info;
|
| }
|
|
|
| // Deletes the texture info for the given texture.
|
| @@ -782,7 +794,7 @@ class GLES2DecoderImpl : public base::SupportsWeakPtr<GLES2DecoderImpl>,
|
| BufferManager::BufferInfo* GetBufferInfo(GLuint client_id) {
|
| BufferManager::BufferInfo* info =
|
| buffer_manager()->GetBufferInfo(client_id);
|
| - return (info && !info->IsDeleted()) ? info : NULL;
|
| + return info;
|
| }
|
|
|
| // Removes any buffers in the VertexAtrribInfos and BufferInfos. This is used
|
| @@ -800,7 +812,7 @@ class GLES2DecoderImpl : public base::SupportsWeakPtr<GLES2DecoderImpl>,
|
| GLuint client_id) {
|
| FramebufferManager::FramebufferInfo* info =
|
| framebuffer_manager()->GetFramebufferInfo(client_id);
|
| - return (info && !info->IsDeleted()) ? info : NULL;
|
| + return info;
|
| }
|
|
|
| // Removes the framebuffer info for the given framebuffer.
|
| @@ -819,7 +831,7 @@ class GLES2DecoderImpl : public base::SupportsWeakPtr<GLES2DecoderImpl>,
|
| GLuint client_id) {
|
| RenderbufferManager::RenderbufferInfo* info =
|
| renderbuffer_manager()->GetRenderbufferInfo(client_id);
|
| - return (info && !info->IsDeleted()) ? info : NULL;
|
| + return info;
|
| }
|
|
|
| // Removes the renderbuffer info for the given renderbuffer.
|
| @@ -1145,7 +1157,7 @@ class GLES2DecoderImpl : public base::SupportsWeakPtr<GLES2DecoderImpl>,
|
| DCHECK(target == GL_ARRAY_BUFFER || target == GL_ELEMENT_ARRAY_BUFFER);
|
| BufferManager::BufferInfo* info = target == GL_ARRAY_BUFFER ?
|
| bound_array_buffer_ : bound_element_array_buffer_;
|
| - return (info && !info->IsDeleted()) ? info : NULL;
|
| + return info;
|
| }
|
|
|
| // Gets the texture id for a given target.
|
| @@ -1176,7 +1188,7 @@ class GLES2DecoderImpl : public base::SupportsWeakPtr<GLES2DecoderImpl>,
|
| NOTREACHED();
|
| return NULL;
|
| }
|
| - return (info && !info->IsDeleted()) ? info : NULL;
|
| + return info;
|
| }
|
|
|
| GLenum GetBindTargetForSamplerType(GLenum type) {
|
| @@ -1203,7 +1215,7 @@ class GLES2DecoderImpl : public base::SupportsWeakPtr<GLES2DecoderImpl>,
|
| NOTREACHED();
|
| break;
|
| }
|
| - return (info && !info->IsDeleted()) ? info : NULL;
|
| + return info;
|
| }
|
|
|
| RenderbufferManager::RenderbufferInfo* GetRenderbufferInfoForTarget(
|
| @@ -1217,7 +1229,7 @@ class GLES2DecoderImpl : public base::SupportsWeakPtr<GLES2DecoderImpl>,
|
| NOTREACHED();
|
| break;
|
| }
|
| - return (info && !info->IsDeleted()) ? info : NULL;
|
| + return info;
|
| }
|
|
|
| // Validates the program and location for a glGetUniform call and returns
|
| @@ -2186,9 +2198,16 @@ bool GLES2DecoderImpl::GenTexturesHelper(GLsizei n, const GLuint* client_ids) {
|
| void GLES2DecoderImpl::DeleteBuffersHelper(
|
| GLsizei n, const GLuint* client_ids) {
|
| for (GLsizei ii = 0; ii < n; ++ii) {
|
| - BufferManager::BufferInfo* info = GetBufferInfo(client_ids[ii]);
|
| - if (info) {
|
| - GLuint service_id = info->service_id();
|
| + BufferManager::BufferInfo* buffer = GetBufferInfo(client_ids[ii]);
|
| + if (buffer && !buffer->IsDeleted()) {
|
| + vertex_attrib_manager_.Unbind(buffer);
|
| + if (bound_array_buffer_ == buffer) {
|
| + bound_array_buffer_ = NULL;
|
| + }
|
| + if (bound_element_array_buffer_ == buffer) {
|
| + bound_element_array_buffer_ = NULL;
|
| + }
|
| + GLuint service_id = buffer->service_id();
|
| glDeleteBuffersARB(1, &service_id);
|
| RemoveBufferInfo(client_ids[ii]);
|
| }
|
| @@ -2201,23 +2220,23 @@ void GLES2DecoderImpl::DeleteFramebuffersHelper(
|
| feature_info_->feature_flags().chromium_framebuffer_multisample;
|
|
|
| for (GLsizei ii = 0; ii < n; ++ii) {
|
| - FramebufferManager::FramebufferInfo* info =
|
| + FramebufferManager::FramebufferInfo* framebuffer =
|
| GetFramebufferInfo(client_ids[ii]);
|
| - if (info) {
|
| - if (info == bound_draw_framebuffer_) {
|
| + if (framebuffer && !framebuffer->IsDeleted()) {
|
| + if (framebuffer == bound_draw_framebuffer_) {
|
| bound_draw_framebuffer_ = NULL;
|
| state_dirty_ = true;
|
| GLenum target = supports_seperate_framebuffer_binds ?
|
| GL_DRAW_FRAMEBUFFER : GL_FRAMEBUFFER;
|
| glBindFramebufferEXT(target, GetBackbufferServiceId());
|
| }
|
| - if (info == bound_read_framebuffer_) {
|
| + if (framebuffer == bound_read_framebuffer_) {
|
| bound_read_framebuffer_ = NULL;
|
| GLenum target = supports_seperate_framebuffer_binds ?
|
| GL_READ_FRAMEBUFFER : GL_FRAMEBUFFER;
|
| glBindFramebufferEXT(target, GetBackbufferServiceId());
|
| }
|
| - GLuint service_id = info->service_id();
|
| + GLuint service_id = framebuffer->service_id();
|
| glDeleteFramebuffersEXT(1, &service_id);
|
| RemoveFramebufferInfo(client_ids[ii]);
|
| }
|
| @@ -2226,12 +2245,33 @@ void GLES2DecoderImpl::DeleteFramebuffersHelper(
|
|
|
| void GLES2DecoderImpl::DeleteRenderbuffersHelper(
|
| GLsizei n, const GLuint* client_ids) {
|
| + bool supports_seperate_framebuffer_binds =
|
| + feature_info_->feature_flags().chromium_framebuffer_multisample;
|
| for (GLsizei ii = 0; ii < n; ++ii) {
|
| - RenderbufferManager::RenderbufferInfo* info =
|
| + RenderbufferManager::RenderbufferInfo* renderbuffer =
|
| GetRenderbufferInfo(client_ids[ii]);
|
| - if (info) {
|
| + if (renderbuffer && !renderbuffer->IsDeleted()) {
|
| + if (bound_renderbuffer_ == renderbuffer) {
|
| + bound_renderbuffer_ = NULL;
|
| + }
|
| + // Unbind from current framebuffers.
|
| + if (supports_seperate_framebuffer_binds) {
|
| + if (bound_read_framebuffer_) {
|
| + bound_read_framebuffer_->UnbindRenderbuffer(
|
| + GL_READ_FRAMEBUFFER, renderbuffer);
|
| + }
|
| + if (bound_draw_framebuffer_) {
|
| + bound_draw_framebuffer_->UnbindRenderbuffer(
|
| + GL_DRAW_FRAMEBUFFER, renderbuffer);
|
| + }
|
| + } else {
|
| + if (bound_draw_framebuffer_) {
|
| + bound_draw_framebuffer_->UnbindRenderbuffer(
|
| + GL_FRAMEBUFFER, renderbuffer);
|
| + }
|
| + }
|
| state_dirty_ = true;
|
| - GLuint service_id = info->service_id();
|
| + GLuint service_id = renderbuffer->service_id();
|
| glDeleteRenderbuffersEXT(1, &service_id);
|
| RemoveRenderbufferInfo(client_ids[ii]);
|
| }
|
| @@ -2240,14 +2280,33 @@ void GLES2DecoderImpl::DeleteRenderbuffersHelper(
|
|
|
| void GLES2DecoderImpl::DeleteTexturesHelper(
|
| GLsizei n, const GLuint* client_ids) {
|
| + bool supports_seperate_framebuffer_binds =
|
| + feature_info_->feature_flags().chromium_framebuffer_multisample;
|
| for (GLsizei ii = 0; ii < n; ++ii) {
|
| - TextureManager::TextureInfo* info = GetTextureInfo(client_ids[ii]);
|
| - if (info) {
|
| - if (info->IsAttachedToFramebuffer()) {
|
| + TextureManager::TextureInfo* texture = GetTextureInfo(client_ids[ii]);
|
| + if (texture && !texture->IsDeleted()) {
|
| + if (texture->IsAttachedToFramebuffer()) {
|
| state_dirty_ = true;
|
| }
|
| - GLuint service_id = info->service_id();
|
| - if (info->IsStreamTexture() && stream_texture_manager_) {
|
| + // Unbind texture from texture units.
|
| + for (size_t jj = 0; jj < group_->max_texture_units(); ++jj) {
|
| + texture_units_[ii].Unbind(texture);
|
| + }
|
| + // Unbind from current framebuffers.
|
| + if (supports_seperate_framebuffer_binds) {
|
| + if (bound_read_framebuffer_) {
|
| + bound_read_framebuffer_->UnbindTexture(GL_READ_FRAMEBUFFER, texture);
|
| + }
|
| + if (bound_draw_framebuffer_) {
|
| + bound_draw_framebuffer_->UnbindTexture(GL_DRAW_FRAMEBUFFER, texture);
|
| + }
|
| + } else {
|
| + if (bound_draw_framebuffer_) {
|
| + bound_draw_framebuffer_->UnbindTexture(GL_FRAMEBUFFER, texture);
|
| + }
|
| + }
|
| + GLuint service_id = texture->service_id();
|
| + if (texture->IsStreamTexture() && stream_texture_manager_) {
|
| stream_texture_manager_->DestroyStreamTexture(service_id);
|
| }
|
| glDeleteTextures(1, &service_id);
|
| @@ -2329,7 +2388,7 @@ void GLES2DecoderImpl::RestoreCurrentTexture2DBindings() {
|
| bool GLES2DecoderImpl::CheckFramebufferValid(
|
| FramebufferManager::FramebufferInfo* framebuffer,
|
| GLenum target, const char* func_name) {
|
| - if (!framebuffer || framebuffer->IsDeleted()) {
|
| + if (!framebuffer) {
|
| return true;
|
| }
|
|
|
| @@ -3798,7 +3857,6 @@ void GLES2DecoderImpl::DoStencilMaskSeparate(GLenum face, GLuint mask) {
|
| // Assumes framebuffer is complete.
|
| void GLES2DecoderImpl::ClearUnclearedAttachments(
|
| GLenum target, FramebufferManager::FramebufferInfo* info) {
|
| - DCHECK(!info->IsDeleted());
|
| if (target == GL_READ_FRAMEBUFFER_EXT) {
|
| // bind this to the DRAW point, clear then bind back to READ
|
| // TODO(gman): I don't think there is any guarantee that an FBO that
|
| @@ -4564,7 +4622,7 @@ bool GLES2DecoderImpl::IsDrawValid(GLuint max_vertex_accessed) {
|
| }
|
| } else {
|
| // This attrib is not used in the current program.
|
| - if (!info->buffer() || info->buffer()->IsDeleted()) {
|
| + if (!info->buffer()) {
|
| SetGLError(
|
| GL_INVALID_OPERATION,
|
| "glDrawXXX: attempt to render with no buffer attached to enabled "
|
| @@ -4817,8 +4875,7 @@ error::Error GLES2DecoderImpl::HandleDrawArrays(
|
|
|
| error::Error GLES2DecoderImpl::HandleDrawElements(
|
| uint32 immediate_data_size, const gles2::DrawElements& c) {
|
| - if (!bound_element_array_buffer_ ||
|
| - bound_element_array_buffer_->IsDeleted()) {
|
| + if (!bound_element_array_buffer_) {
|
| SetGLError(GL_INVALID_OPERATION,
|
| "glDrawElements: No element array buffer bound");
|
| return error::kNoError;
|
| @@ -5117,37 +5174,39 @@ error::Error GLES2DecoderImpl::HandleGetShaderInfoLog(
|
| }
|
|
|
| bool GLES2DecoderImpl::DoIsBuffer(GLuint client_id) {
|
| - const BufferManager::BufferInfo* info = GetBufferInfo(client_id);
|
| - return info && info->IsValid();
|
| + const BufferManager::BufferInfo* buffer = GetBufferInfo(client_id);
|
| + return buffer && buffer->IsValid() && !buffer->IsDeleted();
|
| }
|
|
|
| bool GLES2DecoderImpl::DoIsFramebuffer(GLuint client_id) {
|
| - const FramebufferManager::FramebufferInfo* info =
|
| + const FramebufferManager::FramebufferInfo* framebuffer =
|
| GetFramebufferInfo(client_id);
|
| - return info && info->IsValid();
|
| + return framebuffer && framebuffer->IsValid() && !framebuffer->IsDeleted();
|
| }
|
|
|
| bool GLES2DecoderImpl::DoIsProgram(GLuint client_id) {
|
| // IsProgram is true for programs as soon as they are created, until they are
|
| // deleted and no longer in use.
|
| - return GetProgramInfo(client_id) != NULL;
|
| + const ProgramManager::ProgramInfo* program = GetProgramInfo(client_id);
|
| + return program != NULL && !program->IsDeleted();
|
| }
|
|
|
| bool GLES2DecoderImpl::DoIsRenderbuffer(GLuint client_id) {
|
| - const RenderbufferManager::RenderbufferInfo* info =
|
| + const RenderbufferManager::RenderbufferInfo* renderbuffer =
|
| GetRenderbufferInfo(client_id);
|
| - return info && info->IsValid();
|
| + return renderbuffer && renderbuffer->IsValid() && !renderbuffer->IsDeleted();
|
| }
|
|
|
| bool GLES2DecoderImpl::DoIsShader(GLuint client_id) {
|
| // IsShader is true for shaders as soon as they are created, until they
|
| // are deleted and not attached to any programs.
|
| - return GetShaderInfo(client_id) != NULL;
|
| + const ShaderManager::ShaderInfo* shader = GetShaderInfo(client_id);
|
| + return shader != NULL && !shader->IsDeleted();
|
| }
|
|
|
| bool GLES2DecoderImpl::DoIsTexture(GLuint client_id) {
|
| - const TextureManager::TextureInfo* info = GetTextureInfo(client_id);
|
| - return info && info->IsValid();
|
| + const TextureManager::TextureInfo* texture = GetTextureInfo(client_id);
|
| + return texture && texture->IsValid() && !texture->IsDeleted();
|
| }
|
|
|
| void GLES2DecoderImpl::DoAttachShader(
|
| @@ -5529,10 +5588,6 @@ error::Error GLES2DecoderImpl::HandleReadPixels(
|
| return error::kNoError;
|
| }
|
|
|
| - CopyRealGLErrorsToWrapper();
|
| -
|
| - ScopedResolvedFrameBufferBinder binder(this, false, true);
|
| -
|
| // Get the size of the current fbo or backbuffer.
|
| gfx::Size max_size = GetBoundReadFrameBufferSize();
|
|
|
| @@ -5547,6 +5602,10 @@ error::Error GLES2DecoderImpl::HandleReadPixels(
|
| return error::kNoError;
|
| }
|
|
|
| + CopyRealGLErrorsToWrapper();
|
| +
|
| + ScopedResolvedFrameBufferBinder binder(this, false, true);
|
| +
|
| if (x < 0 || y < 0 || max_x > max_size.width() || max_y > max_size.height()) {
|
| // The user requested an out of range area. Get the results 1 line
|
| // at a time.
|
| @@ -6387,6 +6446,10 @@ void GLES2DecoderImpl::DoCopyTexImage2D(
|
| return;
|
| }
|
|
|
| + if (!CheckBoundFramebuffersValid("glCopyTexImage2D")) {
|
| + return;
|
| + }
|
| +
|
| CopyRealGLErrorsToWrapper();
|
| ScopedResolvedFrameBufferBinder binder(this, false, true);
|
| gfx::Size size = GetBoundReadFrameBufferSize();
|
| @@ -6471,6 +6534,10 @@ void GLES2DecoderImpl::DoCopyTexSubImage2D(
|
| return;
|
| }
|
|
|
| + if (!CheckBoundFramebuffersValid("glCopyTexSubImage2D")) {
|
| + return;
|
| + }
|
| +
|
| ScopedResolvedFrameBufferBinder binder(this, false, true);
|
| gfx::Size size = GetBoundReadFrameBufferSize();
|
| GLint copyX = 0;
|
|
|