1 /*------------------------------------------------------------------------- 2 * OpenGL Conformance Test Suite 3 * ----------------------------- 4 * 5 * Copyright (c) 2015-2016 The Khronos Group Inc. 6 * 7 * Licensed under the Apache License, Version 2.0 (the "License"); 8 * you may not use this file except in compliance with the License. 9 * You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, software 14 * distributed under the License is distributed on an "AS IS" BASIS, 15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 16 * See the License for the specific language governing permissions and 17 * limitations under the License. 18 * 19 */ /*! 20 * \file 21 * \brief 22 */ /*-------------------------------------------------------------------*/ 23 24 /** 25 * \file gl3cTextureSizePromotionTests.hpp 26 * \brief Implements test classes for testing of texture internal format 27 promotion mechanism. 28 */ /*-------------------------------------------------------------------*/ 29 30 #include "gl3cTextureSizePromotion.hpp" 31 32 #include "deMath.h" 33 #include "gluContextInfo.hpp" 34 #include "gluStrUtil.hpp" 35 #include "glwFunctions.hpp" 36 #include "tcuTestLog.hpp" 37 38 /* Stringify macro. */ 39 #define _STR(s) STR(s) 40 #define STR(s) #s 41 42 namespace gl3cts 43 { 44 namespace TextureSizePromotion 45 { 46 Tests::Tests(deqp::Context& context) 47 : TestCaseGroup(context, "texture_size_promotion", "Verifies texture internal format size promotion mechanism.") 48 { 49 /* Left blank on purpose */ 50 } 51 52 void Tests::init(void) 53 { 54 addChild(new TextureSizePromotion::FunctionalTest(m_context)); 55 } 56 57 /*===========================================================================================================*/ 58 59 FunctionalTest::FunctionalTest(deqp::Context& context) 60 : TestCase(context, "functional", "Verifies that texture internal format size promotion mechanism can be used.") 61 , m_vao(0) 62 , m_source_texture(0) 63 , m_destination_texture(0) 64 , m_framebuffer(0) 65 , m_program(0) 66 , m_max_samples(0) 67 { 68 /* Left blank on purpose */ 69 } 70 71 tcu::TestNode::IterateResult FunctionalTest::iterate() 72 { 73 /* Get context setup. */ 74 glu::ContextType context_type = m_context.getRenderContext().getType(); 75 bool is_arb_texture_storage_multisample = 76 m_context.getContextInfo().isExtensionSupported("GL_ARB_texture_storage_multisample"); 77 78 /* Prepare initial results. */ 79 bool is_ok = true; 80 bool was_error = false; 81 82 /* Iterate over test cases. */ 83 try 84 { 85 /* Only for OpenGL 3.1 context. */ 86 if (glu::contextSupports(context_type, glu::ApiType::core(3, 1))) 87 { 88 /* Generate and bind VAO. */ 89 prepareVertexArrayObject(); 90 91 /* For every required format */ 92 for (glw::GLuint i = 0; i < s_formats_size; ++i) 93 { 94 /* Test only if format is required by context. */ 95 if (glu::contextSupports(context_type, s_formats[i].required_by_context.getAPI())) 96 { 97 /* For every target. */ 98 for (glw::GLuint j = 0; j < s_source_texture_targets_count; ++j) 99 { 100 /* Test if it is supported by context or internal format. */ 101 if (isTargetMultisampled(s_source_texture_targets[j])) 102 { 103 if ((!is_arb_texture_storage_multisample) && 104 (!glu::contextSupports(context_type, glu::ApiType::core(4, 3)))) 105 { 106 continue; 107 } 108 109 if (!s_formats[i] 110 .is_color_renderable) /* Multisampled textures need to be set using rendering. */ 111 { 112 continue; 113 } 114 115 if (isDepthType(s_formats[i]) || isStencilType(s_formats[i])) 116 { 117 continue; 118 } 119 } 120 121 if ((isDepthType(s_formats[i]) || isStencilType(s_formats[i])) && 122 (GL_TEXTURE_3D == s_source_texture_targets[j])) 123 { 124 continue; 125 } 126 127 /* Prepare source texture to be tested. */ 128 prepareSourceTexture(s_formats[i], s_source_texture_targets[j]); 129 130 /* Check basic API queries for source texture. */ 131 is_ok = is_ok & checkSourceTextureSizeAndType(s_formats[i], s_source_texture_targets[j]); 132 133 /* For every [R, G, B, A] component. */ 134 for (glw::GLuint k = 0; k < COMPONENTS_COUNT; ++k) 135 { 136 /* Prepare destination texture. */ 137 prepareDestinationTextureAndFramebuffer(s_formats[i], GL_TEXTURE_2D); 138 139 /* Building program (throws on failure). */ 140 m_program = 141 prepareProgram(s_source_texture_targets[j], s_formats[i], ColorChannelSelector(k)); 142 143 /* Setup GL and draw. */ 144 makeProgramAndSourceTextureActive(s_source_texture_targets[j]); 145 146 drawQuad(); 147 148 /* Check results. */ 149 is_ok = is_ok & checkDestinationTexture(s_formats[i], ColorChannelSelector(k), 150 s_source_texture_targets[j], 151 s_source_texture_targets_names[j]); 152 153 /* Cleanup. */ 154 cleanDestinationTexture(); 155 cleanFramebuffer(); 156 cleanProgram(); 157 } 158 159 cleanSourceTexture(); 160 } 161 } 162 } 163 } 164 } 165 catch (...) 166 { 167 /* Error have occured. */ 168 is_ok = false; 169 was_error = true; 170 } 171 172 /* Clean all. */ 173 174 cleanSourceTexture(); 175 cleanDestinationTexture(); 176 cleanFramebuffer(); 177 cleanProgram(); 178 cleanVertexArrayObject(); 179 180 /* Result's setup. */ 181 if (is_ok) 182 { 183 /* Log success. */ 184 m_context.getTestContext().getLog() << tcu::TestLog::Message << "Texture Size Promotion Test have passed." 185 << tcu::TestLog::EndMessage; 186 187 m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass"); 188 } 189 else 190 { 191 if (was_error) 192 { 193 /* Log error. */ 194 m_context.getTestContext().getLog() << tcu::TestLog::Message 195 << "Texture Size Promotion Test have approached error." 196 << tcu::TestLog::EndMessage; 197 198 m_testCtx.setTestResult(QP_TEST_RESULT_INTERNAL_ERROR, "Error"); 199 } 200 else 201 { 202 /* Log fail. */ 203 m_context.getTestContext().getLog() << tcu::TestLog::Message << "Texture Size Promotion Test have failed." 204 << tcu::TestLog::EndMessage; 205 206 m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail"); 207 } 208 } 209 210 /* End test. */ 211 return tcu::TestNode::STOP; 212 } 213 214 void FunctionalTest::prepareVertexArrayObject() 215 { 216 /* GL functions object. */ 217 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 218 219 gl.genVertexArrays(1, &m_vao); 220 GLU_EXPECT_NO_ERROR(gl.getError(), "glGenVertexArrays have failed"); 221 222 gl.bindVertexArray(m_vao); 223 GLU_EXPECT_NO_ERROR(gl.getError(), "glBindVertexArray have failed"); 224 } 225 226 void FunctionalTest::prepareSourceTexture(TextureInternalFormatDescriptor descriptor, glw::GLenum target) 227 { 228 /* GL functions object. */ 229 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 230 231 /* Create and bind texture object. */ 232 gl.genTextures(1, &m_source_texture); 233 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 234 235 gl.bindTexture(target, m_source_texture); 236 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 237 238 /* Select proper data set. */ 239 glw::GLvoid* source_data = DE_NULL; 240 glw::GLenum source_type = GL_NONE; 241 glw::GLenum source_format = GL_RGBA; 242 243 if (isFloatType(descriptor)) /* For floating type. */ 244 { 245 source_data = (glw::GLvoid*)s_source_texture_data_f; 246 source_type = GL_FLOAT; 247 source_format = GL_RGBA; 248 } 249 else 250 { 251 if (isFixedSignedType(descriptor)) /* For fixed signed type. */ 252 { 253 source_data = (glw::GLvoid*)s_source_texture_data_sn; 254 source_type = GL_FLOAT; 255 source_format = GL_RGBA; 256 } 257 else 258 { 259 if (isFixedUnsignedType(descriptor)) /* For fixed unsigned type. */ 260 { 261 source_data = (glw::GLvoid*)s_source_texture_data_n; 262 source_type = GL_FLOAT; 263 source_format = GL_RGBA; 264 } 265 else 266 { 267 if (isIntegerSignedType(descriptor)) /* For integral signed type. */ 268 { 269 source_data = (glw::GLvoid*)s_source_texture_data_i; 270 source_type = GL_INT; 271 source_format = GL_RGBA_INTEGER; 272 } 273 else 274 { 275 if (isIntegerUnsignedType(descriptor)) /* For integral unsigned type. */ 276 { 277 source_data = (glw::GLvoid*)s_source_texture_data_ui; 278 source_type = GL_UNSIGNED_INT; 279 source_format = GL_RGBA_INTEGER; 280 } 281 else 282 { 283 if (isDepthType(descriptor)) /* For depth type. */ 284 { 285 source_data = NULL; 286 source_type = GL_UNSIGNED_INT; 287 source_format = GL_DEPTH_COMPONENT; 288 } 289 else 290 { 291 if (isStencilType(descriptor)) /* For stencil type. */ 292 { 293 source_data = NULL; 294 source_type = GL_UNSIGNED_INT; 295 source_format = GL_STENCIL_INDEX; 296 } 297 } 298 } 299 } 300 } 301 } 302 } 303 304 /* Prepare texture storage depending on the target. */ 305 switch (target) 306 { 307 case GL_TEXTURE_1D: 308 gl.texImage1D(target, 0, descriptor.internal_format, s_source_texture_size, 0, source_format, source_type, 309 source_data); 310 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 311 break; 312 case GL_TEXTURE_1D_ARRAY: 313 case GL_TEXTURE_2D: 314 case GL_TEXTURE_RECTANGLE: 315 gl.texImage2D(target, 0, descriptor.internal_format, s_source_texture_size, s_source_texture_size, 0, 316 source_format, source_type, source_data); 317 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 318 break; 319 case GL_TEXTURE_2D_ARRAY: 320 case GL_TEXTURE_3D: 321 gl.texImage3D(target, 0, descriptor.internal_format, s_source_texture_size, s_source_texture_size, 322 s_source_texture_size, 0, source_format, source_type, source_data); 323 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 324 break; 325 case GL_TEXTURE_2D_MULTISAMPLE: 326 case GL_TEXTURE_2D_MULTISAMPLE_ARRAY: 327 renderDataIntoMultisampledTexture(descriptor, target); 328 break; 329 default: 330 throw 0; 331 } 332 } 333 334 void FunctionalTest::renderDataIntoMultisampledTexture(TextureInternalFormatDescriptor descriptor, glw::GLenum target) 335 { 336 /* GL functions object. */ 337 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 338 339 /* Fetch limits. */ 340 gl.getIntegerv(GL_MAX_SAMPLES, &m_max_samples); 341 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetIntegerv have failed"); 342 343 if (m_max_samples == 0) 344 { 345 m_max_samples = 1; 346 } 347 348 /* Setup target. */ 349 glw::GLenum non_ms_target = (target == GL_TEXTURE_2D_MULTISAMPLE) ? GL_TEXTURE_2D : GL_TEXTURE_2D_ARRAY; 350 351 /* Cleanup required by prepareSourceTexture(...). */ 352 cleanSourceTexture(); 353 354 /* Prepare textures and program. */ 355 prepareSourceTexture(descriptor, non_ms_target); 356 357 prepareDestinationTextureAndFramebuffer(descriptor, target); 358 359 m_program = prepareProgram(non_ms_target, descriptor, COMPONENTS_COUNT); 360 361 /* Setup GL and render texture. */ 362 makeProgramAndSourceTextureActive(non_ms_target); 363 364 drawQuad(); 365 366 /* Cleanup. */ 367 cleanFramebuffer(); 368 cleanSourceTexture(); 369 370 /* Swpaing destination texture to source texture. */ 371 m_source_texture = m_destination_texture; 372 373 m_destination_texture = 0; 374 375 /* Clean program. */ 376 cleanProgram(); 377 } 378 379 void FunctionalTest::prepareDestinationTextureAndFramebuffer(TextureInternalFormatDescriptor descriptor, 380 glw::GLenum target) 381 { 382 /* GL functions object. */ 383 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 384 385 /* Get internal format. */ 386 glw::GLenum internal_format = getDestinationFormatForChannel(descriptor); 387 388 /* Create framebuffer object. */ 389 gl.genFramebuffers(1, &m_framebuffer); 390 GLU_EXPECT_NO_ERROR(gl.getError(), "glGenFramebuffers call failed."); 391 392 gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffer); 393 GLU_EXPECT_NO_ERROR(gl.getError(), "glBindFramebuffer call failed."); 394 395 /* Create framebuffer's destination texture. */ 396 gl.genTextures(1, &m_destination_texture); 397 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 398 399 gl.bindTexture(target, m_destination_texture); 400 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 401 402 /* Allocate texture storage and upload data for test rendering. */ 403 if (target == GL_TEXTURE_2D) 404 { 405 glw::GLenum destination_format = GL_RED; 406 glw::GLenum destination_type = GL_FLOAT; 407 glw::GLvoid* destination_data = (glw::GLvoid*)s_destination_texture_data_f; 408 409 if (isIntegerSignedType(descriptor)) 410 { 411 destination_format = GL_RED_INTEGER; 412 destination_type = GL_INT; 413 destination_data = (glw::GLvoid*)s_destination_texture_data_i; 414 } 415 416 if (isIntegerUnsignedType(descriptor)) 417 { 418 destination_format = GL_RED_INTEGER; 419 destination_type = GL_UNSIGNED_INT; 420 destination_data = (glw::GLvoid*)s_destination_texture_data_ui; 421 } 422 423 gl.texImage2D(target, 0, internal_format, s_source_texture_size, s_source_texture_size, 0, destination_format, 424 destination_type, destination_data); 425 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 426 427 gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, m_destination_texture, 0); 428 GLU_EXPECT_NO_ERROR(gl.getError(), "glFramebufferTexture2D have failed"); 429 } 430 else /* Allocate texture storage for uploading datat for multisampled targets (upload must be done via shader). */ 431 { 432 if (target == GL_TEXTURE_2D_MULTISAMPLE) 433 { 434 gl.texImage2DMultisample(target, m_max_samples - 1, descriptor.internal_format, s_source_texture_size, 435 s_source_texture_size, GL_TRUE); 436 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 437 438 gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, target, m_destination_texture, 0); 439 GLU_EXPECT_NO_ERROR(gl.getError(), "glFramebufferTexture2D have failed"); 440 } 441 else 442 { 443 gl.texImage3DMultisample(target, m_max_samples - 1, descriptor.internal_format, s_source_texture_size, 444 s_source_texture_size, s_source_texture_size, GL_TRUE); 445 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 446 447 gl.framebufferTextureLayer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, m_destination_texture, 0, 0); 448 GLU_EXPECT_NO_ERROR(gl.getError(), "glFramebufferTexture2D have failed"); 449 } 450 } 451 452 /* Check framebuffer completness. */ 453 if (gl.checkFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) 454 { 455 throw 0; 456 } 457 458 /* Setup viewport. */ 459 gl.viewport(0, 0, s_source_texture_size, s_source_texture_size); 460 GLU_EXPECT_NO_ERROR(gl.getError(), "glViewport call failed."); 461 } 462 463 void FunctionalTest::makeProgramAndSourceTextureActive(glw::GLenum target) 464 { 465 /* GL functions object. */ 466 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 467 468 /* Use GLSL program. */ 469 gl.useProgram(m_program); 470 GLU_EXPECT_NO_ERROR(gl.getError(), "glUseProgram have failed"); 471 472 /* Setup source texture. */ 473 gl.activeTexture(GL_TEXTURE0); 474 GLU_EXPECT_NO_ERROR(gl.getError(), "glActiveTexture have failed"); 475 476 gl.bindTexture(target, m_source_texture); 477 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 478 479 glw::GLint location = gl.getUniformLocation(m_program, "data"); 480 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetUniformLocation have failed"); 481 482 gl.uniform1i(location, 0); 483 GLU_EXPECT_NO_ERROR(gl.getError(), "glUniform1i have failed"); 484 } 485 486 bool FunctionalTest::checkSourceTextureSizeAndType(TextureInternalFormatDescriptor descriptor, glw::GLenum target) 487 { 488 /* GL functions object. */ 489 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 490 491 /* query result storage */ 492 glw::GLint red_size = 0; 493 glw::GLint blue_size = 0; 494 glw::GLint green_size = 0; 495 glw::GLint alpha_size = 0; 496 glw::GLint depth_size = 0; 497 glw::GLint stencil_size = 0; 498 499 glw::GLint red_type = 0; 500 glw::GLint green_type = 0; 501 glw::GLint blue_type = 0; 502 glw::GLint alpha_type = 0; 503 glw::GLint depth_type = 0; 504 505 /* Bind texture */ 506 gl.bindTexture(target, m_source_texture); 507 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 508 509 /* queries */ 510 gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_RED_SIZE, &red_size); 511 gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_GREEN_SIZE, &green_size); 512 gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_BLUE_SIZE, &blue_size); 513 gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_ALPHA_SIZE, &alpha_size); 514 gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_DEPTH_SIZE, &depth_size); 515 gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_STENCIL_SIZE, &stencil_size); 516 517 gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_RED_TYPE, &red_type); 518 gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_GREEN_TYPE, &green_type); 519 gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_BLUE_TYPE, &blue_type); 520 gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_ALPHA_TYPE, &alpha_type); 521 gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_DEPTH_TYPE, &depth_type); 522 523 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetTexLevelParameteriv have failed"); 524 525 /* check expected values */ 526 bool is_ok = true; 527 528 is_ok = is_ok && (red_size >= descriptor.min_red_size); 529 is_ok = is_ok && (green_size >= descriptor.min_green_size); 530 is_ok = is_ok && (blue_size >= descriptor.min_blue_size); 531 is_ok = is_ok && (alpha_size >= descriptor.min_alpha_size); 532 is_ok = is_ok && (depth_size >= descriptor.min_depth_size); 533 is_ok = is_ok && (stencil_size >= descriptor.min_stencil_size); 534 535 is_ok = is_ok && ((glw::GLenum)red_type == descriptor.expected_red_type); 536 is_ok = is_ok && ((glw::GLenum)green_type == descriptor.expected_green_type); 537 is_ok = is_ok && ((glw::GLenum)blue_type == descriptor.expected_blue_type); 538 is_ok = is_ok && ((glw::GLenum)alpha_type == descriptor.expected_alpha_type); 539 is_ok = is_ok && ((glw::GLenum)depth_type == descriptor.expected_depth_type); 540 541 /* Log on failure. */ 542 if (!is_ok) 543 { 544 m_context.getTestContext().getLog() 545 << tcu::TestLog::Message << "Promotion from internal format " << descriptor.internal_format_name 546 << " have failed during glGetTexLevelParameteriv query. " 547 << "Expected red size = " << descriptor.min_red_size 548 << ", expected green size = " << descriptor.min_green_size 549 << ", expected blue size = " << descriptor.min_blue_size 550 << ", expected alpha size = " << descriptor.min_alpha_size 551 << ", expected depth size = " << descriptor.min_depth_size 552 << ", expected stencil size = " << descriptor.min_stencil_size << ". Queried red size = " << red_size 553 << ", queried green size = " << green_size << ", queried blue size = " << blue_size 554 << ", queried alpha size = " << alpha_size << ", queried depth size = " << depth_size 555 << ", queried stencil size = " << stencil_size << ". " 556 << "Expected red type = " << glu::getTypeStr(descriptor.expected_red_type) 557 << ", expected green type = " << glu::getTypeStr(descriptor.expected_green_type) 558 << ", expected blue type = " << glu::getTypeStr(descriptor.expected_blue_type) 559 << ", expected alpha type = " << glu::getTypeStr(descriptor.expected_alpha_type) 560 << ", expected depth type = " << glu::getTypeStr(descriptor.expected_depth_type) 561 << ". Queried red type = " << glu::getTypeStr(red_type) 562 << ", queried green type = " << glu::getTypeStr(green_type) 563 << ", queried blue type = " << glu::getTypeStr(blue_type) 564 << ", queried alpha type = " << glu::getTypeStr(alpha_type) 565 << ", queried depth type = " << glu::getTypeStr(depth_type) << "." << tcu::TestLog::EndMessage; 566 } 567 568 /* return results. */ 569 return is_ok; 570 } 571 572 glw::GLenum FunctionalTest::getDestinationFormatForChannel(TextureInternalFormatDescriptor descriptor) 573 { 574 if (isFloatType(descriptor)) 575 { 576 return GL_R32F; 577 } 578 579 if (isFixedUnsignedType(descriptor)) 580 { 581 return GL_R16; 582 } 583 584 if (isFixedSignedType(descriptor)) 585 { 586 return GL_R16_SNORM; 587 } 588 589 if (isIntegerUnsignedType(descriptor)) 590 { 591 return GL_R32UI; 592 } 593 594 if (isIntegerSignedType(descriptor)) 595 { 596 return GL_R32I; 597 } 598 599 return GL_R32F; 600 } 601 602 glw::GLuint FunctionalTest::prepareProgram(glw::GLenum target, TextureInternalFormatDescriptor descriptor, 603 ColorChannelSelector channel) 604 { 605 /* GL functions object. */ 606 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 607 608 /* Preparing sampler name and textelFetch arguments */ 609 std::string sampler_name = ""; 610 std::string texel_fetch_arguments_tail = ""; 611 612 switch (target) 613 { 614 case GL_TEXTURE_1D: 615 sampler_name = "sampler1D"; 616 texel_fetch_arguments_tail = "0, 0"; 617 break; 618 case GL_TEXTURE_2D: 619 sampler_name = "sampler2D"; 620 texel_fetch_arguments_tail = "ivec2(0), 0"; 621 break; 622 case GL_TEXTURE_1D_ARRAY: 623 sampler_name = "sampler1DArray"; 624 texel_fetch_arguments_tail = "ivec2(0), 0"; 625 break; 626 case GL_TEXTURE_RECTANGLE: 627 sampler_name = "sampler2DRect"; 628 texel_fetch_arguments_tail = "ivec2(0)"; 629 break; 630 case GL_TEXTURE_2D_ARRAY: 631 sampler_name = "sampler2DArray"; 632 texel_fetch_arguments_tail = "ivec3(0), 0"; 633 break; 634 case GL_TEXTURE_3D: 635 sampler_name = "sampler3D"; 636 texel_fetch_arguments_tail = "ivec3(0), 0"; 637 break; 638 case GL_TEXTURE_2D_MULTISAMPLE: 639 sampler_name = "sampler2DMS"; 640 texel_fetch_arguments_tail = "ivec2(0), "; 641 texel_fetch_arguments_tail.append(Utilities::itoa(m_max_samples - 1)); 642 break; 643 case GL_TEXTURE_2D_MULTISAMPLE_ARRAY: 644 sampler_name = "sampler2DMSArray"; 645 texel_fetch_arguments_tail = "ivec3(0), "; 646 texel_fetch_arguments_tail.append(Utilities::itoa(m_max_samples - 1)); 647 break; 648 default: 649 throw 0; 650 } 651 652 /* Preparing component selector name */ 653 std::string component_name = ""; 654 655 switch (channel) 656 { 657 case RED_COMPONENT: 658 component_name = ".r"; 659 break; 660 case GREEN_COMPONENT: 661 component_name = ".g"; 662 break; 663 case BLUE_COMPONENT: 664 component_name = ".b"; 665 break; 666 case ALPHA_COMPONENT: 667 component_name = ".a"; 668 break; 669 case COMPONENTS_COUNT: 670 break; 671 default: 672 throw 0; 673 } 674 675 /* Preparing output type name and sampler prefix */ 676 std::string type_name = ""; 677 std::string sampler_prefix = ""; 678 679 if (isFloatType(descriptor) || isFixedSignedType(descriptor) || isFixedUnsignedType(descriptor) || 680 isDepthType(descriptor) || isStencilType(descriptor)) 681 { 682 if (channel == COMPONENTS_COUNT) 683 { 684 type_name = "vec4"; 685 } 686 else 687 { 688 type_name = "float"; 689 } 690 sampler_prefix = ""; 691 } 692 else 693 { 694 if (isIntegerSignedType(descriptor)) 695 { 696 if (channel == COMPONENTS_COUNT) 697 { 698 type_name = "ivec4"; 699 } 700 else 701 { 702 type_name = "int"; 703 } 704 sampler_prefix = "i"; 705 } 706 else 707 { 708 if (channel == COMPONENTS_COUNT) 709 { 710 type_name = "uvec4"; 711 } 712 else 713 { 714 type_name = "uint"; 715 } 716 sampler_prefix = "u"; 717 } 718 } 719 720 std::string template_verison = "#version 150"; 721 722 /* Preprocessing fragment shader source code. */ 723 std::string fragment_shader = s_fragment_shader_template; 724 725 fragment_shader = Utilities::preprocessString(fragment_shader, "TEMPLATE_TYPE", type_name); 726 fragment_shader = 727 Utilities::preprocessString(fragment_shader, "TEMPLATE_SAMPLER", sampler_prefix.append(sampler_name)); 728 fragment_shader = 729 Utilities::preprocessString(fragment_shader, "TEMPLATE_TEXEL_FETCH_ARGUMENTS", texel_fetch_arguments_tail); 730 fragment_shader = Utilities::preprocessString(fragment_shader, "TEMPLATE_COMPONENT", component_name); 731 732 /* Building program. */ 733 glw::GLuint program = 734 Utilities::buildProgram(gl, m_context.getTestContext().getLog(), s_vertex_shader_code, fragment_shader.c_str()); 735 736 if (0 == program) 737 { 738 throw 0; 739 } 740 741 /* Return program name. */ 742 return program; 743 } 744 745 void FunctionalTest::drawQuad() 746 { 747 /* GL functions object. */ 748 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 749 750 /* Draw quad. */ 751 gl.drawArrays(GL_TRIANGLE_STRIP, 0, 4); 752 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays have failed"); 753 } 754 755 void FunctionalTest::cleanSourceTexture() 756 { 757 /* GL functions object. */ 758 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 759 760 /* Delete object. */ 761 if (m_source_texture) 762 { 763 gl.deleteTextures(1, &m_source_texture); 764 GLU_EXPECT_NO_ERROR(gl.getError(), "glDeleteTextures have failed"); 765 766 m_source_texture = 0; 767 } 768 } 769 770 void FunctionalTest::cleanDestinationTexture() 771 { 772 /* GL functions object. */ 773 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 774 775 /* Delete object. */ 776 if (m_destination_texture) 777 { 778 gl.deleteTextures(1, &m_destination_texture); 779 780 m_destination_texture = 0; 781 } 782 } 783 784 void FunctionalTest::cleanFramebuffer() 785 { 786 /* GL functions object. */ 787 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 788 789 /* Delete object. */ 790 if (m_framebuffer) 791 { 792 gl.deleteFramebuffers(1, &m_framebuffer); 793 794 m_framebuffer = 0; 795 } 796 } 797 798 void FunctionalTest::cleanProgram() 799 { 800 /* GL functions object. */ 801 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 802 803 /* Delete object. */ 804 if (m_program) 805 { 806 gl.useProgram(0); 807 808 gl.deleteProgram(m_program); 809 810 m_program = 0; 811 } 812 } 813 814 void FunctionalTest::cleanVertexArrayObject() 815 { 816 /* GL functions object. */ 817 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 818 819 /* Delete object. */ 820 if (m_vao) 821 { 822 gl.deleteVertexArrays(1, &m_vao); 823 824 m_vao = 0; 825 } 826 } 827 828 bool FunctionalTest::checkDestinationTexture(TextureInternalFormatDescriptor descriptor, ColorChannelSelector channel, 829 glw::GLenum target, const glw::GLchar* target_name) 830 { 831 /* GL functions object. */ 832 const glw::Functions& gl = m_context.getRenderContext().getFunctions(); 833 834 /* Check depending on format. */ 835 if (isFloatType(descriptor) || isDepthType(descriptor) || isStencilType(descriptor)) 836 { 837 /* Fetch results from destination texture (attached to current framebuffer). */ 838 glw::GLfloat pixel = 3.1415927f; 839 gl.readPixels(0, 0, 1, 1, GL_RED, GL_FLOAT, &pixel); 840 GLU_EXPECT_NO_ERROR(gl.getError(), "glReadPixels have failed"); 841 842 /* Setup expected value. */ 843 glw::GLfloat expected_value = isChannelTypeNone(descriptor, channel) ? 844 ((channel == ALPHA_COMPONENT) ? 1.f : 0.f) : 845 s_source_texture_data_f[channel]; 846 847 /* Compare expected and fetched values. */ 848 if (fabs(pixel - expected_value) <= getMinPrecision(descriptor, channel)) 849 { 850 /* Test succeeded*/ 851 return true; 852 } 853 else 854 { 855 /* Log failure. */ 856 m_context.getTestContext().getLog() 857 << tcu::TestLog::Message << "Promotion from internal format " << descriptor.internal_format_name 858 << " have failed during functional test of " << s_color_channel_names[channel] 859 << " channel with target " << target_name << ". Expected value = " << expected_value 860 << " read value = " << pixel << "." << tcu::TestLog::EndMessage; 861 } 862 } 863 else 864 { 865 if (isFixedSignedType(descriptor)) 866 { 867 /* Fetch results from destination texture (attached to current framebuffer). */ 868 glw::GLfloat pixel = 3.1415927f; 869 gl.readPixels(0, 0, 1, 1, GL_RED, GL_FLOAT, &pixel); 870 GLU_EXPECT_NO_ERROR(gl.getError(), "glReadPixels have failed"); 871 872 /* Setup expected value. */ 873 /* Signed fixed-point read color are clamped to [0, 1] by default */ 874 glw::GLfloat expected_value = isChannelTypeNone(descriptor, channel) ? 875 ((channel == ALPHA_COMPONENT) ? 1.f : 0.f) : 876 deFloatClamp(s_source_texture_data_sn[channel], 0, 1); 877 878 /* Compare expected and fetched values. */ 879 if (fabs(pixel - expected_value) <= getMinPrecision(descriptor, channel)) 880 { 881 /* Test succeeded*/ 882 return true; 883 } 884 else 885 { 886 /* Log failure. */ 887 m_context.getTestContext().getLog() 888 << tcu::TestLog::Message << "Promotion from internal format " << descriptor.internal_format_name 889 << " have failed during functional test of " << s_color_channel_names[channel] 890 << " channel with target " << target_name << ". Expected value = " << expected_value 891 << " read value = " << pixel << "." << tcu::TestLog::EndMessage; 892 } 893 } 894 else 895 { 896 if (isFixedUnsignedType(descriptor)) 897 { 898 /* Fetch results from destination texture (attached to current framebuffer). */ 899 glw::GLfloat pixel = 3.1415927f; 900 gl.readPixels(0, 0, 1, 1, GL_RED, GL_FLOAT, &pixel); 901 GLU_EXPECT_NO_ERROR(gl.getError(), "glReadPixels have failed"); 902 903 /* Setup expected value. */ 904 glw::GLfloat expected_value = isChannelTypeNone(descriptor, channel) ? 905 ((channel == ALPHA_COMPONENT) ? 1.f : 0.f) : 906 s_source_texture_data_n[channel]; 907 908 /* For sRGB internal formats convert value to linear space. */ 909 if (descriptor.is_sRGB && (channel < ALPHA_COMPONENT)) 910 { 911 expected_value = convert_from_sRGB(expected_value); 912 913 if (isTargetMultisampled( 914 target)) /* In multisampled targets two conversions are made (in upload and in shader) */ 915 { 916 expected_value = convert_from_sRGB(expected_value); 917 } 918 } 919 920 /* Compare expected and fetched values. */ 921 if (fabs(pixel - expected_value) <= getMinPrecision(descriptor, channel)) 922 { 923 /* Test succeeded*/ 924 return true; 925 } 926 else 927 { 928 /* Log failure. */ 929 m_context.getTestContext().getLog() 930 << tcu::TestLog::Message << "Promotion from internal format " << descriptor.internal_format_name 931 << " have failed during functional test of " << s_color_channel_names[channel] 932 << " channel with target " << target_name << ". Expected value = " << expected_value 933 << " read value = " << pixel << "." << tcu::TestLog::EndMessage; 934 } 935 } 936 else 937 { 938 if (isIntegerSignedType(descriptor)) 939 { 940 /* Fetch results from destination texture (attached to current framebuffer). */ 941 glw::GLint pixel = 5; 942 gl.readPixels(0, 0, 1, 1, GL_RED_INTEGER, GL_INT, &pixel); 943 GLU_EXPECT_NO_ERROR(gl.getError(), "glReadPixels have failed"); 944 945 /* Setup expected value. */ 946 glw::GLint expected_value = isChannelTypeNone(descriptor, channel) ? 947 ((channel == ALPHA_COMPONENT) ? 1 : 0) : 948 s_source_texture_data_i[channel]; 949 950 /* Compare expected and fetched values. */ 951 if (pixel == expected_value) 952 { 953 /* Test succeeded*/ 954 return true; 955 } 956 else 957 { 958 /* Log failure. */ 959 m_context.getTestContext().getLog() 960 << tcu::TestLog::Message << "Promotion from internal format " 961 << descriptor.internal_format_name << " have failed during functional test of " 962 << s_color_channel_names[channel] << " channel with target " << target_name 963 << ". Expected value = " << expected_value << " read value = " << pixel << "." 964 << tcu::TestLog::EndMessage; 965 } 966 } 967 else 968 { 969 if (isIntegerUnsignedType(descriptor)) 970 { 971 /* Fetch results from destination texture (attached to current framebuffer). */ 972 glw::GLuint pixel = 5; 973 gl.readPixels(0, 0, 1, 1, GL_RED_INTEGER, GL_UNSIGNED_INT, &pixel); 974 GLU_EXPECT_NO_ERROR(gl.getError(), "glReadPixels have failed"); 975 976 /* Setup expected value. */ 977 glw::GLuint expected_value = isChannelTypeNone(descriptor, channel) ? 978 ((channel == ALPHA_COMPONENT) ? 1 : 0) : 979 s_source_texture_data_ui[channel]; 980 981 /* Compare expected and fetched values. */ 982 if (pixel == expected_value) 983 { 984 /* Test succeeded*/ 985 return true; 986 } 987 else 988 { 989 /* Log failure. */ 990 m_context.getTestContext().getLog() 991 << tcu::TestLog::Message << "Promotion from internal format " 992 << descriptor.internal_format_name << " have failed during functional test of " 993 << s_color_channel_names[channel] << " channel with target " << target_name 994 << ". Expected value = " << expected_value << " read value = " << pixel << "." 995 << tcu::TestLog::EndMessage; 996 } 997 } 998 } 999 } 1000 } 1001 } 1002 1003 /* Test failed. */ 1004 return false; 1005 } 1006 1007 bool FunctionalTest::isFloatType(TextureInternalFormatDescriptor descriptor) 1008 { 1009 return (GL_FLOAT == descriptor.expected_red_type) || (GL_FLOAT == descriptor.expected_green_type) || 1010 (GL_FLOAT == descriptor.expected_blue_type) || (GL_FLOAT == descriptor.expected_alpha_type); 1011 } 1012 1013 bool FunctionalTest::isFixedSignedType(TextureInternalFormatDescriptor descriptor) 1014 { 1015 return (GL_SIGNED_NORMALIZED == descriptor.expected_red_type) || 1016 (GL_SIGNED_NORMALIZED == descriptor.expected_green_type) || 1017 (GL_SIGNED_NORMALIZED == descriptor.expected_blue_type) || 1018 (GL_SIGNED_NORMALIZED == descriptor.expected_alpha_type); 1019 } 1020 1021 bool FunctionalTest::isFixedUnsignedType(TextureInternalFormatDescriptor descriptor) 1022 { 1023 return (GL_UNSIGNED_NORMALIZED == descriptor.expected_red_type) || 1024 (GL_UNSIGNED_NORMALIZED == descriptor.expected_green_type) || 1025 (GL_UNSIGNED_NORMALIZED == descriptor.expected_blue_type) || 1026 (GL_UNSIGNED_NORMALIZED == descriptor.expected_alpha_type); 1027 } 1028 1029 bool FunctionalTest::isIntegerSignedType(TextureInternalFormatDescriptor descriptor) 1030 { 1031 return (GL_INT == descriptor.expected_red_type) || (GL_INT == descriptor.expected_green_type) || 1032 (GL_INT == descriptor.expected_blue_type) || (GL_INT == descriptor.expected_alpha_type); 1033 } 1034 1035 bool FunctionalTest::isIntegerUnsignedType(TextureInternalFormatDescriptor descriptor) 1036 { 1037 return (GL_UNSIGNED_INT == descriptor.expected_red_type) || (GL_UNSIGNED_INT == descriptor.expected_green_type) || 1038 (GL_UNSIGNED_INT == descriptor.expected_blue_type) || (GL_UNSIGNED_INT == descriptor.expected_alpha_type); 1039 } 1040 1041 bool FunctionalTest::isDepthType(TextureInternalFormatDescriptor descriptor) 1042 { 1043 return (GL_NONE != descriptor.expected_depth_type); 1044 } 1045 1046 bool FunctionalTest::isStencilType(TextureInternalFormatDescriptor descriptor) 1047 { 1048 return (descriptor.min_stencil_size > 0); 1049 } 1050 1051 bool FunctionalTest::isChannelTypeNone(TextureInternalFormatDescriptor descriptor, ColorChannelSelector channel) 1052 { 1053 switch (channel) 1054 { 1055 case RED_COMPONENT: 1056 return (GL_NONE == descriptor.expected_red_type); 1057 case GREEN_COMPONENT: 1058 return (GL_NONE == descriptor.expected_green_type); 1059 case BLUE_COMPONENT: 1060 return (GL_NONE == descriptor.expected_blue_type); 1061 case ALPHA_COMPONENT: 1062 return (GL_NONE == descriptor.expected_alpha_type); 1063 default: 1064 throw 0; 1065 } 1066 1067 return false; 1068 } 1069 1070 glw::GLfloat FunctionalTest::getMinPrecision(TextureInternalFormatDescriptor descriptor, ColorChannelSelector channel) 1071 { 1072 /* Select channel data. */ 1073 glw::GLenum type = GL_NONE; 1074 glw::GLuint size = 0; 1075 1076 switch (channel) 1077 { 1078 case RED_COMPONENT: 1079 type = descriptor.expected_red_type; 1080 size = descriptor.min_red_size; 1081 break; 1082 case GREEN_COMPONENT: 1083 type = descriptor.expected_green_type; 1084 size = descriptor.min_green_size; 1085 break; 1086 case BLUE_COMPONENT: 1087 type = descriptor.expected_blue_type; 1088 size = descriptor.min_blue_size; 1089 break; 1090 case ALPHA_COMPONENT: 1091 type = descriptor.expected_alpha_type; 1092 size = descriptor.min_alpha_size; 1093 break; 1094 default: 1095 throw 0; 1096 } 1097 1098 /* If it is empty channel. */ 1099 if ((type == GL_NONE) || (size == 0)) 1100 { 1101 return 0.1f; 1102 } 1103 1104 /* If float type. */ 1105 if (isFloatType(descriptor)) 1106 { 1107 switch (size) 1108 { 1109 case 32: 1110 return 0.00001f; /* specification GL4.5 core constant */ 1111 case 16: 1112 return 1.f / 1024.f; /* specification GL4.5 core 10 bit mantisa constant */ 1113 case 11: 1114 return 1.f / 64.f; /* specification GL4.5 core 6 bit mantisa constant */ 1115 case 10: 1116 return 1.f / 32.f; /* specification GL4.5 core 5 bit mantisa constant */ 1117 default: 1118 return 0.00001f; 1119 } 1120 } 1121 1122 /* Fixed types precision */ 1123 if (isFixedSignedType(descriptor)) 1124 { 1125 return (float)(1.0 / pow(2.0, (double)(size - 1 /* sign bit */))); 1126 } 1127 1128 if (isFixedUnsignedType(descriptor)) 1129 { 1130 return (float)(1.0 / pow(2.0, (double)(size))); 1131 } 1132 1133 /* other aka (unsigned) integer */ 1134 return 1; 1135 } 1136 1137 bool FunctionalTest::isTargetMultisampled(glw::GLenum target) 1138 { 1139 return (GL_TEXTURE_2D_MULTISAMPLE == target) || (GL_TEXTURE_2D_MULTISAMPLE_ARRAY == target); 1140 } 1141 1142 float FunctionalTest::convert_from_sRGB(float value) 1143 { 1144 /* For reference check OpenGL specification (eg. OpenGL 4.5 core profile specification chapter 8.24 */ 1145 if (value > 0.04045f) 1146 { 1147 return deFloatPow((value + 0.055f) / 1.055f, 2.4f); 1148 } 1149 1150 return value / 12.92f; 1151 } 1152 1153 const glw::GLfloat FunctionalTest::s_source_texture_data_f[] = { 0.125f, 0.25f, 0.5f, 0.75f }; 1154 1155 const glw::GLfloat FunctionalTest::s_source_texture_data_n[] = { 0.125f, 0.25f, 0.5f, 0.75f }; 1156 1157 const glw::GLfloat FunctionalTest::s_source_texture_data_sn[] = { -0.125f, 0.25f, -0.5f, 0.75f }; 1158 1159 const glw::GLint FunctionalTest::s_source_texture_data_i[] = { -1, 2, -3, 4 }; 1160 1161 const glw::GLuint FunctionalTest::s_source_texture_data_ui[] = { 4, 3, 2, 1 }; 1162 1163 const glw::GLfloat FunctionalTest::s_destination_texture_data_f[] = { 1164 5.f 1165 }; /* False data for destination texture to be overwriten. */ 1166 1167 const glw::GLint FunctionalTest::s_destination_texture_data_i[] = { 1168 -5 1169 }; /* False data for destination texture to be overwriten. */ 1170 1171 const glw::GLuint FunctionalTest::s_destination_texture_data_ui[] = { 1172 5 1173 }; /* False data for destination texture to be overwriten. */ 1174 1175 const glw::GLenum FunctionalTest::s_source_texture_targets[] = { 1176 GL_TEXTURE_1D, GL_TEXTURE_2D, GL_TEXTURE_1D_ARRAY, GL_TEXTURE_RECTANGLE, 1177 GL_TEXTURE_2D_ARRAY, GL_TEXTURE_3D, GL_TEXTURE_2D_MULTISAMPLE, GL_TEXTURE_2D_MULTISAMPLE_ARRAY 1178 }; 1179 1180 const glw::GLchar* FunctionalTest::s_source_texture_targets_names[] = { 1181 STR(GL_TEXTURE_1D), STR(GL_TEXTURE_2D), STR(GL_TEXTURE_1D_ARRAY), STR(GL_TEXTURE_RECTANGLE), 1182 STR(GL_TEXTURE_2D_ARRAY), STR(GL_TEXTURE_3D), STR(GL_TEXTURE_2D_MULTISAMPLE), STR(GL_TEXTURE_2D_MULTISAMPLE_ARRAY) 1183 }; 1184 1185 const glw::GLuint FunctionalTest::s_source_texture_targets_count = 1186 sizeof(s_source_texture_targets) / sizeof(s_source_texture_targets[0]); 1187 1188 const glw::GLuint FunctionalTest::s_source_texture_size = 1; 1189 1190 const glw::GLchar* FunctionalTest::s_color_channel_names[] = { "red", "green", "blue", "alpha", "all" }; 1191 1192 const FunctionalTest::TextureInternalFormatDescriptor FunctionalTest::s_formats[] = { 1193 /* context version, internal format, internal format name, is sRGB, CR,size{R, G, B, A, D, S}, type of R, type of G, type of B, type of A, type of depth */ 1194 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_R8, STR(GL_R8), false, true, 8, 0, 0, 0, 0, 0, 1195 GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE, GL_NONE, GL_NONE }, 1196 { glu::ContextType(3, 1, glu::PROFILE_CORE), GL_R8_SNORM, STR(GL_R8_SNORM), false, true, 8, 0, 0, 0, 0, 0, 1197 GL_SIGNED_NORMALIZED, GL_NONE, GL_NONE, GL_NONE, GL_NONE }, 1198 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_R16, STR(GL_R16), false, true, 16, 0, 0, 0, 0, 0, 1199 GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE, GL_NONE, GL_NONE }, 1200 { glu::ContextType(3, 1, glu::PROFILE_CORE), GL_R16_SNORM, STR(GL_R16_SNORM), false, true, 16, 0, 0, 0, 0, 0, 1201 GL_SIGNED_NORMALIZED, GL_NONE, GL_NONE, GL_NONE, GL_NONE }, 1202 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RG8, STR(GL_RG8), false, true, 8, 8, 0, 0, 0, 0, 1203 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE, GL_NONE }, 1204 { glu::ContextType(3, 1, glu::PROFILE_CORE), GL_RG8_SNORM, STR(GL_RG8_SNORM), false, true, 8, 8, 0, 0, 0, 0, 1205 GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_NONE, GL_NONE, GL_NONE }, 1206 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RG16, STR(GL_RG16), false, true, 16, 16, 0, 0, 0, 0, 1207 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE, GL_NONE }, 1208 { glu::ContextType(3, 1, glu::PROFILE_CORE), GL_RG16_SNORM, STR(GL_RG16_SNORM), false, true, 16, 16, 0, 0, 0, 0, 1209 GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_NONE, GL_NONE, GL_NONE }, 1210 { glu::ContextType(4, 4, glu::PROFILE_CORE), GL_R3_G3_B2, STR(GL_R3_G3_B2), false, true, 3, 3, 2, 0, 0, 0, 1211 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE }, 1212 { glu::ContextType(4, 4, glu::PROFILE_CORE), GL_RGB4, STR(GL_RGB4), false, true, 4, 4, 4, 0, 0, 0, 1213 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE }, 1214 { glu::ContextType(4, 4, glu::PROFILE_CORE), GL_RGB5, STR(GL_RGB5), false, true, 5, 5, 5, 0, 0, 0, 1215 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE }, 1216 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB8, STR(GL_RGB8), false, true, 8, 8, 8, 0, 0, 0, 1217 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE }, 1218 { glu::ContextType(3, 1, glu::PROFILE_CORE), GL_RGB8_SNORM, STR(GL_RGB8_SNORM), false, true, 8, 8, 8, 0, 0, 0, 1219 GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_NONE, GL_NONE }, 1220 { glu::ContextType(4, 4, glu::PROFILE_CORE), GL_RGB10, STR(GL_RGB10), false, true, 10, 10, 10, 0, 0, 0, 1221 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE }, 1222 { glu::ContextType(4, 4, glu::PROFILE_CORE), GL_RGB12, STR(GL_RGB12), false, true, 12, 12, 12, 0, 0, 0, 1223 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE }, 1224 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB16, STR(GL_RGB16), false, true, 16, 16, 16, 0, 0, 0, 1225 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE }, 1226 { glu::ContextType(3, 1, glu::PROFILE_CORE), GL_RGB16_SNORM, STR(GL_RGB16_SNORM), false, true, 16, 16, 16, 0, 0, 0, 1227 GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_NONE, GL_NONE }, 1228 { glu::ContextType(4, 4, glu::PROFILE_CORE), GL_RGBA2, STR(GL_RGBA2), false, true, 2, 2, 2, 2, 0, 0, 1229 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE }, 1230 { glu::ContextType(4, 2, glu::PROFILE_CORE), GL_RGBA4, STR(GL_RGBA4), false, true, 4, 4, 4, 4, 0, 0, 1231 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE }, 1232 { glu::ContextType(4, 2, glu::PROFILE_CORE), GL_RGB5_A1, STR(GL_RGB5_A1), false, true, 5, 5, 5, 1, 0, 0, 1233 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE }, 1234 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGBA8, STR(GL_RGBA8), false, true, 8, 8, 8, 8, 0, 0, 1235 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE }, 1236 { glu::ContextType(3, 1, glu::PROFILE_CORE), GL_RGBA8_SNORM, STR(GL_RGBA8_SNORM), false, true, 8, 8, 8, 8, 0, 0, 1237 GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_NONE }, 1238 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB10_A2, STR(GL_RGB10_A2), false, true, 10, 10, 10, 2, 0, 0, 1239 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE }, 1240 { glu::ContextType(3, 3, glu::PROFILE_CORE), GL_RGB10_A2UI, STR(GL_RGB10_A2UI), false, true, 10, 10, 10, 2, 0, 0, 1241 GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_NONE }, 1242 { glu::ContextType(4, 4, glu::PROFILE_CORE), GL_RGBA12, STR(GL_RGBA12), false, true, 12, 12, 12, 12, 0, 0, 1243 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE }, 1244 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGBA16, STR(GL_RGBA16), false, true, 16, 16, 16, 16, 0, 0, 1245 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE }, 1246 { glu::ContextType(3, 1, glu::PROFILE_CORE), GL_RGBA16_SNORM, STR(GL_RGBA16_SNORM), false, true, 16, 16, 16, 16, 0, 1247 0, GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_SIGNED_NORMALIZED, GL_NONE }, 1248 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_SRGB8, STR(GL_SRGB8), true, true, 8, 8, 8, 0, 0, 0, 1249 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE, GL_NONE }, 1250 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_SRGB8_ALPHA8, STR(GL_SRGB8_ALPHA8), true, true, 8, 8, 8, 8, 0, 0, 1251 GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_UNSIGNED_NORMALIZED, GL_NONE }, 1252 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_R16F, STR(GL_R16F), false, true, 16, 0, 0, 0, 0, 0, GL_FLOAT, 1253 GL_NONE, GL_NONE, GL_NONE, GL_NONE }, 1254 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RG16F, STR(GL_RG16F), false, true, 16, 16, 0, 0, 0, 0, GL_FLOAT, 1255 GL_FLOAT, GL_NONE, GL_NONE, GL_NONE }, 1256 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB16F, STR(GL_RGB16F), false, true, 16, 16, 16, 0, 0, 0, GL_FLOAT, 1257 GL_FLOAT, GL_FLOAT, GL_NONE, GL_NONE }, 1258 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGBA16F, STR(GL_RGBA16F), false, true, 16, 16, 16, 16, 0, 0, 1259 GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_NONE }, 1260 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_R32F, STR(GL_R32F), false, true, 32, 0, 0, 0, 0, 0, GL_FLOAT, 1261 GL_NONE, GL_NONE, GL_NONE, GL_NONE }, 1262 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RG32F, STR(GL_RG32F), false, true, 32, 32, 0, 0, 0, 0, GL_FLOAT, 1263 GL_FLOAT, GL_NONE, GL_NONE, GL_NONE }, 1264 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB32F, STR(GL_RGB32F), false, true, 32, 32, 32, 0, 0, 0, GL_FLOAT, 1265 GL_FLOAT, GL_FLOAT, GL_NONE, GL_NONE }, 1266 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGBA32F, STR(GL_RGBA32F), false, true, 32, 32, 32, 32, 0, 0, 1267 GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_NONE }, 1268 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_R11F_G11F_B10F, STR(GL_R11F_G11F_B10F), false, true, 11, 11, 10, 0, 1269 0, 0, GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_NONE, GL_NONE }, 1270 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB9_E5, STR(GL_RGB9_E5), false, false, 9, 9, 9, 0, 0, 0, GL_FLOAT, 1271 GL_FLOAT, GL_FLOAT, GL_NONE, GL_NONE }, 1272 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_R8I, STR(GL_R8I), false, true, 8, 0, 0, 0, 0, 0, GL_INT, GL_NONE, 1273 GL_NONE, GL_NONE, GL_NONE }, 1274 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_R8UI, STR(GL_R8UI), false, true, 8, 0, 0, 0, 0, 0, GL_UNSIGNED_INT, 1275 GL_NONE, GL_NONE, GL_NONE, GL_NONE }, 1276 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_R16I, STR(GL_R16I), false, true, 16, 0, 0, 0, 0, 0, GL_INT, GL_NONE, 1277 GL_NONE, GL_NONE, GL_NONE }, 1278 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_R16UI, STR(GL_R16UI), false, true, 16, 0, 0, 0, 0, 0, 1279 GL_UNSIGNED_INT, GL_NONE, GL_NONE, GL_NONE, GL_NONE }, 1280 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_R32I, STR(GL_R32I), false, true, 32, 0, 0, 0, 0, 0, GL_INT, GL_NONE, 1281 GL_NONE, GL_NONE, GL_NONE }, 1282 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_R32UI, STR(GL_R32UI), false, true, 32, 0, 0, 0, 0, 0, 1283 GL_UNSIGNED_INT, GL_NONE, GL_NONE, GL_NONE, GL_NONE }, 1284 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RG8I, STR(GL_RG8I), false, true, 8, 8, 0, 0, 0, 0, GL_INT, GL_INT, 1285 GL_NONE, GL_NONE, GL_NONE }, 1286 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RG8UI, STR(GL_RG8UI), false, true, 8, 8, 0, 0, 0, 0, 1287 GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_NONE, GL_NONE, GL_NONE }, 1288 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RG16I, STR(GL_RG16I), false, true, 16, 16, 0, 0, 0, 0, GL_INT, 1289 GL_INT, GL_NONE, GL_NONE, GL_NONE }, 1290 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RG16UI, STR(GL_RG16UI), false, true, 16, 16, 0, 0, 0, 0, 1291 GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_NONE, GL_NONE, GL_NONE }, 1292 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RG32I, STR(GL_RG32I), false, true, 32, 32, 0, 0, 0, 0, GL_INT, 1293 GL_INT, GL_NONE, GL_NONE, GL_NONE }, 1294 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RG32UI, STR(GL_RG32UI), false, true, 32, 32, 0, 0, 0, 0, 1295 GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_NONE, GL_NONE, GL_NONE }, 1296 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB8I, STR(GL_RGB8I), false, true, 8, 8, 8, 0, 0, 0, GL_INT, GL_INT, 1297 GL_INT, GL_NONE, GL_NONE }, 1298 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB8UI, STR(GL_RGB8UI), false, true, 8, 8, 8, 0, 0, 0, 1299 GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_NONE, GL_NONE }, 1300 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB16I, STR(GL_RGB16I), false, true, 16, 16, 16, 0, 0, 0, GL_INT, 1301 GL_INT, GL_INT, GL_NONE, GL_NONE }, 1302 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB16UI, STR(GL_RGB16UI), false, true, 16, 16, 16, 0, 0, 0, 1303 GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_NONE, GL_NONE }, 1304 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB32I, STR(GL_RGB32I), false, true, 32, 32, 32, 0, 0, 0, GL_INT, 1305 GL_INT, GL_INT, GL_NONE, GL_NONE }, 1306 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGB32UI, STR(GL_RGB32UI), false, true, 32, 32, 32, 0, 0, 0, 1307 GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_NONE, GL_NONE }, 1308 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGBA8I, STR(GL_RGBA8I), false, true, 8, 8, 8, 8, 0, 0, GL_INT, 1309 GL_INT, GL_INT, GL_INT, GL_NONE }, 1310 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGBA8UI, STR(GL_RGBA8UI), false, true, 8, 8, 8, 8, 0, 0, 1311 GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_NONE }, 1312 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGBA16I, STR(GL_RGBA16I), false, true, 16, 16, 16, 16, 0, 0, GL_INT, 1313 GL_INT, GL_INT, GL_INT, GL_NONE }, 1314 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGBA16UI, STR(GL_RGBA16UI), false, true, 16, 16, 16, 16, 0, 0, 1315 GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_NONE }, 1316 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGBA32I, STR(GL_RGBA32I), false, true, 32, 32, 32, 32, 0, 0, GL_INT, 1317 GL_INT, GL_INT, GL_INT, GL_NONE }, 1318 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_RGBA32UI, STR(GL_RGBA32UI), false, true, 32, 32, 32, 32, 0, 0, 1319 GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_UNSIGNED_INT, GL_NONE }, 1320 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_DEPTH_COMPONENT16, STR(GL_DEPTH_COMPONENT16), false, true, 0, 0, 0, 1321 0, 16, 0, GL_NONE, GL_NONE, GL_NONE, GL_NONE, GL_UNSIGNED_NORMALIZED }, 1322 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_DEPTH_COMPONENT24, STR(GL_DEPTH_COMPONENT24), false, true, 0, 0, 0, 1323 0, 24, 0, GL_NONE, GL_NONE, GL_NONE, GL_NONE, GL_UNSIGNED_NORMALIZED }, 1324 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_DEPTH_COMPONENT32F, STR(GL_DEPTH_COMPONENT32F), false, true, 0, 0, 1325 0, 0, 32, 0, GL_NONE, GL_NONE, GL_NONE, GL_NONE, GL_FLOAT }, 1326 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_DEPTH24_STENCIL8, STR(GL_DEPTH24_STENCIL8), false, true, 0, 0, 0, 0, 1327 24, 8, GL_NONE, GL_NONE, GL_NONE, GL_NONE, GL_UNSIGNED_NORMALIZED }, 1328 { glu::ContextType(3, 0, glu::PROFILE_CORE), GL_DEPTH32F_STENCIL8, STR(GL_DEPTH32F_STENCIL8), false, true, 0, 0, 0, 1329 0, 32, 8, GL_NONE, GL_NONE, GL_NONE, GL_NONE, GL_FLOAT } 1330 }; 1331 1332 const glw::GLuint FunctionalTest::s_formats_size = sizeof(s_formats) / sizeof(s_formats[0]); 1333 1334 const glw::GLchar* FunctionalTest::s_vertex_shader_code = "#version 150\n" 1335 "\n" 1336 "void main()\n" 1337 "{\n" 1338 " switch(gl_VertexID % 4)\n" 1339 " {\n" 1340 " case 0:\n" 1341 " gl_Position = vec4(-1.0, -1.0, 0.0, 1.0);\n" 1342 " break;\n" 1343 " case 1:\n" 1344 " gl_Position = vec4(-1.0, 1.0, 0.0, 1.0);\n" 1345 " break;\n" 1346 " case 2:\n" 1347 " gl_Position = vec4( 1.0, -1.0, 0.0, 1.0);\n" 1348 " break;\n" 1349 " case 3:\n" 1350 " gl_Position = vec4( 1.0, 1.0, 0.0, 1.0);\n" 1351 " break;\n" 1352 " }\n" 1353 "}\n"; 1354 1355 const glw::GLchar* FunctionalTest::s_fragment_shader_template = 1356 "#version 150\n" 1357 "\n" 1358 "out TEMPLATE_TYPE result;\n" 1359 "\n" 1360 "uniform TEMPLATE_SAMPLER data;\n" 1361 "\n" 1362 "void main()\n" 1363 "{\n" 1364 " result = texelFetch(data, TEMPLATE_TEXEL_FETCH_ARGUMENTS)TEMPLATE_COMPONENT;\n" 1365 "}\n"; 1366 1367 /*===========================================================================================================*/ 1368 1369 namespace Utilities 1370 { 1371 1372 glw::GLuint buildProgram(glw::Functions const& gl, tcu::TestLog& log, glw::GLchar const* const vertex_shader_source, 1373 glw::GLchar const* const fragment_shader_source) 1374 { 1375 glw::GLuint program = 0; 1376 1377 struct Shader 1378 { 1379 glw::GLchar const* const source; 1380 glw::GLenum const type; 1381 glw::GLuint id; 1382 } shader[] = { { vertex_shader_source, GL_VERTEX_SHADER, 0 }, { fragment_shader_source, GL_FRAGMENT_SHADER, 0 } }; 1383 1384 glw::GLuint const shader_count = sizeof(shader) / sizeof(shader[0]); 1385 1386 try 1387 { 1388 /* Create program. */ 1389 program = gl.createProgram(); 1390 GLU_EXPECT_NO_ERROR(gl.getError(), "glCreateProgram call failed."); 1391 1392 /* Shader compilation. */ 1393 1394 for (glw::GLuint i = 0; i < shader_count; ++i) 1395 { 1396 if (DE_NULL != shader[i].source) 1397 { 1398 shader[i].id = gl.createShader(shader[i].type); 1399 1400 GLU_EXPECT_NO_ERROR(gl.getError(), "glCreateShader call failed."); 1401 1402 gl.attachShader(program, shader[i].id); 1403 1404 GLU_EXPECT_NO_ERROR(gl.getError(), "glAttachShader call failed."); 1405 1406 gl.shaderSource(shader[i].id, 1, &(shader[i].source), NULL); 1407 1408 GLU_EXPECT_NO_ERROR(gl.getError(), "glShaderSource call failed."); 1409 1410 gl.compileShader(shader[i].id); 1411 1412 GLU_EXPECT_NO_ERROR(gl.getError(), "glCompileShader call failed."); 1413 1414 glw::GLint status = GL_FALSE; 1415 1416 gl.getShaderiv(shader[i].id, GL_COMPILE_STATUS, &status); 1417 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetShaderiv call failed."); 1418 1419 if (GL_FALSE == status) 1420 { 1421 glw::GLint log_size = 0; 1422 gl.getShaderiv(shader[i].id, GL_INFO_LOG_LENGTH, &log_size); 1423 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetShaderiv call failed."); 1424 1425 glw::GLchar* log_text = new glw::GLchar[log_size]; 1426 1427 gl.getShaderInfoLog(shader[i].id, log_size, NULL, &log_text[0]); 1428 1429 log << tcu::TestLog::Message << "Shader compilation has failed.\n" 1430 << "Shader type: " << glu::getShaderTypeStr(shader[i].type) << "\n" 1431 << "Shader compilation error log:\n" 1432 << log_text << "\n" 1433 << "Shader source code:\n" 1434 << shader[i].source << "\n" 1435 << tcu::TestLog::EndMessage; 1436 1437 delete[] log_text; 1438 1439 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetShaderInfoLog call failed."); 1440 1441 throw 0; 1442 } 1443 } 1444 } 1445 1446 /* Link. */ 1447 gl.linkProgram(program); 1448 GLU_EXPECT_NO_ERROR(gl.getError(), "glTransformFeedbackVaryings call failed."); 1449 1450 glw::GLint status = GL_FALSE; 1451 1452 gl.getProgramiv(program, GL_LINK_STATUS, &status); 1453 1454 if (GL_TRUE == status) 1455 { 1456 for (glw::GLuint i = 0; i < shader_count; ++i) 1457 { 1458 if (shader[i].id) 1459 { 1460 gl.detachShader(program, shader[i].id); 1461 1462 GLU_EXPECT_NO_ERROR(gl.getError(), "glDetachShader call failed."); 1463 } 1464 } 1465 } 1466 else 1467 { 1468 glw::GLint log_size = 0; 1469 1470 gl.getProgramiv(program, GL_INFO_LOG_LENGTH, &log_size); 1471 1472 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetProgramiv call failed."); 1473 1474 glw::GLchar* log_text = new glw::GLchar[log_size]; 1475 1476 gl.getProgramInfoLog(program, log_size, NULL, &log_text[0]); 1477 1478 log << tcu::TestLog::Message << "Program linkage has failed due to:\n" 1479 << log_text << "\n" 1480 << tcu::TestLog::EndMessage; 1481 1482 delete[] log_text; 1483 1484 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetProgramInfoLog call failed."); 1485 1486 throw 0; 1487 } 1488 } 1489 catch (...) 1490 { 1491 if (program) 1492 { 1493 gl.deleteProgram(program); 1494 1495 program = 0; 1496 } 1497 } 1498 1499 for (glw::GLuint i = 0; i < shader_count; ++i) 1500 { 1501 if (0 != shader[i].id) 1502 { 1503 gl.deleteShader(shader[i].id); 1504 1505 shader[i].id = 0; 1506 } 1507 } 1508 1509 return program; 1510 } 1511 1512 std::string preprocessString(std::string source, std::string key, std::string value) 1513 { 1514 std::string destination = source; 1515 1516 while (true) 1517 { 1518 /* Find token in source code. */ 1519 size_t position = destination.find(key, 0); 1520 1521 /* No more occurences of this key. */ 1522 if (position == std::string::npos) 1523 { 1524 break; 1525 } 1526 1527 /* Replace token with sub_code. */ 1528 destination.replace(position, key.size(), value); 1529 } 1530 1531 return destination; 1532 } 1533 1534 std::string itoa(glw::GLint i) 1535 { 1536 std::stringstream stream; 1537 1538 stream << i; 1539 1540 return stream.str(); 1541 } 1542 1543 } // namespace Utilities 1544 } // namespace TextureSizePromotion 1545 } // namespace gl3cts 1546