Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(303)

Side by Side Diff: gpu/command_buffer/service/gles2_cmd_decoder.cc

Issue 1418113009: Revert of gpu: Make glTexSubImage2D work with GL_SRGB_ALPHA on OpenGL (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 5 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « gpu/BUILD.gn ('k') | gpu/command_buffer/service/gles2_cmd_decoder_unittest_textures.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 "gpu/command_buffer/service/gles2_cmd_decoder.h" 5 #include "gpu/command_buffer/service/gles2_cmd_decoder.h"
6 6
7 #include <stdio.h> 7 #include <stdio.h>
8 8
9 #include <algorithm> 9 #include <algorithm>
10 #include <cmath> 10 #include <cmath>
(...skipping 172 matching lines...) Expand 10 before | Expand all | Expand 10 after
183 } 183 }
184 184
185 struct Vec4f { 185 struct Vec4f {
186 explicit Vec4f(const Vec4& data) { 186 explicit Vec4f(const Vec4& data) {
187 data.GetValues(v); 187 data.GetValues(v);
188 } 188 }
189 189
190 GLfloat v[4]; 190 GLfloat v[4];
191 }; 191 };
192 192
193 // Returns the union of |rect1| and |rect2| if one of the rectangles is empty,
194 // contains the other rectangle or shares an edge with the other rectangle.
195 bool CombineAdjacentRects(const gfx::Rect& rect1,
196 const gfx::Rect& rect2,
197 gfx::Rect* result) {
198 // Return |rect2| if |rect1| is empty or |rect2| contains |rect1|.
199 if (rect1.IsEmpty() || rect2.Contains(rect1)) {
200 *result = rect2;
201 return true;
202 }
203
204 // Return |rect1| if |rect2| is empty or |rect1| contains |rect2|.
205 if (rect2.IsEmpty() || rect1.Contains(rect2)) {
206 *result = rect1;
207 return true;
208 }
209
210 // Return the union of |rect1| and |rect2| if they share an edge.
211 if (rect1.SharesEdgeWith(rect2)) {
212 *result = gfx::UnionRects(rect1, rect2);
213 return true;
214 }
215
216 // Return false if it's not possible to combine |rect1| and |rect2|.
217 return false;
218 }
219
193 GLenum ExtractFormatFromStorageFormat(GLenum internalformat) { 220 GLenum ExtractFormatFromStorageFormat(GLenum internalformat) {
194 switch (internalformat) { 221 switch (internalformat) {
195 case GL_R8: 222 case GL_R8:
196 case GL_R8_SNORM: 223 case GL_R8_SNORM:
197 case GL_R16F: 224 case GL_R16F:
198 case GL_R32F: 225 case GL_R32F:
199 return GL_RED; 226 return GL_RED;
200 case GL_R8UI: 227 case GL_R8UI:
201 case GL_R8I: 228 case GL_R8I:
202 case GL_R16UI: 229 case GL_R16UI:
(...skipping 10856 matching lines...) Expand 10 before | Expand all | Expand 10 after
11059 GLint copyX = 0; 11086 GLint copyX = 0;
11060 GLint copyY = 0; 11087 GLint copyY = 0;
11061 GLint copyWidth = 0; 11088 GLint copyWidth = 0;
11062 GLint copyHeight = 0; 11089 GLint copyHeight = 0;
11063 Clip(x, width, size.width(), &copyX, &copyWidth); 11090 Clip(x, width, size.width(), &copyX, &copyWidth);
11064 Clip(y, height, size.height(), &copyY, &copyHeight); 11091 Clip(y, height, size.height(), &copyY, &copyHeight);
11065 11092
11066 if (xoffset != 0 || yoffset != 0 || width != size.width() || 11093 if (xoffset != 0 || yoffset != 0 || width != size.width() ||
11067 height != size.height()) { 11094 height != size.height()) {
11068 gfx::Rect cleared_rect; 11095 gfx::Rect cleared_rect;
11069 if (TextureManager::CombineAdjacentRects( 11096 if (CombineAdjacentRects(texture->GetLevelClearedRect(target, level),
11070 texture->GetLevelClearedRect(target, level), 11097 gfx::Rect(xoffset, yoffset, width, height),
11071 gfx::Rect(xoffset, yoffset, width, height), &cleared_rect)) { 11098 &cleared_rect)) {
11072 DCHECK_GE(cleared_rect.size().GetArea(), 11099 DCHECK_GE(cleared_rect.size().GetArea(),
11073 texture->GetLevelClearedRect(target, level).size().GetArea()); 11100 texture->GetLevelClearedRect(target, level).size().GetArea());
11074 texture_manager()->SetLevelClearedRect(texture_ref, target, level, 11101 texture_manager()->SetLevelClearedRect(texture_ref, target, level,
11075 cleared_rect); 11102 cleared_rect);
11076 } else { 11103 } else {
11077 // Otherwise clear part of texture level that is not already cleared. 11104 // Otherwise clear part of texture level that is not already cleared.
11078 if (!texture_manager()->ClearTextureLevel(this, texture_ref, target, 11105 if (!texture_manager()->ClearTextureLevel(this, texture_ref, target,
11079 level)) { 11106 level)) {
11080 LOCAL_SET_GL_ERROR(GL_OUT_OF_MEMORY, "glCopyTexSubImage2D", 11107 LOCAL_SET_GL_ERROR(GL_OUT_OF_MEMORY, "glCopyTexSubImage2D",
11081 "dimensions too big"); 11108 "dimensions too big");
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
11115 glCopyTexSubImage2D(target, level, 11142 glCopyTexSubImage2D(target, level,
11116 destX, destY, copyX, copyY, 11143 destX, destY, copyX, copyY,
11117 copyWidth, copyHeight); 11144 copyWidth, copyHeight);
11118 } 11145 }
11119 11146
11120 // This may be a slow command. Exit command processing to allow for 11147 // This may be a slow command. Exit command processing to allow for
11121 // context preemption and GPU watchdog checks. 11148 // context preemption and GPU watchdog checks.
11122 ExitCommandProcessingEarly(); 11149 ExitCommandProcessingEarly();
11123 } 11150 }
11124 11151
11152 bool GLES2DecoderImpl::ValidateTexSubImage2D(
11153 error::Error* error,
11154 const char* function_name,
11155 GLenum target,
11156 GLint level,
11157 GLint xoffset,
11158 GLint yoffset,
11159 GLsizei width,
11160 GLsizei height,
11161 GLenum format,
11162 GLenum type,
11163 const void * data) {
11164 (*error) = error::kNoError;
11165 if (!validators_->texture_target.IsValid(target)) {
11166 LOCAL_SET_GL_ERROR_INVALID_ENUM(function_name, target, "target");
11167 return false;
11168 }
11169 if (width < 0) {
11170 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, "width < 0");
11171 return false;
11172 }
11173 if (height < 0) {
11174 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, "height < 0");
11175 return false;
11176 }
11177 TextureRef* texture_ref = texture_manager()->GetTextureInfoForTarget(
11178 &state_, target);
11179 if (!texture_ref) {
11180 LOCAL_SET_GL_ERROR(
11181 GL_INVALID_OPERATION,
11182 function_name, "unknown texture for target");
11183 return false;
11184 }
11185 Texture* texture = texture_ref->texture();
11186 GLenum current_type = 0;
11187 GLenum internal_format = 0;
11188 if (!texture->GetLevelType(target, level, &current_type, &internal_format)) {
11189 LOCAL_SET_GL_ERROR(
11190 GL_INVALID_OPERATION, function_name, "level does not exist.");
11191 return false;
11192 }
11193 if (!texture_manager()->ValidateTextureParameters(state_.GetErrorState(),
11194 function_name, format, type, internal_format, level)) {
11195 return false;
11196 }
11197 if (type != current_type && !feature_info_->IsES3Enabled()) {
11198 LOCAL_SET_GL_ERROR(
11199 GL_INVALID_OPERATION,
11200 function_name, "type does not match type of texture.");
11201 return false;
11202 }
11203 if (!texture->ValidForTexture(
11204 target, level, xoffset, yoffset, 0, width, height, 1)) {
11205 LOCAL_SET_GL_ERROR(GL_INVALID_VALUE, function_name, "bad dimensions.");
11206 return false;
11207 }
11208 if ((GLES2Util::GetChannelsForFormat(format) &
11209 (GLES2Util::kDepth | GLES2Util::kStencil)) != 0
11210 && !feature_info_->IsES3Enabled()) {
11211 LOCAL_SET_GL_ERROR(
11212 GL_INVALID_OPERATION,
11213 function_name, "can not supply data for depth or stencil textures");
11214 return false;
11215 }
11216 if (data == NULL) {
11217 (*error) = error::kOutOfBounds;
11218 return false;
11219 }
11220 return true;
11221 }
11222
11223 error::Error GLES2DecoderImpl::DoTexSubImage2D(
11224 GLenum target,
11225 GLint level,
11226 GLint xoffset,
11227 GLint yoffset,
11228 GLsizei width,
11229 GLsizei height,
11230 GLenum format,
11231 GLenum type,
11232 const void * data) {
11233 error::Error error = error::kNoError;
11234 if (!ValidateTexSubImage2D(&error, "glTexSubImage2D", target, level,
11235 xoffset, yoffset, width, height, format, type, data)) {
11236 return error;
11237 }
11238 TextureRef* texture_ref = texture_manager()->GetTextureInfoForTarget(
11239 &state_, target);
11240 Texture* texture = texture_ref->texture();
11241 GLsizei tex_width = 0;
11242 GLsizei tex_height = 0;
11243 bool ok = texture->GetLevelSize(
11244 target, level, &tex_width, &tex_height, nullptr);
11245 DCHECK(ok);
11246 if (xoffset != 0 || yoffset != 0 ||
11247 width != tex_width || height != tex_height) {
11248 gfx::Rect cleared_rect;
11249 if (CombineAdjacentRects(texture->GetLevelClearedRect(target, level),
11250 gfx::Rect(xoffset, yoffset, width, height),
11251 &cleared_rect)) {
11252 DCHECK_GE(cleared_rect.size().GetArea(),
11253 texture->GetLevelClearedRect(target, level).size().GetArea());
11254 texture_manager()->SetLevelClearedRect(texture_ref, target, level,
11255 cleared_rect);
11256 } else {
11257 // Otherwise clear part of texture level that is not already cleared.
11258 if (!texture_manager()->ClearTextureLevel(this, texture_ref, target,
11259 level)) {
11260 LOCAL_SET_GL_ERROR(GL_OUT_OF_MEMORY, "glTexSubImage2D",
11261 "dimensions too big");
11262 return error::kNoError;
11263 }
11264 }
11265 ScopedTextureUploadTimer timer(&texture_state_);
11266 glTexSubImage2D(
11267 target, level, xoffset, yoffset, width, height, format, type, data);
11268 return error::kNoError;
11269 }
11270
11271 if (!texture_state_.texsubimage_faster_than_teximage &&
11272 !texture->IsImmutable() &&
11273 !texture->HasImages()) {
11274 ScopedTextureUploadTimer timer(&texture_state_);
11275 GLenum internal_format;
11276 GLenum tex_type;
11277 texture->GetLevelType(target, level, &tex_type, &internal_format);
11278 // NOTE: In OpenGL ES 2.0 border is always zero. If that changes we'll need
11279 // to look it up.
11280 glTexImage2D(
11281 target, level, internal_format, width, height, 0, format, type, data);
11282 } else {
11283 ScopedTextureUploadTimer timer(&texture_state_);
11284 glTexSubImage2D(
11285 target, level, xoffset, yoffset, width, height, format, type, data);
11286 }
11287 texture_manager()->SetLevelCleared(texture_ref, target, level, true);
11288
11289 // This may be a slow command. Exit command processing to allow for
11290 // context preemption and GPU watchdog checks.
11291 ExitCommandProcessingEarly();
11292 return error::kNoError;
11293 }
11294
11125 error::Error GLES2DecoderImpl::HandleTexSubImage2D(uint32 immediate_data_size, 11295 error::Error GLES2DecoderImpl::HandleTexSubImage2D(uint32 immediate_data_size,
11126 const void* cmd_data) { 11296 const void* cmd_data) {
11127 const gles2::cmds::TexSubImage2D& c = 11297 const gles2::cmds::TexSubImage2D& c =
11128 *static_cast<const gles2::cmds::TexSubImage2D*>(cmd_data); 11298 *static_cast<const gles2::cmds::TexSubImage2D*>(cmd_data);
11129 TRACE_EVENT2("gpu", "GLES2DecoderImpl::HandleTexSubImage2D", 11299 TRACE_EVENT2("gpu", "GLES2DecoderImpl::HandleTexSubImage2D",
11130 "width", c.width, "height", c.height); 11300 "width", c.width, "height", c.height);
11131 GLboolean internal = static_cast<GLboolean>(c.internal); 11301 GLboolean internal = static_cast<GLboolean>(c.internal);
11132 if (internal == GL_TRUE && texture_state_.tex_image_failed) 11302 if (internal == GL_TRUE && texture_state_.tex_image_failed)
11133 return error::kNoError; 11303 return error::kNoError;
11134 11304
11135 GLenum target = static_cast<GLenum>(c.target); 11305 GLenum target = static_cast<GLenum>(c.target);
11136 GLint level = static_cast<GLint>(c.level); 11306 GLint level = static_cast<GLint>(c.level);
11137 GLint xoffset = static_cast<GLint>(c.xoffset); 11307 GLint xoffset = static_cast<GLint>(c.xoffset);
11138 GLint yoffset = static_cast<GLint>(c.yoffset); 11308 GLint yoffset = static_cast<GLint>(c.yoffset);
11139 GLsizei width = static_cast<GLsizei>(c.width); 11309 GLsizei width = static_cast<GLsizei>(c.width);
11140 GLsizei height = static_cast<GLsizei>(c.height); 11310 GLsizei height = static_cast<GLsizei>(c.height);
11141 GLenum format = static_cast<GLenum>(c.format); 11311 GLenum format = static_cast<GLenum>(c.format);
11142 GLenum type = static_cast<GLenum>(c.type); 11312 GLenum type = static_cast<GLenum>(c.type);
11143 uint32 data_size; 11313 uint32 data_size;
11144 if (!GLES2Util::ComputeImageDataSizes( 11314 if (!GLES2Util::ComputeImageDataSizes(
11145 width, height, 1, format, type, state_.unpack_alignment, &data_size, 11315 width, height, 1, format, type, state_.unpack_alignment, &data_size,
11146 NULL, NULL)) { 11316 NULL, NULL)) {
11147 return error::kOutOfBounds; 11317 return error::kOutOfBounds;
11148 } 11318 }
11149
11150 const void* pixels = GetSharedMemoryAs<const void*>( 11319 const void* pixels = GetSharedMemoryAs<const void*>(
11151 c.pixels_shm_id, c.pixels_shm_offset, data_size); 11320 c.pixels_shm_id, c.pixels_shm_offset, data_size);
11152 if (!pixels) 11321 return DoTexSubImage2D(
11153 return error::kOutOfBounds; 11322 target, level, xoffset, yoffset, width, height, format, type, pixels);
11154
11155 TextureManager::DoTexSubImageArguments args = {
11156 target, level, xoffset, yoffset, width,
11157 height, format, type, pixels, data_size};
11158 texture_manager()->ValidateAndDoTexSubImage(this, &texture_state_, &state_,
11159 &framebuffer_state_,
11160 "glTexSubImage2D", args);
11161
11162 // This may be a slow command. Exit command processing to allow for
11163 // context preemption and GPU watchdog checks.
11164 ExitCommandProcessingEarly();
11165 return error::kNoError;
11166 } 11323 }
11167 11324
11168 error::Error GLES2DecoderImpl::DoTexSubImage3D( 11325 error::Error GLES2DecoderImpl::DoTexSubImage3D(
11169 GLenum target, 11326 GLenum target,
11170 GLint level, 11327 GLint level,
11171 GLint xoffset, 11328 GLint xoffset,
11172 GLint yoffset, 11329 GLint yoffset,
11173 GLint zoffset, 11330 GLint zoffset,
11174 GLsizei width, 11331 GLsizei width,
11175 GLsizei height, 11332 GLsizei height,
(...skipping 1917 matching lines...) Expand 10 before | Expand all | Expand 10 after
13093 } 13250 }
13094 13251
13095 int dest_width = 0; 13252 int dest_width = 0;
13096 int dest_height = 0; 13253 int dest_height = 0;
13097 bool ok = dest_texture->GetLevelSize( 13254 bool ok = dest_texture->GetLevelSize(
13098 GL_TEXTURE_2D, 0, &dest_width, &dest_height, nullptr); 13255 GL_TEXTURE_2D, 0, &dest_width, &dest_height, nullptr);
13099 DCHECK(ok); 13256 DCHECK(ok);
13100 if (xoffset != 0 || yoffset != 0 || width != dest_width || 13257 if (xoffset != 0 || yoffset != 0 || width != dest_width ||
13101 height != dest_height) { 13258 height != dest_height) {
13102 gfx::Rect cleared_rect; 13259 gfx::Rect cleared_rect;
13103 if (TextureManager::CombineAdjacentRects( 13260 if (CombineAdjacentRects(dest_texture->GetLevelClearedRect(target, 0),
13104 dest_texture->GetLevelClearedRect(target, 0), 13261 gfx::Rect(xoffset, yoffset, width, height),
13105 gfx::Rect(xoffset, yoffset, width, height), &cleared_rect)) { 13262 &cleared_rect)) {
13106 DCHECK_GE(cleared_rect.size().GetArea(), 13263 DCHECK_GE(cleared_rect.size().GetArea(),
13107 dest_texture->GetLevelClearedRect(target, 0).size().GetArea()); 13264 dest_texture->GetLevelClearedRect(target, 0).size().GetArea());
13108 texture_manager()->SetLevelClearedRect(dest_texture_ref, target, 0, 13265 texture_manager()->SetLevelClearedRect(dest_texture_ref, target, 0,
13109 cleared_rect); 13266 cleared_rect);
13110 } else { 13267 } else {
13111 // Otherwise clear part of texture level that is not already cleared. 13268 // Otherwise clear part of texture level that is not already cleared.
13112 if (!texture_manager()->ClearTextureLevel(this, dest_texture_ref, target, 13269 if (!texture_manager()->ClearTextureLevel(this, dest_texture_ref, target,
13113 0)) { 13270 0)) {
13114 LOCAL_SET_GL_ERROR(GL_OUT_OF_MEMORY, "glCopySubTextureCHROMIUM", 13271 LOCAL_SET_GL_ERROR(GL_OUT_OF_MEMORY, "glCopySubTextureCHROMIUM",
13115 "destination texture dimensions too big"); 13272 "destination texture dimensions too big");
(...skipping 315 matching lines...) Expand 10 before | Expand all | Expand 10 after
13431 } 13588 }
13432 13589
13433 int dest_width = 0; 13590 int dest_width = 0;
13434 int dest_height = 0; 13591 int dest_height = 0;
13435 bool ok = dest_texture->GetLevelSize( 13592 bool ok = dest_texture->GetLevelSize(
13436 GL_TEXTURE_2D, 0, &dest_width, &dest_height, nullptr); 13593 GL_TEXTURE_2D, 0, &dest_width, &dest_height, nullptr);
13437 DCHECK(ok); 13594 DCHECK(ok);
13438 if (xoffset != 0 || yoffset != 0 || width != dest_width || 13595 if (xoffset != 0 || yoffset != 0 || width != dest_width ||
13439 height != dest_height) { 13596 height != dest_height) {
13440 gfx::Rect cleared_rect; 13597 gfx::Rect cleared_rect;
13441 if (TextureManager::CombineAdjacentRects( 13598 if (CombineAdjacentRects(dest_texture->GetLevelClearedRect(target, 0),
13442 dest_texture->GetLevelClearedRect(target, 0), 13599 gfx::Rect(xoffset, yoffset, width, height),
13443 gfx::Rect(xoffset, yoffset, width, height), &cleared_rect)) { 13600 &cleared_rect)) {
13444 DCHECK_GE(cleared_rect.size().GetArea(), 13601 DCHECK_GE(cleared_rect.size().GetArea(),
13445 dest_texture->GetLevelClearedRect(target, 0).size().GetArea()); 13602 dest_texture->GetLevelClearedRect(target, 0).size().GetArea());
13446 texture_manager()->SetLevelClearedRect(dest_texture_ref, target, 0, 13603 texture_manager()->SetLevelClearedRect(dest_texture_ref, target, 0,
13447 cleared_rect); 13604 cleared_rect);
13448 } else { 13605 } else {
13449 // Otherwise clear part of texture level that is not already cleared. 13606 // Otherwise clear part of texture level that is not already cleared.
13450 if (!texture_manager()->ClearTextureLevel(this, dest_texture_ref, target, 13607 if (!texture_manager()->ClearTextureLevel(this, dest_texture_ref, target,
13451 0)) { 13608 0)) {
13452 LOCAL_SET_GL_ERROR(GL_OUT_OF_MEMORY, 13609 LOCAL_SET_GL_ERROR(GL_OUT_OF_MEMORY,
13453 "glCompressedCopySubTextureCHROMIUM", 13610 "glCompressedCopySubTextureCHROMIUM",
(...skipping 1816 matching lines...) Expand 10 before | Expand all | Expand 10 after
15270 return error::kNoError; 15427 return error::kNoError;
15271 } 15428 }
15272 15429
15273 // Include the auto-generated part of this file. We split this because it means 15430 // Include the auto-generated part of this file. We split this because it means
15274 // we can easily edit the non-auto generated parts right here in this file 15431 // we can easily edit the non-auto generated parts right here in this file
15275 // instead of having to edit some template or the code generator. 15432 // instead of having to edit some template or the code generator.
15276 #include "gpu/command_buffer/service/gles2_cmd_decoder_autogen.h" 15433 #include "gpu/command_buffer/service/gles2_cmd_decoder_autogen.h"
15277 15434
15278 } // namespace gles2 15435 } // namespace gles2
15279 } // namespace gpu 15436 } // namespace gpu
OLDNEW
« no previous file with comments | « gpu/BUILD.gn ('k') | gpu/command_buffer/service/gles2_cmd_decoder_unittest_textures.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698