diff options
Diffstat (limited to 'gpu')
-rw-r--r-- | gpu/command_buffer/common/gles2_cmd_utils_unittest.cc | 13 | ||||
-rw-r--r-- | gpu/command_buffer/service/feature_info.cc | 5 | ||||
-rw-r--r-- | gpu/command_buffer/service/feature_info_unittest.cc | 18 | ||||
-rw-r--r-- | gpu/command_buffer/service/gl_utils.h | 3 | ||||
-rw-r--r-- | gpu/command_buffer/service/gles2_cmd_decoder.cc | 29 | ||||
-rw-r--r-- | gpu/command_buffer/service/gles2_cmd_decoder_unittest.cc | 122 |
6 files changed, 183 insertions, 7 deletions
diff --git a/gpu/command_buffer/common/gles2_cmd_utils_unittest.cc b/gpu/command_buffer/common/gles2_cmd_utils_unittest.cc index 0e157db..0eb908c 100644 --- a/gpu/command_buffer/common/gles2_cmd_utils_unittest.cc +++ b/gpu/command_buffer/common/gles2_cmd_utils_unittest.cc @@ -234,6 +234,18 @@ TEST_F(GLES2UtilTest, RenderbufferBytesPerPixel) { EXPECT_EQ(0u, GLES2Util::RenderbufferBytesPerPixel(-1)); } +TEST_F(GLES2UtilTest, GetChannelsForCompressedFormat) { + EXPECT_EQ(0u, GLES2Util::GetChannelsForFormat(GL_ETC1_RGB8_OES)); + EXPECT_EQ(0u, GLES2Util::GetChannelsForFormat( + GL_COMPRESSED_RGB_S3TC_DXT1_EXT)); + EXPECT_EQ(0u, GLES2Util::GetChannelsForFormat( + GL_COMPRESSED_RGBA_S3TC_DXT1_EXT)); + EXPECT_EQ(0u, GLES2Util::GetChannelsForFormat( + GL_COMPRESSED_RGBA_S3TC_DXT3_EXT)); + EXPECT_EQ(0u, GLES2Util::GetChannelsForFormat( + GL_COMPRESSED_RGBA_S3TC_DXT5_EXT)); +} + namespace { void CheckParseUniformName( @@ -278,4 +290,3 @@ TEST_F(GLES2UtilTest, ParseUniformName) { } // namespace gles2 } // namespace gpu - diff --git a/gpu/command_buffer/service/feature_info.cc b/gpu/command_buffer/service/feature_info.cc index a8c6679..7f15dbf 100644 --- a/gpu/command_buffer/service/feature_info.cc +++ b/gpu/command_buffer/service/feature_info.cc @@ -504,6 +504,11 @@ void FeatureInfo::AddFeatures(const char* desired_features) { validators_.g_l_state.AddValue(GL_TEXTURE_BINDING_EXTERNAL_OES); } + if (ext.HaveAndDesire("GL_OES_compressed_ETC1_RGB8_texture")) { + AddExtensionString("GL_OES_compressed_ETC1_RGB8_texture"); + validators_.compressed_texture_format.AddValue(GL_ETC1_RGB8_OES); + } + if (ext.Desire("GL_CHROMIUM_stream_texture")) { AddExtensionString("GL_CHROMIUM_stream_texture"); feature_flags_.chromium_stream_texture = true; diff --git a/gpu/command_buffer/service/feature_info_unittest.cc b/gpu/command_buffer/service/feature_info_unittest.cc index a5cfa12..f08d4ce 100644 --- a/gpu/command_buffer/service/feature_info_unittest.cc +++ b/gpu/command_buffer/service/feature_info_unittest.cc @@ -206,6 +206,8 @@ TEST_F(FeatureInfoTest, InitializeNoExtensions) { Not(HasSubstr("GL_ANGLE_texture_usage"))); EXPECT_THAT(info_->extensions(), Not(HasSubstr("GL_EXT_texture_storage"))); + EXPECT_THAT(info_->extensions(), + Not(HasSubstr("GL_OES_compressed_ETC1_RGB8_texture"))); EXPECT_FALSE(info_->feature_flags().npot_ok); EXPECT_FALSE(info_->feature_flags().chromium_webglsl); EXPECT_FALSE(info_->validators()->compressed_texture_format.IsValid( @@ -216,6 +218,8 @@ TEST_F(FeatureInfoTest, InitializeNoExtensions) { GL_COMPRESSED_RGBA_S3TC_DXT3_EXT)); EXPECT_FALSE(info_->validators()->compressed_texture_format.IsValid( GL_COMPRESSED_RGBA_S3TC_DXT5_EXT)); + EXPECT_FALSE(info_->validators()->compressed_texture_format.IsValid( + GL_ETC1_RGB8_OES)); EXPECT_FALSE(info_->validators()->read_pixel_format.IsValid( GL_BGRA_EXT)); EXPECT_FALSE(info_->validators()->texture_parameter.IsValid( @@ -702,6 +706,17 @@ TEST_F(FeatureInfoTest, InitializeOES_EGL_image_external) { GL_TEXTURE_BINDING_EXTERNAL_OES)); } +TEST_F(FeatureInfoTest, InitializeOES_compressed_ETC1_RGB8_texture) { + SetupInitExpectations("GL_OES_compressed_ETC1_RGB8_texture"); + info_->Initialize(NULL); + EXPECT_THAT(info_->extensions(), + HasSubstr("GL_OES_compressed_ETC1_RGB8_texture")); + EXPECT_TRUE(info_->validators()->compressed_texture_format.IsValid( + GL_ETC1_RGB8_OES)); + EXPECT_FALSE(info_->validators()->texture_internal_format.IsValid( + GL_ETC1_RGB8_OES)); +} + TEST_F(FeatureInfoTest, InitializeCHROMIUM_stream_texture) { SetupInitExpectations("GL_CHROMIUM_stream_texture"); info_->Initialize(NULL); @@ -852,6 +867,3 @@ TEST_F(FeatureInfoTest, IsAMDATI) { } // namespace gles2 } // namespace gpu - - - diff --git a/gpu/command_buffer/service/gl_utils.h b/gpu/command_buffer/service/gl_utils.h index e31126f..5baff01 100644 --- a/gpu/command_buffer/service/gl_utils.h +++ b/gpu/command_buffer/service/gl_utils.h @@ -101,6 +101,9 @@ // GL_OES_packed_depth_stencil #define GL_DEPTH24_STENCIL8_OES 0x88F0 +// GL_OES_compressed_ETC1_RGB8_texture +#define GL_ETC1_RGB8_OES 0x8D64 + #define GL_GLEXT_PROTOTYPES 1 // GL_ARB_get_program_binary diff --git a/gpu/command_buffer/service/gles2_cmd_decoder.cc b/gpu/command_buffer/service/gles2_cmd_decoder.cc index a26c6b3..69df928 100644 --- a/gpu/command_buffer/service/gles2_cmd_decoder.cc +++ b/gpu/command_buffer/service/gles2_cmd_decoder.cc @@ -7080,6 +7080,9 @@ const int kS3TCBlockWidth = 4; const int kS3TCBlockHeight = 4; const int kS3TCDXT1BlockSize = 8; const int kS3TCDXT3AndDXT5BlockSize = 16; +const int kETC1BlockWidth = 4; +const int kETC1BlockHeight = 4; +const int kETC1BlockSize = 8; bool IsValidDXTSize(GLint level, GLsizei size) { return (size == 1) || @@ -7114,6 +7117,15 @@ bool GLES2DecoderImpl::ValidateCompressedTexFuncData( bytes_required = num_blocks * kS3TCDXT3AndDXT5BlockSize; break; } + case GL_ETC1_RGB8_OES: { + int num_blocks_across = + (width + kETC1BlockWidth - 1) / kETC1BlockWidth; + int num_blocks_down = + (height + kETC1BlockHeight - 1) / kETC1BlockHeight; + int num_blocks = num_blocks_across * num_blocks_down; + bytes_required = num_blocks * kETC1BlockSize; + break; + } default: SetGLErrorInvalidEnum(function_name, format, "format"); return false; @@ -7144,6 +7156,14 @@ bool GLES2DecoderImpl::ValidateCompressedTexDimensions( } return true; } + case GL_ETC1_RGB8_OES: + if (width <= 0 || height <= 0) { + SetGLError( + GL_INVALID_OPERATION, function_name, + "width or height invalid for level"); + return false; + } + return true; default: return false; } @@ -7185,6 +7205,12 @@ bool GLES2DecoderImpl::ValidateCompressedTexSubDimensions( return ValidateCompressedTexDimensions( function_name, level, width, height, format); } + case GL_ETC1_RGB8_OES: { + SetGLError( + GL_INVALID_OPERATION, function_name, + "TexsubImage2d not supported for ECT1_RGB8_OES textures"); + return false; + } default: return false; } @@ -7763,7 +7789,8 @@ void GLES2DecoderImpl::DoCopyTexSubImage2D( uint32 channels_exist = GLES2Util::GetChannelsForFormat(read_format); uint32 channels_needed = GLES2Util::GetChannelsForFormat(format); - if ((channels_needed & channels_exist) != channels_needed) { + if (!channels_needed || + (channels_needed & channels_exist) != channels_needed) { SetGLError( GL_INVALID_OPERATION, "glCopyTexSubImage2D", "incompatible format"); return; diff --git a/gpu/command_buffer/service/gles2_cmd_decoder_unittest.cc b/gpu/command_buffer/service/gles2_cmd_decoder_unittest.cc index af8b6b1..3a1f4c5 100644 --- a/gpu/command_buffer/service/gles2_cmd_decoder_unittest.cc +++ b/gpu/command_buffer/service/gles2_cmd_decoder_unittest.cc @@ -1866,7 +1866,7 @@ TEST_F(GLES2DecoderTest, GenerateMipmapHandlesOutOfMemory) { .Times(1) .RetiresOnSaturation(); EXPECT_CALL(*gl_, GenerateMipmapEXT(GL_TEXTURE_2D)) - .Times(1); + .Times(1); EXPECT_CALL(*gl_, TexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST_MIPMAP_LINEAR)) .Times(1) @@ -5291,6 +5291,124 @@ TEST_F(GLES2DecoderManualInitTest, CompressedTexImage2DS3TC) { } } +TEST_F(GLES2DecoderManualInitTest, CompressedTexImage2DETC1) { + InitDecoder( + "GL_OES_compressed_ETC1_RGB8_texture", // extensions + false, // has alpha + false, // has depth + false, // has stencil + false, // request alpha + false, // request depth + false, // request stencil + true); // bind generates resource + const uint32 kBucketId = 123; + CommonDecoder::Bucket* bucket = decoder_->CreateBucket(kBucketId); + ASSERT_TRUE(bucket != NULL); + + DoBindTexture(GL_TEXTURE_2D, client_texture_id_, kServiceTextureId); + + const GLenum kFormat = GL_ETC1_RGB8_OES; + const size_t kBlockSize = 8; + + CompressedTexImage2DBucket cmd; + // test small width. + DoCompressedTexImage2D(GL_TEXTURE_2D, 0, kFormat, 4, 8, 0, 16, kBucketId); + EXPECT_EQ(GL_NO_ERROR, GetGLError()); + + // test small height. + DoCompressedTexImage2D(GL_TEXTURE_2D, 0, kFormat, 8, 4, 0, 16, kBucketId); + EXPECT_EQ(GL_NO_ERROR, GetGLError()); + + // test size too large. + cmd.Init(GL_TEXTURE_2D, 0, kFormat, 4, 4, 0, kBucketId); + bucket->SetSize(kBlockSize * 2); + EXPECT_EQ(error::kNoError, ExecuteCmd(cmd)); + EXPECT_EQ(GL_INVALID_VALUE, GetGLError()); + + // test size too small. + cmd.Init(GL_TEXTURE_2D, 0, kFormat, 4, 4, 0, kBucketId); + bucket->SetSize(kBlockSize / 2); + EXPECT_EQ(error::kNoError, ExecuteCmd(cmd)); + EXPECT_EQ(GL_INVALID_VALUE, GetGLError()); + + // Test a 16x16 + DoCompressedTexImage2D( + GL_TEXTURE_2D, 0, kFormat, 16, 16, 0, kBlockSize * 16, kBucketId); + EXPECT_EQ(GL_NO_ERROR, GetGLError()); + + // Test CompressedTexSubImage not allowed + CompressedTexSubImage2DBucket sub_cmd; + bucket->SetSize(kBlockSize); + sub_cmd.Init(GL_TEXTURE_2D, 0, 0, 0, 4, 4, kFormat, kBucketId); + EXPECT_EQ(error::kNoError, ExecuteCmd(sub_cmd)); + EXPECT_EQ(GL_INVALID_OPERATION, GetGLError()); + + // Test TexSubImage not allowed for ETC1 compressed texture + TextureManager::TextureInfo* info = GetTextureInfo(client_texture_id_); + ASSERT_TRUE(info != NULL); + GLenum type, internal_format; + EXPECT_TRUE(info->GetLevelType(GL_TEXTURE_2D, 0, &type, &internal_format)); + EXPECT_EQ(kFormat, internal_format); + TexSubImage2D texsub_cmd; + texsub_cmd.Init(GL_TEXTURE_2D, 0, 0, 0, 4, 4, GL_RGBA, GL_UNSIGNED_BYTE, + kSharedMemoryId, kSharedMemoryOffset, GL_FALSE); + EXPECT_EQ(error::kNoError, ExecuteCmd(texsub_cmd)); + EXPECT_EQ(GL_INVALID_OPERATION, GetGLError()); + + // Test CopyTexSubImage not allowed for ETC1 compressed texture + CopyTexSubImage2D copy_cmd; + copy_cmd.Init(GL_TEXTURE_2D, 0, 0, 0, 0, 0, 4, 4); + EXPECT_EQ(error::kNoError, ExecuteCmd(copy_cmd)); + EXPECT_EQ(GL_INVALID_OPERATION, GetGLError()); +} + +TEST_F(GLES2DecoderManualInitTest, GetCompressedTextureFormatsETC1) { + InitDecoder( + "GL_OES_compressed_ETC1_RGB8_texture", // extensions + false, // has alpha + false, // has depth + false, // has stencil + false, // request alpha + false, // request depth + false, // request stencil + true); // bind generates resource + + EXPECT_CALL(*gl_, GetError()) + .WillOnce(Return(GL_NO_ERROR)) + .WillOnce(Return(GL_NO_ERROR)) + .WillOnce(Return(GL_NO_ERROR)) + .WillOnce(Return(GL_NO_ERROR)) + .RetiresOnSaturation(); + + typedef GetIntegerv::Result Result; + Result* result = static_cast<Result*>(shared_memory_address_); + GetIntegerv cmd; + result->size = 0; + EXPECT_CALL(*gl_, GetIntegerv(_, _)) + .Times(0) + .RetiresOnSaturation(); + cmd.Init( + GL_NUM_COMPRESSED_TEXTURE_FORMATS, + shared_memory_id_, shared_memory_offset_); + EXPECT_EQ(error::kNoError, ExecuteCmd(cmd)); + EXPECT_EQ(1, result->GetNumResults()); + GLint num_formats = result->GetData()[0]; + EXPECT_EQ(1, num_formats); + EXPECT_EQ(GL_NO_ERROR, GetGLError()); + + result->size = 0; + cmd.Init( + GL_COMPRESSED_TEXTURE_FORMATS, + shared_memory_id_, shared_memory_offset_); + EXPECT_EQ(error::kNoError, ExecuteCmd(cmd)); + EXPECT_EQ(num_formats, result->GetNumResults()); + + EXPECT_TRUE(ValueInArray( + GL_ETC1_RGB8_OES, + result->GetData(), result->GetNumResults())); + EXPECT_EQ(GL_NO_ERROR, GetGLError()); +} + TEST_F(GLES2DecoderWithShaderTest, GetProgramInfoCHROMIUMValidArgs) { const uint32 kBucketId = 123; GetProgramInfoCHROMIUM cmd; @@ -5331,7 +5449,7 @@ TEST_F(GLES2DecoderManualInitTest, EGLImageExternalBindTexture) { true); // bind generates resource EXPECT_CALL(*gl_, BindTexture(GL_TEXTURE_EXTERNAL_OES, kNewServiceId)); EXPECT_CALL(*gl_, GenTextures(1, _)) - .WillOnce(SetArgumentPointee<1>(kNewServiceId)); + .WillOnce(SetArgumentPointee<1>(kNewServiceId)); BindTexture cmd; cmd.Init(GL_TEXTURE_EXTERNAL_OES, kNewClientId); EXPECT_EQ(error::kNoError, ExecuteCmd(cmd)); |