Home | History | Annotate | Download | only in gl
      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  gl4cEnhancedLayoutsTests.cpp
     26  * \brief Implements conformance tests for "Enhanced Layouts" functionality.
     27  */ /*-------------------------------------------------------------------*/
     28 
     29 #include "gl4cEnhancedLayoutsTests.hpp"
     30 
     31 #include "gluContextInfo.hpp"
     32 #include "gluDefs.hpp"
     33 #include "gluStrUtil.hpp"
     34 #include "glwEnums.hpp"
     35 #include "glwFunctions.hpp"
     36 #include "tcuTestLog.hpp"
     37 
     38 #include <algorithm>
     39 #include <iomanip>
     40 #include <string>
     41 #include <vector>
     42 
     43 /* DEBUG */
     44 #define USE_NSIGHT 0
     45 #define DEBUG_ENBALE_MESSAGE_CALLBACK 0
     46 #define DEBUG_NEG_LOG_ERROR 0
     47 #define DEBUG_REPLACE_TOKEN 0
     48 #define DEBUG_REPEAT_TEST_CASE 0
     49 #define DEBUG_REPEATED_TEST_CASE 0
     50 
     51 /* Texture test base */
     52 #define DEBUG_TTB_VERIFICATION_SNIPPET_STAGE 0
     53 #define DEBUG_TTB_VERIFICATION_SNIPPET_VARIABLE 0
     54 
     55 /* Tests */
     56 #define DEBUG_VERTEX_ATTRIB_LOCATIONS_TEST_VARIABLE 0
     57 
     58 /* WORKAROUNDS */
     59 #define WRKARD_UNIFORMBLOCKMEMBEROFFSETANDALIGNTEST 0
     60 #define WRKARD_UNIFORMBLOCKMEMBERALIGNNONPOWEROF2TEST 0
     61 #define WRKARD_UNIFORMBLOCKALIGNMENT 0
     62 #define WRKARD_VARYINGLOCATIONSTEST 0
     63 
     64 using namespace glw;
     65 
     66 namespace gl4cts
     67 {
     68 namespace EnhancedLayouts
     69 {
     70 namespace Utils
     71 {
     72 /** Constants used by "random" generators **/
     73 static const GLuint s_rand_start	= 3;
     74 static const GLuint s_rand_max		= 16;
     75 static const GLuint s_rand_max_half = s_rand_max / 2;
     76 
     77 /** Seed used by "random" generators **/
     78 static GLuint s_rand = s_rand_start;
     79 
     80 /** Get "random" unsigned int value
     81  *
     82  * @return Value
     83  **/
     84 static GLuint GetRandUint()
     85 {
     86 	const GLuint rand = s_rand++;
     87 
     88 	if (s_rand_max <= s_rand)
     89 	{
     90 		s_rand = s_rand_start;
     91 	}
     92 
     93 	return rand;
     94 }
     95 
     96 /** Get "random" int value
     97  *
     98  * @return Value
     99  **/
    100 GLint GetRandInt()
    101 {
    102 	const GLint rand = GetRandUint() - s_rand_max_half;
    103 
    104 	return rand;
    105 }
    106 
    107 /** Get "random" double value
    108  *
    109  * @return Value
    110  **/
    111 GLdouble GetRandDouble()
    112 {
    113 	const GLint rand = GetRandInt();
    114 
    115 	GLdouble result = (GLfloat)rand / (GLdouble)s_rand_max_half;
    116 
    117 	return result;
    118 }
    119 
    120 /** Get "random" float value
    121  *
    122  * @return Value
    123  **/
    124 GLfloat GetRandFloat()
    125 {
    126 	const GLint rand = GetRandInt();
    127 
    128 	GLfloat result = (GLfloat)rand / (GLfloat)s_rand_max_half;
    129 
    130 	return result;
    131 }
    132 
    133 /** String used by list routines **/
    134 static const GLchar* const g_list = "LIST";
    135 
    136 /** Type constants **/
    137 const Type Type::_double = Type::GetType(Type::Double, 1, 1);
    138 const Type Type::dmat2   = Type::GetType(Type::Double, 2, 2);
    139 const Type Type::dmat2x3 = Type::GetType(Type::Double, 2, 3);
    140 const Type Type::dmat2x4 = Type::GetType(Type::Double, 2, 4);
    141 const Type Type::dmat3x2 = Type::GetType(Type::Double, 3, 2);
    142 const Type Type::dmat3   = Type::GetType(Type::Double, 3, 3);
    143 const Type Type::dmat3x4 = Type::GetType(Type::Double, 3, 4);
    144 const Type Type::dmat4x2 = Type::GetType(Type::Double, 4, 2);
    145 const Type Type::dmat4x3 = Type::GetType(Type::Double, 4, 3);
    146 const Type Type::dmat4   = Type::GetType(Type::Double, 4, 4);
    147 const Type Type::dvec2   = Type::GetType(Type::Double, 1, 2);
    148 const Type Type::dvec3   = Type::GetType(Type::Double, 1, 3);
    149 const Type Type::dvec4   = Type::GetType(Type::Double, 1, 4);
    150 const Type Type::_int	= Type::GetType(Type::Int, 1, 1);
    151 const Type Type::ivec2   = Type::GetType(Type::Int, 1, 2);
    152 const Type Type::ivec3   = Type::GetType(Type::Int, 1, 3);
    153 const Type Type::ivec4   = Type::GetType(Type::Int, 1, 4);
    154 const Type Type::_float  = Type::GetType(Type::Float, 1, 1);
    155 const Type Type::mat2	= Type::GetType(Type::Float, 2, 2);
    156 const Type Type::mat2x3  = Type::GetType(Type::Float, 2, 3);
    157 const Type Type::mat2x4  = Type::GetType(Type::Float, 2, 4);
    158 const Type Type::mat3x2  = Type::GetType(Type::Float, 3, 2);
    159 const Type Type::mat3	= Type::GetType(Type::Float, 3, 3);
    160 const Type Type::mat3x4  = Type::GetType(Type::Float, 3, 4);
    161 const Type Type::mat4x2  = Type::GetType(Type::Float, 4, 2);
    162 const Type Type::mat4x3  = Type::GetType(Type::Float, 4, 3);
    163 const Type Type::mat4	= Type::GetType(Type::Float, 4, 4);
    164 const Type Type::vec2	= Type::GetType(Type::Float, 1, 2);
    165 const Type Type::vec3	= Type::GetType(Type::Float, 1, 3);
    166 const Type Type::vec4	= Type::GetType(Type::Float, 1, 4);
    167 const Type Type::uint	= Type::GetType(Type::Uint, 1, 1);
    168 const Type Type::uvec2   = Type::GetType(Type::Uint, 1, 2);
    169 const Type Type::uvec3   = Type::GetType(Type::Uint, 1, 3);
    170 const Type Type::uvec4   = Type::GetType(Type::Uint, 1, 4);
    171 
    172 /** Generate data for type. This routine follows STD140 rules
    173  *
    174  * @return Vector of bytes filled with data
    175  **/
    176 std::vector<GLubyte> Type::GenerateData() const
    177 {
    178 	const GLuint alignment = GetActualAlignment(0, false);
    179 
    180 	std::vector<GLubyte> data;
    181 	data.resize(alignment * m_n_columns);
    182 
    183 	for (GLuint column = 0; column < m_n_columns; ++column)
    184 	{
    185 		GLvoid* ptr = (GLvoid*)&data[column * alignment];
    186 
    187 		switch (m_basic_type)
    188 		{
    189 		case Double:
    190 		{
    191 			GLdouble* d_ptr = (GLdouble*)ptr;
    192 
    193 			for (GLuint i = 0; i < m_n_rows; ++i)
    194 			{
    195 				d_ptr[i] = GetRandDouble();
    196 			}
    197 		}
    198 		break;
    199 		case Float:
    200 		{
    201 			GLfloat* f_ptr = (GLfloat*)ptr;
    202 
    203 			for (GLuint i = 0; i < m_n_rows; ++i)
    204 			{
    205 				f_ptr[i] = GetRandFloat();
    206 			}
    207 		}
    208 		break;
    209 		case Int:
    210 		{
    211 			GLint* i_ptr = (GLint*)ptr;
    212 
    213 			for (GLuint i = 0; i < m_n_rows; ++i)
    214 			{
    215 				i_ptr[i] = GetRandInt();
    216 			}
    217 		}
    218 		break;
    219 		case Uint:
    220 		{
    221 			GLuint* ui_ptr = (GLuint*)ptr;
    222 
    223 			for (GLuint i = 0; i < m_n_rows; ++i)
    224 			{
    225 				ui_ptr[i] = GetRandUint();
    226 			}
    227 		}
    228 		break;
    229 		}
    230 	}
    231 
    232 	return data;
    233 }
    234 
    235 /** Generate data for type. This routine packs data tightly.
    236  *
    237  * @return Vector of bytes filled with data
    238  **/
    239 std::vector<GLubyte> Type::GenerateDataPacked() const
    240 {
    241 	const GLuint basic_size = GetTypeSize(m_basic_type);
    242 	const GLuint n_elements = m_n_columns * m_n_rows;
    243 	const GLuint size		= basic_size * n_elements;
    244 
    245 	std::vector<GLubyte> data;
    246 	data.resize(size);
    247 
    248 	GLvoid* ptr = (GLvoid*)&data[0];
    249 
    250 	switch (m_basic_type)
    251 	{
    252 	case Double:
    253 	{
    254 		GLdouble* d_ptr = (GLdouble*)ptr;
    255 
    256 		for (GLuint i = 0; i < n_elements; ++i)
    257 		{
    258 			d_ptr[i] = GetRandDouble();
    259 		}
    260 	}
    261 	break;
    262 	case Float:
    263 	{
    264 		GLfloat* f_ptr = (GLfloat*)ptr;
    265 
    266 		for (GLuint i = 0; i < n_elements; ++i)
    267 		{
    268 			f_ptr[i] = GetRandFloat();
    269 		}
    270 	}
    271 	break;
    272 	case Int:
    273 	{
    274 		GLint* i_ptr = (GLint*)ptr;
    275 
    276 		for (GLuint i = 0; i < n_elements; ++i)
    277 		{
    278 			i_ptr[i] = GetRandInt();
    279 		}
    280 	}
    281 	break;
    282 	case Uint:
    283 	{
    284 		GLuint* ui_ptr = (GLuint*)ptr;
    285 
    286 		for (GLuint i = 0; i < n_elements; ++i)
    287 		{
    288 			ui_ptr[i] = GetRandUint();
    289 		}
    290 	}
    291 	break;
    292 	}
    293 
    294 	return data;
    295 }
    296 
    297 /** Calculate "actual alignment". It work under assumption that align value is valid
    298  *
    299  * @param align    Requested alignment, eg with "align" qualifier
    300  * @param is_array Selects if an array of type or single instance should be considered
    301  *
    302  * @return Calculated value
    303  **/
    304 GLuint Type::GetActualAlignment(GLuint align, bool is_array) const
    305 {
    306 	const GLuint base_alignment = GetBaseAlignment(is_array);
    307 
    308 	return std::max(align, base_alignment);
    309 }
    310 
    311 /** Align given ofset with specified alignment
    312  *
    313  * @param offset    Offset
    314  * @param alignment Alignment
    315  *
    316  * @return Calculated value
    317  **/
    318 GLuint align(GLuint offset, GLuint alignment)
    319 {
    320 	const GLuint rest = offset % alignment;
    321 
    322 	if (0 != rest)
    323 	{
    324 		GLuint missing = alignment - rest;
    325 		offset += missing;
    326 	}
    327 
    328 	return offset;
    329 }
    330 
    331 /** Calculate "actual offset"
    332  *
    333  * @param start_offset     Requested offset
    334  * @param actual_alignment Actual alignemnt
    335  *
    336  * @return Calculated value
    337  **/
    338 GLuint Type::GetActualOffset(GLuint start_offset, GLuint actual_alignment)
    339 {
    340 	GLuint offset = align(start_offset, actual_alignment);
    341 
    342 	return offset;
    343 }
    344 
    345 /** Calculate "base alignment" for given type
    346  *
    347  * @param is_array Select if array or single instance should be considered
    348  *
    349  * @return Calculated value
    350  **/
    351 GLuint Type::GetBaseAlignment(bool is_array) const
    352 {
    353 	GLuint elements = 1;
    354 
    355 	switch (m_n_rows)
    356 	{
    357 	case 2:
    358 		elements = 2;
    359 		break;
    360 	case 3:
    361 	case 4:
    362 		elements = 4;
    363 		break;
    364 	default:
    365 		break;
    366 	}
    367 
    368 	GLuint N		 = GetTypeSize(m_basic_type);
    369 	GLuint alignment = N * elements;
    370 
    371 	if ((true == is_array) || (1 != m_n_columns))
    372 	{
    373 		alignment = align(alignment, 16 /* vec4 alignment */);
    374 	}
    375 
    376 	return alignment;
    377 }
    378 
    379 /** Returns string representing GLSL constructor of type with arguments provided in data
    380  *
    381  * @param data Array of values that will be used as construcotr arguments.
    382  *             It is interpreted as tightly packed array of type matching this type.
    383  *
    384  * @return String in form "Type(args)"
    385  **/
    386 std::string Type::GetGLSLConstructor(const GLvoid* data) const
    387 {
    388 	const GLchar* type = GetGLSLTypeName();
    389 
    390 	std::stringstream stream;
    391 
    392 	stream << type << "(";
    393 
    394 	/* Scalar or vector */
    395 	if (1 == m_n_columns)
    396 	{
    397 		for (GLuint row = 0; row < m_n_rows; ++row)
    398 		{
    399 			switch (m_basic_type)
    400 			{
    401 			case Double:
    402 				stream << ((GLdouble*)data)[row];
    403 				break;
    404 			case Float:
    405 				stream << ((GLfloat*)data)[row];
    406 				break;
    407 			case Int:
    408 				stream << ((GLint*)data)[row];
    409 				break;
    410 			case Uint:
    411 				stream << ((GLuint*)data)[row];
    412 				break;
    413 			}
    414 
    415 			if (row + 1 != m_n_rows)
    416 			{
    417 				stream << ", ";
    418 			}
    419 		}
    420 	}
    421 	else /* Matrix: mat(vec(), vec() .. ) */
    422 	{
    423 		const GLuint basic_size = GetTypeSize(m_basic_type);
    424 		// Very indescoverable defect, the column stride should be calculated by rows, such as mat2x3, which is 2, columns 3 rows, its column stride should be 3 * sizeof(float)
    425 		const GLuint column_stride = m_n_rows * basic_size;
    426 		const Type   column_type   = GetType(m_basic_type, 1, m_n_rows);
    427 
    428 		for (GLuint column = 0; column < m_n_columns; ++column)
    429 		{
    430 			const GLuint  column_offset = column * column_stride;
    431 			const GLvoid* column_data   = (GLubyte*)data + column_offset;
    432 
    433 			stream << column_type.GetGLSLConstructor(column_data);
    434 
    435 			if (column + 1 != m_n_columns)
    436 			{
    437 				stream << ", ";
    438 			}
    439 		}
    440 	}
    441 
    442 	stream << ")";
    443 
    444 	return stream.str();
    445 }
    446 
    447 /** Get glsl name of the type
    448  *
    449  * @return Name of glsl type
    450  **/
    451 const glw::GLchar* Type::GetGLSLTypeName() const
    452 {
    453 	static const GLchar* float_lut[4][4] = {
    454 		{ "float", "vec2", "vec3", "vec4" },
    455 		{ 0, "mat2", "mat2x3", "mat2x4" },
    456 		{ 0, "mat3x2", "mat3", "mat3x4" },
    457 		{ 0, "mat4x2", "mat4x3", "mat4" },
    458 	};
    459 
    460 	static const GLchar* double_lut[4][4] = {
    461 		{ "double", "dvec2", "dvec3", "dvec4" },
    462 		{ 0, "dmat2", "dmat2x3", "dmat2x4" },
    463 		{ 0, "dmat3x2", "dmat3", "dmat3x4" },
    464 		{ 0, "dmat4x2", "dmat4x3", "dmat4" },
    465 	};
    466 
    467 	static const GLchar* int_lut[4] = { "int", "ivec2", "ivec3", "ivec4" };
    468 
    469 	static const GLchar* uint_lut[4] = { "uint", "uvec2", "uvec3", "uvec4" };
    470 
    471 	const GLchar* result = 0;
    472 
    473 	if ((1 > m_n_columns) || (1 > m_n_rows) || (4 < m_n_columns) || (4 < m_n_rows))
    474 	{
    475 		return 0;
    476 	}
    477 
    478 	switch (m_basic_type)
    479 	{
    480 	case Float:
    481 		result = float_lut[m_n_columns - 1][m_n_rows - 1];
    482 		break;
    483 	case Double:
    484 		result = double_lut[m_n_columns - 1][m_n_rows - 1];
    485 		break;
    486 	case Int:
    487 		result = int_lut[m_n_rows - 1];
    488 		break;
    489 	case Uint:
    490 		result = uint_lut[m_n_rows - 1];
    491 		break;
    492 	default:
    493 		TCU_FAIL("Invliad enum");
    494 	}
    495 
    496 	return result;
    497 }
    498 
    499 /** Get number of locations required for the type
    500  *
    501  * @return Number of columns times:
    502  *          - 2 when type is double with 3 or 4 rows,
    503  *          - 1 otherwise or if it's a vertex shader input.
    504  **/
    505 GLuint Type::GetLocations(bool is_vs_input) const
    506 {
    507 	GLuint n_loc_per_column;
    508 
    509 	/* 1 or 2 doubles any for rest */
    510 	if ((2 >= m_n_rows) || (Double != m_basic_type) || is_vs_input)
    511 	{
    512 		n_loc_per_column = 1;
    513 	}
    514 	else
    515 	{
    516 		/* 3 and 4 doubles */
    517 		n_loc_per_column = 2;
    518 	}
    519 
    520 	return n_loc_per_column * m_n_columns;
    521 }
    522 
    523 /** Get size of the type in bytes.
    524  * Note that this routine doesn't consider arrays and assumes
    525  * column_major matrices.
    526  *
    527  * @return Formula:
    528  *          - If std140 packaging and matrix; number of columns * base alignment
    529  *          - Otherwise; number of elements * sizeof(base_type)
    530  **/
    531 GLuint Type::GetSize(const bool is_std140) const
    532 {
    533 	const GLuint basic_type_size = GetTypeSize(m_basic_type);
    534 	const GLuint n_elements		 = m_n_columns * m_n_rows;
    535 
    536 	if (is_std140 && m_n_columns > 1)
    537 	{
    538 		return m_n_columns * GetBaseAlignment(false);
    539 	}
    540 
    541 	return basic_type_size * n_elements;
    542 }
    543 
    544 /** Get GLenum representing the type
    545  *
    546  * @return GLenum
    547  **/
    548 GLenum Type::GetTypeGLenum() const
    549 {
    550 	static const GLenum float_lut[4][4] = {
    551 		{ GL_FLOAT, GL_FLOAT_VEC2, GL_FLOAT_VEC3, GL_FLOAT_VEC4 },
    552 		{ 0, GL_FLOAT_MAT2, GL_FLOAT_MAT2x3, GL_FLOAT_MAT2x4 },
    553 		{ 0, GL_FLOAT_MAT3x2, GL_FLOAT_MAT3, GL_FLOAT_MAT3x4 },
    554 		{ 0, GL_FLOAT_MAT4x2, GL_FLOAT_MAT4x3, GL_FLOAT_MAT4 },
    555 	};
    556 
    557 	static const GLenum double_lut[4][4] = {
    558 		{ GL_DOUBLE, GL_DOUBLE_VEC2, GL_DOUBLE_VEC3, GL_DOUBLE_VEC4 },
    559 		{ 0, GL_DOUBLE_MAT2, GL_DOUBLE_MAT2x3, GL_DOUBLE_MAT2x4 },
    560 		{ 0, GL_DOUBLE_MAT3x2, GL_DOUBLE_MAT3, GL_DOUBLE_MAT3x4 },
    561 		{ 0, GL_DOUBLE_MAT4x2, GL_DOUBLE_MAT4x3, GL_DOUBLE_MAT4 },
    562 	};
    563 
    564 	static const GLenum int_lut[4] = { GL_INT, GL_INT_VEC2, GL_INT_VEC3, GL_INT_VEC4 };
    565 
    566 	static const GLenum uint_lut[4] = { GL_UNSIGNED_INT, GL_UNSIGNED_INT_VEC2, GL_UNSIGNED_INT_VEC3,
    567 										GL_UNSIGNED_INT_VEC4 };
    568 
    569 	GLenum result = 0;
    570 
    571 	if ((1 > m_n_columns) || (1 > m_n_rows) || (4 < m_n_columns) || (4 < m_n_rows))
    572 	{
    573 		return 0;
    574 	}
    575 
    576 	switch (m_basic_type)
    577 	{
    578 	case Float:
    579 		result = float_lut[m_n_columns - 1][m_n_rows - 1];
    580 		break;
    581 	case Double:
    582 		result = double_lut[m_n_columns - 1][m_n_rows - 1];
    583 		break;
    584 	case Int:
    585 		result = int_lut[m_n_rows - 1];
    586 		break;
    587 	case Uint:
    588 		result = uint_lut[m_n_rows - 1];
    589 		break;
    590 	default:
    591 		TCU_FAIL("Invliad enum");
    592 	}
    593 
    594 	return result;
    595 }
    596 
    597 /** Calculate the numbe of components consumed by a type
    598  *   according to 11.1.2.1 Output Variables
    599  *
    600  * @return Calculated number of components for the type
    601  **/
    602 GLuint Type::GetNumComponents() const
    603 {
    604 	// Rule 3 of Section 7.6.2.2
    605 	// If the member is a three-component vector with components consuming N
    606 	// basic machine units, the base alignment is 4N.
    607 	GLuint num_components = (m_n_rows == 3 ? 4 : m_n_rows) * m_n_columns;
    608 
    609 	if (m_basic_type == Double)
    610 	{
    611 		num_components *= 2;
    612 	}
    613 
    614 	return num_components;
    615 }
    616 
    617 /** Calculate stride for the type according to std140 rules
    618  *
    619  * @param alignment        Alignment of type
    620  * @param n_columns        Number of columns
    621  * @param n_array_elements Number of elements in array
    622  *
    623  * @return Calculated value
    624  **/
    625 GLuint Type::CalculateStd140Stride(GLuint alignment, GLuint n_columns, GLuint n_array_elements)
    626 {
    627 	GLuint stride = alignment * n_columns;
    628 	if (0 != n_array_elements)
    629 	{
    630 		stride *= n_array_elements;
    631 	}
    632 
    633 	return stride;
    634 }
    635 
    636 /** Check if glsl support matrices for specific basic type
    637  *
    638  * @param type Basic type
    639  *
    640  * @return true if matrices of <type> are supported, false otherwise
    641  **/
    642 bool Type::DoesTypeSupportMatrix(TYPES type)
    643 {
    644 	bool result = false;
    645 
    646 	switch (type)
    647 	{
    648 	case Float:
    649 	case Double:
    650 		result = true;
    651 		break;
    652 	case Int:
    653 	case Uint:
    654 		result = false;
    655 		break;
    656 	default:
    657 		TCU_FAIL("Invliad enum");
    658 	}
    659 
    660 	return result;
    661 }
    662 
    663 /** Creates instance of Type
    664  *
    665  * @param basic_type Select basic type of instance
    666  * @param n_columns  Number of columns
    667  * @param n_rows     Number of rows
    668  *
    669  * @return Type instance
    670  **/
    671 Type Type::GetType(TYPES basic_type, glw::GLuint n_columns, glw::GLuint n_rows)
    672 {
    673 	Type type = { basic_type, n_columns, n_rows };
    674 
    675 	return type;
    676 }
    677 
    678 /** Get Size of given type in bytes
    679  *
    680  * @param type
    681  *
    682  * @return Size of type
    683  **/
    684 GLuint Type::GetTypeSize(TYPES type)
    685 {
    686 	GLuint result = 0;
    687 
    688 	switch (type)
    689 	{
    690 	case Float:
    691 		result = sizeof(GLfloat);
    692 		break;
    693 	case Double:
    694 		result = sizeof(GLdouble);
    695 		break;
    696 	case Int:
    697 		result = sizeof(GLint);
    698 		break;
    699 	case Uint:
    700 		result = sizeof(GLuint);
    701 		break;
    702 	default:
    703 		TCU_FAIL("Invalid enum");
    704 	}
    705 
    706 	return result;
    707 }
    708 
    709 /** Get GLenum representing given type
    710  *
    711  * @param type
    712  *
    713  * @return GLenum value
    714  **/
    715 GLenum Type::GetTypeGLenum(TYPES type)
    716 {
    717 	GLenum result = 0;
    718 
    719 	switch (type)
    720 	{
    721 	case Float:
    722 		result = GL_FLOAT;
    723 		break;
    724 	case Double:
    725 		result = GL_DOUBLE;
    726 		break;
    727 	case Int:
    728 		result = GL_INT;
    729 		break;
    730 	case Uint:
    731 		result = GL_UNSIGNED_INT;
    732 		break;
    733 	default:
    734 		TCU_FAIL("Invalid enum");
    735 	}
    736 
    737 	return result;
    738 }
    739 
    740 /** Get proper glUniformNdv routine for vectors with specified number of rows
    741  *
    742  * @param gl     GL functions
    743  * @param n_rows Number of rows
    744  *
    745  * @return Function address
    746  **/
    747 uniformNdv getUniformNdv(const glw::Functions& gl, glw::GLuint n_rows)
    748 {
    749 	uniformNdv result = 0;
    750 
    751 	switch (n_rows)
    752 	{
    753 	case 1:
    754 		result = gl.uniform1dv;
    755 		break;
    756 	case 2:
    757 		result = gl.uniform2dv;
    758 		break;
    759 	case 3:
    760 		result = gl.uniform3dv;
    761 		break;
    762 	case 4:
    763 		result = gl.uniform4dv;
    764 		break;
    765 	default:
    766 		TCU_FAIL("Invalid number of rows");
    767 	}
    768 
    769 	return result;
    770 }
    771 
    772 /** Get proper glUniformNfv routine for vectors with specified number of rows
    773  *
    774  * @param gl     GL functions
    775  * @param n_rows Number of rows
    776  *
    777  * @return Function address
    778  **/
    779 uniformNfv getUniformNfv(const glw::Functions& gl, glw::GLuint n_rows)
    780 {
    781 	uniformNfv result = 0;
    782 
    783 	switch (n_rows)
    784 	{
    785 	case 1:
    786 		result = gl.uniform1fv;
    787 		break;
    788 	case 2:
    789 		result = gl.uniform2fv;
    790 		break;
    791 	case 3:
    792 		result = gl.uniform3fv;
    793 		break;
    794 	case 4:
    795 		result = gl.uniform4fv;
    796 		break;
    797 	default:
    798 		TCU_FAIL("Invalid number of rows");
    799 	}
    800 
    801 	return result;
    802 }
    803 
    804 /** Get proper glUniformNiv routine for vectors with specified number of rows
    805  *
    806  * @param gl     GL functions
    807  * @param n_rows Number of rows
    808  *
    809  * @return Function address
    810  **/
    811 uniformNiv getUniformNiv(const glw::Functions& gl, glw::GLuint n_rows)
    812 {
    813 	uniformNiv result = 0;
    814 
    815 	switch (n_rows)
    816 	{
    817 	case 1:
    818 		result = gl.uniform1iv;
    819 		break;
    820 	case 2:
    821 		result = gl.uniform2iv;
    822 		break;
    823 	case 3:
    824 		result = gl.uniform3iv;
    825 		break;
    826 	case 4:
    827 		result = gl.uniform4iv;
    828 		break;
    829 	default:
    830 		TCU_FAIL("Invalid number of rows");
    831 	}
    832 
    833 	return result;
    834 }
    835 
    836 /** Get proper glUniformNuiv routine for vectors with specified number of rows
    837  *
    838  * @param gl     GL functions
    839  * @param n_rows Number of rows
    840  *
    841  * @return Function address
    842  **/
    843 uniformNuiv getUniformNuiv(const glw::Functions& gl, glw::GLuint n_rows)
    844 {
    845 	uniformNuiv result = 0;
    846 
    847 	switch (n_rows)
    848 	{
    849 	case 1:
    850 		result = gl.uniform1uiv;
    851 		break;
    852 	case 2:
    853 		result = gl.uniform2uiv;
    854 		break;
    855 	case 3:
    856 		result = gl.uniform3uiv;
    857 		break;
    858 	case 4:
    859 		result = gl.uniform4uiv;
    860 		break;
    861 	default:
    862 		TCU_FAIL("Invalid number of rows");
    863 	}
    864 
    865 	return result;
    866 }
    867 
    868 /** Get proper glUniformMatrixNdv routine for matrix with specified number of columns and rows
    869  *
    870  * @param gl     GL functions
    871  * @param n_rows Number of rows
    872  *
    873  * @return Function address
    874  **/
    875 uniformMatrixNdv getUniformMatrixNdv(const glw::Functions& gl, glw::GLuint n_columns, glw::GLuint n_rows)
    876 {
    877 	uniformMatrixNdv result = 0;
    878 
    879 	switch (n_columns)
    880 	{
    881 	case 2:
    882 		switch (n_rows)
    883 		{
    884 		case 2:
    885 			result = gl.uniformMatrix2dv;
    886 			break;
    887 		case 3:
    888 			result = gl.uniformMatrix2x3dv;
    889 			break;
    890 		case 4:
    891 			result = gl.uniformMatrix2x4dv;
    892 			break;
    893 		default:
    894 			TCU_FAIL("Invalid number of rows");
    895 		}
    896 		break;
    897 	case 3:
    898 		switch (n_rows)
    899 		{
    900 		case 2:
    901 			result = gl.uniformMatrix3x2dv;
    902 			break;
    903 		case 3:
    904 			result = gl.uniformMatrix3dv;
    905 			break;
    906 		case 4:
    907 			result = gl.uniformMatrix3x4dv;
    908 			break;
    909 		default:
    910 			TCU_FAIL("Invalid number of rows");
    911 		}
    912 		break;
    913 	case 4:
    914 		switch (n_rows)
    915 		{
    916 		case 2:
    917 			result = gl.uniformMatrix4x2dv;
    918 			break;
    919 		case 3:
    920 			result = gl.uniformMatrix4x3dv;
    921 			break;
    922 		case 4:
    923 			result = gl.uniformMatrix4dv;
    924 			break;
    925 		default:
    926 			TCU_FAIL("Invalid number of rows");
    927 		}
    928 		break;
    929 	default:
    930 		TCU_FAIL("Invalid number of columns");
    931 	}
    932 
    933 	return result;
    934 }
    935 
    936 /** Get proper glUniformMatrixNfv routine for vectors with specified number of columns and rows
    937  *
    938  * @param gl     GL functions
    939  * @param n_rows Number of rows
    940  *
    941  * @return Function address
    942  **/
    943 uniformMatrixNfv getUniformMatrixNfv(const glw::Functions& gl, glw::GLuint n_columns, glw::GLuint n_rows)
    944 {
    945 	uniformMatrixNfv result = 0;
    946 
    947 	switch (n_columns)
    948 	{
    949 	case 2:
    950 		switch (n_rows)
    951 		{
    952 		case 2:
    953 			result = gl.uniformMatrix2fv;
    954 			break;
    955 		case 3:
    956 			result = gl.uniformMatrix2x3fv;
    957 			break;
    958 		case 4:
    959 			result = gl.uniformMatrix2x4fv;
    960 			break;
    961 		default:
    962 			TCU_FAIL("Invalid number of rows");
    963 		}
    964 		break;
    965 	case 3:
    966 		switch (n_rows)
    967 		{
    968 		case 2:
    969 			result = gl.uniformMatrix3x2fv;
    970 			break;
    971 		case 3:
    972 			result = gl.uniformMatrix3fv;
    973 			break;
    974 		case 4:
    975 			result = gl.uniformMatrix3x4fv;
    976 			break;
    977 		default:
    978 			TCU_FAIL("Invalid number of rows");
    979 		}
    980 		break;
    981 	case 4:
    982 		switch (n_rows)
    983 		{
    984 		case 2:
    985 			result = gl.uniformMatrix4x2fv;
    986 			break;
    987 		case 3:
    988 			result = gl.uniformMatrix4x3fv;
    989 			break;
    990 		case 4:
    991 			result = gl.uniformMatrix4fv;
    992 			break;
    993 		default:
    994 			TCU_FAIL("Invalid number of rows");
    995 		}
    996 		break;
    997 	default:
    998 		TCU_FAIL("Invalid number of columns");
    999 	}
   1000 
   1001 	return result;
   1002 }
   1003 
   1004 bool verifyVarying(Program& program, const std::string& parent_name, const Variable::Descriptor& desc,
   1005 				   std::stringstream& stream, bool is_input)
   1006 {
   1007 	GLint  component = 0;
   1008 	GLuint index	 = 0;
   1009 	GLenum interface = GL_PROGRAM_INPUT;
   1010 	GLint  location  = 0;
   1011 
   1012 	if (false == is_input)
   1013 	{
   1014 		interface = GL_PROGRAM_OUTPUT;
   1015 	}
   1016 
   1017 	const std::string& name = Utils::Variable::GetReference(parent_name, desc, Utils::Variable::BASIC, 0);
   1018 
   1019 	try
   1020 	{
   1021 		index = program.GetResourceIndex(name, interface);
   1022 
   1023 		program.GetResource(interface, index, GL_LOCATION, 1 /* size */, &location);
   1024 		program.GetResource(interface, index, GL_LOCATION_COMPONENT, 1 /* size */, &component);
   1025 	}
   1026 	catch (std::exception& exc)
   1027 	{
   1028 		stream << "Failed to query program for varying: " << desc.m_name << ". Reason: " << exc.what() << "\n";
   1029 
   1030 		return false;
   1031 	}
   1032 
   1033 	bool result = true;
   1034 
   1035 	if (location != desc.m_expected_location)
   1036 	{
   1037 		stream << "Attribute: " << desc.m_name << " - invalid location: " << location
   1038 			   << " expected: " << desc.m_expected_location << std::endl;
   1039 		result = false;
   1040 	}
   1041 	if (component != desc.m_expected_component)
   1042 	{
   1043 		stream << "Attribute: " << desc.m_name << " - invalid component: " << component
   1044 			   << " expected: " << desc.m_expected_component << std::endl;
   1045 		result = false;
   1046 	}
   1047 
   1048 	return result;
   1049 }
   1050 
   1051 /** Query program resource for given variable and verify that everything is as expected
   1052  *
   1053  * @param program  Program object
   1054  * @param variable Variable object
   1055  * @param stream   Stream that will be used to log any error
   1056  * @param is_input Selects if varying is input or output
   1057  *
   1058  * @return true if verification is positive, false otherwise
   1059  **/
   1060 bool checkVarying(Program& program, const Variable& variable, std::stringstream& stream, bool is_input)
   1061 {
   1062 	bool result = true;
   1063 
   1064 	if (variable.IsBlock())
   1065 	{
   1066 		Utils::Interface* interface = variable.m_descriptor.m_interface;
   1067 		const size_t	  n_members = interface->m_members.size();
   1068 
   1069 		for (size_t i = 0; i < n_members; ++i)
   1070 		{
   1071 			const Variable::Descriptor& member = interface->m_members[i];
   1072 			bool member_result				   = verifyVarying(program, interface->m_name, member, stream, is_input);
   1073 
   1074 			if (false == member_result)
   1075 			{
   1076 				result = false;
   1077 			}
   1078 		}
   1079 	}
   1080 	/*
   1081 	 To query the the location of struct member by glGetProgramResource, we need pass the variable name "gs_fs_output[0].single",
   1082 	 but in original implementation, the test pass the name "Data.single", which can't get any valid result.
   1083 	 struct Data {
   1084 	 dmat2 single;
   1085 	 dmat2 array[1];
   1086 	 };
   1087 	 layout (location = 0) in Data gs_fs_output[1];
   1088 	 */
   1089 	else if (variable.IsStruct())
   1090 	{
   1091 		Utils::Interface* interface		 = variable.m_descriptor.m_interface;
   1092 		const size_t	  n_members		 = interface->m_members.size();
   1093 		std::string		  structVariable = variable.m_descriptor.m_name;
   1094 		// If struct variable is an array
   1095 		if (0 != variable.m_descriptor.m_n_array_elements)
   1096 		{
   1097 			for (GLuint i = 0; i < variable.m_descriptor.m_n_array_elements; i++)
   1098 			{
   1099 				GLchar buffer[16];
   1100 				sprintf(buffer, "%d", i);
   1101 				structVariable.append("[");
   1102 				structVariable.append(buffer);
   1103 				structVariable.append("]");
   1104 				for (size_t j = 0; j < n_members; ++j)
   1105 				{
   1106 					const Variable::Descriptor& member = interface->m_members[j];
   1107 					bool member_result = verifyVarying(program, structVariable, member, stream, is_input);
   1108 
   1109 					if (false == member_result)
   1110 					{
   1111 						result = false;
   1112 					}
   1113 				}
   1114 			}
   1115 		}
   1116 		else
   1117 		{
   1118 			for (GLuint i = 0; i < n_members; ++i)
   1119 			{
   1120 				const Variable::Descriptor& member = interface->m_members[i];
   1121 				bool member_result				   = verifyVarying(program, structVariable, member, stream, is_input);
   1122 
   1123 				if (false == member_result)
   1124 				{
   1125 					result = false;
   1126 				}
   1127 			}
   1128 		}
   1129 	}
   1130 	else
   1131 	{
   1132 		result = verifyVarying(program, "", variable.m_descriptor, stream, is_input);
   1133 	}
   1134 	return result;
   1135 }
   1136 
   1137 /** Query program resource for given variable and verify that everything is as expected
   1138  *
   1139  * @param program  Program object
   1140  * @param variable Variable object
   1141  * @param stream   Stream that will be used to log any error
   1142  *
   1143  * @return true if verification is positive, false otherwise
   1144  **/
   1145 bool checkUniform(Program& program, const Utils::Variable& variable, std::stringstream& stream)
   1146 {
   1147 	bool result = true;
   1148 
   1149 	if (false == variable.IsBlock())
   1150 	{
   1151 		TCU_FAIL("Not implemented");
   1152 	}
   1153 	else
   1154 	{
   1155 		Utils::Interface* interface = variable.m_descriptor.m_interface;
   1156 
   1157 		size_t size = interface->m_members.size();
   1158 
   1159 		std::vector<GLuint>		 indices;
   1160 		std::vector<const char*> names;
   1161 		std::vector<std::string> names_str;
   1162 		std::vector<GLint>		 offsets;
   1163 
   1164 		indices.resize(size);
   1165 		names.resize(size);
   1166 		names_str.resize(size);
   1167 		offsets.resize(size);
   1168 
   1169 		for (size_t i = 0; i < size; ++i)
   1170 		{
   1171 			indices[i] = 0;
   1172 			offsets[i] = 0;
   1173 
   1174 			const std::string& name =
   1175 				Utils::Variable::GetReference(interface->m_name, interface->m_members[i], Utils::Variable::BASIC, 0);
   1176 
   1177 			if (Utils::Variable::INTERFACE == interface->m_members[i].m_type)
   1178 			{
   1179 				const std::string& member_name = Utils::Variable::GetReference(
   1180 					name, interface->m_members[i].m_interface->m_members[0], Utils::Variable::BASIC, 0);
   1181 
   1182 				names_str[i] = member_name;
   1183 			}
   1184 			else
   1185 			{
   1186 				names_str[i] = name;
   1187 			}
   1188 
   1189 			names[i] = names_str[i].c_str();
   1190 		}
   1191 
   1192 		try
   1193 		{
   1194 			program.GetUniformIndices(static_cast<glw::GLsizei>(size), &names[0], &indices[0]);
   1195 			program.GetActiveUniformsiv(static_cast<glw::GLsizei>(size), &indices[0], GL_UNIFORM_OFFSET, &offsets[0]);
   1196 		}
   1197 		catch (std::exception& exc)
   1198 		{
   1199 			stream << "Failed to query program for uniforms in block: " << variable.m_descriptor.m_name
   1200 				   << ". Reason: " << exc.what() << "\n";
   1201 
   1202 			return false;
   1203 		}
   1204 
   1205 		for (size_t i = 0; i < size; ++i)
   1206 		{
   1207 			Utils::Variable::Descriptor& desc = interface->m_members[i];
   1208 
   1209 			if (offsets[i] != (GLint)desc.m_offset)
   1210 			{
   1211 				stream << "Uniform: " << desc.m_name << " - invalid offset: " << offsets[i]
   1212 					   << " expected: " << desc.m_offset << std::endl;
   1213 				result = false;
   1214 			}
   1215 		}
   1216 	}
   1217 
   1218 	return result;
   1219 }
   1220 
   1221 /** Query program resource for given variable and verify that everything is as expected
   1222  *
   1223  * @param program  Program object
   1224  * @param variable Variable object
   1225  * @param stream   Stream that will be used to log any error
   1226  *
   1227  * @return true if verification is positive, false otherwise
   1228  **/
   1229 bool checkSSB(Program& program, const Utils::Variable& variable, std::stringstream& stream)
   1230 {
   1231 	bool result = true;
   1232 
   1233 	if (false == variable.IsBlock())
   1234 	{
   1235 		TCU_FAIL("Not implemented");
   1236 	}
   1237 	else
   1238 	{
   1239 		Utils::Interface* interface = variable.m_descriptor.m_interface;
   1240 
   1241 		size_t size = interface->m_members.size();
   1242 
   1243 		for (size_t i = 0; i < size; ++i)
   1244 		{
   1245 			GLuint		index	= 0;
   1246 			std::string name_str = "";
   1247 			GLint		offset   = 0;
   1248 
   1249 			const std::string& name =
   1250 				Utils::Variable::GetReference(interface->m_name, interface->m_members[i], Utils::Variable::BASIC, 0);
   1251 
   1252 			if (Utils::Variable::INTERFACE == interface->m_members[i].m_type)
   1253 			{
   1254 				const std::string& member_name = Utils::Variable::GetReference(
   1255 					name, interface->m_members[i].m_interface->m_members[0], Utils::Variable::BASIC, 0);
   1256 
   1257 				name_str = member_name;
   1258 			}
   1259 			else
   1260 			{
   1261 				name_str = name;
   1262 			}
   1263 
   1264 			try
   1265 			{
   1266 				index = program.GetResourceIndex(name_str, GL_BUFFER_VARIABLE);
   1267 
   1268 				program.GetResource(GL_BUFFER_VARIABLE, index, GL_OFFSET, 1, &offset);
   1269 			}
   1270 			catch (std::exception& exc)
   1271 			{
   1272 				stream << "Failed to query program for buffer variable: " << variable.m_descriptor.m_name
   1273 					   << ". Reason: " << exc.what() << "\n";
   1274 
   1275 				return false;
   1276 			}
   1277 
   1278 			Utils::Variable::Descriptor& desc = interface->m_members[i];
   1279 
   1280 			if (offset != (GLint)desc.m_offset)
   1281 			{
   1282 				stream << "Uniform: " << desc.m_name << " - invalid offset: " << offset
   1283 					   << " expected: " << desc.m_offset << std::endl;
   1284 				result = false;
   1285 			}
   1286 		}
   1287 	}
   1288 
   1289 	return result;
   1290 }
   1291 
   1292 /** Query program resources at given stage and verifies results
   1293  *
   1294  * @param program           Program object
   1295  * @param program_interface Definition of program interface
   1296  * @param stage             Stage to be verified
   1297  * @param check_inputs      Select if inputs should be verified
   1298  * @param check_outputs     Select if output should be verified
   1299  * @param check_uniforms    Select if uniforms should be verified
   1300  * @param check_ssbs        Select if buffers should be verified
   1301  * @param stream            Stream that will be used to log any error
   1302  *
   1303  * @return true if verification is positive, false otherwise
   1304  **/
   1305 bool checkProgramStage(Program& program, const ProgramInterface& program_interface, Utils::Shader::STAGES stage,
   1306 					   bool check_inputs, bool check_outputs, bool check_uniforms, bool check_ssbs,
   1307 					   std::stringstream& stream)
   1308 {
   1309 	typedef Variable::PtrVector::const_iterator const_iterator;
   1310 
   1311 	const ShaderInterface& interface = program_interface.GetShaderInterface(stage);
   1312 
   1313 	bool result = true;
   1314 
   1315 	/* Inputs */
   1316 	if (true == check_inputs)
   1317 	{
   1318 		const Variable::PtrVector& inputs = interface.m_inputs;
   1319 
   1320 		for (const_iterator it = inputs.begin(); it != inputs.end(); ++it)
   1321 		{
   1322 			if (false == checkVarying(program, **it, stream, true))
   1323 			{
   1324 				result = false;
   1325 			}
   1326 		}
   1327 	}
   1328 
   1329 	/* Outputs */
   1330 	if (true == check_outputs)
   1331 	{
   1332 		const Variable::PtrVector& outputs = interface.m_outputs;
   1333 
   1334 		for (const_iterator it = outputs.begin(); it != outputs.end(); ++it)
   1335 		{
   1336 			if (false == checkVarying(program, **it, stream, false))
   1337 			{
   1338 				result = false;
   1339 			}
   1340 		}
   1341 	}
   1342 
   1343 	/* Uniforms */
   1344 	if (true == check_uniforms)
   1345 	{
   1346 		const Variable::PtrVector& uniforms = interface.m_uniforms;
   1347 
   1348 		for (const_iterator it = uniforms.begin(); it != uniforms.end(); ++it)
   1349 		{
   1350 			if (false == checkUniform(program, **it, stream))
   1351 			{
   1352 				result = false;
   1353 			}
   1354 		}
   1355 	}
   1356 
   1357 	/* SSBs */
   1358 	if (true == check_ssbs)
   1359 	{
   1360 		const Variable::PtrVector& ssbs = interface.m_ssb_blocks;
   1361 
   1362 		for (const_iterator it = ssbs.begin(); it != ssbs.end(); ++it)
   1363 		{
   1364 			if (false == checkSSB(program, **it, stream))
   1365 			{
   1366 				result = false;
   1367 			}
   1368 		}
   1369 	}
   1370 
   1371 	return result;
   1372 }
   1373 
   1374 /** Query resources of monolithic compute program and verifies results
   1375  *
   1376  * @param program           Program object
   1377  * @param program_interface Definition of program interface
   1378  * @param stream            Stream that will be used to log any error
   1379  *
   1380  * @return true if verification is positive, false otherwise
   1381  **/
   1382 bool checkMonolithicComputeProgramInterface(Program& program, const ProgramInterface& program_interface,
   1383 											std::stringstream& stream)
   1384 {
   1385 	bool result = true;
   1386 
   1387 	if (false == checkProgramStage(program, program_interface, Shader::COMPUTE, false, false, true, true, stream))
   1388 	{
   1389 		result = false;
   1390 	}
   1391 
   1392 	/* Done */
   1393 	return result;
   1394 }
   1395 
   1396 /** Query resources of monolithic draw program and verifies results
   1397  *
   1398  * @param program           Program object
   1399  * @param program_interface Definition of program interface
   1400  * @param stream            Stream that will be used to log any error
   1401  *
   1402  * @return true if verification is positive, false otherwise
   1403  **/
   1404 bool checkMonolithicDrawProgramInterface(Program& program, const ProgramInterface& program_interface,
   1405 										 std::stringstream& stream)
   1406 {
   1407 	bool result = true;
   1408 
   1409 	if (false == checkProgramStage(program, program_interface, Shader::VERTEX, true, false, true, true, stream))
   1410 	{
   1411 		result = false;
   1412 	}
   1413 
   1414 	/* Done */
   1415 	return result;
   1416 }
   1417 
   1418 /** Query resources of separable draw program and verifies results
   1419  *
   1420  * @param program           Program object
   1421  * @param program_interface Definition of program interface
   1422  * @param stream            Stream that will be used to log any error
   1423  *
   1424  * @return true if verification is positive, false otherwise
   1425  **/
   1426 bool checkSeparableDrawProgramInterface(Program& program, const ProgramInterface& program_interface,
   1427 										Utils::Shader::STAGES stage, std::stringstream& stream)
   1428 {
   1429 	bool result = true;
   1430 
   1431 	if (false == checkProgramStage(program, program_interface, stage, true, true, true, true, stream))
   1432 	{
   1433 		result = false;
   1434 	}
   1435 
   1436 	/* Done */
   1437 	return result;
   1438 }
   1439 
   1440 /** Check if extension is supported
   1441  *
   1442  * @param context        Test context
   1443  * @param extension_name Name of extension
   1444  *
   1445  * @return true if extension is supported, false otherwise
   1446  **/
   1447 bool isExtensionSupported(deqp::Context& context, const GLchar* extension_name)
   1448 {
   1449 	const std::vector<std::string>& extensions = context.getContextInfo().getExtensions();
   1450 
   1451 	if (std::find(extensions.begin(), extensions.end(), extension_name) == extensions.end())
   1452 	{
   1453 		return false;
   1454 	}
   1455 
   1456 	return true;
   1457 }
   1458 
   1459 /** Check if GL context meets version requirements
   1460  *
   1461  * @param gl             Functions
   1462  * @param required_major Minimum required MAJOR_VERSION
   1463  * @param required_minor Minimum required MINOR_VERSION
   1464  *
   1465  * @return true if GL context version is at least as requested, false otherwise
   1466  **/
   1467 bool isGLVersionAtLeast(const Functions& gl, GLint required_major, GLint required_minor)
   1468 {
   1469 	glw::GLint major = 0;
   1470 	glw::GLint minor = 0;
   1471 
   1472 	gl.getIntegerv(GL_MAJOR_VERSION, &major);
   1473 	gl.getIntegerv(GL_MINOR_VERSION, &minor);
   1474 
   1475 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   1476 
   1477 	if (major > required_major)
   1478 	{
   1479 		/* Major is higher than required one */
   1480 		return true;
   1481 	}
   1482 	else if (major == required_major)
   1483 	{
   1484 		if (minor >= required_minor)
   1485 		{
   1486 			/* Major is equal to required one */
   1487 			/* Minor is higher than or equal to required one */
   1488 			return true;
   1489 		}
   1490 		else
   1491 		{
   1492 			/* Major is equal to required one */
   1493 			/* Minor is lower than required one */
   1494 			return false;
   1495 		}
   1496 	}
   1497 	else
   1498 	{
   1499 		/* Major is lower than required one */
   1500 		return false;
   1501 	}
   1502 }
   1503 
   1504 /** Replace first occurance of <token> with <text> in <string> starting at <search_posistion>
   1505  *
   1506  * @param token           Token string
   1507  * @param search_position Position at which find will start, it is updated to position at which replaced text ends
   1508  * @param text            String that will be used as replacement for <token>
   1509  * @param string          String to work on
   1510  **/
   1511 void replaceToken(const GLchar* token, size_t& search_position, const GLchar* text, std::string& string)
   1512 {
   1513 	const size_t text_length	= strlen(text);
   1514 	const size_t token_length   = strlen(token);
   1515 	const size_t token_position = string.find(token, search_position);
   1516 
   1517 #if DEBUG_REPLACE_TOKEN
   1518 	if (std::string::npos == token_position)
   1519 	{
   1520 		string.append("\n\nInvalid token: ");
   1521 		string.append(token);
   1522 
   1523 		TCU_FAIL(string.c_str());
   1524 	}
   1525 #endif /* DEBUG_REPLACE_TOKEN */
   1526 
   1527 	string.replace(token_position, token_length, text, text_length);
   1528 
   1529 	search_position = token_position + text_length;
   1530 }
   1531 
   1532 /** Replace all occurances of <token> with <text> in <string>
   1533  *
   1534  * @param token           Token string
   1535  * @param text            String that will be used as replacement for <token>
   1536  * @param string          String to work on
   1537  **/
   1538 void replaceAllTokens(const GLchar* token, const GLchar* text, std::string& string)
   1539 {
   1540 	const size_t text_length  = strlen(text);
   1541 	const size_t token_length = strlen(token);
   1542 
   1543 	size_t search_position = 0;
   1544 
   1545 	while (1)
   1546 	{
   1547 		const size_t token_position = string.find(token, search_position);
   1548 
   1549 		if (std::string::npos == token_position)
   1550 		{
   1551 			break;
   1552 		}
   1553 
   1554 		search_position = token_position + text_length;
   1555 
   1556 		string.replace(token_position, token_length, text, text_length);
   1557 	}
   1558 }
   1559 
   1560 /** Rounds up the value to the next power of 2.
   1561  * This routine does not work for 0, see the url for explanations.
   1562  *
   1563  * @param value Starting point
   1564  *
   1565  * @return Calculated value
   1566  **/
   1567 glw::GLuint roundUpToPowerOf2(glw::GLuint value)
   1568 {
   1569 	/* Taken from: graphics.stanford.edu/~seander/bithacks.html */
   1570 	--value;
   1571 
   1572 	value |= value >> 1;
   1573 	value |= value >> 2;
   1574 	value |= value >> 4;
   1575 	value |= value >> 8;
   1576 	value |= value >> 16;
   1577 
   1578 	++value;
   1579 
   1580 	return value;
   1581 }
   1582 
   1583 /** Insert elements of list into string.
   1584  * List in string is represented either by token "LIST" or "SEPARATORLIST".
   1585  * If SEPARATORLIST is available, than SEPARATOR is replaced with <separator>.
   1586  * LIST is replaced with <element>SEPARATORLIST
   1587  *
   1588  * @param element         Element to be inserted
   1589  * @param separator       Separator inserted between elements
   1590  * @param search_position Position in string, where search for list should start
   1591  * @param string          String
   1592  **/
   1593 void insertElementOfList(const GLchar* element, const GLchar* separator, size_t& search_position, std::string& string)
   1594 {
   1595 	static const char* list		= g_list;
   1596 	static const char* sep_list = "SEPARATORLIST";
   1597 
   1598 	/* Try to get "list" positions */
   1599 	const size_t list_position	 = string.find(list, search_position);
   1600 	const size_t sep_list_position = string.find(sep_list, search_position);
   1601 
   1602 	/* There is no list in string */
   1603 	if (std::string::npos == list_position)
   1604 	{
   1605 		return;
   1606 	}
   1607 
   1608 	if (9 /* strlen(SEPARATOR) */ == list_position - sep_list_position)
   1609 	{
   1610 		replaceToken("SEPARATOR", search_position, separator, string);
   1611 	}
   1612 
   1613 	/* Save search_position */
   1614 	const size_t start_position = search_position;
   1615 
   1616 	/* Prepare new element */
   1617 	replaceToken("LIST", search_position, "ELEMENTSEPARATORLIST", string);
   1618 
   1619 	/* Restore search_position */
   1620 	search_position = start_position;
   1621 
   1622 	/* Replace element and separator */
   1623 	replaceToken("ELEMENT", search_position, element, string);
   1624 }
   1625 
   1626 /** Close list in string.
   1627  * If SEPARATORLIST is available, than SEPARATOR is replaced with <separator>
   1628  * LIST is replaced with ""
   1629  *
   1630  * @param separator       Separator inserted between elements
   1631  * @param search_position Position in string, where search for list should start
   1632  * @param string          String
   1633  **/
   1634 void endList(const glw::GLchar* separator, size_t& search_position, std::string& string)
   1635 {
   1636 	const size_t sep_position = string.find("SEPARATOR", search_position);
   1637 	if (std::string::npos != sep_position)
   1638 	{
   1639 		replaceToken("SEPARATOR", search_position, separator, string);
   1640 	}
   1641 
   1642 	replaceToken("LIST", search_position, "", string);
   1643 }
   1644 
   1645 /* Buffer constants */
   1646 const GLuint Buffer::m_invalid_id = -1;
   1647 
   1648 /** Constructor.
   1649  *
   1650  * @param context CTS context.
   1651  **/
   1652 Buffer::Buffer(deqp::Context& context) : m_id(m_invalid_id), m_buffer(Array), m_context(context)
   1653 {
   1654 }
   1655 
   1656 /** Destructor
   1657  *
   1658  **/
   1659 Buffer::~Buffer()
   1660 {
   1661 	Release();
   1662 }
   1663 
   1664 /** Initialize buffer instance
   1665  *
   1666  * @param buffer Buffer type
   1667  * @param usage  Buffer usage enum
   1668  * @param size   <size> parameter
   1669  * @param data   <data> parameter
   1670  **/
   1671 void Buffer::Init(BUFFERS buffer, USAGE usage, GLsizeiptr size, GLvoid* data)
   1672 {
   1673 	/* Delete previous buffer instance */
   1674 	Release();
   1675 
   1676 	m_buffer = buffer;
   1677 
   1678 	const Functions& gl = m_context.getRenderContext().getFunctions();
   1679 
   1680 	Generate(gl, m_id);
   1681 	Bind(gl, m_id, m_buffer);
   1682 	Data(gl, m_buffer, usage, size, data);
   1683 }
   1684 
   1685 /** Release buffer instance
   1686  *
   1687  **/
   1688 void Buffer::Release()
   1689 {
   1690 	if (m_invalid_id != m_id)
   1691 	{
   1692 		const Functions& gl = m_context.getRenderContext().getFunctions();
   1693 
   1694 		gl.deleteBuffers(1, &m_id);
   1695 		m_id = m_invalid_id;
   1696 	}
   1697 }
   1698 
   1699 /** Binds buffer to its target
   1700  *
   1701  **/
   1702 void Buffer::Bind() const
   1703 {
   1704 	const Functions& gl = m_context.getRenderContext().getFunctions();
   1705 
   1706 	Bind(gl, m_id, m_buffer);
   1707 }
   1708 
   1709 /** Binds indexed buffer
   1710  *
   1711  * @param index <index> parameter
   1712  **/
   1713 void Buffer::BindBase(GLuint index) const
   1714 {
   1715 	const Functions& gl = m_context.getRenderContext().getFunctions();
   1716 
   1717 	BindBase(gl, m_id, m_buffer, index);
   1718 }
   1719 
   1720 /** Binds range of buffer
   1721  *
   1722  * @param index  <index> parameter
   1723  * @param offset <offset> parameter
   1724  * @param size   <size> parameter
   1725  **/
   1726 void Buffer::BindRange(GLuint index, GLintptr offset, GLsizeiptr size) const
   1727 {
   1728 	const Functions& gl = m_context.getRenderContext().getFunctions();
   1729 
   1730 	BindRange(gl, m_id, m_buffer, index, offset, size);
   1731 }
   1732 
   1733 /** Allocate memory for buffer and sends initial content
   1734  *
   1735  * @param usage  Buffer usage enum
   1736  * @param size   <size> parameter
   1737  * @param data   <data> parameter
   1738  **/
   1739 void Buffer::Data(USAGE usage, glw::GLsizeiptr size, glw::GLvoid* data)
   1740 {
   1741 	const Functions& gl = m_context.getRenderContext().getFunctions();
   1742 
   1743 	Data(gl, m_buffer, usage, size, data);
   1744 }
   1745 
   1746 /** Maps contents of buffer into CPU space
   1747  *
   1748  * @param access Requested access
   1749  *
   1750  * @return Pointer to memory region available for CPU
   1751  **/
   1752 GLvoid* Buffer::Map(ACCESS access)
   1753 {
   1754 	const Functions& gl = m_context.getRenderContext().getFunctions();
   1755 
   1756 	return Map(gl, m_buffer, access);
   1757 }
   1758 
   1759 /** Allocate memory for buffer and sends initial content
   1760  *
   1761  * @param offset Offset in buffer
   1762  * @param size   <size> parameter
   1763  * @param data   <data> parameter
   1764  **/
   1765 void Buffer::SubData(glw::GLintptr offset, glw::GLsizeiptr size, glw::GLvoid* data)
   1766 {
   1767 	const Functions& gl = m_context.getRenderContext().getFunctions();
   1768 
   1769 	SubData(gl, m_buffer, offset, size, data);
   1770 }
   1771 
   1772 /** Maps contents of buffer into CPU space
   1773  **/
   1774 void Buffer::UnMap()
   1775 {
   1776 	const Functions& gl = m_context.getRenderContext().getFunctions();
   1777 
   1778 	return UnMap(gl, m_buffer);
   1779 }
   1780 
   1781 /** Bind buffer to given target
   1782  *
   1783  * @param gl     GL functions
   1784  * @param id     Id of buffer
   1785  * @param buffer Buffer enum
   1786  **/
   1787 void Buffer::Bind(const Functions& gl, GLuint id, BUFFERS buffer)
   1788 {
   1789 	GLenum target = GetBufferGLenum(buffer);
   1790 
   1791 	gl.bindBuffer(target, id);
   1792 	GLU_EXPECT_NO_ERROR(gl.getError(), "BindBuffer");
   1793 }
   1794 
   1795 /** Binds indexed buffer
   1796  *
   1797  * @param gl     GL functions
   1798  * @param id     Id of buffer
   1799  * @param buffer Buffer enum
   1800  * @param index  <index> parameter
   1801  **/
   1802 void Buffer::BindBase(const Functions& gl, GLuint id, BUFFERS buffer, GLuint index)
   1803 {
   1804 	GLenum target = GetBufferGLenum(buffer);
   1805 
   1806 	gl.bindBufferBase(target, index, id);
   1807 	GLU_EXPECT_NO_ERROR(gl.getError(), "BindBufferBase");
   1808 }
   1809 
   1810 /** Binds buffer range
   1811  *
   1812  * @param gl     GL functions
   1813  * @param id     Id of buffer
   1814  * @param buffer Buffer enum
   1815  * @param index  <index> parameter
   1816  * @param offset <offset> parameter
   1817  * @param size   <size> parameter
   1818  **/
   1819 void Buffer::BindRange(const Functions& gl, GLuint id, BUFFERS buffer, GLuint index, GLintptr offset, GLsizeiptr size)
   1820 {
   1821 	GLenum target = GetBufferGLenum(buffer);
   1822 
   1823 	gl.bindBufferRange(target, index, id, offset, size);
   1824 	GLU_EXPECT_NO_ERROR(gl.getError(), "BindBufferRange");
   1825 }
   1826 
   1827 /** Allocate memory for buffer and sends initial content
   1828  *
   1829  * @param gl     GL functions
   1830  * @param buffer Buffer enum
   1831  * @param usage  Buffer usage enum
   1832  * @param size   <size> parameter
   1833  * @param data   <data> parameter
   1834  **/
   1835 void Buffer::Data(const glw::Functions& gl, BUFFERS buffer, USAGE usage, glw::GLsizeiptr size, glw::GLvoid* data)
   1836 {
   1837 	GLenum target   = GetBufferGLenum(buffer);
   1838 	GLenum gl_usage = GetUsageGLenum(usage);
   1839 
   1840 	gl.bufferData(target, size, data, gl_usage);
   1841 	GLU_EXPECT_NO_ERROR(gl.getError(), "BufferData");
   1842 }
   1843 
   1844 /** Allocate memory for buffer and sends initial content
   1845  *
   1846  * @param gl     GL functions
   1847  * @param buffer Buffer enum
   1848  * @param offset Offset in buffer
   1849  * @param size   <size> parameter
   1850  * @param data   <data> parameter
   1851  **/
   1852 void Buffer::SubData(const glw::Functions& gl, BUFFERS buffer, glw::GLintptr offset, glw::GLsizeiptr size,
   1853 					 glw::GLvoid* data)
   1854 {
   1855 	GLenum target = GetBufferGLenum(buffer);
   1856 
   1857 	gl.bufferSubData(target, offset, size, data);
   1858 	GLU_EXPECT_NO_ERROR(gl.getError(), "BufferSubData");
   1859 }
   1860 
   1861 /** Generate buffer
   1862  *
   1863  * @param gl     GL functions
   1864  * @param out_id Id of buffer
   1865  **/
   1866 void Buffer::Generate(const Functions& gl, GLuint& out_id)
   1867 {
   1868 	GLuint id = m_invalid_id;
   1869 
   1870 	gl.genBuffers(1, &id);
   1871 	GLU_EXPECT_NO_ERROR(gl.getError(), "GenBuffers");
   1872 
   1873 	if (m_invalid_id == id)
   1874 	{
   1875 		TCU_FAIL("Got invalid id");
   1876 	}
   1877 
   1878 	out_id = id;
   1879 }
   1880 
   1881 /** Maps buffer content
   1882  *
   1883  * @param gl     GL functions
   1884  * @param buffer Buffer enum
   1885  * @param access Access rights for mapped region
   1886  *
   1887  * @return Mapped memory
   1888  **/
   1889 void* Buffer::Map(const Functions& gl, BUFFERS buffer, ACCESS access)
   1890 {
   1891 	GLenum target	= GetBufferGLenum(buffer);
   1892 	GLenum gl_access = GetAccessGLenum(access);
   1893 
   1894 	void* result = gl.mapBuffer(target, gl_access);
   1895 	GLU_EXPECT_NO_ERROR(gl.getError(), "MapBuffer");
   1896 
   1897 	return result;
   1898 }
   1899 
   1900 /** Unmaps buffer
   1901  *
   1902  **/
   1903 void Buffer::UnMap(const Functions& gl, BUFFERS buffer)
   1904 {
   1905 	GLenum target = GetBufferGLenum(buffer);
   1906 
   1907 	gl.unmapBuffer(target);
   1908 	GLU_EXPECT_NO_ERROR(gl.getError(), "UnmapBuffer");
   1909 }
   1910 
   1911 /** Return GLenum representation of requested access
   1912  *
   1913  * @param access Requested access
   1914  *
   1915  * @return GLenum value
   1916  **/
   1917 GLenum Buffer::GetAccessGLenum(ACCESS access)
   1918 {
   1919 	GLenum result = 0;
   1920 
   1921 	switch (access)
   1922 	{
   1923 	case ReadOnly:
   1924 		result = GL_READ_ONLY;
   1925 		break;
   1926 	case WriteOnly:
   1927 		result = GL_WRITE_ONLY;
   1928 		break;
   1929 	case ReadWrite:
   1930 		result = GL_READ_WRITE;
   1931 		break;
   1932 	default:
   1933 		TCU_FAIL("Invalid enum");
   1934 	}
   1935 
   1936 	return result;
   1937 }
   1938 
   1939 /** Return GLenum representation of requested buffer type
   1940  *
   1941  * @param buffer Requested buffer type
   1942  *
   1943  * @return GLenum value
   1944  **/
   1945 GLenum Buffer::GetBufferGLenum(BUFFERS buffer)
   1946 {
   1947 	GLenum result = 0;
   1948 
   1949 	switch (buffer)
   1950 	{
   1951 	case Array:
   1952 		result = GL_ARRAY_BUFFER;
   1953 		break;
   1954 	case Element:
   1955 		result = GL_ELEMENT_ARRAY_BUFFER;
   1956 		break;
   1957 	case Shader_Storage:
   1958 		result = GL_SHADER_STORAGE_BUFFER;
   1959 		break;
   1960 	case Texture:
   1961 		result = GL_TEXTURE_BUFFER;
   1962 		break;
   1963 	case Transform_feedback:
   1964 		result = GL_TRANSFORM_FEEDBACK_BUFFER;
   1965 		break;
   1966 	case Uniform:
   1967 		result = GL_UNIFORM_BUFFER;
   1968 		break;
   1969 	default:
   1970 		TCU_FAIL("Invalid enum");
   1971 	}
   1972 
   1973 	return result;
   1974 }
   1975 
   1976 /** Return GLenum representation of requested usage
   1977  *
   1978  * @param usage Requested usage
   1979  *
   1980  * @return GLenum value
   1981  **/
   1982 GLenum Buffer::GetUsageGLenum(USAGE usage)
   1983 {
   1984 	GLenum result = 0;
   1985 
   1986 	switch (usage)
   1987 	{
   1988 	case DynamicCopy:
   1989 		result = GL_DYNAMIC_COPY;
   1990 		break;
   1991 	case DynamicDraw:
   1992 		result = GL_DYNAMIC_DRAW;
   1993 		break;
   1994 	case DynamicRead:
   1995 		result = GL_DYNAMIC_READ;
   1996 		break;
   1997 	case StaticCopy:
   1998 		result = GL_STATIC_COPY;
   1999 		break;
   2000 	case StaticDraw:
   2001 		result = GL_STATIC_DRAW;
   2002 		break;
   2003 	case StaticRead:
   2004 		result = GL_STATIC_READ;
   2005 		break;
   2006 	case StreamCopy:
   2007 		result = GL_STREAM_COPY;
   2008 		break;
   2009 	case StreamDraw:
   2010 		result = GL_STREAM_DRAW;
   2011 		break;
   2012 	case StreamRead:
   2013 		result = GL_STREAM_READ;
   2014 		break;
   2015 	default:
   2016 		TCU_FAIL("Invalid enum");
   2017 	}
   2018 
   2019 	return result;
   2020 }
   2021 
   2022 /** Returns name of buffer target
   2023  *
   2024  * @param buffer Target enum
   2025  *
   2026  * @return Name of target
   2027  **/
   2028 const GLchar* Buffer::GetBufferName(BUFFERS buffer)
   2029 {
   2030 	const GLchar* name = 0;
   2031 
   2032 	switch (buffer)
   2033 	{
   2034 	case Array:
   2035 		name = "Array";
   2036 		break;
   2037 	case Element:
   2038 		name = "Element";
   2039 		break;
   2040 	case Shader_Storage:
   2041 		name = "Shader_Storage";
   2042 		break;
   2043 	case Texture:
   2044 		name = "Texture";
   2045 		break;
   2046 	case Transform_feedback:
   2047 		name = "Transform_feedback";
   2048 		break;
   2049 	case Uniform:
   2050 		name = "Uniform";
   2051 		break;
   2052 	default:
   2053 		TCU_FAIL("Invalid enum");
   2054 	}
   2055 
   2056 	return name;
   2057 }
   2058 
   2059 /* Framebuffer constants */
   2060 const GLuint Framebuffer::m_invalid_id = -1;
   2061 
   2062 /** Constructor
   2063  *
   2064  * @param context CTS context
   2065  **/
   2066 Framebuffer::Framebuffer(deqp::Context& context) : m_id(m_invalid_id), m_context(context)
   2067 {
   2068 	/* Nothing to be done here */
   2069 }
   2070 
   2071 /** Destructor
   2072  *
   2073  **/
   2074 Framebuffer::~Framebuffer()
   2075 {
   2076 	Release();
   2077 }
   2078 
   2079 /** Initialize framebuffer instance
   2080  *
   2081  **/
   2082 void Framebuffer::Init()
   2083 {
   2084 	/* Delete previous instance */
   2085 	Release();
   2086 
   2087 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2088 
   2089 	Generate(gl, m_id);
   2090 }
   2091 
   2092 /** Release framebuffer instance
   2093  *
   2094  **/
   2095 void Framebuffer::Release()
   2096 {
   2097 	if (m_invalid_id != m_id)
   2098 	{
   2099 		const Functions& gl = m_context.getRenderContext().getFunctions();
   2100 
   2101 		gl.deleteFramebuffers(1, &m_id);
   2102 		m_id = m_invalid_id;
   2103 	}
   2104 }
   2105 
   2106 /** Attach texture to specified attachment
   2107  *
   2108  * @param attachment Attachment
   2109  * @param texture_id Texture id
   2110  * @param width      Texture width
   2111  * @param height     Texture height
   2112  **/
   2113 void Framebuffer::AttachTexture(GLenum attachment, GLuint texture_id, GLuint width, GLuint height)
   2114 {
   2115 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2116 
   2117 	AttachTexture(gl, attachment, texture_id, width, height);
   2118 }
   2119 
   2120 /** Binds framebuffer to DRAW_FRAMEBUFFER
   2121  *
   2122  **/
   2123 void Framebuffer::Bind()
   2124 {
   2125 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2126 
   2127 	Bind(gl, m_id);
   2128 }
   2129 
   2130 /** Clear framebuffer
   2131  *
   2132  * @param mask <mask> parameter of glClear. Decides which shall be cleared
   2133  **/
   2134 void Framebuffer::Clear(GLenum mask)
   2135 {
   2136 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2137 
   2138 	Clear(gl, mask);
   2139 }
   2140 
   2141 /** Specifies clear color
   2142  *
   2143  * @param red   Red channel
   2144  * @param green Green channel
   2145  * @param blue  Blue channel
   2146  * @param alpha Alpha channel
   2147  **/
   2148 void Framebuffer::ClearColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha)
   2149 {
   2150 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2151 
   2152 	ClearColor(gl, red, green, blue, alpha);
   2153 }
   2154 
   2155 /** Attach texture to specified attachment
   2156  *
   2157  * @param gl         GL functions
   2158  * @param attachment Attachment
   2159  * @param texture_id Texture id
   2160  * @param width      Texture width
   2161  * @param height     Texture height
   2162  **/
   2163 void Framebuffer::AttachTexture(const Functions& gl, GLenum attachment, GLuint texture_id, GLuint width, GLuint height)
   2164 {
   2165 	gl.framebufferTexture(GL_DRAW_FRAMEBUFFER, attachment, texture_id, 0 /* level */);
   2166 	GLU_EXPECT_NO_ERROR(gl.getError(), "FramebufferTexture");
   2167 
   2168 	gl.viewport(0 /* x */, 0 /* y */, width, height);
   2169 	GLU_EXPECT_NO_ERROR(gl.getError(), "Viewport");
   2170 }
   2171 
   2172 /** Binds framebuffer to DRAW_FRAMEBUFFER
   2173  *
   2174  * @param gl GL functions
   2175  * @param id ID of framebuffer
   2176  **/
   2177 void Framebuffer::Bind(const Functions& gl, GLuint id)
   2178 {
   2179 	gl.bindFramebuffer(GL_DRAW_FRAMEBUFFER, id);
   2180 	GLU_EXPECT_NO_ERROR(gl.getError(), "BindFramebuffer");
   2181 }
   2182 
   2183 /** Clear framebuffer
   2184  *
   2185  * @param gl   GL functions
   2186  * @param mask <mask> parameter of glClear. Decides which shall be cleared
   2187  **/
   2188 void Framebuffer::Clear(const Functions& gl, GLenum mask)
   2189 {
   2190 	gl.clear(mask);
   2191 	GLU_EXPECT_NO_ERROR(gl.getError(), "Clear");
   2192 }
   2193 
   2194 /** Specifies clear color
   2195  *
   2196  * @param gl    GL functions
   2197  * @param red   Red channel
   2198  * @param green Green channel
   2199  * @param blue  Blue channel
   2200  * @param alpha Alpha channel
   2201  **/
   2202 void Framebuffer::ClearColor(const Functions& gl, GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha)
   2203 {
   2204 	gl.clearColor(red, green, blue, alpha);
   2205 	GLU_EXPECT_NO_ERROR(gl.getError(), "ClearColor");
   2206 }
   2207 
   2208 /** Generate framebuffer
   2209  *
   2210  **/
   2211 void Framebuffer::Generate(const Functions& gl, GLuint& out_id)
   2212 {
   2213 	GLuint id = m_invalid_id;
   2214 
   2215 	gl.genFramebuffers(1, &id);
   2216 	GLU_EXPECT_NO_ERROR(gl.getError(), "GenFramebuffers");
   2217 
   2218 	if (m_invalid_id == id)
   2219 	{
   2220 		TCU_FAIL("Invalid id");
   2221 	}
   2222 
   2223 	out_id = id;
   2224 }
   2225 
   2226 /* Shader's constants */
   2227 const GLuint Shader::m_invalid_id = 0;
   2228 
   2229 /** Constructor.
   2230  *
   2231  * @param context CTS context.
   2232  **/
   2233 Shader::Shader(deqp::Context& context) : m_id(m_invalid_id), m_context(context)
   2234 {
   2235 	/* Nothing to be done here */
   2236 }
   2237 
   2238 /** Destructor
   2239  *
   2240  **/
   2241 Shader::~Shader()
   2242 {
   2243 	Release();
   2244 }
   2245 
   2246 /** Initialize shader instance
   2247  *
   2248  * @param stage  Shader stage
   2249  * @param source Source code
   2250  **/
   2251 void Shader::Init(STAGES stage, const std::string& source)
   2252 {
   2253 	if (true == source.empty())
   2254 	{
   2255 		/* No source == no shader */
   2256 		return;
   2257 	}
   2258 
   2259 	/* Delete any previous shader */
   2260 	Release();
   2261 
   2262 	/* Create, set source and compile */
   2263 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2264 
   2265 	Create(gl, stage, m_id);
   2266 	Source(gl, m_id, source);
   2267 
   2268 	try
   2269 	{
   2270 		Compile(gl, m_id);
   2271 	}
   2272 	catch (const CompilationException& exc)
   2273 	{
   2274 		throw InvalidSourceException(exc.what(), source, stage);
   2275 	}
   2276 }
   2277 
   2278 /** Release shader instance
   2279  *
   2280  **/
   2281 void Shader::Release()
   2282 {
   2283 	if (m_invalid_id != m_id)
   2284 	{
   2285 		const Functions& gl = m_context.getRenderContext().getFunctions();
   2286 
   2287 		gl.deleteShader(m_id);
   2288 		m_id = m_invalid_id;
   2289 	}
   2290 }
   2291 
   2292 /** Compile shader
   2293  *
   2294  * @param gl GL functions
   2295  * @param id Shader id
   2296  **/
   2297 void Shader::Compile(const Functions& gl, GLuint id)
   2298 {
   2299 	GLint status = GL_FALSE;
   2300 
   2301 	/* Compile */
   2302 	gl.compileShader(id);
   2303 	GLU_EXPECT_NO_ERROR(gl.getError(), "CompileShader");
   2304 
   2305 	/* Get compilation status */
   2306 	gl.getShaderiv(id, GL_COMPILE_STATUS, &status);
   2307 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetShaderiv");
   2308 
   2309 	/* Log compilation error */
   2310 	if (GL_TRUE != status)
   2311 	{
   2312 		glw::GLint  length = 0;
   2313 		std::string message;
   2314 
   2315 		/* Error log length */
   2316 		gl.getShaderiv(id, GL_INFO_LOG_LENGTH, &length);
   2317 		GLU_EXPECT_NO_ERROR(gl.getError(), "GetShaderiv");
   2318 
   2319 		/* Prepare storage */
   2320 		message.resize(length, 0);
   2321 
   2322 		/* Get error log */
   2323 		gl.getShaderInfoLog(id, length, 0, &message[0]);
   2324 		GLU_EXPECT_NO_ERROR(gl.getError(), "GetShaderInfoLog");
   2325 
   2326 		throw CompilationException(message.c_str());
   2327 	}
   2328 }
   2329 
   2330 /** Create shader
   2331  *
   2332  * @param gl     GL functions
   2333  * @param stage  Shader stage
   2334  * @param out_id Shader id
   2335  **/
   2336 void Shader::Create(const Functions& gl, STAGES stage, GLuint& out_id)
   2337 {
   2338 	const GLenum shaderType = GetShaderStageGLenum(stage);
   2339 	const GLuint id			= gl.createShader(shaderType);
   2340 	GLU_EXPECT_NO_ERROR(gl.getError(), "CreateShader");
   2341 
   2342 	if (m_invalid_id == id)
   2343 	{
   2344 		TCU_FAIL("Failed to create shader");
   2345 	}
   2346 
   2347 	out_id = id;
   2348 }
   2349 
   2350 /** Set shader's source code
   2351  *
   2352  * @param gl     GL functions
   2353  * @param id     Shader id
   2354  * @param source Shader source code
   2355  **/
   2356 void Shader::Source(const Functions& gl, GLuint id, const std::string& source)
   2357 {
   2358 	const GLchar* code = source.c_str();
   2359 
   2360 	gl.shaderSource(id, 1 /* count */, &code, 0 /* lengths */);
   2361 	GLU_EXPECT_NO_ERROR(gl.getError(), "ShaderSource");
   2362 }
   2363 
   2364 /** Get GLenum repesenting shader stage
   2365  *
   2366  * @param stage Shader stage
   2367  *
   2368  * @return GLenum
   2369  **/
   2370 GLenum Shader::GetShaderStageGLenum(STAGES stage)
   2371 {
   2372 	GLenum result = 0;
   2373 
   2374 	switch (stage)
   2375 	{
   2376 	case COMPUTE:
   2377 		result = GL_COMPUTE_SHADER;
   2378 		break;
   2379 	case FRAGMENT:
   2380 		result = GL_FRAGMENT_SHADER;
   2381 		break;
   2382 	case GEOMETRY:
   2383 		result = GL_GEOMETRY_SHADER;
   2384 		break;
   2385 	case TESS_CTRL:
   2386 		result = GL_TESS_CONTROL_SHADER;
   2387 		break;
   2388 	case TESS_EVAL:
   2389 		result = GL_TESS_EVALUATION_SHADER;
   2390 		break;
   2391 	case VERTEX:
   2392 		result = GL_VERTEX_SHADER;
   2393 		break;
   2394 	default:
   2395 		TCU_FAIL("Invalid enum");
   2396 	}
   2397 
   2398 	return result;
   2399 }
   2400 
   2401 /** Get string representing name of shader stage
   2402  *
   2403  * @param stage Shader stage
   2404  *
   2405  * @return String with name of shader stage
   2406  **/
   2407 const glw::GLchar* Shader::GetStageName(STAGES stage)
   2408 {
   2409 	const GLchar* result = 0;
   2410 
   2411 	switch (stage)
   2412 	{
   2413 	case COMPUTE:
   2414 		result = "compute";
   2415 		break;
   2416 	case VERTEX:
   2417 		result = "vertex";
   2418 		break;
   2419 	case TESS_CTRL:
   2420 		result = "tessellation control";
   2421 		break;
   2422 	case TESS_EVAL:
   2423 		result = "tessellation evaluation";
   2424 		break;
   2425 	case GEOMETRY:
   2426 		result = "geometry";
   2427 		break;
   2428 	case FRAGMENT:
   2429 		result = "fragment";
   2430 		break;
   2431 	default:
   2432 		TCU_FAIL("Invalid enum");
   2433 	}
   2434 
   2435 	return result;
   2436 }
   2437 
   2438 /** Logs shader source
   2439  *
   2440  * @param context CTS context
   2441  * @param source  Source of shader
   2442  * @param stage   Shader stage
   2443  **/
   2444 void Shader::LogSource(deqp::Context& context, const std::string& source, STAGES stage)
   2445 {
   2446 	/* Skip empty shaders */
   2447 	if (true == source.empty())
   2448 	{
   2449 		return;
   2450 	}
   2451 
   2452 	context.getTestContext().getLog() << tcu::TestLog::Message
   2453 									  << "Shader source. Stage: " << Shader::GetStageName(stage)
   2454 									  << tcu::TestLog::EndMessage << tcu::TestLog::KernelSource(source);
   2455 }
   2456 
   2457 /** Constructor
   2458  *
   2459  * @param message Compilation error message
   2460  **/
   2461 Shader::CompilationException::CompilationException(const GLchar* message)
   2462 {
   2463 	m_message = message;
   2464 }
   2465 
   2466 /** Returns error messages
   2467  *
   2468  * @return Compilation error message
   2469  **/
   2470 const char* Shader::CompilationException::what() const throw()
   2471 {
   2472 	return m_message.c_str();
   2473 }
   2474 
   2475 /** Constructor
   2476  *
   2477  * @param message Compilation error message
   2478  **/
   2479 Shader::InvalidSourceException::InvalidSourceException(const GLchar* error_message, const std::string& source,
   2480 													   STAGES stage)
   2481 	: m_message(error_message), m_source(source), m_stage(stage)
   2482 {
   2483 }
   2484 
   2485 /** Returns error messages
   2486  *
   2487  * @return Compilation error message
   2488  **/
   2489 const char* Shader::InvalidSourceException::what() const throw()
   2490 {
   2491 	return "Compilation error";
   2492 }
   2493 
   2494 /** Logs error message and shader sources **/
   2495 void Shader::InvalidSourceException::log(deqp::Context& context) const
   2496 {
   2497 	context.getTestContext().getLog() << tcu::TestLog::Message << "Failed to compile shader: " << m_message.c_str()
   2498 									  << tcu::TestLog::EndMessage;
   2499 
   2500 	LogSource(context, m_source, m_stage);
   2501 }
   2502 
   2503 /* Program constants */
   2504 const GLuint Pipeline::m_invalid_id = 0;
   2505 
   2506 /** Constructor.
   2507  *
   2508  * @param context CTS context.
   2509  **/
   2510 Pipeline::Pipeline(deqp::Context& context) : m_id(m_invalid_id), m_context(context)
   2511 {
   2512 	/* Nothing to be done here */
   2513 }
   2514 
   2515 /** Destructor
   2516  *
   2517  **/
   2518 Pipeline::~Pipeline()
   2519 {
   2520 	Release();
   2521 }
   2522 
   2523 /** Initialize pipline object
   2524  *
   2525  **/
   2526 void Pipeline::Init()
   2527 {
   2528 	Release();
   2529 
   2530 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2531 
   2532 	/* Generate */
   2533 	gl.genProgramPipelines(1, &m_id);
   2534 	GLU_EXPECT_NO_ERROR(gl.getError(), "GenProgramPipelines");
   2535 }
   2536 
   2537 /** Release pipeline object
   2538  *
   2539  **/
   2540 void Pipeline::Release()
   2541 {
   2542 	if (m_invalid_id != m_id)
   2543 	{
   2544 		const Functions& gl = m_context.getRenderContext().getFunctions();
   2545 
   2546 		/* Generate */
   2547 		gl.deleteProgramPipelines(1, &m_id);
   2548 		GLU_EXPECT_NO_ERROR(gl.getError(), "DeleteProgramPipelines");
   2549 
   2550 		m_id = m_invalid_id;
   2551 	}
   2552 }
   2553 
   2554 /** Bind pipeline
   2555  *
   2556  **/
   2557 void Pipeline::Bind()
   2558 {
   2559 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2560 
   2561 	Bind(gl, m_id);
   2562 }
   2563 
   2564 /** Set which stages should be active
   2565  *
   2566  * @param program_id Id of program
   2567  * @param stages     Logical combination of enums representing stages
   2568  **/
   2569 void Pipeline::UseProgramStages(GLuint program_id, GLenum stages)
   2570 {
   2571 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2572 
   2573 	UseProgramStages(gl, m_id, program_id, stages);
   2574 }
   2575 
   2576 /** Bind pipeline
   2577  *
   2578  * @param gl Functiions
   2579  * @param id Pipeline id
   2580  **/
   2581 void Pipeline::Bind(const Functions& gl, GLuint id)
   2582 {
   2583 	gl.bindProgramPipeline(id);
   2584 	GLU_EXPECT_NO_ERROR(gl.getError(), "BindProgramPipeline");
   2585 }
   2586 
   2587 /** Set which stages should be active
   2588  *
   2589  * @param gl         Functiions
   2590  * @param id         Pipeline id
   2591  * @param program_id Id of program
   2592  * @param stages     Logical combination of enums representing stages
   2593  **/
   2594 void Pipeline::UseProgramStages(const Functions& gl, GLuint id, GLuint program_id, GLenum stages)
   2595 {
   2596 	gl.useProgramStages(id, stages, program_id);
   2597 	GLU_EXPECT_NO_ERROR(gl.getError(), "UseProgramStages");
   2598 }
   2599 
   2600 /* Program constants */
   2601 const GLuint Program::m_invalid_id = 0;
   2602 
   2603 /** Constructor.
   2604  *
   2605  * @param context CTS context.
   2606  **/
   2607 Program::Program(deqp::Context& context)
   2608 	: m_id(m_invalid_id)
   2609 	, m_compute(context)
   2610 	, m_fragment(context)
   2611 	, m_geometry(context)
   2612 	, m_tess_ctrl(context)
   2613 	, m_tess_eval(context)
   2614 	, m_vertex(context)
   2615 	, m_context(context)
   2616 {
   2617 	/* Nothing to be done here */
   2618 }
   2619 
   2620 /** Destructor
   2621  *
   2622  **/
   2623 Program::~Program()
   2624 {
   2625 	Release();
   2626 }
   2627 
   2628 /** Initialize program instance
   2629  *
   2630  * @param compute_shader                    Compute shader source code
   2631  * @param fragment_shader                   Fragment shader source code
   2632  * @param geometry_shader                   Geometry shader source code
   2633  * @param tessellation_control_shader       Tessellation control shader source code
   2634  * @param tessellation_evaluation_shader    Tessellation evaluation shader source code
   2635  * @param vertex_shader                     Vertex shader source code
   2636  * @param captured_varyings                 Vector of variables to be captured with transfrom feedback
   2637  * @param capture_interleaved               Select mode of transform feedback (separate or interleaved)
   2638  * @param is_separable                      Selects if monolithic or separable program should be built. Defaults to false
   2639  **/
   2640 void Program::Init(const std::string& compute_shader, const std::string& fragment_shader,
   2641 				   const std::string& geometry_shader, const std::string& tessellation_control_shader,
   2642 				   const std::string& tessellation_evaluation_shader, const std::string& vertex_shader,
   2643 				   const NameVector& captured_varyings, bool capture_interleaved, bool is_separable)
   2644 {
   2645 	/* Delete previous program */
   2646 	Release();
   2647 
   2648 	/* GL entry points */
   2649 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2650 
   2651 	/* Initialize shaders */
   2652 	m_compute.Init(Shader::COMPUTE, compute_shader);
   2653 	m_fragment.Init(Shader::FRAGMENT, fragment_shader);
   2654 	m_geometry.Init(Shader::GEOMETRY, geometry_shader);
   2655 	m_tess_ctrl.Init(Shader::TESS_CTRL, tessellation_control_shader);
   2656 	m_tess_eval.Init(Shader::TESS_EVAL, tessellation_evaluation_shader);
   2657 	m_vertex.Init(Shader::VERTEX, vertex_shader);
   2658 
   2659 	/* Create program, set up transform feedback and attach shaders */
   2660 	Create(gl, m_id);
   2661 	Capture(gl, m_id, captured_varyings, capture_interleaved);
   2662 	Attach(gl, m_id, m_compute.m_id);
   2663 	Attach(gl, m_id, m_fragment.m_id);
   2664 	Attach(gl, m_id, m_geometry.m_id);
   2665 	Attach(gl, m_id, m_tess_ctrl.m_id);
   2666 	Attach(gl, m_id, m_tess_eval.m_id);
   2667 	Attach(gl, m_id, m_vertex.m_id);
   2668 
   2669 	/* Set separable parameter */
   2670 	if (true == is_separable)
   2671 	{
   2672 		gl.programParameteri(m_id, GL_PROGRAM_SEPARABLE, GL_TRUE);
   2673 		GLU_EXPECT_NO_ERROR(gl.getError(), "ProgramParameteri");
   2674 	}
   2675 
   2676 	try
   2677 	{
   2678 		/* Link program */
   2679 		Link(gl, m_id);
   2680 	}
   2681 	catch (const LinkageException& exc)
   2682 	{
   2683 		throw BuildException(exc.what(), compute_shader, fragment_shader, geometry_shader, tessellation_control_shader,
   2684 							 tessellation_evaluation_shader, vertex_shader);
   2685 	}
   2686 }
   2687 
   2688 /** Initialize program instance
   2689  *
   2690  * @param compute_shader                    Compute shader source code
   2691  * @param fragment_shader                   Fragment shader source code
   2692  * @param geometry_shader                   Geometry shader source code
   2693  * @param tessellation_control_shader       Tessellation control shader source code
   2694  * @param tessellation_evaluation_shader    Tessellation evaluation shader source code
   2695  * @param vertex_shader                     Vertex shader source code
   2696  * @param is_separable                      Selects if monolithic or separable program should be built. Defaults to false
   2697  **/
   2698 void Program::Init(const std::string& compute_shader, const std::string& fragment_shader,
   2699 				   const std::string& geometry_shader, const std::string& tessellation_control_shader,
   2700 				   const std::string& tessellation_evaluation_shader, const std::string& vertex_shader,
   2701 				   bool is_separable)
   2702 {
   2703 	NameVector captured_varying;
   2704 
   2705 	Init(compute_shader, fragment_shader, geometry_shader, tessellation_control_shader, tessellation_evaluation_shader,
   2706 		 vertex_shader, captured_varying, true, is_separable);
   2707 }
   2708 
   2709 /** Release program instance
   2710  *
   2711  **/
   2712 void Program::Release()
   2713 {
   2714 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2715 
   2716 	if (m_invalid_id != m_id)
   2717 	{
   2718 		Use(gl, m_invalid_id);
   2719 
   2720 		gl.deleteProgram(m_id);
   2721 		m_id = m_invalid_id;
   2722 	}
   2723 
   2724 	m_compute.Release();
   2725 	m_fragment.Release();
   2726 	m_geometry.Release();
   2727 	m_tess_ctrl.Release();
   2728 	m_tess_eval.Release();
   2729 	m_vertex.Release();
   2730 }
   2731 
   2732 /** Get <pname> for a set of active uniforms
   2733  *
   2734  * @param count   Number of indices
   2735  * @param indices Indices of uniforms
   2736  * @param pname   Queired pname
   2737  * @param params  Array that will be filled with values of parameters
   2738  **/
   2739 void Program::GetActiveUniformsiv(GLsizei count, const GLuint* indices, GLenum pname, GLint* params) const
   2740 {
   2741 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2742 
   2743 	GetActiveUniformsiv(gl, m_id, count, indices, pname, params);
   2744 }
   2745 
   2746 /** Get location of attribute
   2747  *
   2748  * @param name Name of attribute
   2749  *
   2750  * @return Result of query
   2751  **/
   2752 glw::GLint Program::GetAttribLocation(const std::string& name) const
   2753 {
   2754 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2755 
   2756 	return GetAttribLocation(gl, m_id, name);
   2757 }
   2758 
   2759 /** Query resource
   2760  *
   2761  * @param interface Interface to be queried
   2762  * @param index     Index of resource
   2763  * @param property  Property to be queried
   2764  * @param buf_size  Size of <params> buffer
   2765  * @param params    Results of query
   2766  **/
   2767 void Program::GetResource(GLenum interface, GLuint index, GLenum property, GLsizei buf_size, GLint* params) const
   2768 {
   2769 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2770 
   2771 	GetResource(gl, m_id, interface, index, property, buf_size, params);
   2772 }
   2773 
   2774 /** Query for index of resource
   2775  *
   2776  * @param name      Name of resource
   2777  * @param interface Interface to be queried
   2778  *
   2779  * @return Result of query
   2780  **/
   2781 glw::GLuint Program::GetResourceIndex(const std::string& name, GLenum interface) const
   2782 {
   2783 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2784 
   2785 	return GetResourceIndex(gl, m_id, name, interface);
   2786 }
   2787 
   2788 /** Get indices for a set of uniforms
   2789  *
   2790  * @param count   Count number of uniforms
   2791  * @param names   Names of uniforms
   2792  * @param indices Buffer that will be filled with indices
   2793  **/
   2794 void Program::GetUniformIndices(GLsizei count, const GLchar** names, GLuint* indices) const
   2795 {
   2796 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2797 
   2798 	GetUniformIndices(gl, m_id, count, names, indices);
   2799 }
   2800 
   2801 /** Get uniform location
   2802  *
   2803  * @param name Name of uniform
   2804  *
   2805  * @return Results of query
   2806  **/
   2807 glw::GLint Program::GetUniformLocation(const std::string& name) const
   2808 {
   2809 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2810 
   2811 	return GetUniformLocation(gl, m_id, name);
   2812 }
   2813 
   2814 /** Set program as active
   2815  *
   2816  **/
   2817 void Program::Use() const
   2818 {
   2819 	const Functions& gl = m_context.getRenderContext().getFunctions();
   2820 
   2821 	Use(gl, m_id);
   2822 }
   2823 
   2824 /** Attach shader to program
   2825  *
   2826  * @param gl         GL functions
   2827  * @param program_id Id of program
   2828  * @param shader_id  Id of shader
   2829  **/
   2830 void Program::Attach(const Functions& gl, GLuint program_id, GLuint shader_id)
   2831 {
   2832 	/* Sanity checks */
   2833 	if ((m_invalid_id == program_id) || (Shader::m_invalid_id == shader_id))
   2834 	{
   2835 		return;
   2836 	}
   2837 
   2838 	gl.attachShader(program_id, shader_id);
   2839 	GLU_EXPECT_NO_ERROR(gl.getError(), "AttachShader");
   2840 }
   2841 
   2842 /** Set up captured varyings
   2843  *
   2844  * @param gl                  GL functions
   2845  * @param id                  Id of program
   2846  * @param captured_varyings   Vector of varyings
   2847  * @param capture_interleaved Selects if interleaved or separate mode should be used
   2848  **/
   2849 void Program::Capture(const Functions& gl, GLuint id, const NameVector& captured_varyings, bool capture_interleaved)
   2850 {
   2851 	const size_t n_varyings = captured_varyings.size();
   2852 
   2853 	if (0 == n_varyings)
   2854 	{
   2855 		/* empty list, skip */
   2856 		return;
   2857 	}
   2858 
   2859 	std::vector<const GLchar*> varying_names;
   2860 	varying_names.resize(n_varyings);
   2861 
   2862 	for (size_t i = 0; i < n_varyings; ++i)
   2863 	{
   2864 		varying_names[i] = captured_varyings[i].c_str();
   2865 	}
   2866 
   2867 	GLenum mode = 0;
   2868 	if (true == capture_interleaved)
   2869 	{
   2870 		mode = GL_INTERLEAVED_ATTRIBS;
   2871 	}
   2872 	else
   2873 	{
   2874 		mode = GL_SEPARATE_ATTRIBS;
   2875 	}
   2876 
   2877 	gl.transformFeedbackVaryings(id, static_cast<GLsizei>(n_varyings), &varying_names[0], mode);
   2878 	GLU_EXPECT_NO_ERROR(gl.getError(), "TransformFeedbackVaryings");
   2879 }
   2880 
   2881 /** Create program instance
   2882  *
   2883  * @param gl     GL functions
   2884  * @param out_id Id of program
   2885  **/
   2886 void Program::Create(const Functions& gl, GLuint& out_id)
   2887 {
   2888 	const GLuint id = gl.createProgram();
   2889 	GLU_EXPECT_NO_ERROR(gl.getError(), "CreateProgram");
   2890 
   2891 	if (m_invalid_id == id)
   2892 	{
   2893 		TCU_FAIL("Failed to create program");
   2894 	}
   2895 
   2896 	out_id = id;
   2897 }
   2898 
   2899 /** Get <pname> for a set of active uniforms
   2900  *
   2901  * @param gl         Functions
   2902  * @param program_id Id of program
   2903  * @param count      Number of indices
   2904  * @param indices    Indices of uniforms
   2905  * @param pname      Queired pname
   2906  * @param params     Array that will be filled with values of parameters
   2907  **/
   2908 void Program::GetActiveUniformsiv(const Functions& gl, GLuint program_id, GLsizei count, const GLuint* indices,
   2909 								  GLenum pname, GLint* params)
   2910 {
   2911 	gl.getActiveUniformsiv(program_id, count, indices, pname, params);
   2912 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetActiveUniformsiv");
   2913 }
   2914 
   2915 /** Get indices for a set of uniforms
   2916  *
   2917  * @param gl         Functions
   2918  * @param program_id Id of program
   2919  * @param count      Count number of uniforms
   2920  * @param names      Names of uniforms
   2921  * @param indices    Buffer that will be filled with indices
   2922  **/
   2923 void Program::GetUniformIndices(const Functions& gl, GLuint program_id, GLsizei count, const GLchar** names,
   2924 								GLuint* indices)
   2925 {
   2926 	gl.getUniformIndices(program_id, count, names, indices);
   2927 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetUniformIndices");
   2928 }
   2929 
   2930 /** Link program
   2931  *
   2932  * @param gl GL functions
   2933  * @param id Id of program
   2934  **/
   2935 void Program::Link(const Functions& gl, GLuint id)
   2936 {
   2937 	GLint status = GL_FALSE;
   2938 
   2939 	gl.linkProgram(id);
   2940 	GLU_EXPECT_NO_ERROR(gl.getError(), "LinkProgram");
   2941 
   2942 	/* Get link status */
   2943 	gl.getProgramiv(id, GL_LINK_STATUS, &status);
   2944 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetProgramiv");
   2945 
   2946 	/* Log link error */
   2947 	if (GL_TRUE != status)
   2948 	{
   2949 		glw::GLint  length = 0;
   2950 		std::string message;
   2951 
   2952 		/* Get error log length */
   2953 		gl.getProgramiv(id, GL_INFO_LOG_LENGTH, &length);
   2954 		GLU_EXPECT_NO_ERROR(gl.getError(), "GetProgramiv");
   2955 
   2956 		message.resize(length, 0);
   2957 
   2958 		/* Get error log */
   2959 		gl.getProgramInfoLog(id, length, 0, &message[0]);
   2960 		GLU_EXPECT_NO_ERROR(gl.getError(), "GetProgramInfoLog");
   2961 
   2962 		throw LinkageException(message.c_str());
   2963 	}
   2964 }
   2965 
   2966 /** Set generic uniform
   2967  *
   2968  * @param gl       Functions
   2969  * @param type     Type of uniform
   2970  * @param count    Length of array
   2971  * @param location Location of uniform
   2972  * @param data     Data that will be used
   2973  **/
   2974 void Program::Uniform(const Functions& gl, const Type& type, GLsizei count, GLint location, const GLvoid* data)
   2975 {
   2976 	if (-1 == location)
   2977 	{
   2978 		TCU_FAIL("Uniform is inactive");
   2979 	}
   2980 
   2981 	switch (type.m_basic_type)
   2982 	{
   2983 	case Type::Double:
   2984 		if (1 == type.m_n_columns)
   2985 		{
   2986 			getUniformNdv(gl, type.m_n_rows)(location, count, (const GLdouble*)data);
   2987 			GLU_EXPECT_NO_ERROR(gl.getError(), "UniformNdv");
   2988 		}
   2989 		else
   2990 		{
   2991 			getUniformMatrixNdv(gl, type.m_n_columns, type.m_n_rows)(location, count, false, (const GLdouble*)data);
   2992 			GLU_EXPECT_NO_ERROR(gl.getError(), "UniformMatrixNdv");
   2993 		}
   2994 		break;
   2995 	case Type::Float:
   2996 		if (1 == type.m_n_columns)
   2997 		{
   2998 			getUniformNfv(gl, type.m_n_rows)(location, count, (const GLfloat*)data);
   2999 			GLU_EXPECT_NO_ERROR(gl.getError(), "UniformNfv");
   3000 		}
   3001 		else
   3002 		{
   3003 			getUniformMatrixNfv(gl, type.m_n_columns, type.m_n_rows)(location, count, false, (const GLfloat*)data);
   3004 			GLU_EXPECT_NO_ERROR(gl.getError(), "UniformMatrixNfv");
   3005 		}
   3006 		break;
   3007 	case Type::Int:
   3008 		getUniformNiv(gl, type.m_n_rows)(location, count, (const GLint*)data);
   3009 		GLU_EXPECT_NO_ERROR(gl.getError(), "UniformNiv");
   3010 		break;
   3011 	case Type::Uint:
   3012 		getUniformNuiv(gl, type.m_n_rows)(location, count, (const GLuint*)data);
   3013 		GLU_EXPECT_NO_ERROR(gl.getError(), "UniformNuiv");
   3014 		break;
   3015 	default:
   3016 		TCU_FAIL("Invalid enum");
   3017 	}
   3018 }
   3019 
   3020 /** Use program
   3021  *
   3022  * @param gl GL functions
   3023  * @param id Id of program
   3024  **/
   3025 void Program::Use(const Functions& gl, GLuint id)
   3026 {
   3027 	gl.useProgram(id);
   3028 	GLU_EXPECT_NO_ERROR(gl.getError(), "UseProgram");
   3029 }
   3030 
   3031 /** Get location of attribute
   3032  *
   3033  * @param gl   GL functions
   3034  * @param id   Id of program
   3035  * @param name Name of attribute
   3036  *
   3037  * @return Location of attribute
   3038  **/
   3039 GLint Program::GetAttribLocation(const Functions& gl, GLuint id, const std::string& name)
   3040 {
   3041 	GLint location = gl.getAttribLocation(id, name.c_str());
   3042 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetAttribLocation");
   3043 
   3044 	return location;
   3045 }
   3046 
   3047 /** Query resource
   3048  *
   3049  * @param gl        GL functions
   3050  * @param id        Id of program
   3051  * @param interface Interface to be queried
   3052  * @param index     Index of resource
   3053  * @param property  Property to be queried
   3054  * @param buf_size  Size of <params> buffer
   3055  * @param params    Results of query
   3056  **/
   3057 void Program::GetResource(const Functions& gl, GLuint id, GLenum interface, GLuint index, GLenum property,
   3058 						  GLsizei buf_size, GLint* params)
   3059 {
   3060 	gl.getProgramResourceiv(id, interface, index, 1 /* propCount */, &property, buf_size /* bufSize */, 0 /* length */,
   3061 							params);
   3062 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetProgramResourceiv");
   3063 }
   3064 
   3065 /** Get index of resource
   3066  *
   3067  * @param gl        GL functions
   3068  * @param id        Id of program
   3069  * @param name      Name of resource
   3070  * @param interface Program interface to queried
   3071  *
   3072  * @return Location of attribute
   3073  **/
   3074 GLuint Program::GetResourceIndex(const Functions& gl, GLuint id, const std::string& name, GLenum interface)
   3075 {
   3076 	GLuint index = gl.getProgramResourceIndex(id, interface, name.c_str());
   3077 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetProgramResourceIndex");
   3078 
   3079 	return index;
   3080 }
   3081 
   3082 /** Get location of attribute
   3083  *
   3084  * @param gl   GL functions
   3085  * @param id   Id of program
   3086  * @param name Name of attribute
   3087  *
   3088  * @return Location of uniform
   3089  **/
   3090 GLint Program::GetUniformLocation(const Functions& gl, GLuint id, const std::string& name)
   3091 {
   3092 	GLint location = gl.getUniformLocation(id, name.c_str());
   3093 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetUniformLocation");
   3094 
   3095 	return location;
   3096 }
   3097 
   3098 /** Constructor
   3099  *
   3100  * @param error_message    Error message
   3101  * @param compute_shader   Source code for compute stage
   3102  * @param fragment_shader  Source code for fragment stage
   3103  * @param geometry_shader  Source code for geometry stage
   3104  * @param tess_ctrl_shader Source code for tessellation control stage
   3105  * @param tess_eval_shader Source code for tessellation evaluation stage
   3106  * @param vertex_shader    Source code for vertex stage
   3107  **/
   3108 Program::BuildException::BuildException(const glw::GLchar* error_message, const std::string compute_shader,
   3109 										const std::string fragment_shader, const std::string geometry_shader,
   3110 										const std::string tess_ctrl_shader, const std::string tess_eval_shader,
   3111 										const std::string vertex_shader)
   3112 	: m_error_message(error_message)
   3113 	, m_compute_shader(compute_shader)
   3114 	, m_fragment_shader(fragment_shader)
   3115 	, m_geometry_shader(geometry_shader)
   3116 	, m_tess_ctrl_shader(tess_ctrl_shader)
   3117 	, m_tess_eval_shader(tess_eval_shader)
   3118 	, m_vertex_shader(vertex_shader)
   3119 {
   3120 }
   3121 
   3122 /** Overwrites std::exception::what method
   3123  *
   3124  * @return Message compossed from error message and shader sources
   3125  **/
   3126 const char* Program::BuildException::what() const throw()
   3127 {
   3128 	return "Failed to link program";
   3129 }
   3130 
   3131 /** Logs error message and shader sources **/
   3132 void Program::BuildException::log(deqp::Context& context) const
   3133 {
   3134 	context.getTestContext().getLog() << tcu::TestLog::Message << "Link failure: " << m_error_message
   3135 									  << tcu::TestLog::EndMessage;
   3136 
   3137 	Shader::LogSource(context, m_vertex_shader, Shader::VERTEX);
   3138 	Shader::LogSource(context, m_tess_ctrl_shader, Shader::TESS_CTRL);
   3139 	Shader::LogSource(context, m_tess_eval_shader, Shader::TESS_EVAL);
   3140 	Shader::LogSource(context, m_geometry_shader, Shader::GEOMETRY);
   3141 	Shader::LogSource(context, m_fragment_shader, Shader::FRAGMENT);
   3142 	Shader::LogSource(context, m_compute_shader, Shader::COMPUTE);
   3143 }
   3144 
   3145 /** Constructor
   3146  *
   3147  * @param message Linking error message
   3148  **/
   3149 Program::LinkageException::LinkageException(const glw::GLchar* message) : m_error_message(message)
   3150 {
   3151 	/* Nothing to be done */
   3152 }
   3153 
   3154 /** Returns error messages
   3155  *
   3156  * @return Linking error message
   3157  **/
   3158 const char* Program::LinkageException::what() const throw()
   3159 {
   3160 	return m_error_message.c_str();
   3161 }
   3162 
   3163 /* Texture constants */
   3164 const GLuint Texture::m_invalid_id = -1;
   3165 
   3166 /** Constructor.
   3167  *
   3168  * @param context CTS context.
   3169  **/
   3170 Texture::Texture(deqp::Context& context) : m_id(m_invalid_id), m_context(context), m_type(TEX_2D)
   3171 {
   3172 	/* Nothing to done here */
   3173 }
   3174 
   3175 /** Destructor
   3176  *
   3177  **/
   3178 Texture::~Texture()
   3179 {
   3180 	Release();
   3181 }
   3182 
   3183 /** Initialize texture instance
   3184  *
   3185  * @param tex_type        Type of texture
   3186  * @param width           Width of texture
   3187  * @param height          Height of texture
   3188  * @param depth           Depth of texture
   3189  * @param internal_format Internal format of texture
   3190  * @param format          Format of texture data
   3191  * @param type            Type of texture data
   3192  * @param data            Texture data
   3193  **/
   3194 void Texture::Init(TYPES tex_type, GLuint width, GLuint height, GLuint depth, GLenum internal_format, GLenum format,
   3195 				   GLenum type, GLvoid* data)
   3196 {
   3197 	const Functions& gl = m_context.getRenderContext().getFunctions();
   3198 
   3199 	/* Delete previous texture */
   3200 	Release();
   3201 
   3202 	m_type = tex_type;
   3203 
   3204 	/* Generate, bind, allocate storage and upload data */
   3205 	Generate(gl, m_id);
   3206 	Bind(gl, m_id, tex_type);
   3207 	Storage(gl, tex_type, width, height, depth, internal_format);
   3208 	Update(gl, tex_type, width, height, depth, format, type, data);
   3209 }
   3210 
   3211 /** Initialize buffer texture
   3212  *
   3213  * @param internal_format Internal format of texture
   3214  * @param buffer_id       Id of buffer that will be used as data source
   3215  **/
   3216 void Texture::Init(GLenum internal_format, GLuint buffer_id)
   3217 {
   3218 	const Functions& gl = m_context.getRenderContext().getFunctions();
   3219 
   3220 	/* Delete previous texture */
   3221 	Release();
   3222 
   3223 	m_type = TEX_BUFFER;
   3224 
   3225 	/* Generate, bind and attach buffer */
   3226 	Generate(gl, m_id);
   3227 	Bind(gl, m_id, TEX_BUFFER);
   3228 	TexBuffer(gl, buffer_id, internal_format);
   3229 }
   3230 
   3231 /** Release texture instance
   3232  *
   3233  **/
   3234 void Texture::Release()
   3235 {
   3236 	if (m_invalid_id != m_id)
   3237 	{
   3238 		const Functions& gl = m_context.getRenderContext().getFunctions();
   3239 
   3240 		gl.deleteTextures(1, &m_id);
   3241 		m_id = m_invalid_id;
   3242 	}
   3243 }
   3244 
   3245 /** Bind texture to its target
   3246  *
   3247  **/
   3248 void Texture::Bind() const
   3249 {
   3250 	const Functions& gl = m_context.getRenderContext().getFunctions();
   3251 
   3252 	Bind(gl, m_id, m_type);
   3253 }
   3254 
   3255 /** Get texture data
   3256  *
   3257  * @param format   Format of data
   3258  * @param type     Type of data
   3259  * @param out_data Buffer for data
   3260  **/
   3261 void Texture::Get(GLenum format, GLenum type, GLvoid* out_data) const
   3262 {
   3263 	const Functions& gl = m_context.getRenderContext().getFunctions();
   3264 
   3265 	Bind(gl, m_id, m_type);
   3266 	Get(gl, m_type, format, type, out_data);
   3267 }
   3268 
   3269 /** Bind texture to target
   3270  *
   3271  * @param gl       GL functions
   3272  * @param id       Id of texture
   3273  * @param tex_type Type of texture
   3274  **/
   3275 void Texture::Bind(const Functions& gl, GLuint id, TYPES tex_type)
   3276 {
   3277 	GLenum target = GetTargetGLenum(tex_type);
   3278 
   3279 	gl.bindTexture(target, id);
   3280 	GLU_EXPECT_NO_ERROR(gl.getError(), "BindTexture");
   3281 }
   3282 
   3283 /** Generate texture instance
   3284  *
   3285  * @param gl     GL functions
   3286  * @param out_id Id of texture
   3287  **/
   3288 void Texture::Generate(const Functions& gl, GLuint& out_id)
   3289 {
   3290 	GLuint id = m_invalid_id;
   3291 
   3292 	gl.genTextures(1, &id);
   3293 	GLU_EXPECT_NO_ERROR(gl.getError(), "GenTextures");
   3294 
   3295 	if (m_invalid_id == id)
   3296 	{
   3297 		TCU_FAIL("Invalid id");
   3298 	}
   3299 
   3300 	out_id = id;
   3301 }
   3302 
   3303 /** Get texture data
   3304  *
   3305  * @param gl       GL functions
   3306  * @param format   Format of data
   3307  * @param type     Type of data
   3308  * @param out_data Buffer for data
   3309  **/
   3310 void Texture::Get(const Functions& gl, TYPES tex_type, GLenum format, GLenum type, GLvoid* out_data)
   3311 {
   3312 	GLenum target = GetTargetGLenum(tex_type);
   3313 
   3314 	if (TEX_CUBE != tex_type)
   3315 	{
   3316 		gl.getTexImage(target, 0 /* level */, format, type, out_data);
   3317 		GLU_EXPECT_NO_ERROR(gl.getError(), "GetTexImage");
   3318 	}
   3319 	else
   3320 	{
   3321 		GLint width;
   3322 		GLint height;
   3323 
   3324 		if ((GL_RGBA != format) && (GL_UNSIGNED_BYTE != type))
   3325 		{
   3326 			TCU_FAIL("Not implemented");
   3327 		}
   3328 
   3329 		GLuint texel_size = 4;
   3330 
   3331 		gl.getTexLevelParameteriv(GL_TEXTURE_CUBE_MAP_POSITIVE_X, 0 /* level */, GL_TEXTURE_WIDTH, &width);
   3332 		GLU_EXPECT_NO_ERROR(gl.getError(), "GetTexLevelParameteriv");
   3333 
   3334 		gl.getTexLevelParameteriv(GL_TEXTURE_CUBE_MAP_POSITIVE_X, 0 /* level */, GL_TEXTURE_HEIGHT, &height);
   3335 		GLU_EXPECT_NO_ERROR(gl.getError(), "GetTexLevelParameteriv");
   3336 
   3337 		const GLuint image_size = width * height * texel_size;
   3338 
   3339 		gl.getTexImage(GL_TEXTURE_CUBE_MAP_POSITIVE_X, 0 /* level */, format, type,
   3340 					   (GLvoid*)((GLchar*)out_data + (image_size * 0)));
   3341 		gl.getTexImage(GL_TEXTURE_CUBE_MAP_NEGATIVE_X, 0 /* level */, format, type,
   3342 					   (GLvoid*)((GLchar*)out_data + (image_size * 1)));
   3343 		gl.getTexImage(GL_TEXTURE_CUBE_MAP_POSITIVE_Y, 0 /* level */, format, type,
   3344 					   (GLvoid*)((GLchar*)out_data + (image_size * 2)));
   3345 		gl.getTexImage(GL_TEXTURE_CUBE_MAP_NEGATIVE_Y, 0 /* level */, format, type,
   3346 					   (GLvoid*)((GLchar*)out_data + (image_size * 3)));
   3347 		gl.getTexImage(GL_TEXTURE_CUBE_MAP_POSITIVE_Z, 0 /* level */, format, type,
   3348 					   (GLvoid*)((GLchar*)out_data + (image_size * 4)));
   3349 		gl.getTexImage(GL_TEXTURE_CUBE_MAP_NEGATIVE_Z, 0 /* level */, format, type,
   3350 					   (GLvoid*)((GLchar*)out_data + (image_size * 5)));
   3351 		GLU_EXPECT_NO_ERROR(gl.getError(), "GetTexImage");
   3352 	}
   3353 }
   3354 
   3355 /** Allocate storage for texture
   3356  *
   3357  * @param gl              GL functions
   3358  * @param tex_type        Type of texture
   3359  * @param width           Width of texture
   3360  * @param height          Height of texture
   3361  * @param depth           Depth of texture
   3362  * @param internal_format Internal format of texture
   3363  **/
   3364 void Texture::Storage(const Functions& gl, TYPES tex_type, GLuint width, GLuint height, GLuint depth,
   3365 					  GLenum internal_format)
   3366 {
   3367 	static const GLuint levels = 1;
   3368 
   3369 	GLenum target = GetTargetGLenum(tex_type);
   3370 
   3371 	switch (tex_type)
   3372 	{
   3373 	case TEX_1D:
   3374 		gl.texStorage1D(target, levels, internal_format, width);
   3375 		GLU_EXPECT_NO_ERROR(gl.getError(), "TexStorage1D");
   3376 		break;
   3377 	case TEX_2D:
   3378 	case TEX_1D_ARRAY:
   3379 	case TEX_2D_RECT:
   3380 	case TEX_CUBE:
   3381 		gl.texStorage2D(target, levels, internal_format, width, height);
   3382 		GLU_EXPECT_NO_ERROR(gl.getError(), "TexStorage2D");
   3383 		break;
   3384 	case TEX_3D:
   3385 	case TEX_2D_ARRAY:
   3386 		gl.texStorage3D(target, levels, internal_format, width, height, depth);
   3387 		GLU_EXPECT_NO_ERROR(gl.getError(), "TexStorage3D");
   3388 		break;
   3389 	default:
   3390 		TCU_FAIL("Invliad enum");
   3391 		break;
   3392 	}
   3393 }
   3394 
   3395 /** Attach buffer as source of texture buffer data
   3396  *
   3397  * @param gl              GL functions
   3398  * @param internal_format Internal format of texture
   3399  * @param buffer_id       Id of buffer that will be used as data source
   3400  **/
   3401 void Texture::TexBuffer(const Functions& gl, GLenum internal_format, GLuint& buffer_id)
   3402 {
   3403 	gl.texBuffer(GL_TEXTURE_BUFFER, internal_format, buffer_id);
   3404 	GLU_EXPECT_NO_ERROR(gl.getError(), "TexBuffer");
   3405 }
   3406 
   3407 /** Update contents of texture
   3408  *
   3409  * @param gl       GL functions
   3410  * @param tex_type Type of texture
   3411  * @param width    Width of texture
   3412  * @param height   Height of texture
   3413  * @param format   Format of data
   3414  * @param type     Type of data
   3415  * @param data     Buffer with image data
   3416  **/
   3417 void Texture::Update(const Functions& gl, TYPES tex_type, GLuint width, GLuint height, GLuint depth, GLenum format,
   3418 					 GLenum type, GLvoid* data)
   3419 {
   3420 	static const GLuint level = 0;
   3421 
   3422 	GLenum target = GetTargetGLenum(tex_type);
   3423 
   3424 	switch (tex_type)
   3425 	{
   3426 	case TEX_1D:
   3427 		gl.texSubImage1D(target, level, 0 /* x */, width, format, type, data);
   3428 		GLU_EXPECT_NO_ERROR(gl.getError(), "TexStorage1D");
   3429 		break;
   3430 	case TEX_2D:
   3431 	case TEX_1D_ARRAY:
   3432 	case TEX_2D_RECT:
   3433 		gl.texSubImage2D(target, level, 0 /* x */, 0 /* y */, width, height, format, type, data);
   3434 		GLU_EXPECT_NO_ERROR(gl.getError(), "TexStorage2D");
   3435 		break;
   3436 	case TEX_CUBE:
   3437 		gl.texSubImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X, level, 0 /* x */, 0 /* y */, width, height, format, type,
   3438 						 data);
   3439 		gl.texSubImage2D(GL_TEXTURE_CUBE_MAP_NEGATIVE_X, level, 0 /* x */, 0 /* y */, width, height, format, type,
   3440 						 data);
   3441 		gl.texSubImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_Y, level, 0 /* x */, 0 /* y */, width, height, format, type,
   3442 						 data);
   3443 		gl.texSubImage2D(GL_TEXTURE_CUBE_MAP_NEGATIVE_Y, level, 0 /* x */, 0 /* y */, width, height, format, type,
   3444 						 data);
   3445 		gl.texSubImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_Z, level, 0 /* x */, 0 /* y */, width, height, format, type,
   3446 						 data);
   3447 		gl.texSubImage2D(GL_TEXTURE_CUBE_MAP_NEGATIVE_Z, level, 0 /* x */, 0 /* y */, width, height, format, type,
   3448 						 data);
   3449 		GLU_EXPECT_NO_ERROR(gl.getError(), "TexStorage2D");
   3450 		break;
   3451 	case TEX_3D:
   3452 	case TEX_2D_ARRAY:
   3453 		gl.texSubImage3D(target, level, 0 /* x */, 0 /* y */, 0 /* z */, width, height, depth, format, type, data);
   3454 		GLU_EXPECT_NO_ERROR(gl.getError(), "TexStorage3D");
   3455 		break;
   3456 	default:
   3457 		TCU_FAIL("Invliad enum");
   3458 		break;
   3459 	}
   3460 }
   3461 
   3462 /** Get target for given texture type
   3463  *
   3464  * @param type Type of texture
   3465  *
   3466  * @return Target
   3467  **/
   3468 GLenum Texture::GetTargetGLenum(TYPES type)
   3469 {
   3470 	GLenum result = 0;
   3471 
   3472 	switch (type)
   3473 	{
   3474 	case TEX_BUFFER:
   3475 		result = GL_TEXTURE_BUFFER;
   3476 		break;
   3477 	case TEX_2D:
   3478 		result = GL_TEXTURE_2D;
   3479 		break;
   3480 	case TEX_2D_RECT:
   3481 		result = GL_TEXTURE_RECTANGLE;
   3482 		break;
   3483 	case TEX_2D_ARRAY:
   3484 		result = GL_TEXTURE_2D_ARRAY;
   3485 		break;
   3486 	case TEX_3D:
   3487 		result = GL_TEXTURE_3D;
   3488 		break;
   3489 	case TEX_CUBE:
   3490 		result = GL_TEXTURE_CUBE_MAP;
   3491 		break;
   3492 	case TEX_1D:
   3493 		result = GL_TEXTURE_1D;
   3494 		break;
   3495 	case TEX_1D_ARRAY:
   3496 		result = GL_TEXTURE_1D_ARRAY;
   3497 		break;
   3498 	}
   3499 
   3500 	return result;
   3501 }
   3502 
   3503 /* VertexArray constants */
   3504 const GLuint VertexArray::m_invalid_id = -1;
   3505 
   3506 /** Constructor.
   3507  *
   3508  * @param context CTS context.
   3509  **/
   3510 VertexArray::VertexArray(deqp::Context& context) : m_id(m_invalid_id), m_context(context)
   3511 {
   3512 }
   3513 
   3514 /** Destructor
   3515  *
   3516  **/
   3517 VertexArray::~VertexArray()
   3518 {
   3519 	Release();
   3520 }
   3521 
   3522 /** Initialize vertex array instance
   3523  *
   3524  **/
   3525 void VertexArray::Init()
   3526 {
   3527 	/* Delete previous instance */
   3528 	Release();
   3529 
   3530 	const Functions& gl = m_context.getRenderContext().getFunctions();
   3531 
   3532 	Generate(gl, m_id);
   3533 }
   3534 
   3535 /** Release vertex array object instance
   3536  *
   3537  **/
   3538 void VertexArray::Release()
   3539 {
   3540 	if (m_invalid_id != m_id)
   3541 	{
   3542 		const Functions& gl = m_context.getRenderContext().getFunctions();
   3543 
   3544 		gl.deleteVertexArrays(1, &m_id);
   3545 
   3546 		m_id = m_invalid_id;
   3547 	}
   3548 }
   3549 
   3550 /** Set attribute in VAO
   3551  *
   3552  * @param index            Index of attribute
   3553  * @param type             Type of attribute
   3554  * @param n_array_elements Arary length
   3555  * @param normalized       Selectis if values should be normalized
   3556  * @param stride           Stride
   3557  * @param pointer          Pointer to data, or offset in buffer
   3558  **/
   3559 void VertexArray::Attribute(GLuint index, const Type& type, GLuint n_array_elements, GLboolean normalized,
   3560 							GLsizei stride, const GLvoid* pointer)
   3561 {
   3562 	const Functions& gl = m_context.getRenderContext().getFunctions();
   3563 
   3564 	AttribPointer(gl, index, type, n_array_elements, normalized, stride, pointer);
   3565 	Enable(gl, index, type, n_array_elements);
   3566 }
   3567 
   3568 /** Binds Vertex array object
   3569  *
   3570  **/
   3571 void VertexArray::Bind()
   3572 {
   3573 	const Functions& gl = m_context.getRenderContext().getFunctions();
   3574 
   3575 	Bind(gl, m_id);
   3576 }
   3577 
   3578 /** Set attribute in VAO
   3579  *
   3580  * @param gl               Functions
   3581  * @param index            Index of attribute
   3582  * @param type             Type of attribute
   3583  * @param n_array_elements Arary length
   3584  * @param normalized       Selectis if values should be normalized
   3585  * @param stride           Stride
   3586  * @param pointer          Pointer to data, or offset in buffer
   3587  **/
   3588 void VertexArray::AttribPointer(const Functions& gl, GLuint index, const Type& type, GLuint n_array_elements,
   3589 								GLboolean normalized, GLsizei stride, const GLvoid* pointer)
   3590 {
   3591 	const GLuint basic_type_size = Type::GetTypeSize(type.m_basic_type);
   3592 	const GLint  size			 = (GLint)type.m_n_rows;
   3593 	const GLuint column_size	 = (GLuint)size * basic_type_size;
   3594 	const GLenum gl_type		 = Type::GetTypeGLenum(type.m_basic_type);
   3595 
   3596 	GLuint offset = 0;
   3597 
   3598 	/* If attribute is not an array */
   3599 	if (0 == n_array_elements)
   3600 	{
   3601 		n_array_elements = 1;
   3602 	}
   3603 
   3604 	/* For each element in array */
   3605 	for (GLuint element = 0; element < n_array_elements; ++element)
   3606 	{
   3607 		/* For each column in matrix */
   3608 		for (GLuint column = 1; column <= type.m_n_columns; ++column)
   3609 		{
   3610 			/* Calculate offset */
   3611 			const GLvoid* ptr = (GLubyte*)pointer + offset;
   3612 
   3613 			/* Set up attribute */
   3614 			switch (type.m_basic_type)
   3615 			{
   3616 			case Type::Float:
   3617 				gl.vertexAttribPointer(index, size, gl_type, normalized, stride, ptr);
   3618 				GLU_EXPECT_NO_ERROR(gl.getError(), "VertexAttribPointer");
   3619 				break;
   3620 			case Type::Int:
   3621 			case Type::Uint:
   3622 				gl.vertexAttribIPointer(index, size, gl_type, stride, ptr);
   3623 				GLU_EXPECT_NO_ERROR(gl.getError(), "VertexAttribIPointer");
   3624 				break;
   3625 			case Type::Double:
   3626 				gl.vertexAttribLPointer(index, size, gl_type, stride, ptr);
   3627 				GLU_EXPECT_NO_ERROR(gl.getError(), "VertexAttribLPointer");
   3628 				break;
   3629 			default:
   3630 				TCU_FAIL("Invalid enum");
   3631 			}
   3632 
   3633 			/* Next location */
   3634 			offset += column_size;
   3635 			index += 1;
   3636 		}
   3637 	}
   3638 }
   3639 
   3640 /** Binds Vertex array object
   3641  *
   3642  * @param gl GL functions
   3643  * @param id ID of vertex array object
   3644  **/
   3645 void VertexArray::Bind(const glw::Functions& gl, glw::GLuint id)
   3646 {
   3647 	gl.bindVertexArray(id);
   3648 	GLU_EXPECT_NO_ERROR(gl.getError(), "BindVertexArray");
   3649 }
   3650 
   3651 /** Disable attribute in VAO
   3652  *
   3653  * @param gl               Functions
   3654  * @param index            Index of attribute
   3655  * @param type             Type of attribute
   3656  * @param n_array_elements Arary length
   3657  **/
   3658 void VertexArray::Disable(const Functions& gl, GLuint index, const Type& type, GLuint n_array_elements)
   3659 {
   3660 	/* If attribute is not an array */
   3661 	if (0 == n_array_elements)
   3662 	{
   3663 		n_array_elements = 1;
   3664 	}
   3665 
   3666 	/* For each element in array */
   3667 	for (GLuint element = 0; element < n_array_elements; ++element)
   3668 	{
   3669 		/* For each column in matrix */
   3670 		for (GLuint column = 1; column <= type.m_n_columns; ++column)
   3671 		{
   3672 			/* Enable attribute array */
   3673 			gl.disableVertexAttribArray(index);
   3674 			GLU_EXPECT_NO_ERROR(gl.getError(), "DisableVertexAttribArray");
   3675 
   3676 			/* Next location */
   3677 			index += 1;
   3678 		}
   3679 	}
   3680 }
   3681 
   3682 /** Set divisor for attribute
   3683  *
   3684  * @param gl               Functions
   3685  * @param index            Index of attribute
   3686  * @param divisor          New divisor value
   3687  **/
   3688 void VertexArray::Divisor(const Functions& gl, GLuint index, GLuint divisor)
   3689 {
   3690 	gl.vertexAttribDivisor(index, divisor);
   3691 	GLU_EXPECT_NO_ERROR(gl.getError(), "VertexAttribDivisor");
   3692 }
   3693 
   3694 /** Enables attribute in VAO
   3695  *
   3696  * @param gl               Functions
   3697  * @param index            Index of attribute
   3698  * @param type             Type of attribute
   3699  * @param n_array_elements Arary length
   3700  **/
   3701 void VertexArray::Enable(const Functions& gl, GLuint index, const Type& type, GLuint n_array_elements)
   3702 {
   3703 	/* If attribute is not an array */
   3704 	if (0 == n_array_elements)
   3705 	{
   3706 		n_array_elements = 1;
   3707 	}
   3708 
   3709 	/* For each element in array */
   3710 	for (GLuint element = 0; element < n_array_elements; ++element)
   3711 	{
   3712 		/* For each column in matrix */
   3713 		for (GLuint column = 1; column <= type.m_n_columns; ++column)
   3714 		{
   3715 			/* Enable attribute array */
   3716 			gl.enableVertexAttribArray(index);
   3717 			GLU_EXPECT_NO_ERROR(gl.getError(), "EnableVertexAttribArray");
   3718 
   3719 			/* Next location */
   3720 			index += 1;
   3721 		}
   3722 	}
   3723 }
   3724 
   3725 /** Generates Vertex array object
   3726  *
   3727  * @param gl     GL functions
   3728  * @param out_id ID of vertex array object
   3729  **/
   3730 void VertexArray::Generate(const glw::Functions& gl, glw::GLuint& out_id)
   3731 {
   3732 	GLuint id = m_invalid_id;
   3733 
   3734 	gl.genVertexArrays(1, &id);
   3735 	GLU_EXPECT_NO_ERROR(gl.getError(), "GenVertexArrays");
   3736 
   3737 	if (m_invalid_id == id)
   3738 	{
   3739 		TCU_FAIL("Invalid id");
   3740 	}
   3741 
   3742 	out_id = id;
   3743 }
   3744 
   3745 /* Constatns used by Variable */
   3746 const GLint Variable::m_automatic_location = -1;
   3747 
   3748 /** Copy constructor
   3749  *
   3750  **/
   3751 Variable::Variable(const Variable& var)
   3752 	: m_data(var.m_data)
   3753 	, m_data_size(var.m_data_size)
   3754 	, m_descriptor(var.m_descriptor.m_name.c_str(), var.m_descriptor.m_qualifiers.c_str(),
   3755 				   var.m_descriptor.m_expected_component, var.m_descriptor.m_expected_location,
   3756 				   var.m_descriptor.m_builtin, var.m_descriptor.m_normalized, var.m_descriptor.m_n_array_elements,
   3757 				   var.m_descriptor.m_expected_stride_of_element, var.m_descriptor.m_offset)
   3758 	, m_storage(var.m_storage)
   3759 {
   3760 	m_descriptor.m_type = var.m_descriptor.m_type;
   3761 
   3762 	if (BUILTIN != var.m_descriptor.m_type)
   3763 	{
   3764 		m_descriptor.m_interface = var.m_descriptor.m_interface;
   3765 	}
   3766 }
   3767 
   3768 /** Get code that defines variable
   3769  *
   3770  * @param flavour Provides info if variable is array or not
   3771  *
   3772  * @return String with code
   3773  **/
   3774 std::string Variable::GetDefinition(FLAVOUR flavour) const
   3775 {
   3776 	return m_descriptor.GetDefinition(flavour, m_storage);
   3777 }
   3778 
   3779 /** Calcualtes stride of variable
   3780  *
   3781  * @return Calculated value
   3782  **/
   3783 GLuint Variable::GetStride() const
   3784 {
   3785 	GLint variable_stride = 0;
   3786 
   3787 	if (0 == m_descriptor.m_n_array_elements)
   3788 	{
   3789 		variable_stride = m_descriptor.m_expected_stride_of_element;
   3790 	}
   3791 	else
   3792 	{
   3793 		variable_stride = m_descriptor.m_expected_stride_of_element * m_descriptor.m_n_array_elements;
   3794 	}
   3795 
   3796 	return variable_stride;
   3797 }
   3798 
   3799 /** Check if variable is block
   3800  *
   3801  * @return true if variable type is block, false otherwise
   3802  **/
   3803 bool Variable::IsBlock() const
   3804 {
   3805 	if (BUILTIN == m_descriptor.m_type)
   3806 	{
   3807 		return false;
   3808 	}
   3809 
   3810 	const Interface* interface = m_descriptor.m_interface;
   3811 	if (0 == interface)
   3812 	{
   3813 		TCU_FAIL("Nullptr");
   3814 	}
   3815 
   3816 	return (Interface::BLOCK == interface->m_type);
   3817 }
   3818 
   3819 /** Check if variable is struct
   3820  *
   3821  * @return true if variable type is struct, false otherwise
   3822  **/
   3823 bool Variable::IsStruct() const
   3824 {
   3825 	if (BUILTIN == m_descriptor.m_type)
   3826 	{
   3827 		return false;
   3828 	}
   3829 
   3830 	const Interface* interface = m_descriptor.m_interface;
   3831 	if (0 == interface)
   3832 	{
   3833 		TCU_FAIL("Nullptr");
   3834 	}
   3835 
   3836 	return (Interface::STRUCT == interface->m_type);
   3837 }
   3838 /** Get code that reference variable
   3839  *
   3840  * @param parent_name Name of parent
   3841  * @param variable    Descriptor of variable
   3842  * @param flavour     Provides info about how variable should be referenced
   3843  * @param array_index Index of array, ignored when variable is not array
   3844  *
   3845  * @return String with code
   3846  **/
   3847 std::string Variable::GetReference(const std::string& parent_name, const Descriptor& variable, FLAVOUR flavour,
   3848 								   GLuint array_index)
   3849 {
   3850 	std::string name;
   3851 
   3852 	/* Prepare name */
   3853 	if (false == parent_name.empty())
   3854 	{
   3855 		name = parent_name;
   3856 		name.append(".");
   3857 		name.append(variable.m_name);
   3858 	}
   3859 	else
   3860 	{
   3861 		name = variable.m_name;
   3862 	}
   3863 
   3864 	/* */
   3865 	switch (flavour)
   3866 	{
   3867 	case Utils::Variable::BASIC:
   3868 		break;
   3869 
   3870 	case Utils::Variable::ARRAY:
   3871 		name.append("[0]");
   3872 		break;
   3873 
   3874 	case Utils::Variable::INDEXED_BY_INVOCATION_ID:
   3875 		name.append("[gl_InvocationID]");
   3876 		break;
   3877 	}
   3878 
   3879 	/* Assumption that both variables have same lengths */
   3880 	if (0 != variable.m_n_array_elements)
   3881 	{
   3882 		GLchar buffer[16];
   3883 		sprintf(buffer, "%d", array_index);
   3884 		name.append("[");
   3885 		name.append(buffer);
   3886 		name.append("]");
   3887 	}
   3888 
   3889 	return name;
   3890 }
   3891 
   3892 /** Get "flavour" of varying
   3893  *
   3894  * @param stage     Stage of shader
   3895  * @param direction Selects if varying is in or out
   3896  *
   3897  * @return Flavour
   3898  **/
   3899 Variable::FLAVOUR Variable::GetFlavour(Shader::STAGES stage, VARYING_DIRECTION direction)
   3900 {
   3901 	FLAVOUR result = BASIC;
   3902 
   3903 	switch (stage)
   3904 	{
   3905 	case Shader::GEOMETRY:
   3906 	case Shader::TESS_EVAL:
   3907 		if (INPUT == direction)
   3908 		{
   3909 			result = ARRAY;
   3910 		}
   3911 		break;
   3912 	case Shader::TESS_CTRL:
   3913 		result = INDEXED_BY_INVOCATION_ID;
   3914 		break;
   3915 	default:
   3916 		break;
   3917 	}
   3918 
   3919 	return result;
   3920 }
   3921 
   3922 /** Constructor, for built-in types
   3923  *
   3924  * @param name                       Name
   3925  * @param qualifiers                 Qualifiers
   3926  * @param expected_component         Expected component of variable
   3927  * @param expected_location          Expected location
   3928  * @param type                       Type
   3929  * @param normalized                 Selects if data should be normalized
   3930  * @param n_array_elements           Length of array
   3931  * @param expected_stride_of_element Expected stride of element
   3932  * @param offset                     Offset
   3933  **/
   3934 Variable::Descriptor::Descriptor(const GLchar* name, const GLchar* qualifiers, GLint expected_component,
   3935 								 GLint expected_location, const Type& type, GLboolean normalized,
   3936 								 GLuint n_array_elements, GLint expected_stride_of_element, GLuint offset)
   3937 	: m_expected_component(expected_component)
   3938 	, m_expected_location(expected_location)
   3939 	, m_expected_stride_of_element(expected_stride_of_element)
   3940 	, m_n_array_elements(n_array_elements)
   3941 	, m_name(name)
   3942 	, m_normalized(normalized)
   3943 	, m_offset(offset)
   3944 	, m_qualifiers(qualifiers)
   3945 	, m_type(BUILTIN)
   3946 	, m_builtin(type)
   3947 {
   3948 }
   3949 
   3950 /** Constructor, for interface types
   3951  *
   3952  * @param name                       Name
   3953  * @param qualifiers                 Qualifiers
   3954  * @param expected_component         Expected component of variable
   3955  * @param expected_location          Expected location
   3956  * @param interface                  Interface of variable
   3957  * @param n_array_elements           Length of array
   3958  * @param expected_stride_of_element Expected stride of element
   3959  * @param offset                     Offset
   3960  **/
   3961 Variable::Descriptor::Descriptor(const GLchar* name, const GLchar* qualifiers, GLint expected_componenet,
   3962 								 GLint expected_location, Interface* interface, GLuint n_array_elements,
   3963 								 GLint expected_stride_of_element, GLuint offset)
   3964 	: m_expected_component(expected_componenet)
   3965 	, m_expected_location(expected_location)
   3966 	, m_expected_stride_of_element(expected_stride_of_element)
   3967 	, m_n_array_elements(n_array_elements)
   3968 	, m_name(name)
   3969 	, m_normalized(GL_FALSE)
   3970 	, m_offset(offset)
   3971 	, m_qualifiers(qualifiers)
   3972 	, m_type(INTERFACE)
   3973 	, m_interface(interface)
   3974 {
   3975 }
   3976 
   3977 /** Get definition of variable
   3978  *
   3979  * @param flavour Flavour of variable
   3980  * @param storage Storage used for variable
   3981  *
   3982  * @return code with defintion
   3983  **/
   3984 std::string Variable::Descriptor::GetDefinition(FLAVOUR flavour, STORAGE storage) const
   3985 {
   3986 	static const GLchar* basic_template = "QUALIFIERS STORAGETYPE NAMEARRAY;";
   3987 	static const GLchar* array_template = "QUALIFIERS STORAGETYPE NAME[]ARRAY;";
   3988 	const GLchar*		 storage_str	= 0;
   3989 
   3990 	std::string definition;
   3991 	size_t		position = 0;
   3992 
   3993 	/* Select definition template */
   3994 	switch (flavour)
   3995 	{
   3996 	case BASIC:
   3997 		definition = basic_template;
   3998 		break;
   3999 	case ARRAY:
   4000 	case INDEXED_BY_INVOCATION_ID:
   4001 		definition = array_template;
   4002 		break;
   4003 	default:
   4004 		TCU_FAIL("Invliad enum");
   4005 		break;
   4006 	}
   4007 
   4008 	if (BUILTIN != m_type)
   4009 	{
   4010 		if (0 == m_interface)
   4011 		{
   4012 			TCU_FAIL("Nullptr");
   4013 		}
   4014 	}
   4015 
   4016 	/* Qualifiers */
   4017 	if (true == m_qualifiers.empty())
   4018 	{
   4019 		replaceToken("QUALIFIERS ", position, "", definition);
   4020 	}
   4021 	else
   4022 	{
   4023 		replaceToken("QUALIFIERS", position, m_qualifiers.c_str(), definition);
   4024 	}
   4025 
   4026 	// According to spec: integer or unsigned integer type must always be declared with flat qualifier
   4027 	bool flat_qualifier = false;
   4028 	if (m_type != BUILTIN && m_interface != NULL)
   4029 	{
   4030 		if (m_interface->m_members[0].m_builtin.m_basic_type == Utils::Type::Int ||
   4031 			m_interface->m_members[0].m_builtin.m_basic_type == Utils::Type::Uint)
   4032 		{
   4033 			flat_qualifier = true;
   4034 		}
   4035 	}
   4036 	/* Storage */
   4037 	switch (storage)
   4038 	{
   4039 	case VARYING_INPUT:
   4040 		storage_str = flat_qualifier ? "flat in " : "in ";
   4041 		break;
   4042 	case VARYING_OUTPUT:
   4043 		storage_str = "out ";
   4044 		break;
   4045 	case UNIFORM:
   4046 		storage_str = "uniform ";
   4047 		break;
   4048 	case SSB:
   4049 		storage_str = "buffer ";
   4050 		break;
   4051 	case MEMBER:
   4052 		storage_str = "";
   4053 		break;
   4054 	default:
   4055 		TCU_FAIL("Invalid enum");
   4056 		break;
   4057 	}
   4058 
   4059 	replaceToken("STORAGE", position, storage_str, definition);
   4060 
   4061 	/* Type */
   4062 	if (BUILTIN == m_type)
   4063 	{
   4064 		replaceToken("TYPE", position, m_builtin.GetGLSLTypeName(), definition);
   4065 	}
   4066 	else
   4067 	{
   4068 		if (Interface::STRUCT == m_interface->m_type)
   4069 		{
   4070 			replaceToken("TYPE", position, m_interface->m_name.c_str(), definition);
   4071 		}
   4072 		else
   4073 		{
   4074 			const std::string& block_definition = m_interface->GetDefinition();
   4075 
   4076 			replaceToken("TYPE", position, block_definition.c_str(), definition);
   4077 		}
   4078 	}
   4079 
   4080 	/* Name */
   4081 	replaceToken("NAME", position, m_name.c_str(), definition);
   4082 
   4083 	/* Array size */
   4084 	if (0 == m_n_array_elements)
   4085 	{
   4086 		replaceToken("ARRAY", position, "", definition);
   4087 	}
   4088 	else
   4089 	{
   4090 		char buffer[16];
   4091 		sprintf(buffer, "[%d]", m_n_array_elements);
   4092 
   4093 		replaceToken("ARRAY", position, buffer, definition);
   4094 	}
   4095 
   4096 	/* Done */
   4097 	return definition;
   4098 }
   4099 
   4100 /** Get definitions for variables collected in vector
   4101  *
   4102  * @param vector  Collection of variables
   4103  * @param flavour Flavour of variables
   4104  *
   4105  * @return Code with definitions
   4106  **/
   4107 std::string GetDefinitions(const Variable::PtrVector& vector, Variable::FLAVOUR flavour)
   4108 {
   4109 	std::string list	 = Utils::g_list;
   4110 	size_t		position = 0;
   4111 
   4112 	for (GLuint i = 0; i < vector.size(); ++i)
   4113 	{
   4114 		Utils::insertElementOfList(vector[i]->GetDefinition(flavour).c_str(), "\n", position, list);
   4115 	}
   4116 
   4117 	Utils::endList("", position, list);
   4118 
   4119 	return list;
   4120 }
   4121 
   4122 /** Get definitions for interfaces collected in vector
   4123  *
   4124  * @param vector Collection of interfaces
   4125  *
   4126  * @return Code with definitions
   4127  **/
   4128 std::string GetDefinitions(const Interface::PtrVector& vector)
   4129 {
   4130 	std::string list	 = Utils::g_list;
   4131 	size_t		position = 0;
   4132 
   4133 	for (GLuint i = 0; i < vector.size(); ++i)
   4134 	{
   4135 		Utils::insertElementOfList(vector[i]->GetDefinition().c_str(), "\n", position, list);
   4136 	}
   4137 
   4138 	Utils::endList("", position, list);
   4139 
   4140 	return list;
   4141 }
   4142 
   4143 /** Constructor
   4144  *
   4145  * @param name Name
   4146  * @param type Type of interface
   4147  **/
   4148 Interface::Interface(const GLchar* name, Interface::TYPE type) : m_name(name), m_type(type)
   4149 {
   4150 }
   4151 
   4152 /** Adds member to interface
   4153  *
   4154  * @param member Descriptor of new member
   4155  *
   4156  * @return Pointer to just created member
   4157  **/
   4158 Variable::Descriptor* Interface::AddMember(const Variable::Descriptor& member)
   4159 {
   4160 	m_members.push_back(member);
   4161 
   4162 	return &m_members.back();
   4163 }
   4164 
   4165 /** Get definition of interface
   4166  *
   4167  * @param Code with definition
   4168  **/
   4169 std::string Interface::GetDefinition() const
   4170 {
   4171 	std::string definition;
   4172 	size_t		position = 0;
   4173 
   4174 	const GLchar* member_list = "    MEMBER_DEFINITION\nMEMBER_LIST";
   4175 
   4176 	if (STRUCT == m_type)
   4177 	{
   4178 		definition = "struct NAME {\nMEMBER_LIST};";
   4179 	}
   4180 	else
   4181 	{
   4182 		definition = "NAME {\nMEMBER_LIST}";
   4183 	}
   4184 
   4185 	/* Name */
   4186 	replaceToken("NAME", position, m_name.c_str(), definition);
   4187 
   4188 	/* Member list */
   4189 	for (GLuint i = 0; i < m_members.size(); ++i)
   4190 	{
   4191 		const size_t	   start_position	= position;
   4192 		const std::string& member_definition = m_members[i].GetDefinition(Variable::BASIC, Variable::MEMBER);
   4193 
   4194 		/* Member list */
   4195 		replaceToken("MEMBER_LIST", position, member_list, definition);
   4196 
   4197 		/* Move back position */
   4198 		position = start_position;
   4199 
   4200 		/* Member definition */
   4201 		replaceToken("MEMBER_DEFINITION", position, member_definition.c_str(), definition);
   4202 	}
   4203 
   4204 	/* Remove last member list */
   4205 	replaceToken("MEMBER_LIST", position, "", definition);
   4206 
   4207 	/* Done */
   4208 	return definition;
   4209 }
   4210 
   4211 /** Adds member of built-in type to interface
   4212  *
   4213  * @param name                       Name
   4214  * @param qualifiers                 Qualifiers
   4215  * @param expected_component         Expected component of variable
   4216  * @param expected_location          Expected location
   4217  * @param type                       Type
   4218  * @param normalized                 Selects if data should be normalized
   4219  * @param n_array_elements           Length of array
   4220  * @param expected_stride_of_element Expected stride of element
   4221  * @param offset                     Offset
   4222  *
   4223  * @return Pointer to just created member
   4224  **/
   4225 Variable::Descriptor* Interface::Member(const GLchar* name, const GLchar* qualifiers, GLint expected_component,
   4226 										GLint expected_location, const Type& type, GLboolean normalized,
   4227 										GLuint n_array_elements, GLint expected_stride_of_element, GLuint offset)
   4228 {
   4229 	return AddMember(Variable::Descriptor(name, qualifiers, expected_component, expected_location, type, normalized,
   4230 										  n_array_elements, expected_stride_of_element, offset));
   4231 }
   4232 
   4233 /** Adds member of interface type to interface
   4234  *
   4235  * @param name                       Name
   4236  * @param qualifiers                 Qualifiers
   4237  * @param expected_component         Expected component of variable
   4238  * @param expected_location          Expected location
   4239  * @param type                       Type
   4240  * @param normalized                 Selects if data should be normalized
   4241  * @param n_array_elements           Length of array
   4242  * @param expected_stride_of_element Expected stride of element
   4243  * @param offset                     Offset
   4244  *
   4245  * @return Pointer to just created member
   4246  **/
   4247 Variable::Descriptor* Interface::Member(const GLchar* name, const GLchar* qualifiers, GLint expected_component,
   4248 										GLint expected_location, Interface* nterface, GLuint n_array_elements,
   4249 										GLint expected_stride_of_element, GLuint offset)
   4250 {
   4251 	return AddMember(Variable::Descriptor(name, qualifiers, expected_component, expected_location, nterface,
   4252 										  n_array_elements, expected_stride_of_element, offset));
   4253 }
   4254 
   4255 /** Clears contents of vector of pointers
   4256  *
   4257  * @tparam T Type of elements
   4258  *
   4259  * @param vector Collection to be cleared
   4260  **/
   4261 template <typename T>
   4262 void clearPtrVector(std::vector<T*>& vector)
   4263 {
   4264 	for (size_t i = 0; i < vector.size(); ++i)
   4265 	{
   4266 		T* t = vector[i];
   4267 
   4268 		vector[i] = 0;
   4269 
   4270 		if (0 != t)
   4271 		{
   4272 			delete t;
   4273 		}
   4274 	}
   4275 
   4276 	vector.clear();
   4277 }
   4278 
   4279 /** Constructor
   4280  *
   4281  * @param stage Stage described by that interface
   4282  **/
   4283 ShaderInterface::ShaderInterface(Shader::STAGES stage) : m_stage(stage)
   4284 {
   4285 	/* Nothing to be done */
   4286 }
   4287 
   4288 /** Get definitions of globals
   4289  *
   4290  * @return Code with definitions
   4291  **/
   4292 std::string ShaderInterface::GetDefinitionsGlobals() const
   4293 {
   4294 	return m_globals;
   4295 }
   4296 
   4297 /** Get definitions of inputs
   4298  *
   4299  * @return Code with definitions
   4300  **/
   4301 std::string ShaderInterface::GetDefinitionsInputs() const
   4302 {
   4303 	Variable::FLAVOUR flavour = Variable::GetFlavour(m_stage, Variable::INPUT);
   4304 
   4305 	return GetDefinitions(m_inputs, flavour);
   4306 }
   4307 
   4308 /** Get definitions of outputs
   4309  *
   4310  * @return Code with definitions
   4311  **/
   4312 std::string ShaderInterface::GetDefinitionsOutputs() const
   4313 {
   4314 	Variable::FLAVOUR flavour = Variable::GetFlavour(m_stage, Variable::OUTPUT);
   4315 
   4316 	return GetDefinitions(m_outputs, flavour);
   4317 }
   4318 
   4319 /** Get definitions of buffers
   4320  *
   4321  * @return Code with definitions
   4322  **/
   4323 std::string ShaderInterface::GetDefinitionsSSBs() const
   4324 {
   4325 	return GetDefinitions(m_ssb_blocks, Variable::BASIC);
   4326 }
   4327 
   4328 /** Get definitions of uniforms
   4329  *
   4330  * @return Code with definitions
   4331  **/
   4332 std::string ShaderInterface::GetDefinitionsUniforms() const
   4333 {
   4334 	return GetDefinitions(m_uniforms, Variable::BASIC);
   4335 }
   4336 
   4337 /** Constructor
   4338  *
   4339  * @param in  Input variable
   4340  * @param out Output variable
   4341  **/
   4342 VaryingConnection::VaryingConnection(Variable* in, Variable* out) : m_in(in), m_out(out)
   4343 {
   4344 	/* NBothing to be done here */
   4345 }
   4346 
   4347 /** Adds new varying connection to given stage
   4348  *
   4349  * @param stage Shader stage
   4350  * @param in    In varying
   4351  * @param out   Out varying
   4352  **/
   4353 void VaryingPassthrough::Add(Shader::STAGES stage, Variable* in, Variable* out)
   4354 {
   4355 	VaryingConnection::Vector& vector = Get(stage);
   4356 
   4357 	vector.push_back(VaryingConnection(in, out));
   4358 }
   4359 
   4360 /** Get all passthrough connections for given stage
   4361  *
   4362  * @param stage Shader stage
   4363  *
   4364  * @return Vector of connections
   4365  **/
   4366 VaryingConnection::Vector& VaryingPassthrough::Get(Shader::STAGES stage)
   4367 {
   4368 	VaryingConnection::Vector* result = 0;
   4369 
   4370 	switch (stage)
   4371 	{
   4372 	case Shader::FRAGMENT:
   4373 		result = &m_fragment;
   4374 		break;
   4375 	case Shader::GEOMETRY:
   4376 		result = &m_geometry;
   4377 		break;
   4378 	case Shader::TESS_CTRL:
   4379 		result = &m_tess_ctrl;
   4380 		break;
   4381 	case Shader::TESS_EVAL:
   4382 		result = &m_tess_eval;
   4383 		break;
   4384 	case Shader::VERTEX:
   4385 		result = &m_vertex;
   4386 		break;
   4387 	default:
   4388 		TCU_FAIL("Invalid enum");
   4389 	}
   4390 
   4391 	return *result;
   4392 }
   4393 
   4394 /** Constructor
   4395  *
   4396  **/
   4397 ProgramInterface::ProgramInterface()
   4398 	: m_compute(Shader::COMPUTE)
   4399 	, m_vertex(Shader::VERTEX)
   4400 	, m_tess_ctrl(Shader::TESS_CTRL)
   4401 	, m_tess_eval(Shader::TESS_EVAL)
   4402 	, m_geometry(Shader::GEOMETRY)
   4403 	, m_fragment(Shader::FRAGMENT)
   4404 {
   4405 }
   4406 
   4407 /** Destructor
   4408  *
   4409  **/
   4410 ProgramInterface::~ProgramInterface()
   4411 {
   4412 	clearPtrVector(m_blocks);
   4413 	clearPtrVector(m_structures);
   4414 }
   4415 
   4416 /** Adds new interface
   4417  *
   4418  * @param name
   4419  * @param type
   4420  *
   4421  * @return Pointer to created interface
   4422  **/
   4423 Interface* ProgramInterface::AddInterface(const GLchar* name, Interface::TYPE type)
   4424 {
   4425 	Interface* interface = 0;
   4426 
   4427 	if (Interface::STRUCT == type)
   4428 	{
   4429 		interface = new Interface(name, type);
   4430 
   4431 		m_structures.push_back(interface);
   4432 	}
   4433 	else
   4434 	{
   4435 		interface = new Interface(name, type);
   4436 
   4437 		m_blocks.push_back(interface);
   4438 	}
   4439 
   4440 	return interface;
   4441 }
   4442 
   4443 /** Adds new block interface
   4444  *
   4445  * @param name
   4446  *
   4447  * @return Pointer to created interface
   4448  **/
   4449 Interface* ProgramInterface::Block(const GLchar* name)
   4450 {
   4451 	return AddInterface(name, Interface::BLOCK);
   4452 }
   4453 
   4454 /** Get interface of given shader stage
   4455  *
   4456  * @param stage Shader stage
   4457  *
   4458  * @return Reference to stage interface
   4459  **/
   4460 ShaderInterface& ProgramInterface::GetShaderInterface(Shader::STAGES stage)
   4461 {
   4462 	ShaderInterface* interface = 0;
   4463 
   4464 	switch (stage)
   4465 	{
   4466 	case Shader::COMPUTE:
   4467 		interface = &m_compute;
   4468 		break;
   4469 	case Shader::FRAGMENT:
   4470 		interface = &m_fragment;
   4471 		break;
   4472 	case Shader::GEOMETRY:
   4473 		interface = &m_geometry;
   4474 		break;
   4475 	case Shader::TESS_CTRL:
   4476 		interface = &m_tess_ctrl;
   4477 		break;
   4478 	case Shader::TESS_EVAL:
   4479 		interface = &m_tess_eval;
   4480 		break;
   4481 	case Shader::VERTEX:
   4482 		interface = &m_vertex;
   4483 		break;
   4484 	default:
   4485 		TCU_FAIL("Invalid enum");
   4486 	}
   4487 
   4488 	return *interface;
   4489 }
   4490 
   4491 /** Get interface of given shader stage
   4492  *
   4493  * @param stage Shader stage
   4494  *
   4495  * @return Reference to stage interface
   4496  **/
   4497 const ShaderInterface& ProgramInterface::GetShaderInterface(Shader::STAGES stage) const
   4498 {
   4499 	const ShaderInterface* interface = 0;
   4500 
   4501 	switch (stage)
   4502 	{
   4503 	case Shader::COMPUTE:
   4504 		interface = &m_compute;
   4505 		break;
   4506 	case Shader::FRAGMENT:
   4507 		interface = &m_fragment;
   4508 		break;
   4509 	case Shader::GEOMETRY:
   4510 		interface = &m_geometry;
   4511 		break;
   4512 	case Shader::TESS_CTRL:
   4513 		interface = &m_tess_ctrl;
   4514 		break;
   4515 	case Shader::TESS_EVAL:
   4516 		interface = &m_tess_eval;
   4517 		break;
   4518 	case Shader::VERTEX:
   4519 		interface = &m_vertex;
   4520 		break;
   4521 	default:
   4522 		TCU_FAIL("Invalid enum");
   4523 	}
   4524 
   4525 	return *interface;
   4526 }
   4527 
   4528 /** Clone interface of Vertex shader stage to other stages
   4529  * It creates matching inputs, outputs, uniforms and buffers in other stages.
   4530  * There are no additional outputs for FRAGMENT shader generated.
   4531  *
   4532  * @param varying_passthrough Collection of varyings connections
   4533  **/
   4534 void ProgramInterface::CloneVertexInterface(VaryingPassthrough& varying_passthrough)
   4535 {
   4536 	/* VS outputs >> TCS inputs >> TCS outputs >> ..  >> FS inputs */
   4537 	for (size_t i = 0; i < m_vertex.m_outputs.size(); ++i)
   4538 	{
   4539 		const Variable& vs_var = *m_vertex.m_outputs[i];
   4540 		const GLchar*   prefix = GetStagePrefix(Shader::VERTEX, vs_var.m_storage);
   4541 
   4542 		cloneVariableForStage(vs_var, Shader::TESS_CTRL, prefix, varying_passthrough);
   4543 		cloneVariableForStage(vs_var, Shader::TESS_EVAL, prefix, varying_passthrough);
   4544 		cloneVariableForStage(vs_var, Shader::GEOMETRY, prefix, varying_passthrough);
   4545 		cloneVariableForStage(vs_var, Shader::FRAGMENT, prefix, varying_passthrough);
   4546 	}
   4547 
   4548 	/* Copy uniforms from VS to other stages */
   4549 	for (size_t i = 0; i < m_vertex.m_uniforms.size(); ++i)
   4550 	{
   4551 		Variable&	 vs_var = *m_vertex.m_uniforms[i];
   4552 		const GLchar* prefix = GetStagePrefix(Shader::VERTEX, vs_var.m_storage);
   4553 
   4554 		cloneVariableForStage(vs_var, Shader::COMPUTE, prefix, varying_passthrough);
   4555 		cloneVariableForStage(vs_var, Shader::TESS_CTRL, prefix, varying_passthrough);
   4556 		cloneVariableForStage(vs_var, Shader::TESS_EVAL, prefix, varying_passthrough);
   4557 		cloneVariableForStage(vs_var, Shader::GEOMETRY, prefix, varying_passthrough);
   4558 		cloneVariableForStage(vs_var, Shader::FRAGMENT, prefix, varying_passthrough);
   4559 
   4560 		/* Uniform blocks needs unique binding */
   4561 		if (true == vs_var.IsBlock())
   4562 		{
   4563 			replaceBinding(vs_var, Shader::VERTEX);
   4564 		}
   4565 	}
   4566 
   4567 	/* Copy SSBs from VS to other stages */
   4568 	for (size_t i = 0; i < m_vertex.m_ssb_blocks.size(); ++i)
   4569 	{
   4570 		Variable&	 vs_var = *m_vertex.m_ssb_blocks[i];
   4571 		const GLchar* prefix = GetStagePrefix(Shader::VERTEX, vs_var.m_storage);
   4572 
   4573 		cloneVariableForStage(vs_var, Shader::COMPUTE, prefix, varying_passthrough);
   4574 		cloneVariableForStage(vs_var, Shader::TESS_CTRL, prefix, varying_passthrough);
   4575 		cloneVariableForStage(vs_var, Shader::TESS_EVAL, prefix, varying_passthrough);
   4576 		cloneVariableForStage(vs_var, Shader::GEOMETRY, prefix, varying_passthrough);
   4577 		cloneVariableForStage(vs_var, Shader::FRAGMENT, prefix, varying_passthrough);
   4578 
   4579 		/* SSBs blocks needs unique binding */
   4580 		if (true == vs_var.IsBlock())
   4581 		{
   4582 			replaceBinding(vs_var, Shader::VERTEX);
   4583 		}
   4584 	}
   4585 
   4586 	m_compute.m_globals   = m_vertex.m_globals;
   4587 	m_fragment.m_globals  = m_vertex.m_globals;
   4588 	m_geometry.m_globals  = m_vertex.m_globals;
   4589 	m_tess_ctrl.m_globals = m_vertex.m_globals;
   4590 	m_tess_eval.m_globals = m_vertex.m_globals;
   4591 }
   4592 
   4593 /** Clone variable for specific stage
   4594  *
   4595  * @param variable            Variable
   4596  * @param stage               Requested stage
   4597  * @param prefix              Prefix used in variable name that is specific for original stage
   4598  * @param varying_passthrough Collection of varyings connections
   4599  **/
   4600 void ProgramInterface::cloneVariableForStage(const Variable& variable, Shader::STAGES stage, const GLchar* prefix,
   4601 											 VaryingPassthrough& varying_passthrough)
   4602 {
   4603 	switch (variable.m_storage)
   4604 	{
   4605 	case Variable::VARYING_OUTPUT:
   4606 	{
   4607 		Variable* in = cloneVariableForStage(variable, stage, Variable::VARYING_INPUT, prefix);
   4608 
   4609 		if (Shader::FRAGMENT != stage)
   4610 		{
   4611 			Variable* out = cloneVariableForStage(variable, stage, Variable::VARYING_OUTPUT, prefix);
   4612 			varying_passthrough.Add(stage, in, out);
   4613 		}
   4614 	}
   4615 	break;
   4616 	case Variable::UNIFORM:
   4617 	case Variable::SSB:
   4618 		cloneVariableForStage(variable, stage, variable.m_storage, prefix);
   4619 		break;
   4620 	default:
   4621 		TCU_FAIL("Invalid enum");
   4622 		break;
   4623 	}
   4624 }
   4625 
   4626 /** Clone variable for specific stage
   4627  *
   4628  * @param variable Variable
   4629  * @param stage    Requested stage
   4630  * @param storage  Storage used by variable
   4631  * @param prefix   Prefix used in variable name that is specific for original stage
   4632  *
   4633  * @return New variable
   4634  **/
   4635 Variable* ProgramInterface::cloneVariableForStage(const Variable& variable, Shader::STAGES stage,
   4636 												  Variable::STORAGE storage, const GLchar* prefix)
   4637 {
   4638 	/* Initialize with original variable */
   4639 	Variable* var = new Variable(variable);
   4640 	if (0 == var)
   4641 	{
   4642 		TCU_FAIL("Memory allocation");
   4643 	}
   4644 
   4645 	/* Set up storage */
   4646 	var->m_storage = storage;
   4647 
   4648 	/* Get name */
   4649 	std::string name = variable.m_descriptor.m_name;
   4650 
   4651 	/* Prefix name with stage ID, empty means default block */
   4652 	if (false == name.empty())
   4653 	{
   4654 		size_t		  position	 = 0;
   4655 		const GLchar* stage_prefix = GetStagePrefix(stage, storage);
   4656 		Utils::replaceToken(prefix, position, stage_prefix, name);
   4657 	}
   4658 	var->m_descriptor.m_name = name;
   4659 
   4660 	/* Clone block */
   4661 	const bool is_block = variable.IsBlock();
   4662 	if (true == is_block)
   4663 	{
   4664 		const Interface* interface = variable.m_descriptor.m_interface;
   4665 
   4666 		Interface* block = CloneBlockForStage(*interface, stage, storage, prefix);
   4667 
   4668 		var->m_descriptor.m_interface = block;
   4669 	}
   4670 
   4671 	/* Store variable */
   4672 	ShaderInterface& si		= GetShaderInterface(stage);
   4673 	Variable*		 result = 0;
   4674 
   4675 	switch (storage)
   4676 	{
   4677 	case Variable::VARYING_INPUT:
   4678 		si.m_inputs.push_back(var);
   4679 		result = si.m_inputs.back();
   4680 		break;
   4681 	case Variable::VARYING_OUTPUT:
   4682 		si.m_outputs.push_back(var);
   4683 		result = si.m_outputs.back();
   4684 		break;
   4685 	case Variable::UNIFORM:
   4686 		/* Uniform blocks needs unique binding */
   4687 		if (true == is_block)
   4688 		{
   4689 			replaceBinding(*var, stage);
   4690 		}
   4691 
   4692 		si.m_uniforms.push_back(var);
   4693 		result = si.m_uniforms.back();
   4694 		break;
   4695 	case Variable::SSB:
   4696 		/* SSBs needs unique binding */
   4697 		if (true == is_block)
   4698 		{
   4699 			replaceBinding(*var, stage);
   4700 		}
   4701 
   4702 		si.m_ssb_blocks.push_back(var);
   4703 		result = si.m_ssb_blocks.back();
   4704 		break;
   4705 	default:
   4706 		TCU_FAIL("Invalid enum");
   4707 		break;
   4708 	}
   4709 
   4710 	return result;
   4711 }
   4712 
   4713 /** clone block to specific stage
   4714  *
   4715  * @param block   Block to be copied
   4716  * @param stage   Specific stage
   4717  * @param storage Storage used by block
   4718  * @param prefix  Prefix used in block name
   4719  *
   4720  * @return New interface
   4721  **/
   4722 Interface* ProgramInterface::CloneBlockForStage(const Interface& block, Shader::STAGES stage, Variable::STORAGE storage,
   4723 												const GLchar* prefix)
   4724 {
   4725 	/* Get name */
   4726 	std::string name = block.m_name;
   4727 
   4728 	/* Prefix name with stage ID */
   4729 	size_t		  position	 = 0;
   4730 	const GLchar* stage_prefix = GetStagePrefix(stage, storage);
   4731 	Utils::replaceToken(prefix, position, stage_prefix, name);
   4732 
   4733 	Interface* ptr = GetBlock(name.c_str());
   4734 
   4735 	if (0 == ptr)
   4736 	{
   4737 		ptr = AddInterface(name.c_str(), Interface::BLOCK);
   4738 	}
   4739 
   4740 	ptr->m_members = block.m_members;
   4741 
   4742 	return ptr;
   4743 }
   4744 
   4745 /** Get stage specific prefix used in names
   4746  *
   4747  * @param stage   Stage
   4748  * @param storage Storage class
   4749  *
   4750  * @return String
   4751  **/
   4752 const GLchar* ProgramInterface::GetStagePrefix(Shader::STAGES stage, Variable::STORAGE storage)
   4753 {
   4754 	static const GLchar* lut[Shader::STAGE_MAX][Variable::STORAGE_MAX] = {
   4755 		/*          IN          OUT         UNIFORM     SSB        MEMBER	*/
   4756 		/* CS  */ { 0, 0, "cs_uni_", "cs_buf_", "" },
   4757 		/* VS  */ { "in_vs_", "vs_tcs_", "vs_uni_", "vs_buf_", "" },
   4758 		/* TCS */ { "vs_tcs_", "tcs_tes_", "tcs_uni_", "tcs_buf_", "" },
   4759 		/* TES */ { "tcs_tes_", "tes_gs_", "tes_uni_", "tes_buf_", "" },
   4760 		/* GS  */ { "tes_gs_", "gs_fs_", "gs_uni_", "gs_buf_", "" },
   4761 		/* FS  */ { "gs_fs_", "fs_out_", "fs_uni_", "fs_buf_", "" },
   4762 	};
   4763 
   4764 	const GLchar* result = 0;
   4765 
   4766 	result = lut[stage][storage];
   4767 
   4768 	return result;
   4769 }
   4770 
   4771 /** Get definitions of all structures used in program interface
   4772  *
   4773  * @return String with code
   4774  **/
   4775 std::string ProgramInterface::GetDefinitionsStructures() const
   4776 {
   4777 	return GetDefinitions(m_structures);
   4778 }
   4779 
   4780 /** Get interface code for stage
   4781  *
   4782  * @param stage Specific stage
   4783  *
   4784  * @return String with code
   4785  **/
   4786 std::string ProgramInterface::GetInterfaceForStage(Shader::STAGES stage) const
   4787 {
   4788 	size_t		position  = 0;
   4789 	std::string interface = "/* Globals */\n"
   4790 							"GLOBALS\n"
   4791 							"\n"
   4792 							"/* Structures */\n"
   4793 							"STRUCTURES\n"
   4794 							"\n"
   4795 							"/* Uniforms */\n"
   4796 							"UNIFORMS\n"
   4797 							"\n"
   4798 							"/* Inputs */\n"
   4799 							"INPUTS\n"
   4800 							"\n"
   4801 							"/* Outputs */\n"
   4802 							"OUTPUTS\n"
   4803 							"\n"
   4804 							"/* Storage */\n"
   4805 							"STORAGE\n";
   4806 
   4807 	const ShaderInterface& si = GetShaderInterface(stage);
   4808 
   4809 	const std::string& structures = GetDefinitionsStructures();
   4810 
   4811 	const std::string& globals  = si.GetDefinitionsGlobals();
   4812 	const std::string& inputs   = si.GetDefinitionsInputs();
   4813 	const std::string& outputs  = si.GetDefinitionsOutputs();
   4814 	const std::string& uniforms = si.GetDefinitionsUniforms();
   4815 	const std::string& ssbs		= si.GetDefinitionsSSBs();
   4816 
   4817 	replaceToken("GLOBALS", position, globals.c_str(), interface);
   4818 	replaceToken("STRUCTURES", position, structures.c_str(), interface);
   4819 	replaceToken("UNIFORMS", position, uniforms.c_str(), interface);
   4820 	replaceToken("INPUTS", position, inputs.c_str(), interface);
   4821 	replaceToken("OUTPUTS", position, outputs.c_str(), interface);
   4822 	replaceToken("STORAGE", position, ssbs.c_str(), interface);
   4823 
   4824 	return interface;
   4825 }
   4826 
   4827 /** Functional object used in find_if algorithm, in search for interface of given name
   4828  *
   4829  **/
   4830 struct matchInterfaceName
   4831 {
   4832 	matchInterfaceName(const GLchar* name) : m_name(name)
   4833 	{
   4834 	}
   4835 
   4836 	bool operator()(const Interface* interface)
   4837 	{
   4838 		return 0 == interface->m_name.compare(m_name);
   4839 	}
   4840 
   4841 	const GLchar* m_name;
   4842 };
   4843 
   4844 /** Finds interface of given name in given vector of interfaces
   4845  *
   4846  * @param vector Collection of interfaces
   4847  * @param name   Requested name
   4848  *
   4849  * @return Pointer to interface if available, 0 otherwise
   4850  **/
   4851 static Interface* findInterfaceByName(Interface::PtrVector& vector, const GLchar* name)
   4852 {
   4853 	Interface::PtrVector::iterator it = std::find_if(vector.begin(), vector.end(), matchInterfaceName(name));
   4854 
   4855 	if (vector.end() != it)
   4856 	{
   4857 		return *it;
   4858 	}
   4859 	else
   4860 	{
   4861 		return 0;
   4862 	}
   4863 }
   4864 
   4865 /** Search for block of given name
   4866  *
   4867  * @param name Name of block
   4868  *
   4869  * @return Pointer to block or 0
   4870  **/
   4871 Interface* ProgramInterface::GetBlock(const GLchar* name)
   4872 {
   4873 	return findInterfaceByName(m_blocks, name);
   4874 }
   4875 
   4876 /** Search for structure of given name
   4877  *
   4878  * @param name Name of structure
   4879  *
   4880  * @return Pointer to structure or 0
   4881  **/
   4882 Interface* ProgramInterface::GetStructure(const GLchar* name)
   4883 {
   4884 	return findInterfaceByName(m_structures, name);
   4885 }
   4886 
   4887 /** Adds new sturcture to interface
   4888  *
   4889  * @param name Name of structure
   4890  *
   4891  * @return Created structure
   4892  **/
   4893 Interface* ProgramInterface::Structure(const GLchar* name)
   4894 {
   4895 	return AddInterface(name, Interface::STRUCT);
   4896 }
   4897 
   4898 /** Replace "BINDING" token in qualifiers string to value specific for given stage
   4899  *
   4900  * @param variable Variable to modify
   4901  * @param stage    Requested stage
   4902  **/
   4903 void ProgramInterface::replaceBinding(Variable& variable, Shader::STAGES stage)
   4904 {
   4905 	GLchar binding[16];
   4906 	sprintf(binding, "%d", stage);
   4907 	replaceAllTokens("BINDING", binding, variable.m_descriptor.m_qualifiers);
   4908 }
   4909 } /* Utils namespace */
   4910 
   4911 /** Debuging procedure. Logs parameters.
   4912  *
   4913  * @param source   As specified in GL spec.
   4914  * @param type     As specified in GL spec.
   4915  * @param id       As specified in GL spec.
   4916  * @param severity As specified in GL spec.
   4917  * @param ignored
   4918  * @param message  As specified in GL spec.
   4919  * @param info     Pointer to instance of Context used by test.
   4920  */
   4921 void GLW_APIENTRY debug_proc(GLenum source, GLenum type, GLuint id, GLenum severity, GLsizei /* length */,
   4922 							 const GLchar* message, void* info)
   4923 {
   4924 	deqp::Context* ctx = (deqp::Context*)info;
   4925 
   4926 	const GLchar* source_str   = "Unknown";
   4927 	const GLchar* type_str	 = "Unknown";
   4928 	const GLchar* severity_str = "Unknown";
   4929 
   4930 	switch (source)
   4931 	{
   4932 	case GL_DEBUG_SOURCE_API:
   4933 		source_str = "API";
   4934 		break;
   4935 	case GL_DEBUG_SOURCE_APPLICATION:
   4936 		source_str = "APP";
   4937 		break;
   4938 	case GL_DEBUG_SOURCE_OTHER:
   4939 		source_str = "OTR";
   4940 		break;
   4941 	case GL_DEBUG_SOURCE_SHADER_COMPILER:
   4942 		source_str = "COM";
   4943 		break;
   4944 	case GL_DEBUG_SOURCE_THIRD_PARTY:
   4945 		source_str = "3RD";
   4946 		break;
   4947 	case GL_DEBUG_SOURCE_WINDOW_SYSTEM:
   4948 		source_str = "WS";
   4949 		break;
   4950 	default:
   4951 		break;
   4952 	}
   4953 
   4954 	switch (type)
   4955 	{
   4956 	case GL_DEBUG_TYPE_DEPRECATED_BEHAVIOR:
   4957 		type_str = "DEPRECATED_BEHAVIOR";
   4958 		break;
   4959 	case GL_DEBUG_TYPE_ERROR:
   4960 		type_str = "ERROR";
   4961 		break;
   4962 	case GL_DEBUG_TYPE_MARKER:
   4963 		type_str = "MARKER";
   4964 		break;
   4965 	case GL_DEBUG_TYPE_OTHER:
   4966 		type_str = "OTHER";
   4967 		break;
   4968 	case GL_DEBUG_TYPE_PERFORMANCE:
   4969 		type_str = "PERFORMANCE";
   4970 		break;
   4971 	case GL_DEBUG_TYPE_POP_GROUP:
   4972 		type_str = "POP_GROUP";
   4973 		break;
   4974 	case GL_DEBUG_TYPE_PORTABILITY:
   4975 		type_str = "PORTABILITY";
   4976 		break;
   4977 	case GL_DEBUG_TYPE_PUSH_GROUP:
   4978 		type_str = "PUSH_GROUP";
   4979 		break;
   4980 	case GL_DEBUG_TYPE_UNDEFINED_BEHAVIOR:
   4981 		type_str = "UNDEFINED_BEHAVIOR";
   4982 		break;
   4983 	default:
   4984 		break;
   4985 	}
   4986 
   4987 	switch (severity)
   4988 	{
   4989 	case GL_DEBUG_SEVERITY_HIGH:
   4990 		severity_str = "H";
   4991 		break;
   4992 	case GL_DEBUG_SEVERITY_LOW:
   4993 		severity_str = "L";
   4994 		break;
   4995 	case GL_DEBUG_SEVERITY_MEDIUM:
   4996 		severity_str = "M";
   4997 		break;
   4998 	case GL_DEBUG_SEVERITY_NOTIFICATION:
   4999 		severity_str = "N";
   5000 		break;
   5001 	default:
   5002 		break;
   5003 	}
   5004 
   5005 	ctx->getTestContext().getLog() << tcu::TestLog::Message << "DEBUG_INFO: " << std::setw(3) << source_str << "|"
   5006 								   << severity_str << "|" << std::setw(18) << type_str << "|" << std::setw(12) << id
   5007 								   << ": " << message << tcu::TestLog::EndMessage;
   5008 }
   5009 
   5010 /** Constructor
   5011  *
   5012  * @param context          Test context
   5013  * @param test_name        Test name
   5014  * @param test_description Test description
   5015  **/
   5016 TestBase::TestBase(deqp::Context& context, const GLchar* test_name, const GLchar* test_description)
   5017 	: TestCase(context, test_name, test_description)
   5018 {
   5019 	/* Nothing to be done here */
   5020 }
   5021 
   5022 /** Execute test
   5023  *
   5024  * @return tcu::TestNode::STOP otherwise
   5025  **/
   5026 tcu::TestNode::IterateResult TestBase::iterate()
   5027 {
   5028 	bool test_result;
   5029 
   5030 #if DEBUG_ENBALE_MESSAGE_CALLBACK
   5031 	const Functions& gl = m_context.getRenderContext().getFunctions();
   5032 
   5033 	gl.debugMessageCallback(debug_proc, &m_context);
   5034 	GLU_EXPECT_NO_ERROR(gl.getError(), "DebugMessageCallback");
   5035 #endif /* DEBUG_ENBALE_MESSAGE_CALLBACK */
   5036 
   5037 	try
   5038 	{
   5039 		/* Execute test */
   5040 		test_result = test();
   5041 	}
   5042 	catch (std::exception& exc)
   5043 	{
   5044 		TCU_FAIL(exc.what());
   5045 	}
   5046 
   5047 	/* Set result */
   5048 	if (true == test_result)
   5049 	{
   5050 		m_context.getTestContext().setTestResult(QP_TEST_RESULT_PASS, "Pass");
   5051 	}
   5052 	else
   5053 	{
   5054 		m_context.getTestContext().setTestResult(QP_TEST_RESULT_FAIL, "Fail");
   5055 	}
   5056 
   5057 	/* Done */
   5058 	return tcu::TestNode::STOP;
   5059 }
   5060 
   5061 /** Get last input location available for given type at specific stage
   5062  *
   5063  * @param stage        Shader stage
   5064  * @param type         Input type
   5065  * @param array_length Length of input array
   5066  *
   5067  * @return Last location index
   5068  **/
   5069 GLint TestBase::getLastInputLocation(Utils::Shader::STAGES stage, const Utils::Type& type, GLuint array_length)
   5070 {
   5071 	GLint  divide = 4; /* 4 components per location */
   5072 	GLint  param  = 0;
   5073 	GLenum pname  = 0;
   5074 
   5075 	/* Select pnmae */
   5076 	switch (stage)
   5077 	{
   5078 	case Utils::Shader::FRAGMENT:
   5079 		pname = GL_MAX_FRAGMENT_INPUT_COMPONENTS;
   5080 		break;
   5081 	case Utils::Shader::GEOMETRY:
   5082 		pname = GL_MAX_GEOMETRY_INPUT_COMPONENTS;
   5083 		break;
   5084 	case Utils::Shader::TESS_CTRL:
   5085 		pname = GL_MAX_TESS_CONTROL_INPUT_COMPONENTS;
   5086 		break;
   5087 	case Utils::Shader::TESS_EVAL:
   5088 		pname = GL_MAX_TESS_EVALUATION_INPUT_COMPONENTS;
   5089 		break;
   5090 	case Utils::Shader::VERTEX:
   5091 		pname  = GL_MAX_VERTEX_ATTRIBS;
   5092 		divide = 1;
   5093 		break;
   5094 	default:
   5095 		TCU_FAIL("Invalid enum");
   5096 		break;
   5097 	}
   5098 
   5099 	/* Zero means no array, but 1 slot is required */
   5100 	if (0 == array_length)
   5101 	{
   5102 		array_length += 1;
   5103 	}
   5104 
   5105 	/* Get MAX */
   5106 	const Functions& gl = m_context.getRenderContext().getFunctions();
   5107 
   5108 	gl.getIntegerv(pname, &param);
   5109 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   5110 
   5111 /* Calculate */
   5112 #if WRKARD_VARYINGLOCATIONSTEST
   5113 
   5114 	const GLint n_avl_locations = 16;
   5115 
   5116 #else
   5117 
   5118 	const GLint n_avl_locations = param / divide;
   5119 
   5120 #endif
   5121 
   5122 	const GLuint n_req_location = type.GetLocations(stage == Utils::Shader::VERTEX) * array_length;
   5123 
   5124 	return n_avl_locations - n_req_location; /* last is max - 1 */
   5125 }
   5126 
   5127 /** Get last input location available for given type at specific stage
   5128  *
   5129  * @param stage        Shader stage
   5130  * @param type         Input type
   5131  * @param array_length Length of input array
   5132  *
   5133  * @return Last location index
   5134  **/
   5135 GLint TestBase::getLastOutputLocation(Utils::Shader::STAGES stage, const Utils::Type& type, GLuint array_length)
   5136 {
   5137 	GLint  param = 0;
   5138 	GLenum pname = 0;
   5139 
   5140 	/* Select pnmae */
   5141 	switch (stage)
   5142 	{
   5143 	case Utils::Shader::GEOMETRY:
   5144 		pname = GL_MAX_GEOMETRY_OUTPUT_COMPONENTS;
   5145 		break;
   5146 	case Utils::Shader::TESS_CTRL:
   5147 		pname = GL_MAX_TESS_CONTROL_OUTPUT_COMPONENTS;
   5148 		break;
   5149 	case Utils::Shader::TESS_EVAL:
   5150 		pname = GL_MAX_TESS_EVALUATION_OUTPUT_COMPONENTS;
   5151 		break;
   5152 	case Utils::Shader::VERTEX:
   5153 		pname = GL_MAX_VERTEX_OUTPUT_COMPONENTS;
   5154 		break;
   5155 	default:
   5156 		TCU_FAIL("Invalid enum");
   5157 		break;
   5158 	}
   5159 
   5160 	/* Zero means no array, but 1 slot is required */
   5161 	if (0 == array_length)
   5162 	{
   5163 		array_length += 1;
   5164 	}
   5165 
   5166 	/* Get MAX */
   5167 	const Functions& gl = m_context.getRenderContext().getFunctions();
   5168 
   5169 	gl.getIntegerv(pname, &param);
   5170 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   5171 
   5172 /* Calculate */
   5173 #if WRKARD_VARYINGLOCATIONSTEST
   5174 
   5175 	const GLint n_avl_locations = 16;
   5176 
   5177 #else
   5178 
   5179 	const GLint n_avl_locations = param / 4; /* 4 components per location */
   5180 
   5181 #endif
   5182 
   5183 	const GLuint n_req_location = type.GetLocations() * array_length;
   5184 
   5185 	return n_avl_locations - n_req_location; /* last is max - 1 */
   5186 }
   5187 
   5188 /** Basic implementation
   5189  *
   5190  * @param ignored
   5191  *
   5192  * @return Empty string
   5193  **/
   5194 std::string TestBase::getTestCaseName(GLuint /* test_case_index */)
   5195 {
   5196 	std::string result;
   5197 
   5198 	return result;
   5199 }
   5200 
   5201 /** Basic implementation
   5202  *
   5203  * @return 1
   5204  **/
   5205 GLuint TestBase::getTestCaseNumber()
   5206 {
   5207 	return 1;
   5208 }
   5209 
   5210 /** Check if flat qualifier is required for given type, stage and storage
   5211  *
   5212  * @param stage        Shader stage
   5213  * @param type         Input type
   5214  * @param storage      Storage of variable
   5215  *
   5216  * @return Last location index
   5217  **/
   5218 bool TestBase::isFlatRequired(Utils::Shader::STAGES stage, const Utils::Type& type,
   5219 							  Utils::Variable::STORAGE storage) const
   5220 {
   5221 	/* Float types do not need flat at all */
   5222 	if (Utils::Type::Float == type.m_basic_type)
   5223 	{
   5224 		return false;
   5225 	}
   5226 
   5227 	/* Inputs to fragment shader */
   5228 	if ((Utils::Shader::FRAGMENT == stage) && (Utils::Variable::VARYING_INPUT == storage))
   5229 	{
   5230 		return true;
   5231 	}
   5232 
   5233 	/* Outputs from geometry shader */
   5234 	if ((Utils::Shader::FRAGMENT == stage) && (Utils::Variable::VARYING_OUTPUT == storage))
   5235 	{
   5236 		return true;
   5237 	}
   5238 
   5239 	return false;
   5240 }
   5241 
   5242 /** Basic implementation of testInit method
   5243  *
   5244  **/
   5245 void TestBase::testInit()
   5246 {
   5247 }
   5248 
   5249 /** Calculate stride for interface
   5250  *
   5251  * @param interface Interface
   5252  *
   5253  * @return Calculated value
   5254  **/
   5255 GLuint TestBase::calculateStride(const Utils::Interface& interface) const
   5256 {
   5257 	const size_t n_members = interface.m_members.size();
   5258 
   5259 	GLuint stride = 0;
   5260 
   5261 	for (size_t i = 0; i < n_members; ++i)
   5262 	{
   5263 		const Utils::Variable::Descriptor& member		  = interface.m_members[i];
   5264 		const GLuint					   member_offset  = member.m_offset;
   5265 		const GLuint					   member_stride  = member.m_expected_stride_of_element;
   5266 		const GLuint					   member_ends_at = member_offset + member_stride;
   5267 
   5268 		stride = std::max(stride, member_ends_at);
   5269 	}
   5270 
   5271 	return stride;
   5272 }
   5273 
   5274 /** Generate data for interface. This routine is recursive
   5275  *
   5276  * @param interface Interface
   5277  * @param offset    Offset in out_data
   5278  * @param out_data  Buffer to be filled
   5279  **/
   5280 void TestBase::generateData(const Utils::Interface& interface, GLuint offset, std::vector<GLubyte>& out_data) const
   5281 {
   5282 	const size_t n_members = interface.m_members.size();
   5283 	GLubyte*	 ptr	   = &out_data[offset];
   5284 
   5285 	for (size_t i = 0; i < n_members; ++i)
   5286 	{
   5287 		const Utils::Variable::Descriptor& member		 = interface.m_members[i];
   5288 		const GLuint					   member_offset = member.m_offset;
   5289 		const GLuint n_elements = (0 == member.m_n_array_elements) ? 1 : member.m_n_array_elements;
   5290 
   5291 		for (GLuint element = 0; element < n_elements; ++element)
   5292 		{
   5293 			const GLuint element_offset = element * member.m_expected_stride_of_element;
   5294 			const GLuint data_offfset   = member_offset + element_offset;
   5295 
   5296 			if (Utils::Variable::BUILTIN == member.m_type)
   5297 			{
   5298 				const std::vector<GLubyte>& data = member.m_builtin.GenerateData();
   5299 
   5300 				memcpy(ptr + data_offfset, &data[0], data.size());
   5301 			}
   5302 			else
   5303 			{
   5304 				generateData(*member.m_interface, offset + data_offfset, out_data);
   5305 			}
   5306 		}
   5307 	}
   5308 }
   5309 
   5310 /** Get type at index
   5311  *
   5312  * @param index Index of requested type
   5313  *
   5314  * @return Type
   5315  **/
   5316 Utils::Type TestBase::getType(GLuint index) const
   5317 {
   5318 	Utils::Type type;
   5319 
   5320 	switch (index)
   5321 	{
   5322 	case 0:
   5323 		type = Utils::Type::_double;
   5324 		break;
   5325 	case 1:
   5326 		type = Utils::Type::dmat2;
   5327 		break;
   5328 	case 2:
   5329 		type = Utils::Type::dmat2x3;
   5330 		break;
   5331 	case 3:
   5332 		type = Utils::Type::dmat2x4;
   5333 		break;
   5334 	case 4:
   5335 		type = Utils::Type::dmat3;
   5336 		break;
   5337 	case 5:
   5338 		type = Utils::Type::dmat3x2;
   5339 		break;
   5340 	case 6:
   5341 		type = Utils::Type::dmat3x4;
   5342 		break;
   5343 	case 7:
   5344 		type = Utils::Type::dmat4;
   5345 		break;
   5346 	case 8:
   5347 		type = Utils::Type::dmat4x2;
   5348 		break;
   5349 	case 9:
   5350 		type = Utils::Type::dmat4x3;
   5351 		break;
   5352 	case 10:
   5353 		type = Utils::Type::dvec2;
   5354 		break;
   5355 	case 11:
   5356 		type = Utils::Type::dvec3;
   5357 		break;
   5358 	case 12:
   5359 		type = Utils::Type::dvec4;
   5360 		break;
   5361 	case 13:
   5362 		type = Utils::Type::_float;
   5363 		break;
   5364 	case 14:
   5365 		type = Utils::Type::mat2;
   5366 		break;
   5367 	case 15:
   5368 		type = Utils::Type::mat2x3;
   5369 		break;
   5370 	case 16:
   5371 		type = Utils::Type::mat2x4;
   5372 		break;
   5373 	case 17:
   5374 		type = Utils::Type::mat3;
   5375 		break;
   5376 	case 18:
   5377 		type = Utils::Type::mat3x2;
   5378 		break;
   5379 	case 19:
   5380 		type = Utils::Type::mat3x4;
   5381 		break;
   5382 	case 20:
   5383 		type = Utils::Type::mat4;
   5384 		break;
   5385 	case 21:
   5386 		type = Utils::Type::mat4x2;
   5387 		break;
   5388 	case 22:
   5389 		type = Utils::Type::mat4x3;
   5390 		break;
   5391 	case 23:
   5392 		type = Utils::Type::vec2;
   5393 		break;
   5394 	case 24:
   5395 		type = Utils::Type::vec3;
   5396 		break;
   5397 	case 25:
   5398 		type = Utils::Type::vec4;
   5399 		break;
   5400 	case 26:
   5401 		type = Utils::Type::_int;
   5402 		break;
   5403 	case 27:
   5404 		type = Utils::Type::ivec2;
   5405 		break;
   5406 	case 28:
   5407 		type = Utils::Type::ivec3;
   5408 		break;
   5409 	case 29:
   5410 		type = Utils::Type::ivec4;
   5411 		break;
   5412 	case 30:
   5413 		type = Utils::Type::uint;
   5414 		break;
   5415 	case 31:
   5416 		type = Utils::Type::uvec2;
   5417 		break;
   5418 	case 32:
   5419 		type = Utils::Type::uvec3;
   5420 		break;
   5421 	case 33:
   5422 		type = Utils::Type::uvec4;
   5423 		break;
   5424 	default:
   5425 		TCU_FAIL("invalid enum");
   5426 	}
   5427 
   5428 	return type;
   5429 }
   5430 
   5431 /** Get name of type at index
   5432  *
   5433  * @param index Index of type
   5434  *
   5435  * @return Name
   5436  **/
   5437 std::string TestBase::getTypeName(GLuint index) const
   5438 {
   5439 	std::string name = getType(index).GetGLSLTypeName();
   5440 
   5441 	return name;
   5442 }
   5443 
   5444 /** Get number of types
   5445  *
   5446  * @return 34
   5447  **/
   5448 glw::GLuint TestBase::getTypesNumber() const
   5449 {
   5450 	return 34;
   5451 }
   5452 
   5453 /** Execute test
   5454  *
   5455  * @return true if test pass, false otherwise
   5456  **/
   5457 bool TestBase::test()
   5458 {
   5459 	bool   result		= true;
   5460 	GLuint n_test_cases = 0;
   5461 
   5462 	/* Prepare test */
   5463 	testInit();
   5464 
   5465 	/* GL entry points */
   5466 	const Functions& gl = m_context.getRenderContext().getFunctions();
   5467 
   5468 	/* Tessellation patch set up */
   5469 	gl.patchParameteri(GL_PATCH_VERTICES, 1);
   5470 	GLU_EXPECT_NO_ERROR(gl.getError(), "PatchParameteri");
   5471 
   5472 	/* Get number of test cases */
   5473 	n_test_cases = getTestCaseNumber();
   5474 
   5475 #if DEBUG_REPEAT_TEST_CASE
   5476 
   5477 	while (1)
   5478 	{
   5479 		GLuint test_case = DEBUG_REPEATED_TEST_CASE;
   5480 
   5481 #else /* DEBUG_REPEAT_TEST_CASE */
   5482 
   5483 	for (GLuint test_case = 0; test_case < n_test_cases; ++test_case)
   5484 	{
   5485 
   5486 #endif /* DEBUG_REPEAT_TEST_CASE */
   5487 
   5488 		bool case_result = true;
   5489 
   5490 		/* Execute case */
   5491 		if (false == testCase(test_case))
   5492 		{
   5493 			case_result = false;
   5494 		}
   5495 
   5496 		/* Log failure */
   5497 		if (false == case_result)
   5498 		{
   5499 			const std::string& test_case_name = getTestCaseName(test_case);
   5500 
   5501 			if (false == test_case_name.empty())
   5502 			{
   5503 				m_context.getTestContext().getLog() << tcu::TestLog::Message << "Test case (" << test_case_name
   5504 													<< ") failed." << tcu::TestLog::EndMessage;
   5505 			}
   5506 			else
   5507 			{
   5508 				m_context.getTestContext().getLog() << tcu::TestLog::Message << "Test case (" << test_case
   5509 													<< ") failed." << tcu::TestLog::EndMessage;
   5510 			}
   5511 
   5512 			result = false;
   5513 		}
   5514 	}
   5515 
   5516 	/* Done */
   5517 	return result;
   5518 }
   5519 
   5520 /* Constants used by BufferTestBase */
   5521 const GLuint BufferTestBase::bufferDescriptor::m_non_indexed = -1;
   5522 
   5523 /** Constructor
   5524  *
   5525  * @param context          Test context
   5526  * @param test_name        Name of test
   5527  * @param test_description Description of test
   5528  **/
   5529 BufferTestBase::BufferTestBase(deqp::Context& context, const GLchar* test_name, const GLchar* test_description)
   5530 	: TestBase(context, test_name, test_description)
   5531 {
   5532 }
   5533 
   5534 /** Execute drawArrays for single vertex
   5535  *
   5536  * @param ignored
   5537  *
   5538  * @return true
   5539  **/
   5540 bool BufferTestBase::executeDrawCall(bool tesEnabled, GLuint /* test_case_index */)
   5541 {
   5542 	const Functions& gl = m_context.getRenderContext().getFunctions();
   5543 
   5544 	gl.disable(GL_RASTERIZER_DISCARD);
   5545 	GLU_EXPECT_NO_ERROR(gl.getError(), "Disable");
   5546 
   5547 	gl.beginTransformFeedback(GL_POINTS);
   5548 	GLU_EXPECT_NO_ERROR(gl.getError(), "BeginTransformFeedback");
   5549 
   5550 	// Only TES is existed, glDrawArray can use the parameter GL_PATCHES
   5551 	if (tesEnabled == false)
   5552 	{
   5553 		gl.drawArrays(GL_POINTS, 0 /* first */, 1 /* count */);
   5554 	}
   5555 	else
   5556 	{
   5557 		gl.drawArrays(GL_PATCHES, 0 /* first */, 1 /* count */);
   5558 	}
   5559 
   5560 	GLU_EXPECT_NO_ERROR(gl.getError(), "DrawArrays");
   5561 
   5562 	gl.endTransformFeedback();
   5563 	GLU_EXPECT_NO_ERROR(gl.getError(), "EndTransformFeedback");
   5564 
   5565 	return true;
   5566 }
   5567 
   5568 /** Get descriptors of buffers necessary for test
   5569  *
   5570  * @param ignored
   5571  * @param ignored
   5572  **/
   5573 void BufferTestBase::getBufferDescriptors(glw::GLuint /* test_case_index */,
   5574 										  bufferDescriptor::Vector& /* out_descriptors */)
   5575 {
   5576 	/* Nothhing to be done */
   5577 }
   5578 
   5579 /** Get list of names of varyings that will be registered with TransformFeedbackVaryings
   5580  *
   5581  * @param ignored
   5582  * @param ignored
   5583  **/
   5584 void BufferTestBase::getCapturedVaryings(glw::GLuint /* test_case_index */,
   5585 										 Utils::Program::NameVector& /* captured_varyings */)
   5586 {
   5587 	/* Nothing to be done */
   5588 }
   5589 
   5590 /** Get body of main function for given shader stage
   5591  *
   5592  * @param ignored
   5593  * @param ignored
   5594  * @param out_assignments  Set to empty
   5595  * @param out_calculations Set to empty
   5596  **/
   5597 void BufferTestBase::getShaderBody(glw::GLuint /* test_case_index */, Utils::Shader::STAGES /* stage */,
   5598 								   std::string& out_assignments, std::string& out_calculations)
   5599 {
   5600 	out_assignments  = "";
   5601 	out_calculations = "";
   5602 }
   5603 
   5604 /** Get interface of shader
   5605  *
   5606  * @param ignored
   5607  * @param ignored
   5608  * @param out_interface Set to ""
   5609  **/
   5610 void BufferTestBase::getShaderInterface(glw::GLuint /* test_case_index */, Utils::Shader::STAGES /* stage */,
   5611 										std::string& out_interface)
   5612 {
   5613 	out_interface = "";
   5614 }
   5615 
   5616 /** Get source code of shader
   5617  *
   5618  * @param test_case_index Index of test case
   5619  * @param stage           Shader stage
   5620  *
   5621  * @return Source
   5622  **/
   5623 std::string BufferTestBase::getShaderSource(glw::GLuint test_case_index, Utils::Shader::STAGES stage)
   5624 {
   5625 	std::string assignments;
   5626 	std::string calculations;
   5627 	std::string interface;
   5628 
   5629 	/* */
   5630 	getShaderBody(test_case_index, stage, assignments, calculations);
   5631 	getShaderInterface(test_case_index, stage, interface);
   5632 
   5633 	/* */
   5634 	std::string source = getShaderTemplate(stage);
   5635 
   5636 	/* */
   5637 	size_t position = 0;
   5638 	Utils::replaceToken("INTERFACE", position, interface.c_str(), source);
   5639 	Utils::replaceToken("CALCULATIONS", position, calculations.c_str(), source);
   5640 	Utils::replaceToken("ASSIGNMENTS", position, assignments.c_str(), source);
   5641 
   5642 	/* */
   5643 	return source;
   5644 }
   5645 
   5646 /** Inspects program to check if all resources are as expected
   5647  *
   5648  * @param ignored
   5649  * @param ignored
   5650  * @param ignored
   5651  *
   5652  * @return true
   5653  **/
   5654 bool BufferTestBase::inspectProgram(GLuint /* test_case_index */, Utils::Program& /* program */,
   5655 									std::stringstream& /* out_stream */)
   5656 {
   5657 	return true;
   5658 }
   5659 
   5660 /** Runs test case
   5661  *
   5662  * @param test_case_index Id of test case
   5663  *
   5664  * @return true if test case pass, false otherwise
   5665  **/
   5666 bool BufferTestBase::testCase(GLuint test_case_index)
   5667 {
   5668 	try
   5669 	{
   5670 		bufferCollection		   buffers;
   5671 		Utils::Program::NameVector captured_varyings;
   5672 		bufferDescriptor::Vector   descriptors;
   5673 		Utils::Program			   program(m_context);
   5674 		Utils::VertexArray		   vao(m_context);
   5675 
   5676 		/* Get captured varyings */
   5677 		getCapturedVaryings(test_case_index, captured_varyings);
   5678 
   5679 		/* Get shader sources */
   5680 		const std::string& fragment_shader  = getShaderSource(test_case_index, Utils::Shader::FRAGMENT);
   5681 		const std::string& geometry_shader  = getShaderSource(test_case_index, Utils::Shader::GEOMETRY);
   5682 		const std::string& tess_ctrl_shader = getShaderSource(test_case_index, Utils::Shader::TESS_CTRL);
   5683 		const std::string& tess_eval_shader = getShaderSource(test_case_index, Utils::Shader::TESS_EVAL);
   5684 		const std::string& vertex_shader	= getShaderSource(test_case_index, Utils::Shader::VERTEX);
   5685 
   5686 		/* Set up program */
   5687 		program.Init("" /* compute_shader */, fragment_shader, geometry_shader, tess_ctrl_shader, tess_eval_shader,
   5688 					 vertex_shader, captured_varyings, true, false /* is_separable */);
   5689 
   5690 		/* Inspection */
   5691 		{
   5692 			std::stringstream stream;
   5693 			if (false == inspectProgram(test_case_index, program, stream))
   5694 			{
   5695 				m_context.getTestContext().getLog()
   5696 					<< tcu::TestLog::Message
   5697 					<< "Program inspection failed. Test case: " << getTestCaseName(test_case_index)
   5698 					<< ". Reason: " << stream.str() << tcu::TestLog::EndMessage
   5699 					<< tcu::TestLog::KernelSource(vertex_shader) << tcu::TestLog::KernelSource(tess_ctrl_shader)
   5700 					<< tcu::TestLog::KernelSource(tess_eval_shader) << tcu::TestLog::KernelSource(geometry_shader)
   5701 					<< tcu::TestLog::KernelSource(fragment_shader);
   5702 
   5703 				return false;
   5704 			}
   5705 		}
   5706 
   5707 		program.Use();
   5708 
   5709 		/* Set up buffers */
   5710 		getBufferDescriptors(test_case_index, descriptors);
   5711 		cleanBuffers();
   5712 		prepareBuffers(descriptors, buffers);
   5713 
   5714 		/* Set up vao */
   5715 		vao.Init();
   5716 		vao.Bind();
   5717 
   5718 		/* Draw */
   5719 		bool result = executeDrawCall((program.m_tess_eval.m_id != 0), test_case_index);
   5720 
   5721 #if USE_NSIGHT
   5722 		m_context.getRenderContext().postIterate();
   5723 #endif
   5724 
   5725 		if (false == result)
   5726 		{
   5727 			m_context.getTestContext().getLog()
   5728 				<< tcu::TestLog::KernelSource(vertex_shader) << tcu::TestLog::KernelSource(tess_ctrl_shader)
   5729 				<< tcu::TestLog::KernelSource(tess_eval_shader) << tcu::TestLog::KernelSource(geometry_shader)
   5730 				<< tcu::TestLog::KernelSource(fragment_shader);
   5731 
   5732 			return false;
   5733 		}
   5734 
   5735 		/* Verify result */
   5736 		if (false == verifyBuffers(buffers))
   5737 		{
   5738 			m_context.getTestContext().getLog()
   5739 				<< tcu::TestLog::KernelSource(vertex_shader) << tcu::TestLog::KernelSource(tess_ctrl_shader)
   5740 				<< tcu::TestLog::KernelSource(tess_eval_shader) << tcu::TestLog::KernelSource(geometry_shader)
   5741 				<< tcu::TestLog::KernelSource(fragment_shader);
   5742 
   5743 			return false;
   5744 		}
   5745 	}
   5746 	catch (Utils::Shader::InvalidSourceException& exc)
   5747 	{
   5748 		exc.log(m_context);
   5749 		TCU_FAIL(exc.what());
   5750 	}
   5751 	catch (Utils::Program::BuildException& exc)
   5752 	{
   5753 		exc.log(m_context);
   5754 		TCU_FAIL(exc.what());
   5755 	}
   5756 
   5757 	/* Done */
   5758 	return true;
   5759 }
   5760 
   5761 /** Verify contents of buffers
   5762  *
   5763  * @param buffers Collection of buffers to be verified
   5764  *
   5765  * @return true if everything is as expected, false otherwise
   5766  **/
   5767 bool BufferTestBase::verifyBuffers(bufferCollection& buffers)
   5768 {
   5769 	bool result = true;
   5770 
   5771 	for (bufferCollection::Vector::iterator it = buffers.m_vector.begin(), end = buffers.m_vector.end(); end != it;
   5772 		 ++it)
   5773 	{
   5774 		bufferCollection::pair& pair	   = *it;
   5775 		Utils::Buffer*			buffer	 = pair.m_buffer;
   5776 		bufferDescriptor*		descriptor = pair.m_descriptor;
   5777 		size_t					size	   = descriptor->m_expected_data.size();
   5778 
   5779 		/* Skip buffers that have no expected data */
   5780 		if (0 == size)
   5781 		{
   5782 			continue;
   5783 		}
   5784 
   5785 		/* Get pointer to contents of buffer */
   5786 		buffer->Bind();
   5787 		GLvoid* buffer_data = buffer->Map(Utils::Buffer::ReadOnly);
   5788 
   5789 		/* Get pointer to expected data */
   5790 		GLvoid* expected_data = &descriptor->m_expected_data[0];
   5791 
   5792 		/* Compare */
   5793 		int res = memcmp(buffer_data, expected_data, size);
   5794 
   5795 		if (0 != res)
   5796 		{
   5797 			m_context.getTestContext().getLog()
   5798 				<< tcu::TestLog::Message
   5799 				<< "Invalid result. Buffer: " << Utils::Buffer::GetBufferName(descriptor->m_target)
   5800 				<< ". Index: " << descriptor->m_index << tcu::TestLog::EndMessage;
   5801 
   5802 			result = false;
   5803 		}
   5804 
   5805 		/* Release buffer mapping */
   5806 		buffer->UnMap();
   5807 	}
   5808 
   5809 	return result;
   5810 }
   5811 
   5812 /** Unbinds all uniforms and xfb
   5813  *
   5814  **/
   5815 void BufferTestBase::cleanBuffers()
   5816 {
   5817 	const Functions& gl = m_context.getRenderContext().getFunctions();
   5818 
   5819 	GLint max_uni = 0;
   5820 	GLint max_xfb = 0;
   5821 
   5822 	gl.getIntegerv(GL_MAX_UNIFORM_BUFFER_BINDINGS, &max_uni);
   5823 	gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_BUFFERS, &max_xfb);
   5824 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   5825 
   5826 	for (GLint i = 0; i < max_uni; ++i)
   5827 	{
   5828 		Utils::Buffer::BindBase(gl, 0, Utils::Buffer::Uniform, i);
   5829 	}
   5830 
   5831 	for (GLint i = 0; i < max_xfb; ++i)
   5832 	{
   5833 		Utils::Buffer::BindBase(gl, 0, Utils::Buffer::Transform_feedback, i);
   5834 	}
   5835 }
   5836 
   5837 /** Get template of shader for given stage
   5838  *
   5839  * @param stage Stage
   5840  *
   5841  * @return Template of shader source
   5842  **/
   5843 std::string BufferTestBase::getShaderTemplate(Utils::Shader::STAGES stage)
   5844 {
   5845 	static const GLchar* compute_shader_template = "#version 430 core\n"
   5846 												   "#extension GL_ARB_enhanced_layouts : require\n"
   5847 												   "\n"
   5848 												   "layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
   5849 												   "\n"
   5850 												   "writeonly uniform uimage2D uni_image;\n"
   5851 												   "\n"
   5852 												   "INTERFACE"
   5853 												   "\n"
   5854 												   "void main()\n"
   5855 												   "{\n"
   5856 												   "CALCULATIONS"
   5857 												   "\n"
   5858 												   "ASSIGNMENTS"
   5859 												   "}\n"
   5860 												   "\n";
   5861 
   5862 	static const GLchar* fragment_shader_template = "#version 430 core\n"
   5863 													"#extension GL_ARB_enhanced_layouts : require\n"
   5864 													"\n"
   5865 													"INTERFACE"
   5866 													"\n"
   5867 													"void main()\n"
   5868 													"{\n"
   5869 													"CALCULATIONS"
   5870 													"\n"
   5871 													"ASSIGNMENTS"
   5872 													"}\n"
   5873 													"\n";
   5874 
   5875 	// max_vertices is set to 3 for the test case "xfb_vertex_streams" declares 3 streams in geometry shader,
   5876 	// according to spec, max_vertices should be no less than 3 if there are 3 streams in GS.
   5877 	static const GLchar* geometry_shader_template = "#version 430 core\n"
   5878 													"#extension GL_ARB_enhanced_layouts : require\n"
   5879 													"\n"
   5880 													"layout(points)                   in;\n"
   5881 													"layout(points, max_vertices = 3) out;\n"
   5882 													"\n"
   5883 													"INTERFACE"
   5884 													"\n"
   5885 													"void main()\n"
   5886 													"{\n"
   5887 													"CALCULATIONS"
   5888 													"\n"
   5889 													"\n"
   5890 													"ASSIGNMENTS"
   5891 													"    gl_Position  = vec4(0, 0, 0, 1);\n"
   5892 													"    EmitVertex();\n"
   5893 													"}\n"
   5894 													"\n";
   5895 
   5896 	static const GLchar* tess_ctrl_shader_template = "#version 430 core\n"
   5897 													 "#extension GL_ARB_enhanced_layouts : require\n"
   5898 													 "\n"
   5899 													 "layout(vertices = 1) out;\n"
   5900 													 "\n"
   5901 													 "INTERFACE"
   5902 													 "\n"
   5903 													 "void main()\n"
   5904 													 "{\n"
   5905 													 "CALCULATIONS"
   5906 													 "\n"
   5907 													 "ASSIGNMENTS"
   5908 													 "\n"
   5909 													 "    gl_TessLevelOuter[0] = 1.0;\n"
   5910 													 "    gl_TessLevelOuter[1] = 1.0;\n"
   5911 													 "    gl_TessLevelOuter[2] = 1.0;\n"
   5912 													 "    gl_TessLevelOuter[3] = 1.0;\n"
   5913 													 "    gl_TessLevelInner[0] = 1.0;\n"
   5914 													 "    gl_TessLevelInner[1] = 1.0;\n"
   5915 													 "}\n"
   5916 													 "\n";
   5917 
   5918 	static const GLchar* tess_eval_shader_template = "#version 430 core\n"
   5919 													 "#extension GL_ARB_enhanced_layouts : require\n"
   5920 													 "\n"
   5921 													 "layout(isolines, point_mode) in;\n"
   5922 													 "\n"
   5923 													 "INTERFACE"
   5924 													 "\n"
   5925 													 "void main()\n"
   5926 													 "{\n"
   5927 													 "CALCULATIONS"
   5928 													 "\n"
   5929 													 "ASSIGNMENTS"
   5930 													 "}\n"
   5931 													 "\n";
   5932 
   5933 	static const GLchar* vertex_shader_template = "#version 430 core\n"
   5934 												  "#extension GL_ARB_enhanced_layouts : require\n"
   5935 												  "\n"
   5936 												  "INTERFACE"
   5937 												  "\n"
   5938 												  "void main()\n"
   5939 												  "{\n"
   5940 												  "CALCULATIONS"
   5941 												  "\n"
   5942 												  "ASSIGNMENTS"
   5943 												  "}\n"
   5944 												  "\n";
   5945 
   5946 	const GLchar* result = 0;
   5947 
   5948 	switch (stage)
   5949 	{
   5950 	case Utils::Shader::COMPUTE:
   5951 		result = compute_shader_template;
   5952 		break;
   5953 	case Utils::Shader::FRAGMENT:
   5954 		result = fragment_shader_template;
   5955 		break;
   5956 	case Utils::Shader::GEOMETRY:
   5957 		result = geometry_shader_template;
   5958 		break;
   5959 	case Utils::Shader::TESS_CTRL:
   5960 		result = tess_ctrl_shader_template;
   5961 		break;
   5962 	case Utils::Shader::TESS_EVAL:
   5963 		result = tess_eval_shader_template;
   5964 		break;
   5965 	case Utils::Shader::VERTEX:
   5966 		result = vertex_shader_template;
   5967 		break;
   5968 	default:
   5969 		TCU_FAIL("Invalid enum");
   5970 	}
   5971 
   5972 	return result;
   5973 }
   5974 
   5975 /** Prepare buffer according to descriptor
   5976  *
   5977  * @param buffer Buffer to prepare
   5978  * @param desc   Descriptor
   5979  **/
   5980 void BufferTestBase::prepareBuffer(Utils::Buffer& buffer, bufferDescriptor& desc)
   5981 {
   5982 	GLsizeiptr size = 0;
   5983 	GLvoid*	data = 0;
   5984 
   5985 	if (false == desc.m_initial_data.empty())
   5986 	{
   5987 		size = desc.m_initial_data.size();
   5988 		data = &desc.m_initial_data[0];
   5989 	}
   5990 	else if (false == desc.m_expected_data.empty())
   5991 	{
   5992 		size = desc.m_expected_data.size();
   5993 	}
   5994 
   5995 	buffer.Init(desc.m_target, Utils::Buffer::StaticDraw, size, data);
   5996 
   5997 	if (bufferDescriptor::m_non_indexed != desc.m_index)
   5998 	{
   5999 		buffer.BindBase(desc.m_index);
   6000 	}
   6001 	else
   6002 	{
   6003 		buffer.Bind();
   6004 	}
   6005 }
   6006 
   6007 /** Prepare collection of buffer
   6008  *
   6009  * @param descriptors Collection of descriptors
   6010  * @param out_buffers Collection of buffers
   6011  **/
   6012 void BufferTestBase::prepareBuffers(bufferDescriptor::Vector& descriptors, bufferCollection& out_buffers)
   6013 {
   6014 	for (bufferDescriptor::Vector::iterator it = descriptors.begin(), end = descriptors.end(); end != it; ++it)
   6015 	{
   6016 		bufferCollection::pair pair;
   6017 
   6018 		pair.m_buffer = new Utils::Buffer(m_context);
   6019 		if (0 == pair.m_buffer)
   6020 		{
   6021 			TCU_FAIL("Memory allocation failed");
   6022 		}
   6023 
   6024 		pair.m_descriptor = &(*it);
   6025 
   6026 		prepareBuffer(*pair.m_buffer, *pair.m_descriptor);
   6027 
   6028 		out_buffers.m_vector.push_back(pair);
   6029 	}
   6030 }
   6031 
   6032 /** Destructor
   6033  *
   6034  **/
   6035 BufferTestBase::bufferCollection::~bufferCollection()
   6036 {
   6037 	for (Vector::iterator it = m_vector.begin(), end = m_vector.end(); end != it; ++it)
   6038 	{
   6039 		if (0 != it->m_buffer)
   6040 		{
   6041 			delete it->m_buffer;
   6042 			it->m_buffer = 0;
   6043 		}
   6044 	}
   6045 }
   6046 
   6047 /** Constructor
   6048  *
   6049  * @param context          Test context
   6050  * @param test_name        Name of test
   6051  * @param test_description Description of test
   6052  **/
   6053 NegativeTestBase::NegativeTestBase(deqp::Context& context, const GLchar* test_name, const GLchar* test_description)
   6054 	: TestBase(context, test_name, test_description)
   6055 {
   6056 }
   6057 
   6058 /** Selects if "compute" stage is relevant for test
   6059  *
   6060  * @param ignored
   6061  *
   6062  * @return true
   6063  **/
   6064 bool NegativeTestBase::isComputeRelevant(GLuint /* test_case_index */)
   6065 {
   6066 	return true;
   6067 }
   6068 
   6069 /** Selects if compilation failure is expected result
   6070  *
   6071  * @param ignored
   6072  *
   6073  * @return true
   6074  **/
   6075 bool NegativeTestBase::isFailureExpected(GLuint /* test_case_index */)
   6076 {
   6077 	return true;
   6078 }
   6079 
   6080 /** Runs test case
   6081  *
   6082  * @param test_case_index Id of test case
   6083  *
   6084  * @return true if test case pass, false otherwise
   6085  **/
   6086 bool NegativeTestBase::testCase(GLuint test_case_index)
   6087 {
   6088 	bool test_case_result = true;
   6089 
   6090 	/* Compute */
   6091 	if (true == isComputeRelevant(test_case_index))
   6092 	{
   6093 		const std::string& cs_source		   = getShaderSource(test_case_index, Utils::Shader::COMPUTE);
   6094 		bool			   is_build_error	  = false;
   6095 		const bool		   is_failure_expected = isFailureExpected(test_case_index);
   6096 		Utils::Program	 program(m_context);
   6097 
   6098 		try
   6099 		{
   6100 			program.Init(cs_source, "" /* fs */, "" /* gs */, "" /* tcs */, "" /* tes */, "" /* vs */,
   6101 						 false /* separable */);
   6102 		}
   6103 		catch (Utils::Shader::InvalidSourceException& exc)
   6104 		{
   6105 			if (false == is_failure_expected)
   6106 			{
   6107 				m_context.getTestContext().getLog()
   6108 					<< tcu::TestLog::Message << "Unexpected error in shader compilation: " << tcu::TestLog::EndMessage;
   6109 				exc.log(m_context);
   6110 			}
   6111 
   6112 #if DEBUG_NEG_LOG_ERROR
   6113 
   6114 			else
   6115 			{
   6116 				m_context.getTestContext().getLog()
   6117 					<< tcu::TestLog::Message << "Error in shader compilation was expected, logged for verification: "
   6118 					<< tcu::TestLog::EndMessage;
   6119 				exc.log(m_context);
   6120 			}
   6121 
   6122 #endif /* DEBUG_NEG_LOG_ERROR */
   6123 
   6124 			is_build_error = true;
   6125 		}
   6126 		catch (Utils::Program::BuildException& exc)
   6127 		{
   6128 			if (false == is_failure_expected)
   6129 			{
   6130 				m_context.getTestContext().getLog()
   6131 					<< tcu::TestLog::Message << "Unexpected error in program linking: " << tcu::TestLog::EndMessage;
   6132 				exc.log(m_context);
   6133 			}
   6134 
   6135 #if DEBUG_NEG_LOG_ERROR
   6136 
   6137 			else
   6138 			{
   6139 				m_context.getTestContext().getLog()
   6140 					<< tcu::TestLog::Message
   6141 					<< "Error in program linking was expected, logged for verification: " << tcu::TestLog::EndMessage;
   6142 				exc.log(m_context);
   6143 			}
   6144 
   6145 #endif /* DEBUG_NEG_LOG_ERROR */
   6146 
   6147 			is_build_error = true;
   6148 		}
   6149 
   6150 		if (is_build_error != is_failure_expected)
   6151 		{
   6152 			if (!is_build_error)
   6153 			{
   6154 				m_context.getTestContext().getLog()
   6155 					<< tcu::TestLog::Message << "Unexpected success: " << tcu::TestLog::EndMessage;
   6156 				Utils::Shader::LogSource(m_context, cs_source, Utils::Shader::COMPUTE);
   6157 			}
   6158 			test_case_result = false;
   6159 		}
   6160 	}
   6161 	else /* Draw */
   6162 	{
   6163 		const std::string& fs_source		   = getShaderSource(test_case_index, Utils::Shader::FRAGMENT);
   6164 		const std::string& gs_source		   = getShaderSource(test_case_index, Utils::Shader::GEOMETRY);
   6165 		bool			   is_build_error	  = false;
   6166 		const bool		   is_failure_expected = isFailureExpected(test_case_index);
   6167 		Utils::Program	 program(m_context);
   6168 		const std::string& tcs_source = getShaderSource(test_case_index, Utils::Shader::TESS_CTRL);
   6169 		const std::string& tes_source = getShaderSource(test_case_index, Utils::Shader::TESS_EVAL);
   6170 		const std::string& vs_source  = getShaderSource(test_case_index, Utils::Shader::VERTEX);
   6171 
   6172 		try
   6173 		{
   6174 			program.Init("" /* cs */, fs_source, gs_source, tcs_source, tes_source, vs_source, false /* separable */);
   6175 		}
   6176 		catch (Utils::Shader::InvalidSourceException& exc)
   6177 		{
   6178 			if (false == is_failure_expected)
   6179 			{
   6180 				m_context.getTestContext().getLog()
   6181 					<< tcu::TestLog::Message << "Unexpected error in shader compilation: " << tcu::TestLog::EndMessage;
   6182 				exc.log(m_context);
   6183 			}
   6184 
   6185 #if DEBUG_NEG_LOG_ERROR
   6186 
   6187 			else
   6188 			{
   6189 				m_context.getTestContext().getLog()
   6190 					<< tcu::TestLog::Message << "Error in shader compilation was expected, logged for verification: "
   6191 					<< tcu::TestLog::EndMessage;
   6192 				exc.log(m_context);
   6193 			}
   6194 
   6195 #endif /* DEBUG_NEG_LOG_ERROR */
   6196 
   6197 			is_build_error = true;
   6198 		}
   6199 		catch (Utils::Program::BuildException& exc)
   6200 		{
   6201 			if (false == is_failure_expected)
   6202 			{
   6203 				m_context.getTestContext().getLog()
   6204 					<< tcu::TestLog::Message << "Unexpected error in program linking: " << tcu::TestLog::EndMessage;
   6205 				exc.log(m_context);
   6206 			}
   6207 
   6208 #if DEBUG_NEG_LOG_ERROR
   6209 
   6210 			else
   6211 			{
   6212 				m_context.getTestContext().getLog()
   6213 					<< tcu::TestLog::Message
   6214 					<< "Error in program linking was expected, logged for verification: " << tcu::TestLog::EndMessage;
   6215 				exc.log(m_context);
   6216 			}
   6217 
   6218 #endif /* DEBUG_NEG_LOG_ERROR */
   6219 
   6220 			is_build_error = true;
   6221 		}
   6222 
   6223 		if (is_build_error != is_failure_expected)
   6224 		{
   6225 			if (!is_build_error)
   6226 			{
   6227 				m_context.getTestContext().getLog()
   6228 					<< tcu::TestLog::Message << "Unexpected success: " << tcu::TestLog::EndMessage;
   6229 				Utils::Shader::LogSource(m_context, vs_source, Utils::Shader::VERTEX);
   6230 				Utils::Shader::LogSource(m_context, tcs_source, Utils::Shader::TESS_CTRL);
   6231 				Utils::Shader::LogSource(m_context, tes_source, Utils::Shader::TESS_EVAL);
   6232 				Utils::Shader::LogSource(m_context, gs_source, Utils::Shader::GEOMETRY);
   6233 				Utils::Shader::LogSource(m_context, fs_source, Utils::Shader::FRAGMENT);
   6234 			}
   6235 			test_case_result = false;
   6236 		}
   6237 	}
   6238 
   6239 	return test_case_result;
   6240 }
   6241 
   6242 /* Constants used by TextureTestBase */
   6243 const glw::GLuint TextureTestBase::m_width  = 16;
   6244 const glw::GLuint TextureTestBase::m_height = 16;
   6245 
   6246 /** Constructor
   6247  *
   6248  * @param context          Test context
   6249  * @param test_name        Name of test
   6250  * @param test_description Description of test
   6251  **/
   6252 TextureTestBase::TextureTestBase(deqp::Context& context, const GLchar* test_name, const GLchar* test_description)
   6253 	: TestBase(context, test_name, test_description)
   6254 {
   6255 }
   6256 
   6257 /** Get locations for all inputs with automatic_location
   6258  *
   6259  * @param program           Program object
   6260  * @param program_interface Interface of program
   6261  **/
   6262 void TextureTestBase::prepareAttribLocation(Utils::Program& program, Utils::ProgramInterface& program_interface)
   6263 {
   6264 	Utils::ShaderInterface& si = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   6265 
   6266 	Utils::Variable::PtrVector& inputs = si.m_inputs;
   6267 
   6268 	for (Utils::Variable::PtrVector::iterator it = inputs.begin(); inputs.end() != it; ++it)
   6269 	{
   6270 		/* Test does not specify location, query value and set */
   6271 		if (Utils::Variable::m_automatic_location == (*it)->m_descriptor.m_expected_location)
   6272 		{
   6273 			GLuint index	= program.GetResourceIndex((*it)->m_descriptor.m_name, GL_PROGRAM_INPUT);
   6274 			GLint  location = 0;
   6275 
   6276 			program.GetResource(GL_PROGRAM_INPUT, index, GL_LOCATION, 1 /* size */, &location);
   6277 
   6278 			(*it)->m_descriptor.m_expected_location = location;
   6279 		}
   6280 	}
   6281 }
   6282 
   6283 /** Verifies contents of drawn image
   6284  *
   6285  * @param ignored
   6286  * @param color_0 Verified image
   6287  *
   6288  * @return true if image is filled with 1, false otherwise
   6289  **/
   6290 bool TextureTestBase::checkResults(glw::GLuint /* test_case_index */, Utils::Texture& color_0)
   6291 {
   6292 	static const GLuint size		   = m_width * m_height;
   6293 	static const GLuint expected_color = 1;
   6294 
   6295 	std::vector<GLuint> data;
   6296 	data.resize(size);
   6297 
   6298 	color_0.Get(GL_RED_INTEGER, GL_UNSIGNED_INT, &data[0]);
   6299 
   6300 	for (GLuint i = 0; i < size; ++i)
   6301 	{
   6302 		const GLuint color = data[i];
   6303 
   6304 		if (expected_color != color)
   6305 		{
   6306 			m_context.getTestContext().getLog() << tcu::TestLog::Message << "R32UI[" << i << "]:" << color
   6307 												<< tcu::TestLog::EndMessage;
   6308 			return false;
   6309 		}
   6310 	}
   6311 
   6312 	return true;
   6313 }
   6314 
   6315 /** Execute dispatch compute for 16x16x1
   6316  *
   6317  * @param ignored
   6318  **/
   6319 void TextureTestBase::executeDispatchCall(GLuint /* test_case_index */)
   6320 {
   6321 	const Functions& gl = m_context.getRenderContext().getFunctions();
   6322 
   6323 	gl.dispatchCompute(16 /* x */, 16 /* y */, 1 /* z */);
   6324 	GLU_EXPECT_NO_ERROR(gl.getError(), "DispatchCompute");
   6325 }
   6326 
   6327 /** Execute drawArrays for single vertex
   6328  *
   6329  * @param ignored
   6330  **/
   6331 void TextureTestBase::executeDrawCall(GLuint /* test_case_index */)
   6332 {
   6333 	const Functions& gl = m_context.getRenderContext().getFunctions();
   6334 
   6335 	gl.drawArrays(GL_PATCHES, 0 /* first */, 1 /* count */);
   6336 	GLU_EXPECT_NO_ERROR(gl.getError(), "DrawArrays");
   6337 }
   6338 
   6339 /** Prepare code snippet that will pass in variables to out variables
   6340  *
   6341  * @param ignored
   6342  * @param varying_passthrough Collection of connections between in and out variables
   6343  * @param stage               Shader stage
   6344  *
   6345  * @return Code that pass in variables to next stage
   6346  **/
   6347 std::string TextureTestBase::getPassSnippet(GLuint /* test_case_index */,
   6348 											Utils::VaryingPassthrough& varying_passthrough, Utils::Shader::STAGES stage)
   6349 {
   6350 	static const GLchar* separator = "\n    ";
   6351 
   6352 	/* Skip for compute shader */
   6353 	if (Utils::Shader::COMPUTE == stage)
   6354 	{
   6355 		return "";
   6356 	}
   6357 
   6358 	Utils::VaryingConnection::Vector& vector = varying_passthrough.Get(stage);
   6359 
   6360 	std::string result   = Utils::g_list;
   6361 	size_t		position = 0;
   6362 
   6363 	for (GLuint i = 0; i < vector.size(); ++i)
   6364 	{
   6365 
   6366 		Utils::VaryingConnection& connection = vector[i];
   6367 
   6368 		Utils::Variable* in  = connection.m_in;
   6369 		Utils::Variable* out = connection.m_out;
   6370 
   6371 		Utils::Variable::FLAVOUR in_flavour  = Utils::Variable::GetFlavour(stage, Utils::Variable::INPUT);
   6372 		Utils::Variable::FLAVOUR out_flavour = Utils::Variable::GetFlavour(stage, Utils::Variable::OUTPUT);
   6373 
   6374 		const std::string passthrough =
   6375 			getVariablePassthrough("", in->m_descriptor, in_flavour, "", out->m_descriptor, out_flavour);
   6376 
   6377 		Utils::insertElementOfList(passthrough.c_str(), separator, position, result);
   6378 	}
   6379 
   6380 	Utils::endList("", position, result);
   6381 
   6382 	return result;
   6383 }
   6384 
   6385 /** Basic implementation of method getProgramInterface
   6386  *
   6387  * @param ignored
   6388  * @param ignored
   6389  * @param ignored
   6390  **/
   6391 void TextureTestBase::getProgramInterface(GLuint /* test_case_index */,
   6392 										  Utils::ProgramInterface& /* program_interface */,
   6393 										  Utils::VaryingPassthrough& /* varying_passthrough */)
   6394 {
   6395 }
   6396 
   6397 /** Prepare code snippet that will verify in and uniform variables
   6398  *
   6399  * @param ignored
   6400  * @param program_interface Interface of program
   6401  * @param stage             Shader stage
   6402  *
   6403  * @return Code that verify variables
   6404  **/
   6405 std::string TextureTestBase::getVerificationSnippet(GLuint /* test_case_index */,
   6406 													Utils::ProgramInterface& program_interface,
   6407 													Utils::Shader::STAGES	stage)
   6408 {
   6409 	static const GLchar* separator = " ||\n        ";
   6410 
   6411 	std::string verification = "if (LIST)\n"
   6412 							   "    {\n"
   6413 							   "        result = 0u;\n"
   6414 							   "    }\n";
   6415 
   6416 	/* Get flavour of in and out variables */
   6417 	Utils::Variable::FLAVOUR in_flavour = Utils::Variable::GetFlavour(stage, Utils::Variable::INPUT);
   6418 
   6419 	/* Get interface for shader stage */
   6420 	Utils::ShaderInterface& si = program_interface.GetShaderInterface(stage);
   6421 
   6422 	/* There are no varialbes to verify */
   6423 	if ((0 == si.m_inputs.size()) && (0 == si.m_uniforms.size()) && (0 == si.m_ssb_blocks.size()))
   6424 	{
   6425 		return "";
   6426 	}
   6427 
   6428 	/* For each in variable insert verification code */
   6429 	size_t position = 0;
   6430 
   6431 	for (GLuint i = 0; i < si.m_inputs.size(); ++i)
   6432 	{
   6433 		const Utils::Variable& var				= *si.m_inputs[i];
   6434 		const std::string&	 var_verification = getVariableVerification("", var.m_data, var.m_descriptor, in_flavour);
   6435 
   6436 		Utils::insertElementOfList(var_verification.c_str(), separator, position, verification);
   6437 	}
   6438 
   6439 	/* For each unifrom variable insert verification code */
   6440 	for (GLuint i = 0; i < si.m_uniforms.size(); ++i)
   6441 	{
   6442 		const Utils::Variable& var = *si.m_uniforms[i];
   6443 		const std::string&	 var_verification =
   6444 			getVariableVerification("", var.m_data, var.m_descriptor, Utils::Variable::BASIC);
   6445 
   6446 		Utils::insertElementOfList(var_verification.c_str(), separator, position, verification);
   6447 	}
   6448 
   6449 	/* For each ssb variable insert verification code */
   6450 	for (GLuint i = 0; i < si.m_ssb_blocks.size(); ++i)
   6451 	{
   6452 		const Utils::Variable& var = *si.m_ssb_blocks[i];
   6453 		const std::string&	 var_verification =
   6454 			getVariableVerification("", var.m_data, var.m_descriptor, Utils::Variable::BASIC);
   6455 
   6456 		Utils::insertElementOfList(var_verification.c_str(), separator, position, verification);
   6457 	}
   6458 
   6459 	Utils::endList("", position, verification);
   6460 
   6461 #if DEBUG_TTB_VERIFICATION_SNIPPET_STAGE
   6462 
   6463 	{
   6464 		GLchar buffer[16];
   6465 		sprintf(buffer, "%d", stage + 10);
   6466 		Utils::replaceToken("0u", position, buffer, verification);
   6467 	}
   6468 
   6469 #elif DEBUG_TTB_VERIFICATION_SNIPPET_VARIABLE
   6470 
   6471 	if (Utils::Shader::VERTEX == stage)
   6472 	{
   6473 		Utils::replaceToken("0u", position, "in_vs_first.x", verification);
   6474 	}
   6475 	else
   6476 	{
   6477 		Utils::replaceToken("0u", position, "31u", verification);
   6478 	}
   6479 
   6480 #endif
   6481 
   6482 	/* Done */
   6483 	return verification;
   6484 }
   6485 
   6486 /** Selects if "compute" stage is relevant for test
   6487  *
   6488  * @param ignored
   6489  *
   6490  * @return true
   6491  **/
   6492 bool TextureTestBase::isComputeRelevant(GLuint /* test_case_index */)
   6493 {
   6494 	return true;
   6495 }
   6496 
   6497 /** Selects if "draw" stages are relevant for test
   6498  *
   6499  * @param ignored
   6500  *
   6501  * @return true
   6502  **/
   6503 bool TextureTestBase::isDrawRelevant(GLuint /* test_case_index */)
   6504 {
   6505 	return true;
   6506 }
   6507 
   6508 /** Prepare code that will do assignment of single in to single out
   6509  *
   6510  * @param in_parent_name  Name of parent in variable
   6511  * @param in_variable     Descriptor of in variable
   6512  * @param in_flavour      Flavoud of in variable
   6513  * @param out_parent_name Name of parent out variable
   6514  * @param out_variable    Descriptor of out variable
   6515  * @param out_flavour     Flavoud of out variable
   6516  *
   6517  * @return Code that does OUT = IN
   6518  **/
   6519 std::string TextureTestBase::getVariablePassthrough(const std::string&				   in_parent_name,
   6520 													const Utils::Variable::Descriptor& in_variable,
   6521 													Utils::Variable::FLAVOUR		   in_flavour,
   6522 													const std::string&				   out_parent_name,
   6523 													const Utils::Variable::Descriptor& out_variable,
   6524 													Utils::Variable::FLAVOUR		   out_flavour)
   6525 {
   6526 	bool				 done		  = false;
   6527 	GLuint				 index		  = 0;
   6528 	GLuint				 member_index = 0;
   6529 	size_t				 position	 = 0;
   6530 	std::string			 result		  = Utils::g_list;
   6531 	static const GLchar* separator	= ";\n    ";
   6532 
   6533 	/* For each member of each array element */
   6534 	do
   6535 	{
   6536 		const std::string in_name  = Utils::Variable::GetReference(in_parent_name, in_variable, in_flavour, index);
   6537 		const std::string out_name = Utils::Variable::GetReference(out_parent_name, out_variable, out_flavour, index);
   6538 		std::string		  passthrough;
   6539 
   6540 		/* Prepare verification */
   6541 		if (Utils::Variable::BUILTIN == in_variable.m_type)
   6542 		{
   6543 			size_t pass_position = 0;
   6544 
   6545 			passthrough = "OUT = IN;";
   6546 
   6547 			Utils::replaceToken("OUT", pass_position, out_name.c_str(), passthrough);
   6548 			Utils::replaceToken("IN", pass_position, in_name.c_str(), passthrough);
   6549 
   6550 			/* Increment index */
   6551 			++index;
   6552 		}
   6553 		else
   6554 		{
   6555 			const Utils::Interface* in_interface  = in_variable.m_interface;
   6556 			const Utils::Interface* out_interface = out_variable.m_interface;
   6557 
   6558 			if ((0 == in_interface) || (0 == out_interface))
   6559 			{
   6560 				TCU_FAIL("Nullptr");
   6561 			}
   6562 
   6563 			const Utils::Variable::Descriptor& in_member  = in_interface->m_members[member_index];
   6564 			const Utils::Variable::Descriptor& out_member = out_interface->m_members[member_index];
   6565 
   6566 			passthrough = getVariablePassthrough(in_name, in_member, Utils::Variable::BASIC, out_name, out_member,
   6567 												 Utils::Variable::BASIC);
   6568 
   6569 			/* Increment member_index */
   6570 			++member_index;
   6571 
   6572 			/* Increment index and reset member_index if all members were processed */
   6573 			if (in_interface->m_members.size() == member_index)
   6574 			{
   6575 				++index;
   6576 				member_index = 0;
   6577 			}
   6578 		}
   6579 
   6580 		/* Check if loop should end */
   6581 		if ((index >= in_variable.m_n_array_elements) && (0 == member_index))
   6582 		{
   6583 			done = true;
   6584 		}
   6585 
   6586 		Utils::insertElementOfList(passthrough.c_str(), separator, position, result);
   6587 
   6588 	} while (true != done);
   6589 
   6590 	Utils::endList("", position, result);
   6591 
   6592 	/* Done */
   6593 	return result;
   6594 }
   6595 
   6596 /** Get verification of single variable
   6597  *
   6598  * @param parent_name Name of parent variable
   6599  * @param data        Data that should be used as EXPECTED
   6600  * @param variable    Descriptor of variable
   6601  * @param flavour     Flavour of variable
   6602  *
   6603  * @return Code that does (EXPECTED != VALUE) ||
   6604  **/
   6605 std::string TextureTestBase::getVariableVerification(const std::string& parent_name, const GLvoid* data,
   6606 													 const Utils::Variable::Descriptor& variable,
   6607 													 Utils::Variable::FLAVOUR			flavour)
   6608 {
   6609 	static const GLchar* logic_op   = " ||\n        ";
   6610 	const GLuint		 n_elements = (0 == variable.m_n_array_elements) ? 1 : variable.m_n_array_elements;
   6611 	size_t				 position   = 0;
   6612 	std::string			 result		= Utils::g_list;
   6613 	GLint				 stride		= variable.m_expected_stride_of_element;
   6614 
   6615 	/* For each each array element */
   6616 	for (GLuint element = 0; element < n_elements; ++element)
   6617 	{
   6618 		const std::string name = Utils::Variable::GetReference(parent_name, variable, flavour, element);
   6619 
   6620 		/* Calculate data pointer */
   6621 		GLvoid* data_ptr = (GLvoid*)((GLubyte*)data + element * stride);
   6622 
   6623 		/* Prepare verification */
   6624 		if (Utils::Variable::BUILTIN == variable.m_type)
   6625 		{
   6626 			const std::string& expected = variable.m_builtin.GetGLSLConstructor(data_ptr);
   6627 			std::string		   verification;
   6628 			size_t			   verification_position = 0;
   6629 
   6630 			verification = "(EXPECTED != NAME)";
   6631 
   6632 			Utils::replaceToken("EXPECTED", verification_position, expected.c_str(), verification);
   6633 			Utils::replaceToken("NAME", verification_position, name.c_str(), verification);
   6634 
   6635 			Utils::insertElementOfList(verification.c_str(), logic_op, position, result);
   6636 		}
   6637 		else
   6638 		{
   6639 			const Utils::Interface* interface = variable.m_interface;
   6640 
   6641 			if (0 == interface)
   6642 			{
   6643 				TCU_FAIL("Nullptr");
   6644 			}
   6645 
   6646 			const GLuint n_members = static_cast<GLuint>(interface->m_members.size());
   6647 
   6648 			/* for each member */
   6649 			for (GLuint member_index = 0; member_index < n_members; ++member_index)
   6650 			{
   6651 				const Utils::Variable::Descriptor& member = interface->m_members[member_index];
   6652 
   6653 				/* Get verification of member */
   6654 				const std::string& verification =
   6655 					getVariableVerification(name, (GLubyte*)data_ptr + member.m_offset, member, Utils::Variable::BASIC);
   6656 
   6657 				Utils::insertElementOfList(verification.c_str(), logic_op, position, result);
   6658 			}
   6659 		}
   6660 	}
   6661 
   6662 	Utils::endList("", position, result);
   6663 
   6664 	return result;
   6665 }
   6666 
   6667 /** Prepare attributes, vertex array object and array buffer
   6668  *
   6669  * @param test_case_index   Index of test case
   6670  * @param program_interface Interface of program
   6671  * @param buffer            Array buffer
   6672  * @param vao               Vertex array object
   6673  **/
   6674 void TextureTestBase::prepareAttributes(GLuint test_case_index, Utils::ProgramInterface& program_interface,
   6675 										Utils::Buffer& buffer, Utils::VertexArray& vao)
   6676 {
   6677 	bool use_component_qualifier = useComponentQualifier(test_case_index);
   6678 
   6679 	/* Get shader interface */
   6680 	Utils::ShaderInterface& si = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   6681 
   6682 	/* Bind vao and buffer */
   6683 	vao.Bind();
   6684 	buffer.Bind();
   6685 
   6686 	/* Skip if there are no input variables in vertex shader */
   6687 	if (0 == si.m_inputs.size())
   6688 	{
   6689 		return;
   6690 	}
   6691 
   6692 	/* Calculate vertex stride and check */
   6693 	GLint vertex_stride = 0;
   6694 
   6695 	for (GLuint i = 0; i < si.m_inputs.size(); ++i)
   6696 	{
   6697 		Utils::Variable& variable = *si.m_inputs[i];
   6698 
   6699 		GLint variable_size = static_cast<GLuint>(variable.m_data_size);
   6700 
   6701 		GLint ends_at = variable_size + variable.m_descriptor.m_offset;
   6702 
   6703 		vertex_stride = std::max(vertex_stride, ends_at);
   6704 	}
   6705 
   6706 	/* Prepare buffer data and set up vao */
   6707 	std::vector<GLubyte> buffer_data;
   6708 	buffer_data.resize(vertex_stride);
   6709 
   6710 	GLubyte* ptr = &buffer_data[0];
   6711 
   6712 	for (GLuint i = 0; i < si.m_inputs.size(); ++i)
   6713 	{
   6714 		Utils::Variable& variable = *si.m_inputs[i];
   6715 
   6716 		memcpy(ptr + variable.m_descriptor.m_offset, variable.m_data, variable.m_data_size);
   6717 
   6718 		if (false == use_component_qualifier)
   6719 		{
   6720 			vao.Attribute(variable.m_descriptor.m_expected_location, variable.m_descriptor.m_builtin,
   6721 						  variable.m_descriptor.m_n_array_elements, variable.m_descriptor.m_normalized,
   6722 						  variable.GetStride(), (GLvoid*)(intptr_t)variable.m_descriptor.m_offset);
   6723 		}
   6724 		else if (0 == variable.m_descriptor.m_expected_component)
   6725 		{
   6726 			/* Components can only be applied to vectors.
   6727 			 Assumption that test use all 4 components */
   6728 			const Utils::Type& type =
   6729 				Utils::Type::GetType(variable.m_descriptor.m_builtin.m_basic_type, 1 /* n_columns */, 4 /* n_rows */);
   6730 
   6731 			vao.Attribute(variable.m_descriptor.m_expected_location, type, variable.m_descriptor.m_n_array_elements,
   6732 						  variable.m_descriptor.m_normalized, variable.GetStride(),
   6733 						  (GLvoid*)(intptr_t)variable.m_descriptor.m_offset);
   6734 		}
   6735 	}
   6736 
   6737 	/* Update buffer */
   6738 	buffer.Data(Utils::Buffer::StaticDraw, vertex_stride, ptr);
   6739 }
   6740 
   6741 /** Get locations for all outputs with automatic_location
   6742  *
   6743  * @param program           Program object
   6744  * @param program_interface Interface of program
   6745  **/
   6746 void TextureTestBase::prepareFragmentDataLoc(Utils::Program& program, Utils::ProgramInterface& program_interface)
   6747 {
   6748 	Utils::ShaderInterface&		si		= program_interface.GetShaderInterface(Utils::Shader::FRAGMENT);
   6749 	Utils::Variable::PtrVector& outputs = si.m_outputs;
   6750 
   6751 	for (Utils::Variable::PtrVector::iterator it = outputs.begin(); outputs.end() != it; ++it)
   6752 	{
   6753 		/* Test does not specify location, query value and set */
   6754 		if (Utils::Variable::m_automatic_location == (*it)->m_descriptor.m_expected_location)
   6755 		{
   6756 			GLuint index	= program.GetResourceIndex((*it)->m_descriptor.m_name, GL_PROGRAM_OUTPUT);
   6757 			GLint  location = 0;
   6758 
   6759 			program.GetResource(GL_PROGRAM_OUTPUT, index, GL_LOCATION, 1 /* size */, &location);
   6760 
   6761 			(*it)->m_descriptor.m_expected_location = location;
   6762 		}
   6763 	}
   6764 }
   6765 
   6766 /** Prepare framebuffer with single texture as color attachment
   6767  *
   6768  * @param framebuffer     Framebuffer
   6769  * @param color_0_texture Texture that will used as color attachment
   6770  **/
   6771 void TextureTestBase::prepareFramebuffer(Utils::Framebuffer& framebuffer, Utils::Texture& color_0_texture)
   6772 {
   6773 	/* Prepare data */
   6774 	std::vector<GLuint> texture_data;
   6775 	texture_data.resize(m_width * m_height);
   6776 
   6777 	for (GLuint i = 0; i < texture_data.size(); ++i)
   6778 	{
   6779 		texture_data[i] = 0x20406080;
   6780 	}
   6781 
   6782 	/* Prepare texture */
   6783 	color_0_texture.Init(Utils::Texture::TEX_2D, m_width, m_height, 0, GL_R32UI, GL_RED_INTEGER, GL_UNSIGNED_INT,
   6784 						 &texture_data[0]);
   6785 
   6786 	/* Prepare framebuffer */
   6787 	framebuffer.Init();
   6788 	framebuffer.Bind();
   6789 	framebuffer.AttachTexture(GL_COLOR_ATTACHMENT0, color_0_texture.m_id, m_width, m_height);
   6790 
   6791 	framebuffer.ClearColor(0.0f, 0.0f, 0.0f, 0.0f);
   6792 	framebuffer.Clear(GL_COLOR_BUFFER_BIT);
   6793 }
   6794 
   6795 /** Prepare iamge unit for compute shader
   6796  *
   6797  * @param location      Uniform location
   6798  * @param image_texture Texture that will used as color attachment
   6799  **/
   6800 void TextureTestBase::prepareImage(GLint location, Utils::Texture& image_texture) const
   6801 {
   6802 	static const GLuint image_unit = 0;
   6803 
   6804 	std::vector<GLuint> texture_data;
   6805 	texture_data.resize(m_width * m_height);
   6806 
   6807 	for (GLuint i = 0; i < texture_data.size(); ++i)
   6808 	{
   6809 		texture_data[i] = 0x20406080;
   6810 	}
   6811 
   6812 	image_texture.Init(Utils::Texture::TEX_2D, m_width, m_height, 0, GL_R32UI, GL_RED_INTEGER, GL_UNSIGNED_INT,
   6813 					   &texture_data[0]);
   6814 
   6815 	const Functions& gl = m_context.getRenderContext().getFunctions();
   6816 
   6817 	gl.bindImageTexture(image_unit, image_texture.m_id, 0 /* level */, GL_FALSE /* layered */, 0 /* Layer */,
   6818 						GL_WRITE_ONLY, GL_R32UI);
   6819 	GLU_EXPECT_NO_ERROR(gl.getError(), "BindImageTexture");
   6820 
   6821 	Utils::Program::Uniform(gl, Utils::Type::_int, 1 /* count */, location, &image_unit);
   6822 }
   6823 
   6824 /** Basic implementation
   6825  *
   6826  * @param ignored
   6827  * @param si        Shader interface
   6828  * @param program   Program
   6829  * @param cs_buffer Buffer for ssb blocks
   6830  **/
   6831 void TextureTestBase::prepareSSBs(GLuint /* test_case_index */, Utils::ShaderInterface& si, Utils::Program& program,
   6832 								  Utils::Buffer& buffer)
   6833 {
   6834 	/* Skip if there are no input variables in vertex shader */
   6835 	if (0 == si.m_ssb_blocks.size())
   6836 	{
   6837 		return;
   6838 	}
   6839 
   6840 	/* Calculate vertex stride */
   6841 	GLint ssbs_stride = 0;
   6842 
   6843 	for (GLuint i = 0; i < si.m_ssb_blocks.size(); ++i)
   6844 	{
   6845 		Utils::Variable& variable = *si.m_ssb_blocks[i];
   6846 
   6847 		if (false == variable.IsBlock())
   6848 		{
   6849 			continue;
   6850 		}
   6851 
   6852 		GLint variable_stride = variable.GetStride();
   6853 
   6854 		GLint ends_at = variable_stride + variable.m_descriptor.m_offset;
   6855 
   6856 		ssbs_stride = std::max(ssbs_stride, ends_at);
   6857 	}
   6858 
   6859 	/* Set active program */
   6860 	program.Use();
   6861 
   6862 	/* Allocate */
   6863 	buffer.Bind();
   6864 	buffer.Data(Utils::Buffer::StaticDraw, ssbs_stride, 0);
   6865 
   6866 	/* Set up uniforms */
   6867 	for (GLuint i = 0; i < si.m_ssb_blocks.size(); ++i)
   6868 	{
   6869 		Utils::Variable& variable = *si.m_ssb_blocks[i];
   6870 
   6871 		/* prepareUnifor should work fine for ssb blocks */
   6872 		prepareUniform(program, variable, buffer);
   6873 	}
   6874 }
   6875 
   6876 /** Basic implementation
   6877  *
   6878  * @param test_case_index   Test case index
   6879  * @param program_interface Program interface
   6880  * @param program           Program
   6881  * @param cs_buffer         Buffer for compute shader stage
   6882  **/
   6883 void TextureTestBase::prepareSSBs(GLuint test_case_index, Utils::ProgramInterface& program_interface,
   6884 								  Utils::Program& program, Utils::Buffer& cs_buffer)
   6885 {
   6886 	cs_buffer.Init(Utils::Buffer::Shader_Storage, Utils::Buffer::StaticDraw, 0, 0);
   6887 
   6888 	Utils::ShaderInterface& cs = program_interface.GetShaderInterface(Utils::Shader::COMPUTE);
   6889 
   6890 	prepareSSBs(test_case_index, cs, program, cs_buffer);
   6891 
   6892 	cs_buffer.BindBase(Utils::Shader::COMPUTE);
   6893 }
   6894 
   6895 /** Basic implementation
   6896  *
   6897  * @param test_case_index   Test case index
   6898  * @param program_interface Program interface
   6899  * @param program           Program
   6900  * @param fs_buffer         Buffer for fragment shader stage
   6901  * @param gs_buffer         Buffer for geometry shader stage
   6902  * @param tcs_buffer        Buffer for tessellation control shader stage
   6903  * @param tes_buffer        Buffer for tessellation evaluation shader stage
   6904  * @param vs_buffer         Buffer for vertex shader stage
   6905  **/
   6906 void TextureTestBase::prepareSSBs(GLuint test_case_index, Utils::ProgramInterface& program_interface,
   6907 								  Utils::Program& program, Utils::Buffer& fs_buffer, Utils::Buffer& gs_buffer,
   6908 								  Utils::Buffer& tcs_buffer, Utils::Buffer& tes_buffer, Utils::Buffer& vs_buffer)
   6909 {
   6910 	fs_buffer.Init(Utils::Buffer::Shader_Storage, Utils::Buffer::StaticDraw, 0, 0);
   6911 	gs_buffer.Init(Utils::Buffer::Shader_Storage, Utils::Buffer::StaticDraw, 0, 0);
   6912 	tcs_buffer.Init(Utils::Buffer::Shader_Storage, Utils::Buffer::StaticDraw, 0, 0);
   6913 	tes_buffer.Init(Utils::Buffer::Shader_Storage, Utils::Buffer::StaticDraw, 0, 0);
   6914 	vs_buffer.Init(Utils::Buffer::Shader_Storage, Utils::Buffer::StaticDraw, 0, 0);
   6915 
   6916 	Utils::ShaderInterface& fs  = program_interface.GetShaderInterface(Utils::Shader::FRAGMENT);
   6917 	Utils::ShaderInterface& gs  = program_interface.GetShaderInterface(Utils::Shader::GEOMETRY);
   6918 	Utils::ShaderInterface& tcs = program_interface.GetShaderInterface(Utils::Shader::TESS_CTRL);
   6919 	Utils::ShaderInterface& tes = program_interface.GetShaderInterface(Utils::Shader::TESS_EVAL);
   6920 	Utils::ShaderInterface& vs  = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   6921 
   6922 	prepareSSBs(test_case_index, fs, program, fs_buffer);
   6923 	prepareSSBs(test_case_index, gs, program, gs_buffer);
   6924 	prepareSSBs(test_case_index, tcs, program, tcs_buffer);
   6925 	prepareSSBs(test_case_index, tes, program, tes_buffer);
   6926 	prepareSSBs(test_case_index, vs, program, vs_buffer);
   6927 
   6928 	fs_buffer.BindBase(Utils::Shader::FRAGMENT);
   6929 	gs_buffer.BindBase(Utils::Shader::GEOMETRY);
   6930 	tcs_buffer.BindBase(Utils::Shader::TESS_CTRL);
   6931 	tes_buffer.BindBase(Utils::Shader::TESS_EVAL);
   6932 	vs_buffer.BindBase(Utils::Shader::VERTEX);
   6933 }
   6934 
   6935 /** Updates buffer data with variable
   6936  *
   6937  * @param program  Program object
   6938  * @param variable Variable
   6939  * @param buffer   Buffer
   6940  **/
   6941 void TextureTestBase::prepareUniform(Utils::Program& program, Utils::Variable& variable, Utils::Buffer& buffer)
   6942 {
   6943 	const Functions& gl = m_context.getRenderContext().getFunctions();
   6944 
   6945 	GLsizei count = variable.m_descriptor.m_n_array_elements;
   6946 	if (0 == count)
   6947 	{
   6948 		count = 1;
   6949 	}
   6950 
   6951 	if (Utils::Variable::BUILTIN == variable.m_descriptor.m_type)
   6952 	{
   6953 		program.Uniform(gl, variable.m_descriptor.m_builtin, count, variable.m_descriptor.m_expected_location,
   6954 						variable.m_data);
   6955 	}
   6956 	else
   6957 	{
   6958 		const bool is_block = variable.IsBlock();
   6959 
   6960 		if (false == is_block)
   6961 		{
   6962 			TCU_FAIL("Not implemented");
   6963 		}
   6964 		else
   6965 		{
   6966 			buffer.SubData(variable.m_descriptor.m_offset, variable.m_descriptor.m_expected_stride_of_element * count,
   6967 						   variable.m_data);
   6968 		}
   6969 	}
   6970 }
   6971 
   6972 /** Basic implementation
   6973  *
   6974  * @param ignored
   6975  * @param si        Shader interface
   6976  * @param program   Program
   6977  * @param cs_buffer Buffer for uniform blocks
   6978  **/
   6979 void TextureTestBase::prepareUniforms(GLuint /* test_case_index */, Utils::ShaderInterface& si, Utils::Program& program,
   6980 									  Utils::Buffer& buffer)
   6981 {
   6982 	/* Skip if there are no input variables in vertex shader */
   6983 	if (0 == si.m_uniforms.size())
   6984 	{
   6985 		return;
   6986 	}
   6987 
   6988 	/* Calculate vertex stride */
   6989 	GLint uniforms_stride = 0;
   6990 
   6991 	for (GLuint i = 0; i < si.m_uniforms.size(); ++i)
   6992 	{
   6993 		Utils::Variable& variable = *si.m_uniforms[i];
   6994 
   6995 		if (false == variable.IsBlock())
   6996 		{
   6997 			continue;
   6998 		}
   6999 
   7000 		GLint variable_stride = variable.GetStride();
   7001 
   7002 		GLint ends_at = variable_stride + variable.m_descriptor.m_offset;
   7003 
   7004 		uniforms_stride = std::max(uniforms_stride, ends_at);
   7005 	}
   7006 
   7007 	/* Set active program */
   7008 	program.Use();
   7009 
   7010 	/* Allocate */
   7011 	buffer.Bind();
   7012 	buffer.Data(Utils::Buffer::StaticDraw, uniforms_stride, 0);
   7013 
   7014 	/* Set up uniforms */
   7015 	for (GLuint i = 0; i < si.m_uniforms.size(); ++i)
   7016 	{
   7017 		Utils::Variable& variable = *si.m_uniforms[i];
   7018 
   7019 		prepareUniform(program, variable, buffer);
   7020 	}
   7021 }
   7022 
   7023 /** Basic implementation
   7024  *
   7025  * @param test_case_index   Test case index
   7026  * @param program_interface Program interface
   7027  * @param program           Program
   7028  * @param cs_buffer         Buffer for compute shader stage
   7029  **/
   7030 void TextureTestBase::prepareUniforms(GLuint test_case_index, Utils::ProgramInterface& program_interface,
   7031 									  Utils::Program& program, Utils::Buffer& cs_buffer)
   7032 {
   7033 	cs_buffer.Init(Utils::Buffer::Uniform, Utils::Buffer::StaticDraw, 0, 0);
   7034 
   7035 	Utils::ShaderInterface& cs = program_interface.GetShaderInterface(Utils::Shader::COMPUTE);
   7036 
   7037 	prepareUniforms(test_case_index, cs, program, cs_buffer);
   7038 
   7039 	cs_buffer.BindBase(Utils::Shader::COMPUTE);
   7040 }
   7041 
   7042 /** Basic implementation
   7043  *
   7044  * @param test_case_index   Test case index
   7045  * @param program_interface Program interface
   7046  * @param program           Program
   7047  * @param fs_buffer         Buffer for fragment shader stage
   7048  * @param gs_buffer         Buffer for geometry shader stage
   7049  * @param tcs_buffer        Buffer for tessellation control shader stage
   7050  * @param tes_buffer        Buffer for tessellation evaluation shader stage
   7051  * @param vs_buffer         Buffer for vertex shader stage
   7052  **/
   7053 void TextureTestBase::prepareUniforms(GLuint test_case_index, Utils::ProgramInterface& program_interface,
   7054 									  Utils::Program& program, Utils::Buffer& fs_buffer, Utils::Buffer& gs_buffer,
   7055 									  Utils::Buffer& tcs_buffer, Utils::Buffer& tes_buffer, Utils::Buffer& vs_buffer)
   7056 {
   7057 	fs_buffer.Init(Utils::Buffer::Uniform, Utils::Buffer::StaticDraw, 0, 0);
   7058 	gs_buffer.Init(Utils::Buffer::Uniform, Utils::Buffer::StaticDraw, 0, 0);
   7059 	tcs_buffer.Init(Utils::Buffer::Uniform, Utils::Buffer::StaticDraw, 0, 0);
   7060 	tes_buffer.Init(Utils::Buffer::Uniform, Utils::Buffer::StaticDraw, 0, 0);
   7061 	vs_buffer.Init(Utils::Buffer::Uniform, Utils::Buffer::StaticDraw, 0, 0);
   7062 
   7063 	Utils::ShaderInterface& fs  = program_interface.GetShaderInterface(Utils::Shader::FRAGMENT);
   7064 	Utils::ShaderInterface& gs  = program_interface.GetShaderInterface(Utils::Shader::GEOMETRY);
   7065 	Utils::ShaderInterface& tcs = program_interface.GetShaderInterface(Utils::Shader::TESS_CTRL);
   7066 	Utils::ShaderInterface& tes = program_interface.GetShaderInterface(Utils::Shader::TESS_EVAL);
   7067 	Utils::ShaderInterface& vs  = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   7068 
   7069 	prepareUniforms(test_case_index, fs, program, fs_buffer);
   7070 	prepareUniforms(test_case_index, gs, program, gs_buffer);
   7071 	prepareUniforms(test_case_index, tcs, program, tcs_buffer);
   7072 	prepareUniforms(test_case_index, tes, program, tes_buffer);
   7073 	prepareUniforms(test_case_index, vs, program, vs_buffer);
   7074 
   7075 	fs_buffer.BindBase(Utils::Shader::FRAGMENT);
   7076 	gs_buffer.BindBase(Utils::Shader::GEOMETRY);
   7077 	tcs_buffer.BindBase(Utils::Shader::TESS_CTRL);
   7078 	tes_buffer.BindBase(Utils::Shader::TESS_EVAL);
   7079 	vs_buffer.BindBase(Utils::Shader::VERTEX);
   7080 }
   7081 
   7082 /** Basic implementation
   7083  *
   7084  * @param test_case_index   Test case index
   7085  * @param program_interface Program interface
   7086  * @param program           Program
   7087  * @param fs_buffer         Buffer for fragment shader stage
   7088  * @param gs_buffer         Buffer for geometry shader stage
   7089  * @param tcs_buffer        Buffer for tessellation control shader stage
   7090  * @param tes_buffer        Buffer for tessellation evaluation shader stage
   7091  * @param vs_buffer         Buffer for vertex shader stage
   7092  **/
   7093 void TextureTestBase::prepareUniforms(GLuint test_case_index, Utils::ProgramInterface& program_interface,
   7094 									  Utils::Program& fs_program, Utils::Program& gs_program,
   7095 									  Utils::Program& tcs_program, Utils::Program& tes_program,
   7096 									  Utils::Program& vs_program, Utils::Buffer& fs_buffer, Utils::Buffer& gs_buffer,
   7097 									  Utils::Buffer& tcs_buffer, Utils::Buffer& tes_buffer, Utils::Buffer& vs_buffer)
   7098 {
   7099 	fs_buffer.Init(Utils::Buffer::Uniform, Utils::Buffer::StaticDraw, 0, 0);
   7100 	gs_buffer.Init(Utils::Buffer::Uniform, Utils::Buffer::StaticDraw, 0, 0);
   7101 	tcs_buffer.Init(Utils::Buffer::Uniform, Utils::Buffer::StaticDraw, 0, 0);
   7102 	tes_buffer.Init(Utils::Buffer::Uniform, Utils::Buffer::StaticDraw, 0, 0);
   7103 	vs_buffer.Init(Utils::Buffer::Uniform, Utils::Buffer::StaticDraw, 0, 0);
   7104 
   7105 	Utils::ShaderInterface& fs  = program_interface.GetShaderInterface(Utils::Shader::FRAGMENT);
   7106 	Utils::ShaderInterface& gs  = program_interface.GetShaderInterface(Utils::Shader::GEOMETRY);
   7107 	Utils::ShaderInterface& tcs = program_interface.GetShaderInterface(Utils::Shader::TESS_CTRL);
   7108 	Utils::ShaderInterface& tes = program_interface.GetShaderInterface(Utils::Shader::TESS_EVAL);
   7109 	Utils::ShaderInterface& vs  = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   7110 
   7111 	prepareUniforms(test_case_index, fs, fs_program, fs_buffer);
   7112 	fs_buffer.BindBase(Utils::Shader::FRAGMENT);
   7113 
   7114 	prepareUniforms(test_case_index, gs, gs_program, gs_buffer);
   7115 	gs_buffer.BindBase(Utils::Shader::GEOMETRY);
   7116 
   7117 	prepareUniforms(test_case_index, tcs, tcs_program, tcs_buffer);
   7118 	tcs_buffer.BindBase(Utils::Shader::TESS_CTRL);
   7119 
   7120 	prepareUniforms(test_case_index, tes, tes_program, tes_buffer);
   7121 	tes_buffer.BindBase(Utils::Shader::TESS_EVAL);
   7122 
   7123 	prepareUniforms(test_case_index, vs, vs_program, vs_buffer);
   7124 	vs_buffer.BindBase(Utils::Shader::VERTEX);
   7125 }
   7126 
   7127 /** Prepare source for shader
   7128  *
   7129  * @param test_case_index     Index of test case
   7130  * @param program_interface   Interface of program
   7131  * @param varying_passthrough Collection of connection between in and out variables
   7132  * @param stage               Shader stage
   7133  *
   7134  * @return Source of shader
   7135  **/
   7136 std::string TextureTestBase::getShaderSource(GLuint test_case_index, Utils::ProgramInterface& program_interface,
   7137 											 Utils::VaryingPassthrough& varying_passthrough,
   7138 											 Utils::Shader::STAGES		stage)
   7139 {
   7140 	/* Get strings */
   7141 	const GLchar*	  shader_template  = getShaderTemplate(stage);
   7142 	const std::string& shader_interface = program_interface.GetInterfaceForStage(stage);
   7143 
   7144 	const std::string& verification = getVerificationSnippet(test_case_index, program_interface, stage);
   7145 
   7146 	const std::string& passthrough = getPassSnippet(test_case_index, varying_passthrough, stage);
   7147 
   7148 	const GLchar* per_vertex = "";
   7149 
   7150 	std::string source   = shader_template;
   7151 	size_t		position = 0;
   7152 
   7153 	/* Replace tokens in template */
   7154 	if (Utils::Shader::GEOMETRY == stage)
   7155 	{
   7156 		if (false == useMonolithicProgram(test_case_index))
   7157 		{
   7158 			per_vertex = "out gl_PerVertex {\n"
   7159 						 "vec4 gl_Position;\n"
   7160 						 "};\n"
   7161 						 "\n";
   7162 		}
   7163 
   7164 		Utils::replaceToken("PERVERTEX", position, per_vertex, source);
   7165 	}
   7166 
   7167 	Utils::replaceToken("INTERFACE", position, shader_interface.c_str(), source);
   7168 	Utils::replaceToken("VERIFICATION", position, verification.c_str(), source);
   7169 
   7170 	if (false == verification.empty())
   7171 	{
   7172 		Utils::replaceAllTokens("ELSE", "    else ", source);
   7173 	}
   7174 	else
   7175 	{
   7176 		Utils::replaceAllTokens("ELSE", "", source);
   7177 	}
   7178 
   7179 	Utils::replaceAllTokens("PASSTHROUGH", passthrough.c_str(), source);
   7180 
   7181 	/* Done */
   7182 	return source;
   7183 }
   7184 
   7185 /** Returns template of shader for given stage
   7186  *
   7187  * @param stage Shade stage
   7188  *
   7189  * @return Proper template
   7190  **/
   7191 const GLchar* TextureTestBase::getShaderTemplate(Utils::Shader::STAGES stage)
   7192 {
   7193 
   7194 	static const GLchar* compute_shader_template =
   7195 		"#version 430 core\n"
   7196 		"#extension GL_ARB_enhanced_layouts : require\n"
   7197 		"\n"
   7198 		"layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
   7199 		"\n"
   7200 		"writeonly uniform uimage2D uni_image;\n"
   7201 		"\n"
   7202 		"INTERFACE"
   7203 		"\n"
   7204 		"void main()\n"
   7205 		"{\n"
   7206 		"    uint result = 1u;\n"
   7207 		"\n"
   7208 		"    VERIFICATION"
   7209 		"\n"
   7210 		"    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), uvec4(result, 0, 0, 0));\n"
   7211 		"}\n"
   7212 		"\n";
   7213 
   7214 	static const GLchar* fragment_shader_template = "#version 430 core\n"
   7215 													"#extension GL_ARB_enhanced_layouts : require\n"
   7216 													"\n"
   7217 													"flat in  uint gs_fs_result;\n"
   7218 													"     out uint fs_out_result;\n"
   7219 													"\n"
   7220 													"INTERFACE"
   7221 													"\n"
   7222 													"void main()\n"
   7223 													"{\n"
   7224 													"    uint result = 1u;\n"
   7225 													"\n"
   7226 													"    if (1u != gs_fs_result)\n"
   7227 													"    {\n"
   7228 													"         result = gs_fs_result;\n"
   7229 													"    }\n"
   7230 													"ELSEVERIFICATION"
   7231 													"\n"
   7232 													"    fs_out_result = result;\n"
   7233 													"    PASSTHROUGH\n"
   7234 													"}\n"
   7235 													"\n";
   7236 
   7237 	static const GLchar* geometry_shader_template =
   7238 		"#version 430 core\n"
   7239 		"#extension GL_ARB_enhanced_layouts : require\n"
   7240 		"\n"
   7241 		"layout(points)                           in;\n"
   7242 		"layout(triangle_strip, max_vertices = 4) out;\n"
   7243 		"\n"
   7244 		"     in  uint tes_gs_result[];\n"
   7245 		"flat out uint gs_fs_result;\n"
   7246 		"\n"
   7247 		"PERVERTEX" /* Separable programs require explicit declaration of gl_PerVertex */
   7248 		"INTERFACE"
   7249 		"\n"
   7250 		"void main()\n"
   7251 		"{\n"
   7252 		"    uint result = 1u;\n"
   7253 		"\n"
   7254 		"    if (1u != tes_gs_result[0])\n"
   7255 		"    {\n"
   7256 		"         result = tes_gs_result[0];\n"
   7257 		"    }\n"
   7258 		"ELSEVERIFICATION"
   7259 		"\n"
   7260 		"    gs_fs_result = result;\n"
   7261 		"    PASSTHROUGH\n"
   7262 		"    gl_Position  = vec4(-1, -1, 0, 1);\n"
   7263 		"    EmitVertex();\n"
   7264 		"    gs_fs_result = result;\n"
   7265 		"    PASSTHROUGH\n"
   7266 		"    gl_Position  = vec4(-1, 1, 0, 1);\n"
   7267 		"    EmitVertex();\n"
   7268 		"    gs_fs_result = result;\n"
   7269 		"    PASSTHROUGH\n"
   7270 		"    gl_Position  = vec4(1, -1, 0, 1);\n"
   7271 		"    EmitVertex();\n"
   7272 		"    gs_fs_result = result;\n"
   7273 		"    PASSTHROUGH\n"
   7274 		"    gl_Position  = vec4(1, 1, 0, 1);\n"
   7275 		"    EmitVertex();\n"
   7276 		"}\n"
   7277 		"\n";
   7278 
   7279 	static const GLchar* tess_ctrl_shader_template = "#version 430 core\n"
   7280 													 "#extension GL_ARB_enhanced_layouts : require\n"
   7281 													 "\n"
   7282 													 "layout(vertices = 1) out;\n"
   7283 													 "\n"
   7284 													 "in  uint vs_tcs_result[];\n"
   7285 													 "out uint tcs_tes_result[];\n"
   7286 													 "\n"
   7287 													 "INTERFACE"
   7288 													 "\n"
   7289 													 "void main()\n"
   7290 													 "{\n"
   7291 													 "    uint result = 1u;\n"
   7292 													 "\n"
   7293 													 "    if (1u != vs_tcs_result[gl_InvocationID])\n"
   7294 													 "    {\n"
   7295 													 "         result = vs_tcs_result[gl_InvocationID];\n"
   7296 													 "    }\n"
   7297 													 "ELSEVERIFICATION"
   7298 													 "\n"
   7299 													 "    tcs_tes_result[gl_InvocationID] = result;\n"
   7300 													 "\n"
   7301 													 "    PASSTHROUGH\n"
   7302 													 "\n"
   7303 													 "    gl_TessLevelOuter[0] = 1.0;\n"
   7304 													 "    gl_TessLevelOuter[1] = 1.0;\n"
   7305 													 "    gl_TessLevelOuter[2] = 1.0;\n"
   7306 													 "    gl_TessLevelOuter[3] = 1.0;\n"
   7307 													 "    gl_TessLevelInner[0] = 1.0;\n"
   7308 													 "    gl_TessLevelInner[1] = 1.0;\n"
   7309 													 "}\n"
   7310 													 "\n";
   7311 
   7312 	static const GLchar* tess_eval_shader_template = "#version 430 core\n"
   7313 													 "#extension GL_ARB_enhanced_layouts : require\n"
   7314 													 "\n"
   7315 													 "layout(isolines, point_mode) in;\n"
   7316 													 "\n"
   7317 													 "in  uint tcs_tes_result[];\n"
   7318 													 "out uint tes_gs_result;\n"
   7319 													 "\n"
   7320 													 "INTERFACE"
   7321 													 "\n"
   7322 													 "void main()\n"
   7323 													 "{\n"
   7324 													 "    uint result = 1u;\n"
   7325 													 "\n"
   7326 													 "    if (1 != tcs_tes_result[0])\n"
   7327 													 "    {\n"
   7328 													 "         result = tcs_tes_result[0];\n"
   7329 													 "    }\n"
   7330 													 "ELSEVERIFICATION"
   7331 													 "\n"
   7332 													 "    tes_gs_result = result;\n"
   7333 													 "\n"
   7334 													 "    PASSTHROUGH\n"
   7335 													 "}\n"
   7336 													 "\n";
   7337 
   7338 	static const GLchar* vertex_shader_template = "#version 430 core\n"
   7339 												  "#extension GL_ARB_enhanced_layouts : require\n"
   7340 												  "\n"
   7341 												  "out uint vs_tcs_result;\n"
   7342 												  "\n"
   7343 												  "INTERFACE"
   7344 												  "\n"
   7345 												  "void main()\n"
   7346 												  "{\n"
   7347 												  "    uint result = 1u;\n"
   7348 												  "\n"
   7349 												  "    VERIFICATION\n"
   7350 												  "\n"
   7351 												  "    vs_tcs_result = result;\n"
   7352 												  "\n"
   7353 												  "    PASSTHROUGH\n"
   7354 												  "}\n"
   7355 												  "\n";
   7356 
   7357 	const GLchar* result = 0;
   7358 
   7359 	switch (stage)
   7360 	{
   7361 	case Utils::Shader::COMPUTE:
   7362 		result = compute_shader_template;
   7363 		break;
   7364 	case Utils::Shader::FRAGMENT:
   7365 		result = fragment_shader_template;
   7366 		break;
   7367 	case Utils::Shader::GEOMETRY:
   7368 		result = geometry_shader_template;
   7369 		break;
   7370 	case Utils::Shader::TESS_CTRL:
   7371 		result = tess_ctrl_shader_template;
   7372 		break;
   7373 	case Utils::Shader::TESS_EVAL:
   7374 		result = tess_eval_shader_template;
   7375 		break;
   7376 	case Utils::Shader::VERTEX:
   7377 		result = vertex_shader_template;
   7378 		break;
   7379 	default:
   7380 		TCU_FAIL("Invalid enum");
   7381 	}
   7382 
   7383 	return result;
   7384 }
   7385 
   7386 /** Runs test case
   7387  *
   7388  * @param test_case_index Id of test case
   7389  *
   7390  * @return true if test case pass, false otherwise
   7391  **/
   7392 bool TextureTestBase::testCase(GLuint test_case_index)
   7393 {
   7394 	try
   7395 	{
   7396 		if (true == useMonolithicProgram(test_case_index))
   7397 		{
   7398 			return testMonolithic(test_case_index);
   7399 		}
   7400 		else
   7401 		{
   7402 			return testSeparable(test_case_index);
   7403 		}
   7404 	}
   7405 	catch (Utils::Shader::InvalidSourceException& exc)
   7406 	{
   7407 		exc.log(m_context);
   7408 		TCU_FAIL(exc.what());
   7409 	}
   7410 	catch (Utils::Program::BuildException& exc)
   7411 	{
   7412 		TCU_FAIL(exc.what());
   7413 	}
   7414 }
   7415 
   7416 /** Runs "draw" test with monolithic program
   7417  *
   7418  * @param test_case_index Id of test case
   7419  **/
   7420 bool TextureTestBase::testMonolithic(GLuint test_case_index)
   7421 {
   7422 	Utils::ProgramInterface   program_interface;
   7423 	Utils::VaryingPassthrough varying_passthrough;
   7424 
   7425 	/* */
   7426 	const std::string& test_name = getTestCaseName(test_case_index);
   7427 
   7428 	/* */
   7429 	getProgramInterface(test_case_index, program_interface, varying_passthrough);
   7430 
   7431 	bool result = true;
   7432 	/* Draw */
   7433 	if (true == isDrawRelevant(test_case_index))
   7434 	{
   7435 		Utils::Buffer	  buffer_attr(m_context);
   7436 		Utils::Buffer	  buffer_ssb_fs(m_context);
   7437 		Utils::Buffer	  buffer_ssb_gs(m_context);
   7438 		Utils::Buffer	  buffer_ssb_tcs(m_context);
   7439 		Utils::Buffer	  buffer_ssb_tes(m_context);
   7440 		Utils::Buffer	  buffer_ssb_vs(m_context);
   7441 		Utils::Buffer	  buffer_u_fs(m_context);
   7442 		Utils::Buffer	  buffer_u_gs(m_context);
   7443 		Utils::Buffer	  buffer_u_tcs(m_context);
   7444 		Utils::Buffer	  buffer_u_tes(m_context);
   7445 		Utils::Buffer	  buffer_u_vs(m_context);
   7446 		Utils::Framebuffer framebuffer(m_context);
   7447 		Utils::Program	 program(m_context);
   7448 		Utils::Texture	 texture_fb(m_context);
   7449 		Utils::VertexArray vao(m_context);
   7450 
   7451 		/* */
   7452 		const std::string& fragment_shader =
   7453 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::FRAGMENT);
   7454 		const std::string& geometry_shader =
   7455 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::GEOMETRY);
   7456 		const std::string& tess_ctrl_shader =
   7457 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::TESS_CTRL);
   7458 		const std::string& tess_eval_shader =
   7459 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::TESS_EVAL);
   7460 		const std::string& vertex_shader =
   7461 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::VERTEX);
   7462 
   7463 		program.Init("" /* compute_shader */, fragment_shader, geometry_shader, tess_ctrl_shader, tess_eval_shader,
   7464 					 vertex_shader, false /* is_separable */);
   7465 
   7466 		/* */
   7467 		prepareAttribLocation(program, program_interface);
   7468 		prepareFragmentDataLoc(program, program_interface);
   7469 
   7470 		/* */
   7471 		std::stringstream stream;
   7472 		if (false == Utils::checkMonolithicDrawProgramInterface(program, program_interface, stream))
   7473 		{
   7474 			m_context.getTestContext().getLog()
   7475 				<< tcu::TestLog::Message << "FAILURE. Test case: " << test_name
   7476 				<< ". Inspection of draw program interface failed:\n"
   7477 				<< stream.str() << tcu::TestLog::EndMessage << tcu::TestLog::KernelSource(vertex_shader)
   7478 				<< tcu::TestLog::KernelSource(tess_ctrl_shader) << tcu::TestLog::KernelSource(tess_eval_shader)
   7479 				<< tcu::TestLog::KernelSource(geometry_shader) << tcu::TestLog::KernelSource(fragment_shader);
   7480 
   7481 			return false;
   7482 		}
   7483 
   7484 		/* */
   7485 		program.Use();
   7486 
   7487 		/* */
   7488 		buffer_attr.Init(Utils::Buffer::Array, Utils::Buffer::StaticDraw, 0, 0);
   7489 		vao.Init();
   7490 		prepareAttributes(test_case_index, program_interface, buffer_attr, vao);
   7491 
   7492 		/* */
   7493 		prepareUniforms(test_case_index, program_interface, program, buffer_u_fs, buffer_u_gs, buffer_u_tcs,
   7494 						buffer_u_tes, buffer_u_vs);
   7495 
   7496 		prepareSSBs(test_case_index, program_interface, program, buffer_ssb_fs, buffer_ssb_gs, buffer_ssb_tcs,
   7497 					buffer_ssb_tes, buffer_ssb_vs);
   7498 
   7499 		/* */
   7500 		prepareFramebuffer(framebuffer, texture_fb);
   7501 
   7502 		/* Draw */
   7503 		executeDrawCall(test_case_index);
   7504 
   7505 #if USE_NSIGHT
   7506 		m_context.getRenderContext().postIterate();
   7507 #endif
   7508 
   7509 		/* Check results */
   7510 		if (false == checkResults(test_case_index, texture_fb))
   7511 		{
   7512 			m_context.getTestContext().getLog()
   7513 				<< tcu::TestLog::Message << "FAILURE. Test case: " << test_name << ". Draw - invalid results."
   7514 				<< tcu::TestLog::EndMessage << tcu::TestLog::KernelSource(vertex_shader)
   7515 				<< tcu::TestLog::KernelSource(tess_ctrl_shader) << tcu::TestLog::KernelSource(tess_eval_shader)
   7516 				<< tcu::TestLog::KernelSource(geometry_shader) << tcu::TestLog::KernelSource(fragment_shader);
   7517 
   7518 			result = false;
   7519 		}
   7520 	}
   7521 
   7522 	/* Compute */
   7523 	if (true == isComputeRelevant(test_case_index))
   7524 	{
   7525 		Utils::Buffer	  buffer_ssb_cs(m_context);
   7526 		Utils::Buffer	  buffer_u_cs(m_context);
   7527 		Utils::Program	 program(m_context);
   7528 		Utils::Texture	 texture_im(m_context);
   7529 		Utils::VertexArray vao(m_context);
   7530 
   7531 		/* */
   7532 		const std::string& compute_shader =
   7533 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::COMPUTE);
   7534 
   7535 		program.Init(compute_shader, "" /* fragment_shader */, "" /* geometry_shader */, "" /* tess_ctrl_shader */,
   7536 					 "" /* tess_eval_shader */, "" /* vertex_shader */, false /* is_separable */);
   7537 
   7538 		/* */
   7539 		{
   7540 			std::stringstream stream;
   7541 
   7542 			if (false == Utils::checkMonolithicComputeProgramInterface(program, program_interface, stream))
   7543 			{
   7544 				m_context.getTestContext().getLog() << tcu::TestLog::Message << "FAILURE. Test case: " << test_name
   7545 													<< ". Inspection of compute program interface failed:\n"
   7546 													<< stream.str() << tcu::TestLog::EndMessage;
   7547 
   7548 				return false;
   7549 			}
   7550 		}
   7551 
   7552 		/* */
   7553 		program.Use();
   7554 
   7555 		/* */
   7556 		vao.Init();
   7557 		vao.Bind();
   7558 
   7559 		/* */
   7560 		prepareUniforms(test_case_index, program_interface, program, buffer_u_cs);
   7561 
   7562 		prepareSSBs(test_case_index, program_interface, program, buffer_ssb_cs);
   7563 
   7564 		/* */
   7565 		GLint image_location = program.GetUniformLocation("uni_image");
   7566 		prepareImage(image_location, texture_im);
   7567 
   7568 		/* Draw */
   7569 		executeDispatchCall(test_case_index);
   7570 
   7571 #if USE_NSIGHT
   7572 		m_context.getRenderContext().postIterate();
   7573 #endif
   7574 
   7575 		/* Check results */
   7576 		if (false == checkResults(test_case_index, texture_im))
   7577 		{
   7578 			m_context.getTestContext().getLog() << tcu::TestLog::Message << "FAILURE. Test case: " << test_name
   7579 												<< ". Compute - invalid results." << tcu::TestLog::EndMessage
   7580 												<< tcu::TestLog::KernelSource(compute_shader);
   7581 
   7582 			result = false;
   7583 		}
   7584 	}
   7585 
   7586 	return result;
   7587 }
   7588 
   7589 /** Runs "draw" test with separable program
   7590  *
   7591  * @param test_case_index Id of test case
   7592  **/
   7593 bool TextureTestBase::testSeparable(GLuint test_case_index)
   7594 {
   7595 	Utils::ProgramInterface   program_interface;
   7596 	Utils::VaryingPassthrough varying_passthrough;
   7597 
   7598 	/* */
   7599 	const std::string& test_name = getTestCaseName(test_case_index);
   7600 
   7601 	/* */
   7602 	getProgramInterface(test_case_index, program_interface, varying_passthrough);
   7603 
   7604 	bool result = true;
   7605 	/* Draw */
   7606 	if (true == isDrawRelevant(test_case_index))
   7607 	{
   7608 		Utils::Buffer	  buffer_attr(m_context);
   7609 		Utils::Buffer	  buffer_u_fs(m_context);
   7610 		Utils::Buffer	  buffer_u_gs(m_context);
   7611 		Utils::Buffer	  buffer_u_tcs(m_context);
   7612 		Utils::Buffer	  buffer_u_tes(m_context);
   7613 		Utils::Buffer	  buffer_u_vs(m_context);
   7614 		Utils::Framebuffer framebuffer(m_context);
   7615 		Utils::Pipeline	pipeline(m_context);
   7616 		Utils::Program	 program_fs(m_context);
   7617 		Utils::Program	 program_gs(m_context);
   7618 		Utils::Program	 program_tcs(m_context);
   7619 		Utils::Program	 program_tes(m_context);
   7620 		Utils::Program	 program_vs(m_context);
   7621 		Utils::Texture	 texture_fb(m_context);
   7622 		Utils::VertexArray vao(m_context);
   7623 
   7624 		/* */
   7625 		const std::string& fs =
   7626 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::FRAGMENT);
   7627 		const std::string& gs =
   7628 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::GEOMETRY);
   7629 		const std::string& tcs =
   7630 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::TESS_CTRL);
   7631 		const std::string& tes =
   7632 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::TESS_EVAL);
   7633 		const std::string& vs =
   7634 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::VERTEX);
   7635 
   7636 		program_fs.Init("" /*cs*/, fs, "" /*gs*/, "" /*tcs*/, "" /*tes*/, "" /*vs*/, true /* is_separable */);
   7637 		program_gs.Init("" /*cs*/, "" /*fs*/, gs, "" /*tcs*/, "" /*tes*/, "" /*vs*/, true /* is_separable */);
   7638 		program_tcs.Init("" /*cs*/, "" /*fs*/, "" /*gs*/, tcs, "" /*tes*/, "" /*vs*/, true /* is_separable */);
   7639 		program_tes.Init("" /*cs*/, "" /*fs*/, "" /*gs*/, "" /*tcs*/, tes, "" /*vs*/, true /* is_separable */);
   7640 		program_vs.Init("" /*cs*/, "" /*fs*/, "" /*gs*/, "" /*tcs*/, "" /*tes*/, vs, true /* is_separable */);
   7641 
   7642 		/* */
   7643 		prepareAttribLocation(program_vs, program_interface);
   7644 		prepareFragmentDataLoc(program_vs, program_interface);
   7645 
   7646 		/* */
   7647 		std::stringstream stream;
   7648 		if ((false ==
   7649 			 Utils::checkSeparableDrawProgramInterface(program_vs, program_interface, Utils::Shader::VERTEX, stream)) ||
   7650 			(false == Utils::checkSeparableDrawProgramInterface(program_fs, program_interface, Utils::Shader::FRAGMENT,
   7651 																stream)) ||
   7652 			(false == Utils::checkSeparableDrawProgramInterface(program_gs, program_interface, Utils::Shader::GEOMETRY,
   7653 																stream)) ||
   7654 			(false == Utils::checkSeparableDrawProgramInterface(program_tcs, program_interface,
   7655 																Utils::Shader::TESS_CTRL, stream)) ||
   7656 			(false == Utils::checkSeparableDrawProgramInterface(program_tes, program_interface,
   7657 																Utils::Shader::TESS_EVAL, stream)))
   7658 		{
   7659 			m_context.getTestContext().getLog() << tcu::TestLog::Message << "FAILURE. Test case: " << test_name
   7660 												<< ". Inspection of separable draw program interface failed:\n"
   7661 												<< stream.str() << tcu::TestLog::EndMessage
   7662 												<< tcu::TestLog::KernelSource(vs) << tcu::TestLog::KernelSource(tcs)
   7663 												<< tcu::TestLog::KernelSource(tes) << tcu::TestLog::KernelSource(gs)
   7664 												<< tcu::TestLog::KernelSource(fs);
   7665 
   7666 			return false;
   7667 		}
   7668 
   7669 		/* */
   7670 		pipeline.Init();
   7671 		pipeline.UseProgramStages(program_fs.m_id, GL_FRAGMENT_SHADER_BIT);
   7672 		pipeline.UseProgramStages(program_gs.m_id, GL_GEOMETRY_SHADER_BIT);
   7673 		pipeline.UseProgramStages(program_tcs.m_id, GL_TESS_CONTROL_SHADER_BIT);
   7674 		pipeline.UseProgramStages(program_tes.m_id, GL_TESS_EVALUATION_SHADER_BIT);
   7675 		pipeline.UseProgramStages(program_vs.m_id, GL_VERTEX_SHADER_BIT);
   7676 		pipeline.Bind();
   7677 
   7678 		/* */
   7679 
   7680 		buffer_attr.Init(Utils::Buffer::Array, Utils::Buffer::StaticDraw, 0, 0);
   7681 		vao.Init();
   7682 		prepareAttributes(test_case_index, program_interface, buffer_attr, vao);
   7683 
   7684 		/* */
   7685 		prepareUniforms(test_case_index, program_interface, program_fs, program_gs, program_tcs, program_tes,
   7686 						program_vs, buffer_u_fs, buffer_u_gs, buffer_u_tcs, buffer_u_tes, buffer_u_vs);
   7687 
   7688 		Utils::Program::Use(m_context.getRenderContext().getFunctions(), Utils::Program::m_invalid_id);
   7689 
   7690 		/* */
   7691 		prepareFramebuffer(framebuffer, texture_fb);
   7692 
   7693 		/* Draw */
   7694 		executeDrawCall(test_case_index);
   7695 
   7696 #if USE_NSIGHT
   7697 		m_context.getRenderContext().postIterate();
   7698 #endif
   7699 
   7700 		/* Check results */
   7701 		if (false == checkResults(test_case_index, texture_fb))
   7702 		{
   7703 			m_context.getTestContext().getLog()
   7704 				<< tcu::TestLog::Message << "FAILURE. Test case: " << test_name << ". Draw - invalid results."
   7705 				<< tcu::TestLog::EndMessage << tcu::TestLog::KernelSource(vs) << tcu::TestLog::KernelSource(tcs)
   7706 				<< tcu::TestLog::KernelSource(tes) << tcu::TestLog::KernelSource(gs) << tcu::TestLog::KernelSource(fs);
   7707 
   7708 			result = false;
   7709 		}
   7710 	}
   7711 
   7712 	/* Compute */
   7713 	if (true == isComputeRelevant(test_case_index))
   7714 	{
   7715 		Utils::Buffer	  buffer_u_cs(m_context);
   7716 		Utils::Program	 program(m_context);
   7717 		Utils::Texture	 texture_im(m_context);
   7718 		Utils::VertexArray vao(m_context);
   7719 
   7720 		/* */
   7721 		const std::string& compute_shader =
   7722 			getShaderSource(test_case_index, program_interface, varying_passthrough, Utils::Shader::COMPUTE);
   7723 
   7724 		program.Init(compute_shader, "" /* fragment_shader */, "" /* geometry_shader */, "" /* tess_ctrl_shader */,
   7725 					 "" /* tess_eval_shader */, "" /* vertex_shader */, false /* is_separable */);
   7726 
   7727 		/* */
   7728 		{
   7729 			std::stringstream stream;
   7730 
   7731 			if (false == Utils::checkMonolithicComputeProgramInterface(program, program_interface, stream))
   7732 			{
   7733 				m_context.getTestContext().getLog() << tcu::TestLog::Message << "FAILURE. Test case: " << test_name
   7734 													<< ". Inspection of compute program interface failed:\n"
   7735 													<< stream.str() << tcu::TestLog::EndMessage;
   7736 
   7737 				return false;
   7738 			}
   7739 		}
   7740 
   7741 		/* */
   7742 		program.Use();
   7743 
   7744 		/* */
   7745 		vao.Init();
   7746 		vao.Bind();
   7747 
   7748 		/* */
   7749 		prepareUniforms(test_case_index, program_interface, program, buffer_u_cs);
   7750 
   7751 		/* */
   7752 		GLint image_location = program.GetUniformLocation("uni_image");
   7753 		prepareImage(image_location, texture_im);
   7754 
   7755 		/* Draw */
   7756 		executeDispatchCall(test_case_index);
   7757 
   7758 #if USE_NSIGHT
   7759 		m_context.getRenderContext().postIterate();
   7760 #endif
   7761 
   7762 		/* Check results */
   7763 		if (false == checkResults(test_case_index, texture_im))
   7764 		{
   7765 			m_context.getTestContext().getLog() << tcu::TestLog::Message << "FAILURE. Test case: " << test_name
   7766 												<< ". Compute - invalid results." << tcu::TestLog::EndMessage
   7767 												<< tcu::TestLog::KernelSource(compute_shader);
   7768 
   7769 			result = false;
   7770 		}
   7771 	}
   7772 
   7773 	return result;
   7774 }
   7775 
   7776 /** Basic implementation
   7777  *
   7778  * @param ignored
   7779  *
   7780  * @return false
   7781  **/
   7782 bool TextureTestBase::useComponentQualifier(glw::GLuint /* test_case_index */)
   7783 {
   7784 	return false;
   7785 }
   7786 
   7787 /** Basic implementation
   7788  *
   7789  * @param ignored
   7790  *
   7791  * @return true
   7792  **/
   7793 bool TextureTestBase::useMonolithicProgram(GLuint /* test_case_index */)
   7794 {
   7795 	return true;
   7796 }
   7797 
   7798 /** Constructor
   7799  *
   7800  * @param context Test framework context
   7801  **/
   7802 APIConstantValuesTest::APIConstantValuesTest(deqp::Context& context)
   7803 	: TestCase(context, "api_constant_values", "Test verifies values of api constants")
   7804 {
   7805 	/* Nothing to be done here */
   7806 }
   7807 
   7808 /** Execute test
   7809  *
   7810  * @return tcu::TestNode::STOP otherwise
   7811  **/
   7812 tcu::TestNode::IterateResult APIConstantValuesTest::iterate()
   7813 {
   7814 	static const GLuint expected_comp = 64;
   7815 	static const GLuint expected_xfb  = 4;
   7816 	static const GLuint expected_sep  = 4;
   7817 	GLint				max_comp	  = 0;
   7818 	GLint				max_xfb		  = 0;
   7819 	GLint				max_sep		  = 0;
   7820 	bool				test_result   = true;
   7821 
   7822 	const Functions& gl = m_context.getRenderContext().getFunctions();
   7823 
   7824 	gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_BUFFERS, &max_xfb);
   7825 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   7826 	gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS, &max_comp);
   7827 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   7828 	gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS, &max_sep);
   7829 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   7830 
   7831 	if (expected_xfb > (GLuint)max_xfb)
   7832 	{
   7833 		m_context.getTestContext().getLog() << tcu::TestLog::Message
   7834 											<< "Invalid GL_MAX_TRANSFORM_FEEDBACK_BUFFERS. Got " << max_xfb
   7835 											<< " Expected at least " << expected_xfb << tcu::TestLog::EndMessage;
   7836 
   7837 		test_result = false;
   7838 	}
   7839 
   7840 	if (expected_comp > (GLuint)max_comp)
   7841 	{
   7842 		m_context.getTestContext().getLog()
   7843 			<< tcu::TestLog::Message << "Invalid GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS. Got " << max_comp
   7844 			<< " Expected at least " << expected_comp << tcu::TestLog::EndMessage;
   7845 
   7846 		test_result = false;
   7847 	}
   7848 
   7849 	if (expected_sep > (GLuint)max_sep)
   7850 	{
   7851 		m_context.getTestContext().getLog() << tcu::TestLog::Message
   7852 											<< "Invalid GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS. Got " << max_comp
   7853 											<< " Expected at least " << expected_comp << tcu::TestLog::EndMessage;
   7854 
   7855 		test_result = false;
   7856 	}
   7857 
   7858 	/* Set result */
   7859 	if (true == test_result)
   7860 	{
   7861 		m_context.getTestContext().setTestResult(QP_TEST_RESULT_PASS, "Pass");
   7862 	}
   7863 	else
   7864 	{
   7865 		m_context.getTestContext().setTestResult(QP_TEST_RESULT_FAIL, "Fail");
   7866 	}
   7867 
   7868 	/* Done */
   7869 	return tcu::TestNode::STOP;
   7870 }
   7871 
   7872 /** Constructor
   7873  *
   7874  * @param context Test framework context
   7875  **/
   7876 APIErrorsTest::APIErrorsTest(deqp::Context& context)
   7877 	: TestCase(context, "api_errors", "Test verifies errors reeturned by api")
   7878 {
   7879 	/* Nothing to be done here */
   7880 }
   7881 
   7882 /** Execute test
   7883  *
   7884  * @return tcu::TestNode::STOP otherwise
   7885  **/
   7886 tcu::TestNode::IterateResult APIErrorsTest::iterate()
   7887 {
   7888 	GLint		   length = 0;
   7889 	GLchar		   name[64];
   7890 	GLint		   param = 0;
   7891 	Utils::Program program(m_context);
   7892 	bool		   test_result = true;
   7893 
   7894 	const Functions& gl = m_context.getRenderContext().getFunctions();
   7895 
   7896 	try
   7897 	{
   7898 		program.Init("" /* cs */, "#version 430 core\n"
   7899 								  "#extension GL_ARB_enhanced_layouts : require\n"
   7900 								  "\n"
   7901 								  "in  vec4 vs_fs;\n"
   7902 								  "out vec4 fs_out;\n"
   7903 								  "\n"
   7904 								  "void main()\n"
   7905 								  "{\n"
   7906 								  "    fs_out = vs_fs;\n"
   7907 								  "}\n"
   7908 								  "\n" /* fs */,
   7909 					 "" /* gs */, "" /* tcs */, "" /* tes */, "#version 430 core\n"
   7910 															  "#extension GL_ARB_enhanced_layouts : require\n"
   7911 															  "\n"
   7912 															  "in  vec4 in_vs;\n"
   7913 															  "layout (xfb_offset = 16) out vec4 vs_fs;\n"
   7914 															  "\n"
   7915 															  "void main()\n"
   7916 															  "{\n"
   7917 															  "    vs_fs = in_vs;\n"
   7918 															  "}\n"
   7919 															  "\n" /* vs */,
   7920 					 false /* separable */);
   7921 	}
   7922 	catch (Utils::Shader::InvalidSourceException& exc)
   7923 	{
   7924 		exc.log(m_context);
   7925 		TCU_FAIL(exc.what());
   7926 	}
   7927 	catch (Utils::Program::BuildException& exc)
   7928 	{
   7929 		TCU_FAIL(exc.what());
   7930 	}
   7931 
   7932 	/*
   7933 	 * - GetProgramInterfaceiv should generate INVALID_OPERATION when
   7934 	 * <programInterface> is TRANSFORM_FEEDBACK_BUFFER and <pname> is one of the
   7935 	 * following:
   7936 	 *   * MAX_NAME_LENGTH,
   7937 	 *   * MAX_NUM_ACTIVE_VARIABLES;
   7938 	 */
   7939 	gl.getProgramInterfaceiv(program.m_id, GL_TRANSFORM_FEEDBACK_BUFFER, GL_MAX_NAME_LENGTH, &param);
   7940 	checkError(GL_INVALID_OPERATION, "GetProgramInterfaceiv(GL_TRANSFORM_FEEDBACK_BUFFER, GL_MAX_NAME_LENGTH)",
   7941 			   test_result);
   7942 
   7943 	/*
   7944 	 * - GetProgramResourceIndex should generate INVALID_ENUM when
   7945 	 * <programInterface> is TRANSFORM_FEEDBACK_BUFFER;
   7946 	 */
   7947 	gl.getProgramResourceIndex(program.m_id, GL_TRANSFORM_FEEDBACK_BUFFER, "0");
   7948 	checkError(GL_INVALID_ENUM, "GetProgramResourceIndex(GL_TRANSFORM_FEEDBACK_BUFFER)", test_result);
   7949 	/*
   7950 	 * - GetProgramResourceName should generate INVALID_ENUM when
   7951 	 * <programInterface> is TRANSFORM_FEEDBACK_BUFFER;
   7952 	 */
   7953 	gl.getProgramResourceName(program.m_id, GL_TRANSFORM_FEEDBACK_BUFFER, 0 /* index */, 64 /* bufSize */, &length,
   7954 							  name);
   7955 	checkError(GL_INVALID_ENUM, "GetProgramResourceName(GL_TRANSFORM_FEEDBACK_BUFFER)", test_result);
   7956 
   7957 	/* Set result */
   7958 	if (true == test_result)
   7959 	{
   7960 		m_context.getTestContext().setTestResult(QP_TEST_RESULT_PASS, "Pass");
   7961 	}
   7962 	else
   7963 	{
   7964 		m_context.getTestContext().setTestResult(QP_TEST_RESULT_FAIL, "Fail");
   7965 	}
   7966 
   7967 	/* Done */
   7968 	return tcu::TestNode::STOP;
   7969 }
   7970 
   7971 /** Check if error is the expected one.
   7972  *
   7973  * @param expected_error Expected error
   7974  * @param message        Message to log in case of error
   7975  * @param test_result    Test result, set to false in case of invalid error
   7976  **/
   7977 void APIErrorsTest::checkError(GLenum expected_error, const GLchar* message, bool& test_result)
   7978 {
   7979 	const Functions& gl = m_context.getRenderContext().getFunctions();
   7980 
   7981 	GLenum error = gl.getError();
   7982 
   7983 	if (error != expected_error)
   7984 	{
   7985 		m_context.getTestContext().getLog()
   7986 			<< tcu::TestLog::Message << "Failure. Invalid error. Got " << glu::getErrorStr(error) << " expected "
   7987 			<< glu::getErrorStr(expected_error) << " Msg: " << message << tcu::TestLog::EndMessage;
   7988 
   7989 		test_result = false;
   7990 	}
   7991 }
   7992 
   7993 /** Constructor
   7994  *
   7995  * @param context Test framework context
   7996  **/
   7997 GLSLContantImmutablityTest::GLSLContantImmutablityTest(deqp::Context& context)
   7998 	: NegativeTestBase(context, "glsl_contant_immutablity", "Test verifies that glsl constants cannot be modified")
   7999 {
   8000 	/* Nothing to be done here */
   8001 }
   8002 
   8003 /** Source for given test case and stage
   8004  *
   8005  * @param test_case_index Index of test case
   8006  * @param stage           Shader stage
   8007  *
   8008  * @return Shader source
   8009  **/
   8010 std::string GLSLContantImmutablityTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   8011 {
   8012 	static const GLchar* cs = "#version 430 core\n"
   8013 							  "#extension GL_ARB_enhanced_layouts : require\n"
   8014 							  "\n"
   8015 							  "layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
   8016 							  "\n"
   8017 							  "writeonly uniform uimage2D uni_image;\n"
   8018 							  "\n"
   8019 							  "void main()\n"
   8020 							  "{\n"
   8021 							  "    uint result = 1u;\n"
   8022 							  "    CONSTANT = 3;\n"
   8023 							  "\n"
   8024 							  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), uvec4(result, 0, 0, 0));\n"
   8025 							  "}\n"
   8026 							  "\n";
   8027 	static const GLchar* fs = "#version 430 core\n"
   8028 							  "#extension GL_ARB_enhanced_layouts : require\n"
   8029 							  "\n"
   8030 							  "in  vec4 gs_fs;\n"
   8031 							  "out vec4 fs_out;\n"
   8032 							  "\n"
   8033 							  "void main()\n"
   8034 							  "{\n"
   8035 							  "ASSIGNMENT"
   8036 							  "    fs_out = gs_fs;\n"
   8037 							  "}\n"
   8038 							  "\n";
   8039 	static const GLchar* gs = "#version 430 core\n"
   8040 							  "#extension GL_ARB_enhanced_layouts : require\n"
   8041 							  "\n"
   8042 							  "layout(points)                           in;\n"
   8043 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   8044 							  "\n"
   8045 							  "in  vec4 tes_gs[];\n"
   8046 							  "out vec4 gs_fs;\n"
   8047 							  "\n"
   8048 							  "void main()\n"
   8049 							  "{\n"
   8050 							  "ASSIGNMENT"
   8051 							  "    gs_fs = tes_gs[0];\n"
   8052 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   8053 							  "    EmitVertex();\n"
   8054 							  "    gs_fs = tes_gs[0];\n"
   8055 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   8056 							  "    EmitVertex();\n"
   8057 							  "    gs_fs = tes_gs[0];\n"
   8058 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   8059 							  "    EmitVertex();\n"
   8060 							  "    gs_fs = tes_gs[0];\n"
   8061 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   8062 							  "    EmitVertex();\n"
   8063 							  "}\n"
   8064 							  "\n";
   8065 	static const GLchar* tcs = "#version 430 core\n"
   8066 							   "#extension GL_ARB_enhanced_layouts : require\n"
   8067 							   "\n"
   8068 							   "layout(vertices = 1) out;\n"
   8069 							   "\n"
   8070 							   "in  vec4 vs_tcs[];\n"
   8071 							   "out vec4 tcs_tes[];\n"
   8072 							   "\n"
   8073 							   "void main()\n"
   8074 							   "{\n"
   8075 							   "\n"
   8076 							   "ASSIGNMENT"
   8077 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   8078 							   "\n"
   8079 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   8080 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   8081 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   8082 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   8083 							   "    gl_TessLevelInner[0] = 1.0;\n"
   8084 							   "    gl_TessLevelInner[1] = 1.0;\n"
   8085 							   "}\n"
   8086 							   "\n";
   8087 	static const GLchar* tes = "#version 430 core\n"
   8088 							   "#extension GL_ARB_enhanced_layouts : require\n"
   8089 							   "\n"
   8090 							   "layout(isolines, point_mode) in;\n"
   8091 							   "\n"
   8092 							   "in  vec4 tcs_tes[];\n"
   8093 							   "out vec4 tes_gs;\n"
   8094 							   "\n"
   8095 							   "void main()\n"
   8096 							   "{\n"
   8097 							   "ASSIGNMENT"
   8098 							   "    tes_gs = tcs_tes[0];\n"
   8099 							   "}\n"
   8100 							   "\n";
   8101 	static const GLchar* vs = "#version 430 core\n"
   8102 							  "#extension GL_ARB_enhanced_layouts : require\n"
   8103 							  "\n"
   8104 							  "in  vec4 in_vs;\n"
   8105 							  "out vec4 vs_tcs;\n"
   8106 							  "\n"
   8107 							  "void main()\n"
   8108 							  "{\n"
   8109 							  "ASSIGNMENT"
   8110 							  "    vs_tcs = in_vs;\n"
   8111 							  "}\n"
   8112 							  "\n";
   8113 
   8114 	std::string source;
   8115 	testCase&   test_case = m_test_cases[test_case_index];
   8116 
   8117 	if (Utils::Shader::COMPUTE == test_case.m_stage)
   8118 	{
   8119 		size_t position = 0;
   8120 
   8121 		source = cs;
   8122 
   8123 		Utils::replaceToken("CONSTANT", position, getConstantName(test_case.m_constant), source);
   8124 	}
   8125 	else
   8126 	{
   8127 		std::string assignment = "    CONSTANT = 3;\n";
   8128 		size_t		position   = 0;
   8129 
   8130 		switch (stage)
   8131 		{
   8132 		case Utils::Shader::FRAGMENT:
   8133 			source = fs;
   8134 			break;
   8135 		case Utils::Shader::GEOMETRY:
   8136 			source = gs;
   8137 			break;
   8138 		case Utils::Shader::TESS_CTRL:
   8139 			source = tcs;
   8140 			break;
   8141 		case Utils::Shader::TESS_EVAL:
   8142 			source = tes;
   8143 			break;
   8144 		case Utils::Shader::VERTEX:
   8145 			source = vs;
   8146 			break;
   8147 		default:
   8148 			TCU_FAIL("Invalid enum");
   8149 		}
   8150 
   8151 		if (test_case.m_stage == stage)
   8152 		{
   8153 			Utils::replaceToken("CONSTANT", position, getConstantName(test_case.m_constant), assignment);
   8154 		}
   8155 		else
   8156 		{
   8157 			assignment = "";
   8158 		}
   8159 
   8160 		position = 0;
   8161 		Utils::replaceToken("ASSIGNMENT", position, assignment.c_str(), source);
   8162 	}
   8163 
   8164 	return source;
   8165 }
   8166 
   8167 /** Get description of test case
   8168  *
   8169  * @param test_case_index Index of test case
   8170  *
   8171  * @return Constant name
   8172  **/
   8173 std::string GLSLContantImmutablityTest::getTestCaseName(GLuint test_case_index)
   8174 {
   8175 	std::string result = getConstantName(m_test_cases[test_case_index].m_constant);
   8176 
   8177 	return result;
   8178 }
   8179 
   8180 /** Get number of test cases
   8181  *
   8182  * @return Number of test cases
   8183  **/
   8184 GLuint GLSLContantImmutablityTest::getTestCaseNumber()
   8185 {
   8186 	return static_cast<GLuint>(m_test_cases.size());
   8187 }
   8188 
   8189 /** Selects if "compute" stage is relevant for test
   8190  *
   8191  * @param test_case_index Index of test case
   8192  *
   8193  * @return true when tested stage is compute
   8194  **/
   8195 bool GLSLContantImmutablityTest::isComputeRelevant(GLuint test_case_index)
   8196 {
   8197 	return (Utils::Shader::COMPUTE == m_test_cases[test_case_index].m_stage);
   8198 }
   8199 
   8200 /** Prepare all test cases
   8201  *
   8202  **/
   8203 void GLSLContantImmutablityTest::testInit()
   8204 {
   8205 	for (GLuint constant = 0; constant < CONSTANTS_MAX; ++constant)
   8206 	{
   8207 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   8208 		{
   8209 			testCase test_case = { (CONSTANTS)constant, (Utils::Shader::STAGES)stage };
   8210 
   8211 			m_test_cases.push_back(test_case);
   8212 		}
   8213 	}
   8214 }
   8215 
   8216 /** Get name of glsl constant
   8217  *
   8218  * @param Constant id
   8219  *
   8220  * @return Name of constant used in GLSL
   8221  **/
   8222 const GLchar* GLSLContantImmutablityTest::getConstantName(CONSTANTS constant)
   8223 {
   8224 	const GLchar* name = "";
   8225 
   8226 	switch (constant)
   8227 	{
   8228 	case GL_ARB_ENHANCED_LAYOUTS:
   8229 		name = "GL_ARB_enhanced_layouts";
   8230 		break;
   8231 	case GL_MAX_XFB:
   8232 		name = "gl_MaxTransformFeedbackBuffers";
   8233 		break;
   8234 	case GL_MAX_XFB_INT_COMP:
   8235 		name = "gl_MaxTransformFeedbackInterleavedComponents";
   8236 		break;
   8237 	default:
   8238 		TCU_FAIL("Invalid enum");
   8239 	}
   8240 
   8241 	return name;
   8242 }
   8243 
   8244 /** Constructor
   8245  *
   8246  * @param context Test framework context
   8247  **/
   8248 GLSLContantValuesTest::GLSLContantValuesTest(deqp::Context& context)
   8249 	: TextureTestBase(context, "glsl_contant_values", "Test verifies values of constant symbols")
   8250 {
   8251 }
   8252 
   8253 /** Selects if "compute" stage is relevant for test
   8254  *
   8255  * @param ignored
   8256  *
   8257  * @return false
   8258  **/
   8259 bool GLSLContantValuesTest::isComputeRelevant(GLuint /* test_case_index */)
   8260 {
   8261 	return false;
   8262 }
   8263 
   8264 /** Prepare code snippet that will verify in and uniform variables
   8265  *
   8266  * @param ignored
   8267  * @param ignored
   8268  * @param stage   Shader stage
   8269  *
   8270  * @return Code that verify variables
   8271  **/
   8272 std::string GLSLContantValuesTest::getVerificationSnippet(GLuint /* test_case_index */,
   8273 														  Utils::ProgramInterface& /* program_interface */,
   8274 														  Utils::Shader::STAGES stage)
   8275 {
   8276 	/* Get constants */
   8277 	const Functions& gl = m_context.getRenderContext().getFunctions();
   8278 
   8279 	GLint max_transform_feedback_buffers				= 0;
   8280 	GLint max_transform_feedback_interleaved_components = 0;
   8281 
   8282 	gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_BUFFERS, &max_transform_feedback_buffers);
   8283 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   8284 	gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS, &max_transform_feedback_interleaved_components);
   8285 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   8286 
   8287 	std::string verification;
   8288 
   8289 	if (Utils::Shader::VERTEX == stage)
   8290 	{
   8291 		verification = "if (1 != GL_ARB_enhanced_layouts)\n"
   8292 					   "    {\n"
   8293 					   "        result = 0;\n"
   8294 					   "    }\n"
   8295 					   "    else if (MAX_TRANSFORM_FEEDBACK_BUFFERS\n"
   8296 					   "        != gl_MaxTransformFeedbackBuffers)\n"
   8297 					   "    {\n"
   8298 					   "        result = 0;\n"
   8299 					   "    }\n"
   8300 					   "    else if (MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS \n"
   8301 					   "        != gl_MaxTransformFeedbackInterleavedComponents)\n"
   8302 					   "    {\n"
   8303 					   "        result = 0;\n"
   8304 					   "    }\n";
   8305 
   8306 		size_t position = 0;
   8307 		GLchar buffer[16];
   8308 
   8309 		sprintf(buffer, "%d", max_transform_feedback_buffers);
   8310 		Utils::replaceToken("MAX_TRANSFORM_FEEDBACK_BUFFERS", position, buffer, verification);
   8311 
   8312 		sprintf(buffer, "%d", max_transform_feedback_interleaved_components);
   8313 		Utils::replaceToken("MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS", position, buffer, verification);
   8314 	}
   8315 	else
   8316 	{
   8317 		verification = "";
   8318 	}
   8319 
   8320 	return verification;
   8321 }
   8322 
   8323 /** Constructor
   8324  *
   8325  * @param context Test framework context
   8326  **/
   8327 GLSLConstantIntegralExpressionTest::GLSLConstantIntegralExpressionTest(deqp::Context& context)
   8328 	: TextureTestBase(context, "glsl_constant_integral_expression",
   8329 					  "Test verifies that symbols can be used as constant integral expressions")
   8330 {
   8331 }
   8332 
   8333 /** Get interface of program
   8334  *
   8335  * @param ignored
   8336  * @param program_interface Interface of program
   8337  * @param ignored
   8338  **/
   8339 void GLSLConstantIntegralExpressionTest::getProgramInterface(GLuint /* test_case_index */,
   8340 															 Utils::ProgramInterface& program_interface,
   8341 															 Utils::VaryingPassthrough& /* varying_passthrough */)
   8342 {
   8343 	/* Get constants */
   8344 	const Functions& gl = m_context.getRenderContext().getFunctions();
   8345 
   8346 	GLint max_transform_feedback_buffers				= 0;
   8347 	GLint max_transform_feedback_interleaved_components = 0;
   8348 
   8349 	gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_BUFFERS, &max_transform_feedback_buffers);
   8350 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   8351 	gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS, &max_transform_feedback_interleaved_components);
   8352 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   8353 
   8354 	GLuint gohan_div = std::max(1, max_transform_feedback_buffers / 16);
   8355 	GLuint goten_div = std::max(1, max_transform_feedback_interleaved_components / 16);
   8356 
   8357 	m_gohan_length = max_transform_feedback_buffers / gohan_div;
   8358 	m_goten_length = max_transform_feedback_interleaved_components / goten_div;
   8359 
   8360 	/* Globals */
   8361 	std::string globals = "uniform uint goku [GL_ARB_enhanced_layouts / 1];\n"
   8362 						  "uniform uint gohan[gl_MaxTransformFeedbackBuffers / GOHAN_DIV];\n"
   8363 						  "uniform uint goten[gl_MaxTransformFeedbackInterleavedComponents / GOTEN_DIV];\n";
   8364 
   8365 	size_t position = 0;
   8366 	GLchar buffer[16];
   8367 
   8368 	sprintf(buffer, "%d", gohan_div);
   8369 	Utils::replaceToken("GOHAN_DIV", position, buffer, globals);
   8370 
   8371 	sprintf(buffer, "%d", goten_div);
   8372 	Utils::replaceToken("GOTEN_DIV", position, buffer, globals);
   8373 
   8374 	program_interface.m_vertex.m_globals	= globals;
   8375 	program_interface.m_tess_ctrl.m_globals = globals;
   8376 	program_interface.m_tess_eval.m_globals = globals;
   8377 	program_interface.m_geometry.m_globals  = globals;
   8378 	program_interface.m_fragment.m_globals  = globals;
   8379 	program_interface.m_compute.m_globals   = globals;
   8380 }
   8381 
   8382 /** Prepare code snippet that will verify in and uniform variables
   8383  *
   8384  * @param ignored
   8385  * @param ignored
   8386  * @param ignored
   8387  *
   8388  * @return Code that verify variables
   8389  **/
   8390 std::string GLSLConstantIntegralExpressionTest::getVerificationSnippet(GLuint /* test_case_index */,
   8391 																	   Utils::ProgramInterface& /* program_interface */,
   8392 																	   Utils::Shader::STAGES /* stage */)
   8393 {
   8394 	std::string verification = "{\n"
   8395 							   "        uint goku_sum = 0;\n"
   8396 							   "        uint gohan_sum = 0;\n"
   8397 							   "        uint goten_sum = 0;\n"
   8398 							   "\n"
   8399 							   "        for (uint i = 0u; i < goku.length(); ++i)\n"
   8400 							   "        {\n"
   8401 							   "            goku_sum += goku[i];\n"
   8402 							   "        }\n"
   8403 							   "\n"
   8404 							   "        for (uint i = 0u; i < gohan.length(); ++i)\n"
   8405 							   "        {\n"
   8406 							   "            gohan_sum += gohan[i];\n"
   8407 							   "        }\n"
   8408 							   "\n"
   8409 							   "        for (uint i = 0u; i < goten.length(); ++i)\n"
   8410 							   "        {\n"
   8411 							   "            goten_sum += goten[i];\n"
   8412 							   "        }\n"
   8413 							   "\n"
   8414 							   "        if ( (1u != goku_sum)  &&\n"
   8415 							   "             (EXPECTED_GOHAN_SUMu != gohan_sum) ||\n"
   8416 							   "             (EXPECTED_GOTEN_SUMu != goten_sum) )\n"
   8417 							   "        {\n"
   8418 							   "            result = 0u;\n"
   8419 							   "        }\n"
   8420 							   "    }\n";
   8421 
   8422 	size_t position = 0;
   8423 	GLchar buffer[16];
   8424 
   8425 	sprintf(buffer, "%d", m_gohan_length);
   8426 	Utils::replaceToken("EXPECTED_GOHAN_SUM", position, buffer, verification);
   8427 
   8428 	sprintf(buffer, "%d", m_goten_length);
   8429 	Utils::replaceToken("EXPECTED_GOTEN_SUM", position, buffer, verification);
   8430 
   8431 	return verification;
   8432 }
   8433 
   8434 /** Prepare unifroms
   8435  *
   8436  * @param ignored
   8437  * @param ignored
   8438  * @param program Program object
   8439  * @param ignored
   8440  **/
   8441 void GLSLConstantIntegralExpressionTest::prepareUniforms(GLuint /* test_case_index */,
   8442 														 Utils::ProgramInterface& /* program_interface */,
   8443 														 Utils::Program& program, Utils::Buffer& /* cs_buffer */)
   8444 {
   8445 	static const GLuint uniform_data[16] = { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 };
   8446 
   8447 	const Functions& gl = m_context.getRenderContext().getFunctions();
   8448 
   8449 	GLint goku_location  = program.GetUniformLocation("goku");
   8450 	GLint gohan_location = program.GetUniformLocation("gohan");
   8451 	GLint goten_location = program.GetUniformLocation("goten");
   8452 
   8453 	program.Uniform(gl, Utils::Type::uint, 1 /* count */, goku_location, uniform_data);
   8454 	program.Uniform(gl, Utils::Type::uint, m_gohan_length, gohan_location, uniform_data);
   8455 	program.Uniform(gl, Utils::Type::uint, m_goten_length, goten_location, uniform_data);
   8456 }
   8457 
   8458 /** Prepare unifroms
   8459  *
   8460  * @param test_case_index   Pass as param to first implemetnation
   8461  * @param program_interface Pass as param to first implemetnation
   8462  * @param program           Pass as param to first implemetnation
   8463  * @param ignored
   8464  * @param ignored
   8465  * @param ignored
   8466  * @param ignored
   8467  * @param vs_buffer         Pass as param to first implemetnation
   8468  **/
   8469 void GLSLConstantIntegralExpressionTest::prepareUniforms(GLuint					  test_case_index,
   8470 														 Utils::ProgramInterface& program_interface,
   8471 														 Utils::Program& program, Utils::Buffer& /* fs_buffer */,
   8472 														 Utils::Buffer& /* gs_buffer */,
   8473 														 Utils::Buffer& /* tcs_buffer */,
   8474 														 Utils::Buffer& /* tes_buffer */, Utils::Buffer& vs_buffer)
   8475 {
   8476 	/* Call first implementation */
   8477 	prepareUniforms(test_case_index, program_interface, program, vs_buffer);
   8478 }
   8479 
   8480 /** Constructor
   8481  *
   8482  * @param context Test framework context
   8483  **/
   8484 UniformBlockMemberOffsetAndAlignTest::UniformBlockMemberOffsetAndAlignTest(deqp::Context& context)
   8485 	: TextureTestBase(context, "uniform_block_member_offset_and_align",
   8486 					  "Test verifies offsets and alignment of uniform buffer members")
   8487 {
   8488 }
   8489 
   8490 /** Get interface of program
   8491  *
   8492  * @param test_case_index     Test case index
   8493  * @param program_interface   Interface of program
   8494  * @param varying_passthrough Collection of connections between in and out variables
   8495  **/
   8496 void UniformBlockMemberOffsetAndAlignTest::getProgramInterface(GLuint					  test_case_index,
   8497 															   Utils::ProgramInterface&   program_interface,
   8498 															   Utils::VaryingPassthrough& varying_passthrough)
   8499 {
   8500 	std::string globals = "const int basic_size = BASIC_SIZE;\n"
   8501 						  "const int type_align = TYPE_ALIGN;\n"
   8502 						  "const int type_size  = TYPE_SIZE;\n";
   8503 
   8504 	Utils::Type  type		 = getType(test_case_index);
   8505 	GLuint		 basic_size  = Utils::Type::GetTypeSize(type.m_basic_type);
   8506 	const GLuint base_align  = type.GetBaseAlignment(false);
   8507 	const GLuint array_align = type.GetBaseAlignment(true);
   8508 	const GLuint base_stride = Utils::Type::CalculateStd140Stride(base_align, type.m_n_columns, 0);
   8509 	const GLuint type_align  = Utils::roundUpToPowerOf2(base_stride);
   8510 
   8511 	/* Calculate offsets */
   8512 	const GLuint first_offset  = 0;
   8513 	const GLuint second_offset = type.GetActualOffset(base_stride, basic_size / 2);
   8514 
   8515 #if WRKARD_UNIFORMBLOCKMEMBEROFFSETANDALIGNTEST
   8516 
   8517 	const GLuint third_offset   = type.GetActualOffset(second_offset + base_stride, base_align);
   8518 	const GLuint fourth_offset  = type.GetActualOffset(third_offset + base_stride, base_align);
   8519 	const GLuint fifth_offset   = type.GetActualOffset(fourth_offset + base_stride, base_align);
   8520 	const GLuint sixth_offset   = type.GetActualOffset(fifth_offset + base_stride, array_align);
   8521 	const GLuint seventh_offset = type.GetActualOffset(sixth_offset + base_stride, array_align);
   8522 	const GLuint eigth_offset   = type.GetActualOffset(seventh_offset + base_stride, array_align);
   8523 
   8524 #else /* WRKARD_UNIFORMBLOCKMEMBEROFFSETANDALIGNTEST */
   8525 
   8526 	const GLuint third_offset   = type.GetActualOffset(second_offset + base_stride, 2 * type_align);
   8527 	const GLuint fourth_offset  = type.GetActualOffset(3 * type_align + base_stride, base_align);
   8528 	const GLuint fifth_offset   = type.GetActualOffset(fourth_offset + base_stride, base_align);
   8529 	const GLuint sixth_offset   = type.GetActualOffset(fifth_offset + base_stride, array_align);
   8530 	const GLuint seventh_offset = type.GetActualOffset(sixth_offset + base_stride, array_align);
   8531 	const GLuint eigth_offset   = type.GetActualOffset(seventh_offset + base_stride, 8 * basic_size);
   8532 
   8533 #endif /* WRKARD_UNIFORMBLOCKMEMBEROFFSETANDALIGNTEST */
   8534 
   8535 	/* Prepare data */
   8536 	const std::vector<GLubyte>& first  = type.GenerateData();
   8537 	const std::vector<GLubyte>& second = type.GenerateData();
   8538 	const std::vector<GLubyte>& third  = type.GenerateData();
   8539 	const std::vector<GLubyte>& fourth = type.GenerateData();
   8540 
   8541 	m_data.resize(eigth_offset + base_stride);
   8542 	GLubyte* ptr = &m_data[0];
   8543 	memcpy(ptr + first_offset, &first[0], first.size());
   8544 	memcpy(ptr + second_offset, &second[0], second.size());
   8545 	memcpy(ptr + third_offset, &third[0], third.size());
   8546 	memcpy(ptr + fourth_offset, &fourth[0], fourth.size());
   8547 	memcpy(ptr + fifth_offset, &fourth[0], fourth.size());
   8548 	memcpy(ptr + sixth_offset, &third[0], third.size());
   8549 	memcpy(ptr + seventh_offset, &second[0], second.size());
   8550 	memcpy(ptr + eigth_offset, &first[0], first.size());
   8551 
   8552 	/* Prepare globals */
   8553 	size_t position = 0;
   8554 	GLchar buffer[16];
   8555 
   8556 	sprintf(buffer, "%d", basic_size);
   8557 	Utils::replaceToken("BASIC_SIZE", position, buffer, globals);
   8558 
   8559 	sprintf(buffer, "%d", type_align);
   8560 	Utils::replaceToken("TYPE_ALIGN", position, buffer, globals);
   8561 
   8562 	sprintf(buffer, "%d", base_stride);
   8563 	Utils::replaceToken("TYPE_SIZE", position, buffer, globals);
   8564 
   8565 	/* Prepare Block */
   8566 	Utils::Interface* vs_uni_block = program_interface.Block("vs_uni_Block");
   8567 
   8568 	vs_uni_block->Member("at_first_offset", "layout(offset = 0, align = 8 * basic_size)", 0 /* expected_component */,
   8569 						 0 /* expected_location */, type, false /* normalized */, 0 /* n_array_elements */, base_stride,
   8570 						 first_offset);
   8571 
   8572 	vs_uni_block->Member("at_second_offset", "layout(offset = type_size, align = basic_size / 2)",
   8573 						 0 /* expected_component */, 0 /* expected_location */, type, false /* normalized */,
   8574 						 0 /* n_array_elements */, base_stride, second_offset);
   8575 
   8576 	vs_uni_block->Member("at_third_offset", "layout(align = 2 * type_align)", 0 /* expected_component */,
   8577 						 0 /* expected_location */, type, false /* normalized */, 0 /* n_array_elements */, base_stride,
   8578 						 third_offset);
   8579 
   8580 	vs_uni_block->Member("at_fourth_offset", "layout(offset = 3 * type_align + type_size)", 0 /* expected_component */,
   8581 						 0 /* expected_location */, type, false /* normalized */, 0 /* n_array_elements */, base_stride,
   8582 						 fourth_offset);
   8583 
   8584 	vs_uni_block->Member("at_fifth_offset", "", 0 /* expected_component */, 0 /* expected_location */, type,
   8585 						 false /* normalized */, 0 /* n_array_elements */, base_stride, fifth_offset);
   8586 
   8587 	vs_uni_block->Member("at_sixth_offset", "", 0 /* expected_component */, 0 /* expected_location */, type,
   8588 						 false /* normalized */, 2 /* n_array_elements */, array_align * 2, sixth_offset);
   8589 
   8590 	vs_uni_block->Member("at_eigth_offset", "layout(align = 8 * basic_size)", 0 /* expected_component */,
   8591 						 0 /* expected_location */, type, false /* normalized */, 0 /* n_array_elements */, base_stride,
   8592 						 eigth_offset);
   8593 
   8594 	Utils::ShaderInterface& vs_si = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   8595 
   8596 	/* Add globals */
   8597 	vs_si.m_globals = globals;
   8598 
   8599 	/* Add uniform BLOCK */
   8600 	vs_si.Uniform("vs_uni_block", "layout (std140, binding = BINDING)", 0, 0, vs_uni_block, 0,
   8601 				  static_cast<glw::GLint>(m_data.size()), 0, &m_data[0], m_data.size());
   8602 
   8603 	/* */
   8604 	program_interface.CloneVertexInterface(varying_passthrough);
   8605 }
   8606 
   8607 /** Get type name
   8608  *
   8609  * @param test_case_index Index of test case
   8610  *
   8611  * @return Name of type test in test_case_index
   8612  **/
   8613 std::string UniformBlockMemberOffsetAndAlignTest::getTestCaseName(glw::GLuint test_case_index)
   8614 {
   8615 	return getTypeName(test_case_index);
   8616 }
   8617 
   8618 /** Returns number of types to test
   8619  *
   8620  * @return Number of types, 34
   8621  **/
   8622 glw::GLuint UniformBlockMemberOffsetAndAlignTest::getTestCaseNumber()
   8623 {
   8624 	return getTypesNumber();
   8625 }
   8626 
   8627 /** Prepare code snippet that will verify in and uniform variables
   8628  *
   8629  * @param ignored
   8630  * @param ignored
   8631  * @param stage   Shader stage
   8632  *
   8633  * @return Code that verify variables
   8634  **/
   8635 std::string UniformBlockMemberOffsetAndAlignTest::getVerificationSnippet(
   8636 	GLuint /* test_case_index */, Utils::ProgramInterface& /* program_interface */, Utils::Shader::STAGES stage)
   8637 {
   8638 	std::string verification = "if ( (PREFIXblock.at_first_offset  != PREFIXblock.at_eigth_offset   ) ||\n"
   8639 							   "         (PREFIXblock.at_second_offset != PREFIXblock.at_sixth_offset[1]) ||\n"
   8640 							   "         (PREFIXblock.at_third_offset  != PREFIXblock.at_sixth_offset[0]) ||\n"
   8641 							   "         (PREFIXblock.at_fourth_offset != PREFIXblock.at_fifth_offset   )  )\n"
   8642 							   "    {\n"
   8643 							   "        result = 0;\n"
   8644 							   "    }";
   8645 
   8646 	const GLchar* prefix = Utils::ProgramInterface::GetStagePrefix(stage, Utils::Variable::UNIFORM);
   8647 
   8648 	Utils::replaceAllTokens("PREFIX", prefix, verification);
   8649 
   8650 	return verification;
   8651 }
   8652 
   8653 /** Constructor
   8654  *
   8655  * @param context Test framework context
   8656  **/
   8657 UniformBlockLayoutQualifierConflictTest::UniformBlockLayoutQualifierConflictTest(deqp::Context& context)
   8658 	: NegativeTestBase(
   8659 		  context, "uniform_block_layout_qualifier_conflict",
   8660 		  "Test verifies that std140 is required when offset and/or align qualifiers are used with uniform block")
   8661 {
   8662 	/* Nothing to be done here */
   8663 }
   8664 
   8665 /** Source for given test case and stage
   8666  *
   8667  * @param test_case_index Index of test case
   8668  * @param stage           Shader stage
   8669  *
   8670  * @return Shader source
   8671  **/
   8672 std::string UniformBlockLayoutQualifierConflictTest::getShaderSource(GLuint				   test_case_index,
   8673 																	 Utils::Shader::STAGES stage)
   8674 {
   8675 	static const GLchar* cs = "#version 430 core\n"
   8676 							  "#extension GL_ARB_enhanced_layouts : require\n"
   8677 							  "\n"
   8678 							  "layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
   8679 							  "\n"
   8680 							  "LAYOUTuniform Block {\n"
   8681 							  "    layout(offset = 16) vec4 boy;\n"
   8682 							  "    layout(align  = 64) vec4 man;\n"
   8683 							  "} uni_block;\n"
   8684 							  "\n"
   8685 							  "writeonly uniform image2D uni_image;\n"
   8686 							  "\n"
   8687 							  "void main()\n"
   8688 							  "{\n"
   8689 							  "    vec4 result = uni_block.boy + uni_block.man;\n"
   8690 							  "\n"
   8691 							  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), result);\n"
   8692 							  "}\n"
   8693 							  "\n";
   8694 	static const GLchar* fs = "#version 430 core\n"
   8695 							  "#extension GL_ARB_enhanced_layouts : require\n"
   8696 							  "\n"
   8697 							  "LAYOUTuniform Block {\n"
   8698 							  "    layout(offset = 16) vec4 boy;\n"
   8699 							  "    layout(align  = 64) vec4 man;\n"
   8700 							  "} uni_block;\n"
   8701 							  "\n"
   8702 							  "in  vec4 gs_fs;\n"
   8703 							  "out vec4 fs_out;\n"
   8704 							  "\n"
   8705 							  "void main()\n"
   8706 							  "{\n"
   8707 							  "    fs_out = gs_fs + uni_block.boy + uni_block.man;\n"
   8708 							  "}\n"
   8709 							  "\n";
   8710 	static const GLchar* gs = "#version 430 core\n"
   8711 							  "#extension GL_ARB_enhanced_layouts : require\n"
   8712 							  "\n"
   8713 							  "layout(points)                           in;\n"
   8714 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   8715 							  "\n"
   8716 							  "LAYOUTuniform Block {\n"
   8717 							  "    layout(offset = 16) vec4 boy;\n"
   8718 							  "    layout(align  = 64) vec4 man;\n"
   8719 							  "} uni_block;\n"
   8720 							  "\n"
   8721 							  "in  vec4 tes_gs[];\n"
   8722 							  "out vec4 gs_fs;\n"
   8723 							  "\n"
   8724 							  "void main()\n"
   8725 							  "{\n"
   8726 							  "    gs_fs = tes_gs[0] + uni_block.boy + uni_block.man;\n"
   8727 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   8728 							  "    EmitVertex();\n"
   8729 							  "    gs_fs = tes_gs[0] + uni_block.boy + uni_block.man;\n"
   8730 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   8731 							  "    EmitVertex();\n"
   8732 							  "    gs_fs = tes_gs[0] + uni_block.boy + uni_block.man;\n"
   8733 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   8734 							  "    EmitVertex();\n"
   8735 							  "    gs_fs = tes_gs[0] + uni_block.boy + uni_block.man;\n"
   8736 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   8737 							  "    EmitVertex();\n"
   8738 							  "}\n"
   8739 							  "\n";
   8740 	static const GLchar* tcs =
   8741 		"#version 430 core\n"
   8742 		"#extension GL_ARB_enhanced_layouts : require\n"
   8743 		"\n"
   8744 		"layout(vertices = 1) out;\n"
   8745 		"\n"
   8746 		"LAYOUTuniform Block {\n"
   8747 		"    layout(offset = 16) vec4 boy;\n"
   8748 		"    layout(align  = 64) vec4 man;\n"
   8749 		"} uni_block;\n"
   8750 		"\n"
   8751 		"in  vec4 vs_tcs[];\n"
   8752 		"out vec4 tcs_tes[];\n"
   8753 		"\n"
   8754 		"void main()\n"
   8755 		"{\n"
   8756 		"\n"
   8757 		"    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID] + uni_block.boy + uni_block.man;\n"
   8758 		"\n"
   8759 		"    gl_TessLevelOuter[0] = 1.0;\n"
   8760 		"    gl_TessLevelOuter[1] = 1.0;\n"
   8761 		"    gl_TessLevelOuter[2] = 1.0;\n"
   8762 		"    gl_TessLevelOuter[3] = 1.0;\n"
   8763 		"    gl_TessLevelInner[0] = 1.0;\n"
   8764 		"    gl_TessLevelInner[1] = 1.0;\n"
   8765 		"}\n"
   8766 		"\n";
   8767 	static const GLchar* tes = "#version 430 core\n"
   8768 							   "#extension GL_ARB_enhanced_layouts : require\n"
   8769 							   "\n"
   8770 							   "layout(isolines, point_mode) in;\n"
   8771 							   "\n"
   8772 							   "LAYOUTuniform Block {\n"
   8773 							   "    layout(offset = 16) vec4 boy;\n"
   8774 							   "    layout(align  = 64) vec4 man;\n"
   8775 							   "} uni_block;\n"
   8776 							   "\n"
   8777 							   "in  vec4 tcs_tes[];\n"
   8778 							   "out vec4 tes_gs;\n"
   8779 							   "\n"
   8780 							   "void main()\n"
   8781 							   "{\n"
   8782 							   "    tes_gs = tcs_tes[0] + uni_block.boy + uni_block.man;\n"
   8783 							   "}\n"
   8784 							   "\n";
   8785 	static const GLchar* vs = "#version 430 core\n"
   8786 							  "#extension GL_ARB_enhanced_layouts : require\n"
   8787 							  "\n"
   8788 							  "LAYOUTuniform Block {\n"
   8789 							  "    layout(offset = 16) vec4 boy;\n"
   8790 							  "    layout(align  = 64) vec4 man;\n"
   8791 							  "} uni_block;\n"
   8792 							  "\n"
   8793 							  "in  vec4 in_vs;\n"
   8794 							  "out vec4 vs_tcs;\n"
   8795 							  "\n"
   8796 							  "void main()\n"
   8797 							  "{\n"
   8798 							  "    vs_tcs = in_vs + uni_block.boy + uni_block.man;\n"
   8799 							  "}\n"
   8800 							  "\n";
   8801 
   8802 	std::string   layout	= "";
   8803 	size_t		  position  = 0;
   8804 	testCase&	 test_case = m_test_cases[test_case_index];
   8805 	const GLchar* qualifier = getQualifierName(test_case.m_qualifier);
   8806 	std::string   source;
   8807 
   8808 	if (0 != qualifier[0])
   8809 	{
   8810 		size_t layout_position = 0;
   8811 
   8812 		layout = "layout (QUALIFIER) ";
   8813 
   8814 		Utils::replaceToken("QUALIFIER", layout_position, qualifier, layout);
   8815 	}
   8816 
   8817 	switch (stage)
   8818 	{
   8819 	case Utils::Shader::COMPUTE:
   8820 		source = cs;
   8821 		break;
   8822 	case Utils::Shader::FRAGMENT:
   8823 		source = fs;
   8824 		break;
   8825 	case Utils::Shader::GEOMETRY:
   8826 		source = gs;
   8827 		break;
   8828 	case Utils::Shader::TESS_CTRL:
   8829 		source = tcs;
   8830 		break;
   8831 	case Utils::Shader::TESS_EVAL:
   8832 		source = tes;
   8833 		break;
   8834 	case Utils::Shader::VERTEX:
   8835 		source = vs;
   8836 		break;
   8837 	default:
   8838 		TCU_FAIL("Invalid enum");
   8839 	}
   8840 
   8841 	if (test_case.m_stage == stage)
   8842 	{
   8843 		Utils::replaceToken("LAYOUT", position, layout.c_str(), source);
   8844 	}
   8845 	else
   8846 	{
   8847 		Utils::replaceToken("LAYOUT", position, "layout (std140) ", source);
   8848 	}
   8849 
   8850 	return source;
   8851 }
   8852 
   8853 /** Get description of test case
   8854  *
   8855  * @param test_case_index Index of test case
   8856  *
   8857  * @return Qualifier name
   8858  **/
   8859 std::string UniformBlockLayoutQualifierConflictTest::getTestCaseName(GLuint test_case_index)
   8860 {
   8861 	std::string result = getQualifierName(m_test_cases[test_case_index].m_qualifier);
   8862 
   8863 	return result;
   8864 }
   8865 
   8866 /** Get number of test cases
   8867  *
   8868  * @return Number of test cases
   8869  **/
   8870 GLuint UniformBlockLayoutQualifierConflictTest::getTestCaseNumber()
   8871 {
   8872 	return static_cast<GLuint>(m_test_cases.size());
   8873 }
   8874 
   8875 /** Selects if "compute" stage is relevant for test
   8876  *
   8877  * @param test_case_index Index of test case
   8878  *
   8879  * @return true when tested stage is compute
   8880  **/
   8881 bool UniformBlockLayoutQualifierConflictTest::isComputeRelevant(GLuint test_case_index)
   8882 {
   8883 	return (Utils::Shader::COMPUTE == m_test_cases[test_case_index].m_stage);
   8884 }
   8885 
   8886 /** Selects if compilation failure is expected result
   8887  *
   8888  * @param test_case_index Index of test case
   8889  *
   8890  * @return false for STD140 cases, true otherwise
   8891  **/
   8892 bool UniformBlockLayoutQualifierConflictTest::isFailureExpected(GLuint test_case_index)
   8893 {
   8894 	return (STD140 != m_test_cases[test_case_index].m_qualifier);
   8895 }
   8896 
   8897 /** Prepare all test cases
   8898  *
   8899  **/
   8900 void UniformBlockLayoutQualifierConflictTest::testInit()
   8901 {
   8902 	for (GLuint qualifier = 0; qualifier < QUALIFIERS_MAX; ++qualifier)
   8903 	{
   8904 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   8905 		{
   8906 			testCase test_case = { (QUALIFIERS)qualifier, (Utils::Shader::STAGES)stage };
   8907 
   8908 			m_test_cases.push_back(test_case);
   8909 		}
   8910 	}
   8911 }
   8912 
   8913 /** Get name of glsl constant
   8914  *
   8915  * @param Constant id
   8916  *
   8917  * @return Name of constant used in GLSL
   8918  **/
   8919 const GLchar* UniformBlockLayoutQualifierConflictTest::getQualifierName(QUALIFIERS qualifier)
   8920 {
   8921 	const GLchar* name = "";
   8922 
   8923 	switch (qualifier)
   8924 	{
   8925 	case DEFAULT:
   8926 		name = "";
   8927 		break;
   8928 	case STD140:
   8929 		name = "std140";
   8930 		break;
   8931 	case SHARED:
   8932 		name = "shared";
   8933 		break;
   8934 	case PACKED:
   8935 		name = "packed";
   8936 		break;
   8937 	default:
   8938 		TCU_FAIL("Invalid enum");
   8939 	}
   8940 
   8941 	return name;
   8942 }
   8943 
   8944 /** Constructor
   8945  *
   8946  * @param context Test framework context
   8947  **/
   8948 UniformBlockMemberInvalidOffsetAlignmentTest::UniformBlockMemberInvalidOffsetAlignmentTest(deqp::Context& context)
   8949 	: NegativeTestBase(context, "uniform_block_member_invalid_offset_alignment",
   8950 					   "Test verifies that invalid alignment of offset qualifiers cause compilation failure")
   8951 {
   8952 	/* Nothing to be done here */
   8953 }
   8954 
   8955 /** Constructor
   8956  *
   8957  * @param context     Test framework context
   8958  * @param name        Test name
   8959  * @param description Test description
   8960  **/
   8961 UniformBlockMemberInvalidOffsetAlignmentTest::UniformBlockMemberInvalidOffsetAlignmentTest(
   8962 	deqp::Context& context, const glw::GLchar* name, const glw::GLchar* description)
   8963 	: NegativeTestBase(context, name, description)
   8964 {
   8965 	/* Nothing to be done here */
   8966 }
   8967 
   8968 /** Source for given test case and stage
   8969  *
   8970  * @param test_case_index Index of test case
   8971  * @param stage           Shader stage
   8972  *
   8973  * @return Shader source
   8974  **/
   8975 std::string UniformBlockMemberInvalidOffsetAlignmentTest::getShaderSource(GLuint				test_case_index,
   8976 																		  Utils::Shader::STAGES stage)
   8977 {
   8978 	static const GLchar* cs = "#version 430 core\n"
   8979 							  "#extension GL_ARB_enhanced_layouts : require\n"
   8980 							  "\n"
   8981 							  "layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
   8982 							  "\n"
   8983 							  "layout (std140) uniform Block {\n"
   8984 							  "    layout (offset = OFFSET) TYPE member;\n"
   8985 							  "} block;\n"
   8986 							  "\n"
   8987 							  "writeonly uniform image2D uni_image;\n"
   8988 							  "\n"
   8989 							  "void main()\n"
   8990 							  "{\n"
   8991 							  "    vec4 result = vec4(1, 0, 0.5, 1);\n"
   8992 							  "\n"
   8993 							  "    if (TYPE(1) == block.member)\n"
   8994 							  "    {\n"
   8995 							  "        result = vec4(1, 1, 1, 1);\n"
   8996 							  "    }\n"
   8997 							  "\n"
   8998 							  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), result);\n"
   8999 							  "}\n"
   9000 							  "\n";
   9001 	static const GLchar* fs = "#version 430 core\n"
   9002 							  "#extension GL_ARB_enhanced_layouts : require\n"
   9003 							  "\n"
   9004 							  "in  vec4 gs_fs;\n"
   9005 							  "out vec4 fs_out;\n"
   9006 							  "\n"
   9007 							  "void main()\n"
   9008 							  "{\n"
   9009 							  "    fs_out = gs_fs;\n"
   9010 							  "}\n"
   9011 							  "\n";
   9012 	static const GLchar* fs_tested = "#version 430 core\n"
   9013 									 "#extension GL_ARB_enhanced_layouts : require\n"
   9014 									 "\n"
   9015 									 "layout (std140) uniform Block {\n"
   9016 									 "    layout (offset = OFFSET) TYPE member;\n"
   9017 									 "} block;\n"
   9018 									 "\n"
   9019 									 "in  vec4 gs_fs;\n"
   9020 									 "out vec4 fs_out;\n"
   9021 									 "\n"
   9022 									 "void main()\n"
   9023 									 "{\n"
   9024 									 "    if (TYPE(1) == block.member)\n"
   9025 									 "    {\n"
   9026 									 "        fs_out = vec4(1, 1, 1, 1);\n"
   9027 									 "    }\n"
   9028 									 "\n"
   9029 									 "    fs_out += gs_fs;\n"
   9030 									 "}\n"
   9031 									 "\n";
   9032 	static const GLchar* gs = "#version 430 core\n"
   9033 							  "#extension GL_ARB_enhanced_layouts : require\n"
   9034 							  "\n"
   9035 							  "layout(points)                           in;\n"
   9036 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   9037 							  "\n"
   9038 							  "in  vec4 tes_gs[];\n"
   9039 							  "out vec4 gs_fs;\n"
   9040 							  "\n"
   9041 							  "void main()\n"
   9042 							  "{\n"
   9043 							  "    gs_fs = tes_gs[0];\n"
   9044 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   9045 							  "    EmitVertex();\n"
   9046 							  "    gs_fs = tes_gs[0];\n"
   9047 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   9048 							  "    EmitVertex();\n"
   9049 							  "    gs_fs = tes_gs[0];\n"
   9050 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   9051 							  "    EmitVertex();\n"
   9052 							  "    gs_fs = tes_gs[0];\n"
   9053 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   9054 							  "    EmitVertex();\n"
   9055 							  "}\n"
   9056 							  "\n";
   9057 	static const GLchar* gs_tested = "#version 430 core\n"
   9058 									 "#extension GL_ARB_enhanced_layouts : require\n"
   9059 									 "\n"
   9060 									 "layout(points)                           in;\n"
   9061 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   9062 									 "\n"
   9063 									 "layout (std140) uniform Block {\n"
   9064 									 "    layout (offset = OFFSET) TYPE member;\n"
   9065 									 "} block;\n"
   9066 									 "\n"
   9067 									 "in  vec4 tes_gs[];\n"
   9068 									 "out vec4 gs_fs;\n"
   9069 									 "\n"
   9070 									 "void main()\n"
   9071 									 "{\n"
   9072 									 "    if (TYPE(1) == block.member)\n"
   9073 									 "    {\n"
   9074 									 "        gs_fs = vec4(1, 1, 1, 1);\n"
   9075 									 "    }\n"
   9076 									 "\n"
   9077 									 "    gs_fs += tes_gs[0];\n"
   9078 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   9079 									 "    EmitVertex();\n"
   9080 									 "    gs_fs += tes_gs[0];\n"
   9081 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   9082 									 "    EmitVertex();\n"
   9083 									 "    gs_fs += tes_gs[0];\n"
   9084 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   9085 									 "    EmitVertex();\n"
   9086 									 "    gs_fs += tes_gs[0];\n"
   9087 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   9088 									 "    EmitVertex();\n"
   9089 									 "}\n"
   9090 									 "\n";
   9091 	static const GLchar* tcs = "#version 430 core\n"
   9092 							   "#extension GL_ARB_enhanced_layouts : require\n"
   9093 							   "\n"
   9094 							   "layout(vertices = 1) out;\n"
   9095 							   "\n"
   9096 							   "in  vec4 vs_tcs[];\n"
   9097 							   "out vec4 tcs_tes[];\n"
   9098 							   "\n"
   9099 							   "void main()\n"
   9100 							   "{\n"
   9101 							   "\n"
   9102 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   9103 							   "\n"
   9104 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   9105 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   9106 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   9107 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   9108 							   "    gl_TessLevelInner[0] = 1.0;\n"
   9109 							   "    gl_TessLevelInner[1] = 1.0;\n"
   9110 							   "}\n"
   9111 							   "\n";
   9112 	static const GLchar* tcs_tested = "#version 430 core\n"
   9113 									  "#extension GL_ARB_enhanced_layouts : require\n"
   9114 									  "\n"
   9115 									  "layout(vertices = 1) out;\n"
   9116 									  "\n"
   9117 									  "layout (std140) uniform Block {\n"
   9118 									  "    layout (offset = OFFSET) TYPE member;\n"
   9119 									  "} block;\n"
   9120 									  "\n"
   9121 									  "in  vec4 vs_tcs[];\n"
   9122 									  "out vec4 tcs_tes[];\n"
   9123 									  "\n"
   9124 									  "void main()\n"
   9125 									  "{\n"
   9126 									  "    if (TYPE(1) == block.member)\n"
   9127 									  "    {\n"
   9128 									  "        tcs_tes[gl_InvocationID] = vec4(1, 1, 1, 1);\n"
   9129 									  "    }\n"
   9130 									  "\n"
   9131 									  "\n"
   9132 									  "    tcs_tes[gl_InvocationID] += vs_tcs[gl_InvocationID];\n"
   9133 									  "\n"
   9134 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   9135 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   9136 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   9137 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   9138 									  "    gl_TessLevelInner[0] = 1.0;\n"
   9139 									  "    gl_TessLevelInner[1] = 1.0;\n"
   9140 									  "}\n"
   9141 									  "\n";
   9142 	static const GLchar* tes = "#version 430 core\n"
   9143 							   "#extension GL_ARB_enhanced_layouts : require\n"
   9144 							   "\n"
   9145 							   "layout(isolines, point_mode) in;\n"
   9146 							   "\n"
   9147 							   "in  vec4 tcs_tes[];\n"
   9148 							   "out vec4 tes_gs;\n"
   9149 							   "\n"
   9150 							   "void main()\n"
   9151 							   "{\n"
   9152 							   "    tes_gs = tcs_tes[0];\n"
   9153 							   "}\n"
   9154 							   "\n";
   9155 	static const GLchar* tes_tested = "#version 430 core\n"
   9156 									  "#extension GL_ARB_enhanced_layouts : require\n"
   9157 									  "\n"
   9158 									  "layout(isolines, point_mode) in;\n"
   9159 									  "\n"
   9160 									  "layout (std140) uniform Block {\n"
   9161 									  "    layout (offset = OFFSET) TYPE member;\n"
   9162 									  "} block;\n"
   9163 									  "\n"
   9164 									  "in  vec4 tcs_tes[];\n"
   9165 									  "out vec4 tes_gs;\n"
   9166 									  "\n"
   9167 									  "void main()\n"
   9168 									  "{\n"
   9169 									  "    if (TYPE(1) == block.member)\n"
   9170 									  "    {\n"
   9171 									  "        tes_gs = vec4(1, 1, 1, 1);\n"
   9172 									  "    }\n"
   9173 									  "\n"
   9174 									  "    tes_gs += tcs_tes[0];\n"
   9175 									  "}\n"
   9176 									  "\n";
   9177 	static const GLchar* vs = "#version 430 core\n"
   9178 							  "#extension GL_ARB_enhanced_layouts : require\n"
   9179 							  "\n"
   9180 							  "in  vec4 in_vs;\n"
   9181 							  "out vec4 vs_tcs;\n"
   9182 							  "\n"
   9183 							  "void main()\n"
   9184 							  "{\n"
   9185 							  "    vs_tcs = in_vs;\n"
   9186 							  "}\n"
   9187 							  "\n";
   9188 	static const GLchar* vs_tested = "#version 430 core\n"
   9189 									 "#extension GL_ARB_enhanced_layouts : require\n"
   9190 									 "\n"
   9191 									 "layout (std140) uniform Block {\n"
   9192 									 "    layout (offset = OFFSET) TYPE member;\n"
   9193 									 "} block;\n"
   9194 									 "\n"
   9195 									 "in  vec4 in_vs;\n"
   9196 									 "out vec4 vs_tcs;\n"
   9197 									 "\n"
   9198 									 "void main()\n"
   9199 									 "{\n"
   9200 									 "    if (TYPE(1) == block.member)\n"
   9201 									 "    {\n"
   9202 									 "        vs_tcs = vec4(1, 1, 1, 1);\n"
   9203 									 "    }\n"
   9204 									 "\n"
   9205 									 "    vs_tcs += in_vs;\n"
   9206 									 "}\n"
   9207 									 "\n";
   9208 
   9209 	std::string source;
   9210 	testCase&   test_case = m_test_cases[test_case_index];
   9211 
   9212 	if (test_case.m_stage == stage)
   9213 	{
   9214 		GLchar			   buffer[16];
   9215 		const GLuint	   offset	= test_case.m_offset;
   9216 		size_t			   position  = 0;
   9217 		const Utils::Type& type		 = test_case.m_type;
   9218 		const GLchar*	  type_name = type.GetGLSLTypeName();
   9219 
   9220 		sprintf(buffer, "%d", offset);
   9221 
   9222 		switch (stage)
   9223 		{
   9224 		case Utils::Shader::COMPUTE:
   9225 			source = cs;
   9226 			break;
   9227 		case Utils::Shader::FRAGMENT:
   9228 			source = fs_tested;
   9229 			break;
   9230 		case Utils::Shader::GEOMETRY:
   9231 			source = gs_tested;
   9232 			break;
   9233 		case Utils::Shader::TESS_CTRL:
   9234 			source = tcs_tested;
   9235 			break;
   9236 		case Utils::Shader::TESS_EVAL:
   9237 			source = tes_tested;
   9238 			break;
   9239 		case Utils::Shader::VERTEX:
   9240 			source = vs_tested;
   9241 			break;
   9242 		default:
   9243 			TCU_FAIL("Invalid enum");
   9244 		}
   9245 
   9246 		Utils::replaceToken("OFFSET", position, buffer, source);
   9247 		Utils::replaceToken("TYPE", position, type_name, source);
   9248 		Utils::replaceToken("TYPE", position, type_name, source);
   9249 	}
   9250 	else
   9251 	{
   9252 		switch (stage)
   9253 		{
   9254 		case Utils::Shader::FRAGMENT:
   9255 			source = fs;
   9256 			break;
   9257 		case Utils::Shader::GEOMETRY:
   9258 			source = gs;
   9259 			break;
   9260 		case Utils::Shader::TESS_CTRL:
   9261 			source = tcs;
   9262 			break;
   9263 		case Utils::Shader::TESS_EVAL:
   9264 			source = tes;
   9265 			break;
   9266 		case Utils::Shader::VERTEX:
   9267 			source = vs;
   9268 			break;
   9269 		default:
   9270 			TCU_FAIL("Invalid enum");
   9271 		}
   9272 	}
   9273 
   9274 	return source;
   9275 }
   9276 
   9277 /** Get description of test case
   9278  *
   9279  * @param test_case_index Index of test case
   9280  *
   9281  * @return Type name and offset
   9282  **/
   9283 std::string UniformBlockMemberInvalidOffsetAlignmentTest::getTestCaseName(GLuint test_case_index)
   9284 {
   9285 	std::stringstream stream;
   9286 	testCase&		  test_case = m_test_cases[test_case_index];
   9287 
   9288 	stream << "Type: " << test_case.m_type.GetGLSLTypeName() << ", offset: " << test_case.m_offset;
   9289 
   9290 	return stream.str();
   9291 }
   9292 
   9293 /** Get number of test cases
   9294  *
   9295  * @return Number of test cases
   9296  **/
   9297 GLuint UniformBlockMemberInvalidOffsetAlignmentTest::getTestCaseNumber()
   9298 {
   9299 	return static_cast<GLuint>(m_test_cases.size());
   9300 }
   9301 
   9302 /** Get the maximum size for an uniform block
   9303  *
   9304  * @return The maximum size in basic machine units of a uniform block.
   9305  **/
   9306 GLint UniformBlockMemberInvalidOffsetAlignmentTest::getMaxBlockSize()
   9307 {
   9308 	const Functions& gl		  = m_context.getRenderContext().getFunctions();
   9309 	GLint			 max_size = 0;
   9310 
   9311 	gl.getIntegerv(GL_MAX_UNIFORM_BLOCK_SIZE, &max_size);
   9312 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   9313 
   9314 	return max_size;
   9315 }
   9316 
   9317 /** Selects if "compute" stage is relevant for test
   9318  *
   9319  * @param test_case_index Index of test case
   9320  *
   9321  * @return true when tested stage is compute
   9322  **/
   9323 bool UniformBlockMemberInvalidOffsetAlignmentTest::isComputeRelevant(GLuint test_case_index)
   9324 {
   9325 	return (Utils::Shader::COMPUTE == m_test_cases[test_case_index].m_stage);
   9326 }
   9327 
   9328 /** Selects if compilation failure is expected result
   9329  *
   9330  * @param test_case_index Index of test case
   9331  *
   9332  * @return should_fail field from testCase
   9333  **/
   9334 bool UniformBlockMemberInvalidOffsetAlignmentTest::isFailureExpected(GLuint test_case_index)
   9335 {
   9336 	return m_test_cases[test_case_index].m_should_fail;
   9337 }
   9338 
   9339 /** Checks if stage is supported
   9340  *
   9341  * @param stage ignored
   9342  *
   9343  * @return true
   9344  **/
   9345 bool UniformBlockMemberInvalidOffsetAlignmentTest::isStageSupported(Utils::Shader::STAGES /* stage */)
   9346 {
   9347 	return true;
   9348 }
   9349 
   9350 /** Prepare all test cases
   9351  *
   9352  **/
   9353 void UniformBlockMemberInvalidOffsetAlignmentTest::testInit()
   9354 {
   9355 	const GLuint n_types = getTypesNumber();
   9356 	bool		 stage_support[Utils::Shader::STAGE_MAX];
   9357 
   9358 	for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   9359 	{
   9360 		stage_support[stage] = isStageSupported((Utils::Shader::STAGES)stage);
   9361 	}
   9362 
   9363 	for (GLuint i = 0; i < n_types; ++i)
   9364 	{
   9365 		const Utils::Type& type		  = getType(i);
   9366 		const GLuint	   alignment  = type.GetBaseAlignment(false);
   9367 		const GLuint	   type_size  = type.GetSize(true);
   9368 		const GLuint	   sec_to_end = getMaxBlockSize() - 2 * type_size;
   9369 
   9370 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   9371 		{
   9372 			if (false == stage_support[stage])
   9373 			{
   9374 				continue;
   9375 			}
   9376 
   9377 			for (GLuint offset = 0; offset <= type_size; ++offset)
   9378 			{
   9379 				const GLuint modulo		 = offset % alignment;
   9380 				const bool   is_aligned  = (0 == modulo) ? true : false;
   9381 				const bool   should_fail = !is_aligned;
   9382 
   9383 				testCase test_case = { offset, should_fail, (Utils::Shader::STAGES)stage, type };
   9384 
   9385 				m_test_cases.push_back(test_case);
   9386 			}
   9387 
   9388 			for (GLuint offset = sec_to_end; offset <= sec_to_end + type_size; ++offset)
   9389 			{
   9390 				const GLuint modulo		 = offset % alignment;
   9391 				const bool   is_aligned  = (0 == modulo) ? true : false;
   9392 				const bool   should_fail = !is_aligned;
   9393 
   9394 				testCase test_case = { offset, should_fail, (Utils::Shader::STAGES)stage, type };
   9395 
   9396 				m_test_cases.push_back(test_case);
   9397 			}
   9398 		}
   9399 	}
   9400 }
   9401 
   9402 /** Constructor
   9403  *
   9404  * @param context Test framework context
   9405  **/
   9406 UniformBlockMemberOverlappingOffsetsTest::UniformBlockMemberOverlappingOffsetsTest(deqp::Context& context)
   9407 	: NegativeTestBase(context, "uniform_block_member_overlapping_offsets",
   9408 					   "Test verifies that overlapping offsets qualifiers cause compilation failure")
   9409 {
   9410 	/* Nothing to be done here */
   9411 }
   9412 
   9413 /** Constructor
   9414  *
   9415  * @param context Test framework context
   9416  * @param name        Test name
   9417  * @param description Test description
   9418  **/
   9419 UniformBlockMemberOverlappingOffsetsTest::UniformBlockMemberOverlappingOffsetsTest(deqp::Context&	 context,
   9420 																				   const glw::GLchar* name,
   9421 																				   const glw::GLchar* description)
   9422 	: NegativeTestBase(context, name, description)
   9423 {
   9424 	/* Nothing to be done here */
   9425 }
   9426 
   9427 /** Source for given test case and stage
   9428  *
   9429  * @param test_case_index Index of test case
   9430  * @param stage           Shader stage
   9431  *
   9432  * @return Shader source
   9433  **/
   9434 std::string UniformBlockMemberOverlappingOffsetsTest::getShaderSource(GLuint				test_case_index,
   9435 																	  Utils::Shader::STAGES stage)
   9436 {
   9437 	static const GLchar* cs = "#version 430 core\n"
   9438 							  "#extension GL_ARB_enhanced_layouts : require\n"
   9439 							  "\n"
   9440 							  "layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
   9441 							  "\n"
   9442 							  "layout (std140) uniform Block {\n"
   9443 							  "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   9444 							  "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   9445 							  "} block;\n"
   9446 							  "\n"
   9447 							  "writeonly uniform image2D uni_image;\n"
   9448 							  "\n"
   9449 							  "void main()\n"
   9450 							  "{\n"
   9451 							  "    vec4 result = vec4(1, 0, 0.5, 1);\n"
   9452 							  "\n"
   9453 							  "    if ((BOY_TYPE(1) == block.boy) ||\n"
   9454 							  "        (MAN_TYPE(0) == block.man) )\n"
   9455 							  "    {\n"
   9456 							  "        result = vec4(1, 1, 1, 1);\n"
   9457 							  "    }\n"
   9458 							  "\n"
   9459 							  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), result);\n"
   9460 							  "}\n"
   9461 							  "\n";
   9462 	static const GLchar* fs = "#version 430 core\n"
   9463 							  "#extension GL_ARB_enhanced_layouts : require\n"
   9464 							  "\n"
   9465 							  "in  vec4 gs_fs;\n"
   9466 							  "out vec4 fs_out;\n"
   9467 							  "\n"
   9468 							  "void main()\n"
   9469 							  "{\n"
   9470 							  "    fs_out = gs_fs;\n"
   9471 							  "}\n"
   9472 							  "\n";
   9473 	static const GLchar* fs_tested = "#version 430 core\n"
   9474 									 "#extension GL_ARB_enhanced_layouts : require\n"
   9475 									 "\n"
   9476 									 "layout (std140) uniform Block {\n"
   9477 									 "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   9478 									 "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   9479 									 "} block;\n"
   9480 									 "\n"
   9481 									 "in  vec4 gs_fs;\n"
   9482 									 "out vec4 fs_out;\n"
   9483 									 "\n"
   9484 									 "void main()\n"
   9485 									 "{\n"
   9486 									 "    if ((BOY_TYPE(1) == block.boy) ||\n"
   9487 									 "        (MAN_TYPE(0) == block.man) )\n"
   9488 									 "    {\n"
   9489 									 "        fs_out = vec4(1, 1, 1, 1);\n"
   9490 									 "    }\n"
   9491 									 "\n"
   9492 									 "    fs_out += gs_fs;\n"
   9493 									 "}\n"
   9494 									 "\n";
   9495 	static const GLchar* gs = "#version 430 core\n"
   9496 							  "#extension GL_ARB_enhanced_layouts : require\n"
   9497 							  "\n"
   9498 							  "layout(points)                           in;\n"
   9499 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   9500 							  "\n"
   9501 							  "in  vec4 tes_gs[];\n"
   9502 							  "out vec4 gs_fs;\n"
   9503 							  "\n"
   9504 							  "void main()\n"
   9505 							  "{\n"
   9506 							  "    gs_fs = tes_gs[0];\n"
   9507 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   9508 							  "    EmitVertex();\n"
   9509 							  "    gs_fs = tes_gs[0];\n"
   9510 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   9511 							  "    EmitVertex();\n"
   9512 							  "    gs_fs = tes_gs[0];\n"
   9513 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   9514 							  "    EmitVertex();\n"
   9515 							  "    gs_fs = tes_gs[0];\n"
   9516 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   9517 							  "    EmitVertex();\n"
   9518 							  "}\n"
   9519 							  "\n";
   9520 	static const GLchar* gs_tested = "#version 430 core\n"
   9521 									 "#extension GL_ARB_enhanced_layouts : require\n"
   9522 									 "\n"
   9523 									 "layout(points)                           in;\n"
   9524 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   9525 									 "\n"
   9526 									 "layout (std140) uniform Block {\n"
   9527 									 "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   9528 									 "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   9529 									 "} block;\n"
   9530 									 "\n"
   9531 									 "in  vec4 tes_gs[];\n"
   9532 									 "out vec4 gs_fs;\n"
   9533 									 "\n"
   9534 									 "void main()\n"
   9535 									 "{\n"
   9536 									 "    if ((BOY_TYPE(1) == block.boy) ||\n"
   9537 									 "        (MAN_TYPE(0) == block.man) )\n"
   9538 									 "    {\n"
   9539 									 "        gs_fs = vec4(1, 1, 1, 1);\n"
   9540 									 "    }\n"
   9541 									 "\n"
   9542 									 "    gs_fs += tes_gs[0];\n"
   9543 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   9544 									 "    EmitVertex();\n"
   9545 									 "    gs_fs += tes_gs[0];\n"
   9546 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   9547 									 "    EmitVertex();\n"
   9548 									 "    gs_fs += tes_gs[0];\n"
   9549 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   9550 									 "    EmitVertex();\n"
   9551 									 "    gs_fs += tes_gs[0];\n"
   9552 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   9553 									 "    EmitVertex();\n"
   9554 									 "}\n"
   9555 									 "\n";
   9556 	static const GLchar* tcs = "#version 430 core\n"
   9557 							   "#extension GL_ARB_enhanced_layouts : require\n"
   9558 							   "\n"
   9559 							   "layout(vertices = 1) out;\n"
   9560 							   "\n"
   9561 							   "in  vec4 vs_tcs[];\n"
   9562 							   "out vec4 tcs_tes[];\n"
   9563 							   "\n"
   9564 							   "void main()\n"
   9565 							   "{\n"
   9566 							   "\n"
   9567 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   9568 							   "\n"
   9569 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   9570 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   9571 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   9572 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   9573 							   "    gl_TessLevelInner[0] = 1.0;\n"
   9574 							   "    gl_TessLevelInner[1] = 1.0;\n"
   9575 							   "}\n"
   9576 							   "\n";
   9577 	static const GLchar* tcs_tested = "#version 430 core\n"
   9578 									  "#extension GL_ARB_enhanced_layouts : require\n"
   9579 									  "\n"
   9580 									  "layout(vertices = 1) out;\n"
   9581 									  "\n"
   9582 									  "layout (std140) uniform Block {\n"
   9583 									  "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   9584 									  "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   9585 									  "} block;\n"
   9586 									  "\n"
   9587 									  "in  vec4 vs_tcs[];\n"
   9588 									  "out vec4 tcs_tes[];\n"
   9589 									  "\n"
   9590 									  "void main()\n"
   9591 									  "{\n"
   9592 									  "    if ((BOY_TYPE(1) == block.boy) ||\n"
   9593 									  "        (MAN_TYPE(0) == block.man) )\n"
   9594 									  "    {\n"
   9595 									  "        tcs_tes[gl_InvocationID] = vec4(1, 1, 1, 1);\n"
   9596 									  "    }\n"
   9597 									  "\n"
   9598 									  "\n"
   9599 									  "    tcs_tes[gl_InvocationID] += vs_tcs[gl_InvocationID];\n"
   9600 									  "\n"
   9601 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   9602 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   9603 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   9604 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   9605 									  "    gl_TessLevelInner[0] = 1.0;\n"
   9606 									  "    gl_TessLevelInner[1] = 1.0;\n"
   9607 									  "}\n"
   9608 									  "\n";
   9609 	static const GLchar* tes = "#version 430 core\n"
   9610 							   "#extension GL_ARB_enhanced_layouts : require\n"
   9611 							   "\n"
   9612 							   "layout(isolines, point_mode) in;\n"
   9613 							   "\n"
   9614 							   "in  vec4 tcs_tes[];\n"
   9615 							   "out vec4 tes_gs;\n"
   9616 							   "\n"
   9617 							   "void main()\n"
   9618 							   "{\n"
   9619 							   "    tes_gs = tcs_tes[0];\n"
   9620 							   "}\n"
   9621 							   "\n";
   9622 	static const GLchar* tes_tested = "#version 430 core\n"
   9623 									  "#extension GL_ARB_enhanced_layouts : require\n"
   9624 									  "\n"
   9625 									  "layout(isolines, point_mode) in;\n"
   9626 									  "\n"
   9627 									  "layout (std140) uniform Block {\n"
   9628 									  "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   9629 									  "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   9630 									  "} block;\n"
   9631 									  "\n"
   9632 									  "in  vec4 tcs_tes[];\n"
   9633 									  "out vec4 tes_gs;\n"
   9634 									  "\n"
   9635 									  "void main()\n"
   9636 									  "{\n"
   9637 									  "    if ((BOY_TYPE(1) == block.boy) ||\n"
   9638 									  "        (MAN_TYPE(0) == block.man) )\n"
   9639 									  "    {\n"
   9640 									  "        tes_gs = vec4(1, 1, 1, 1);\n"
   9641 									  "    }\n"
   9642 									  "\n"
   9643 									  "    tes_gs += tcs_tes[0];\n"
   9644 									  "}\n"
   9645 									  "\n";
   9646 	static const GLchar* vs = "#version 430 core\n"
   9647 							  "#extension GL_ARB_enhanced_layouts : require\n"
   9648 							  "\n"
   9649 							  "in  vec4 in_vs;\n"
   9650 							  "out vec4 vs_tcs;\n"
   9651 							  "\n"
   9652 							  "void main()\n"
   9653 							  "{\n"
   9654 							  "    vs_tcs = in_vs;\n"
   9655 							  "}\n"
   9656 							  "\n";
   9657 	static const GLchar* vs_tested = "#version 430 core\n"
   9658 									 "#extension GL_ARB_enhanced_layouts : require\n"
   9659 									 "\n"
   9660 									 "layout (std140) uniform Block {\n"
   9661 									 "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   9662 									 "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   9663 									 "} block;\n"
   9664 									 "\n"
   9665 									 "in  vec4 in_vs;\n"
   9666 									 "out vec4 vs_tcs;\n"
   9667 									 "\n"
   9668 									 "void main()\n"
   9669 									 "{\n"
   9670 									 "    if ((BOY_TYPE(1) == block.boy) ||\n"
   9671 									 "        (MAN_TYPE(0) == block.man) )\n"
   9672 									 "    {\n"
   9673 									 "        vs_tcs = vec4(1, 1, 1, 1);\n"
   9674 									 "    }\n"
   9675 									 "\n"
   9676 									 "    vs_tcs += in_vs;\n"
   9677 									 "}\n"
   9678 									 "\n";
   9679 
   9680 	std::string source;
   9681 	testCase&   test_case = m_test_cases[test_case_index];
   9682 
   9683 	if (test_case.m_stage == stage)
   9684 	{
   9685 		GLchar			   buffer[16];
   9686 		const GLuint	   boy_offset	= test_case.m_boy_offset;
   9687 		const Utils::Type& boy_type		 = test_case.m_boy_type;
   9688 		const GLchar*	  boy_type_name = boy_type.GetGLSLTypeName();
   9689 		const GLuint	   man_offset	= test_case.m_man_offset;
   9690 		const Utils::Type& man_type		 = test_case.m_man_type;
   9691 		const GLchar*	  man_type_name = man_type.GetGLSLTypeName();
   9692 		size_t			   position		 = 0;
   9693 
   9694 		switch (stage)
   9695 		{
   9696 		case Utils::Shader::COMPUTE:
   9697 			source = cs;
   9698 			break;
   9699 		case Utils::Shader::FRAGMENT:
   9700 			source = fs_tested;
   9701 			break;
   9702 		case Utils::Shader::GEOMETRY:
   9703 			source = gs_tested;
   9704 			break;
   9705 		case Utils::Shader::TESS_CTRL:
   9706 			source = tcs_tested;
   9707 			break;
   9708 		case Utils::Shader::TESS_EVAL:
   9709 			source = tes_tested;
   9710 			break;
   9711 		case Utils::Shader::VERTEX:
   9712 			source = vs_tested;
   9713 			break;
   9714 		default:
   9715 			TCU_FAIL("Invalid enum");
   9716 		}
   9717 
   9718 		sprintf(buffer, "%d", boy_offset);
   9719 		Utils::replaceToken("BOY_OFFSET", position, buffer, source);
   9720 		Utils::replaceToken("BOY_TYPE", position, boy_type_name, source);
   9721 		sprintf(buffer, "%d", man_offset);
   9722 		Utils::replaceToken("MAN_OFFSET", position, buffer, source);
   9723 		Utils::replaceToken("MAN_TYPE", position, man_type_name, source);
   9724 		Utils::replaceToken("BOY_TYPE", position, boy_type_name, source);
   9725 		Utils::replaceToken("MAN_TYPE", position, man_type_name, source);
   9726 	}
   9727 	else
   9728 	{
   9729 		switch (stage)
   9730 		{
   9731 		case Utils::Shader::FRAGMENT:
   9732 			source = fs;
   9733 			break;
   9734 		case Utils::Shader::GEOMETRY:
   9735 			source = gs;
   9736 			break;
   9737 		case Utils::Shader::TESS_CTRL:
   9738 			source = tcs;
   9739 			break;
   9740 		case Utils::Shader::TESS_EVAL:
   9741 			source = tes;
   9742 			break;
   9743 		case Utils::Shader::VERTEX:
   9744 			source = vs;
   9745 			break;
   9746 		default:
   9747 			TCU_FAIL("Invalid enum");
   9748 		}
   9749 	}
   9750 
   9751 	return source;
   9752 }
   9753 
   9754 /** Get description of test case
   9755  *
   9756  * @param test_case_index Index of test case
   9757  *
   9758  * @return Type name and offset
   9759  **/
   9760 std::string UniformBlockMemberOverlappingOffsetsTest::getTestCaseName(GLuint test_case_index)
   9761 {
   9762 	std::stringstream stream;
   9763 	testCase&		  test_case = m_test_cases[test_case_index];
   9764 
   9765 	stream << "Type: " << test_case.m_boy_type.GetGLSLTypeName() << ", offset: " << test_case.m_boy_offset
   9766 		   << ". Type: " << test_case.m_man_type.GetGLSLTypeName() << ", offset: " << test_case.m_man_offset;
   9767 
   9768 	return stream.str();
   9769 }
   9770 
   9771 /** Get number of test cases
   9772  *
   9773  * @return Number of test cases
   9774  **/
   9775 GLuint UniformBlockMemberOverlappingOffsetsTest::getTestCaseNumber()
   9776 {
   9777 	return static_cast<GLuint>(m_test_cases.size());
   9778 }
   9779 
   9780 /** Selects if "compute" stage is relevant for test
   9781  *
   9782  * @param test_case_index Index of test case
   9783  *
   9784  * @return true when tested stage is compute
   9785  **/
   9786 bool UniformBlockMemberOverlappingOffsetsTest::isComputeRelevant(GLuint test_case_index)
   9787 {
   9788 	return (Utils::Shader::COMPUTE == m_test_cases[test_case_index].m_stage);
   9789 }
   9790 
   9791 /** Checks if stage is supported
   9792  *
   9793  * @param stage ignored
   9794  *
   9795  * @return true
   9796  **/
   9797 bool UniformBlockMemberOverlappingOffsetsTest::isStageSupported(Utils::Shader::STAGES /* stage */)
   9798 {
   9799 	return true;
   9800 }
   9801 
   9802 /** Prepare all test cases
   9803  *
   9804  **/
   9805 void UniformBlockMemberOverlappingOffsetsTest::testInit()
   9806 {
   9807 	const GLuint n_types = getTypesNumber();
   9808 	bool		 stage_support[Utils::Shader::STAGE_MAX];
   9809 
   9810 	for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   9811 	{
   9812 		stage_support[stage] = isStageSupported((Utils::Shader::STAGES)stage);
   9813 	}
   9814 
   9815 	for (GLuint i = 0; i < n_types; ++i)
   9816 	{
   9817 		const Utils::Type& boy_type = getType(i);
   9818 		const GLuint	   boy_size = boy_type.GetActualAlignment(1 /* align */, false /* is_array*/);
   9819 
   9820 		for (GLuint j = 0; j < n_types; ++j)
   9821 		{
   9822 			const Utils::Type& man_type  = getType(j);
   9823 			const GLuint	   man_align = man_type.GetBaseAlignment(false);
   9824 			const GLuint	   man_size  = man_type.GetActualAlignment(1 /* align */, false /* is_array*/);
   9825 
   9826 			const GLuint boy_offset		  = lcm(boy_size, man_size);
   9827 			const GLuint man_after_start  = boy_offset + 1;
   9828 			const GLuint man_after_off	= man_type.GetActualOffset(man_after_start, man_size);
   9829 			const GLuint man_before_start = boy_offset - man_align;
   9830 			const GLuint man_before_off   = man_type.GetActualOffset(man_before_start, man_size);
   9831 
   9832 			for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   9833 			{
   9834 				if (false == stage_support[stage])
   9835 				{
   9836 					continue;
   9837 				}
   9838 
   9839 				if ((boy_offset > man_before_off) && (boy_offset < man_before_off + man_size))
   9840 				{
   9841 					testCase test_case = { boy_offset, boy_type, man_before_off, man_type,
   9842 										   (Utils::Shader::STAGES)stage };
   9843 
   9844 					m_test_cases.push_back(test_case);
   9845 				}
   9846 
   9847 				if ((boy_offset < man_after_off) && (boy_offset + boy_size > man_after_off))
   9848 				{
   9849 					testCase test_case = { boy_offset, boy_type, man_after_off, man_type,
   9850 										   (Utils::Shader::STAGES)stage };
   9851 
   9852 					m_test_cases.push_back(test_case);
   9853 				}
   9854 
   9855 				/* Boy offset, should be fine for both types */
   9856 				testCase test_case = { boy_offset, boy_type, boy_offset, man_type, (Utils::Shader::STAGES)stage };
   9857 
   9858 				m_test_cases.push_back(test_case);
   9859 			}
   9860 		}
   9861 	}
   9862 }
   9863 
   9864 /** Find greatest common divisor for a and b
   9865  *
   9866  * @param a A argument
   9867  * @param b B argument
   9868  *
   9869  * @return Found gcd value
   9870  **/
   9871 GLuint UniformBlockMemberOverlappingOffsetsTest::gcd(GLuint a, GLuint b)
   9872 {
   9873 	if ((0 != a) && (0 == b))
   9874 	{
   9875 		return a;
   9876 	}
   9877 	else
   9878 	{
   9879 		GLuint greater = std::max(a, b);
   9880 		GLuint lesser  = std::min(a, b);
   9881 
   9882 		return gcd(lesser, greater % lesser);
   9883 	}
   9884 }
   9885 
   9886 /** Find lowest common multiple for a and b
   9887  *
   9888  * @param a A argument
   9889  * @param b B argument
   9890  *
   9891  * @return Found gcd value
   9892  **/
   9893 GLuint UniformBlockMemberOverlappingOffsetsTest::lcm(GLuint a, GLuint b)
   9894 {
   9895 	return (a * b) / gcd(a, b);
   9896 }
   9897 
   9898 /** Constructor
   9899  *
   9900  * @param context Test framework context
   9901  **/
   9902 UniformBlockMemberAlignNonPowerOf2Test::UniformBlockMemberAlignNonPowerOf2Test(deqp::Context& context)
   9903 	: NegativeTestBase(context, "uniform_block_member_align_non_power_of_2",
   9904 					   "Test verifies that align qualifier requires value that is a power of 2")
   9905 {
   9906 	/* Nothing to be done here */
   9907 }
   9908 
   9909 /** Constructor
   9910  *
   9911  * @param context Test framework context
   9912  * @param name        Test name
   9913  * @param description Test description
   9914  **/
   9915 UniformBlockMemberAlignNonPowerOf2Test::UniformBlockMemberAlignNonPowerOf2Test(deqp::Context&	 context,
   9916 																			   const glw::GLchar* name,
   9917 																			   const glw::GLchar* description)
   9918 	: NegativeTestBase(context, name, description)
   9919 {
   9920 	/* Nothing to be done here */
   9921 }
   9922 
   9923 /** Source for given test case and stage
   9924  *
   9925  * @param test_case_index Index of test case
   9926  * @param stage           Shader stage
   9927  *
   9928  * @return Shader source
   9929  **/
   9930 std::string UniformBlockMemberAlignNonPowerOf2Test::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   9931 {
   9932 	static const GLchar* cs = "#version 430 core\n"
   9933 							  "#extension GL_ARB_enhanced_layouts : require\n"
   9934 							  "\n"
   9935 							  "layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
   9936 							  "\n"
   9937 							  "layout (std140) uniform Block {\n"
   9938 							  "    vec4 boy;\n"
   9939 							  "    layout (align = ALIGN) TYPE man;\n"
   9940 							  "} block;\n"
   9941 							  "\n"
   9942 							  "writeonly uniform image2D uni_image;\n"
   9943 							  "\n"
   9944 							  "void main()\n"
   9945 							  "{\n"
   9946 							  "    vec4 result = vec4(1, 0, 0.5, 1);\n"
   9947 							  "\n"
   9948 							  "    if (TYPE(0) == block.man)\n"
   9949 							  "    {\n"
   9950 							  "        result = vec4(1, 1, 1, 1) - block.boy;\n"
   9951 							  "    }\n"
   9952 							  "\n"
   9953 							  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), result);\n"
   9954 							  "}\n"
   9955 							  "\n";
   9956 	static const GLchar* fs = "#version 430 core\n"
   9957 							  "#extension GL_ARB_enhanced_layouts : require\n"
   9958 							  "\n"
   9959 							  "in  vec4 gs_fs;\n"
   9960 							  "out vec4 fs_out;\n"
   9961 							  "\n"
   9962 							  "void main()\n"
   9963 							  "{\n"
   9964 							  "    fs_out = gs_fs;\n"
   9965 							  "}\n"
   9966 							  "\n";
   9967 	static const GLchar* fs_tested = "#version 430 core\n"
   9968 									 "#extension GL_ARB_enhanced_layouts : require\n"
   9969 									 "\n"
   9970 									 "layout (std140) uniform Block {\n"
   9971 									 "    vec4 boy;\n"
   9972 									 "    layout (align = ALIGN) TYPE man;\n"
   9973 									 "} block;\n"
   9974 									 "\n"
   9975 									 "in  vec4 gs_fs;\n"
   9976 									 "out vec4 fs_out;\n"
   9977 									 "\n"
   9978 									 "void main()\n"
   9979 									 "{\n"
   9980 									 "    if (TYPE(0) == block.man)\n"
   9981 									 "    {\n"
   9982 									 "        fs_out = block.boy;\n"
   9983 									 "    }\n"
   9984 									 "\n"
   9985 									 "    fs_out += gs_fs;\n"
   9986 									 "}\n"
   9987 									 "\n";
   9988 	static const GLchar* gs = "#version 430 core\n"
   9989 							  "#extension GL_ARB_enhanced_layouts : require\n"
   9990 							  "\n"
   9991 							  "layout(points)                           in;\n"
   9992 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   9993 							  "\n"
   9994 							  "in  vec4 tes_gs[];\n"
   9995 							  "out vec4 gs_fs;\n"
   9996 							  "\n"
   9997 							  "void main()\n"
   9998 							  "{\n"
   9999 							  "    gs_fs = tes_gs[0];\n"
   10000 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   10001 							  "    EmitVertex();\n"
   10002 							  "    gs_fs = tes_gs[0];\n"
   10003 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   10004 							  "    EmitVertex();\n"
   10005 							  "    gs_fs = tes_gs[0];\n"
   10006 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   10007 							  "    EmitVertex();\n"
   10008 							  "    gs_fs = tes_gs[0];\n"
   10009 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   10010 							  "    EmitVertex();\n"
   10011 							  "}\n"
   10012 							  "\n";
   10013 	static const GLchar* gs_tested = "#version 430 core\n"
   10014 									 "#extension GL_ARB_enhanced_layouts : require\n"
   10015 									 "\n"
   10016 									 "layout(points)                           in;\n"
   10017 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   10018 									 "\n"
   10019 									 "layout (std140) uniform Block {\n"
   10020 									 "    vec4 boy;\n"
   10021 									 "    layout (align = ALIGN) TYPE man;\n"
   10022 									 "} block;\n"
   10023 									 "\n"
   10024 									 "in  vec4 tes_gs[];\n"
   10025 									 "out vec4 gs_fs;\n"
   10026 									 "\n"
   10027 									 "void main()\n"
   10028 									 "{\n"
   10029 									 "    if (TYPE(0) == block.man)\n"
   10030 									 "    {\n"
   10031 									 "        gs_fs = block.boy;\n"
   10032 									 "    }\n"
   10033 									 "\n"
   10034 									 "    gs_fs += tes_gs[0];\n"
   10035 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   10036 									 "    EmitVertex();\n"
   10037 									 "    gs_fs += tes_gs[0];\n"
   10038 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   10039 									 "    EmitVertex();\n"
   10040 									 "    gs_fs += tes_gs[0];\n"
   10041 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   10042 									 "    EmitVertex();\n"
   10043 									 "    gs_fs += tes_gs[0];\n"
   10044 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   10045 									 "    EmitVertex();\n"
   10046 									 "}\n"
   10047 									 "\n";
   10048 	static const GLchar* tcs = "#version 430 core\n"
   10049 							   "#extension GL_ARB_enhanced_layouts : require\n"
   10050 							   "\n"
   10051 							   "layout(vertices = 1) out;\n"
   10052 							   "\n"
   10053 							   "in  vec4 vs_tcs[];\n"
   10054 							   "out vec4 tcs_tes[];\n"
   10055 							   "\n"
   10056 							   "void main()\n"
   10057 							   "{\n"
   10058 							   "\n"
   10059 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   10060 							   "\n"
   10061 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   10062 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   10063 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   10064 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   10065 							   "    gl_TessLevelInner[0] = 1.0;\n"
   10066 							   "    gl_TessLevelInner[1] = 1.0;\n"
   10067 							   "}\n"
   10068 							   "\n";
   10069 	static const GLchar* tcs_tested = "#version 430 core\n"
   10070 									  "#extension GL_ARB_enhanced_layouts : require\n"
   10071 									  "\n"
   10072 									  "layout(vertices = 1) out;\n"
   10073 									  "\n"
   10074 									  "layout (std140) uniform Block {\n"
   10075 									  "    vec4 boy;\n"
   10076 									  "    layout (align = ALIGN) TYPE man;\n"
   10077 									  "} block;\n"
   10078 									  "\n"
   10079 									  "in  vec4 vs_tcs[];\n"
   10080 									  "out vec4 tcs_tes[];\n"
   10081 									  "\n"
   10082 									  "void main()\n"
   10083 									  "{\n"
   10084 									  "    if (TYPE(0) == block.man)\n"
   10085 									  "    {\n"
   10086 									  "        tcs_tes[gl_InvocationID] = block.boy;\n"
   10087 									  "    }\n"
   10088 									  "\n"
   10089 									  "\n"
   10090 									  "    tcs_tes[gl_InvocationID] += vs_tcs[gl_InvocationID];\n"
   10091 									  "\n"
   10092 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   10093 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   10094 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   10095 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   10096 									  "    gl_TessLevelInner[0] = 1.0;\n"
   10097 									  "    gl_TessLevelInner[1] = 1.0;\n"
   10098 									  "}\n"
   10099 									  "\n";
   10100 	static const GLchar* tes = "#version 430 core\n"
   10101 							   "#extension GL_ARB_enhanced_layouts : require\n"
   10102 							   "\n"
   10103 							   "layout(isolines, point_mode) in;\n"
   10104 							   "\n"
   10105 							   "in  vec4 tcs_tes[];\n"
   10106 							   "out vec4 tes_gs;\n"
   10107 							   "\n"
   10108 							   "void main()\n"
   10109 							   "{\n"
   10110 							   "    tes_gs = tcs_tes[0];\n"
   10111 							   "}\n"
   10112 							   "\n";
   10113 	static const GLchar* tes_tested = "#version 430 core\n"
   10114 									  "#extension GL_ARB_enhanced_layouts : require\n"
   10115 									  "\n"
   10116 									  "layout(isolines, point_mode) in;\n"
   10117 									  "\n"
   10118 									  "layout (std140) uniform Block {\n"
   10119 									  "    vec4 boy;\n"
   10120 									  "    layout (align = ALIGN) TYPE man;\n"
   10121 									  "} block;\n"
   10122 									  "\n"
   10123 									  "in  vec4 tcs_tes[];\n"
   10124 									  "out vec4 tes_gs;\n"
   10125 									  "\n"
   10126 									  "void main()\n"
   10127 									  "{\n"
   10128 									  "    if (TYPE(0) == block.man)\n"
   10129 									  "    {\n"
   10130 									  "        tes_gs = block.boy;\n"
   10131 									  "    }\n"
   10132 									  "\n"
   10133 									  "    tes_gs += tcs_tes[0];\n"
   10134 									  "}\n"
   10135 									  "\n";
   10136 	static const GLchar* vs = "#version 430 core\n"
   10137 							  "#extension GL_ARB_enhanced_layouts : require\n"
   10138 							  "\n"
   10139 							  "in  vec4 in_vs;\n"
   10140 							  "out vec4 vs_tcs;\n"
   10141 							  "\n"
   10142 							  "void main()\n"
   10143 							  "{\n"
   10144 							  "    vs_tcs = in_vs;\n"
   10145 							  "}\n"
   10146 							  "\n";
   10147 	static const GLchar* vs_tested = "#version 430 core\n"
   10148 									 "#extension GL_ARB_enhanced_layouts : require\n"
   10149 									 "\n"
   10150 									 "layout (std140) uniform Block {\n"
   10151 									 "    vec4 boy;\n"
   10152 									 "    layout (align = ALIGN) TYPE man;\n"
   10153 									 "} block;\n"
   10154 									 "\n"
   10155 									 "in  vec4 in_vs;\n"
   10156 									 "out vec4 vs_tcs;\n"
   10157 									 "\n"
   10158 									 "void main()\n"
   10159 									 "{\n"
   10160 									 "    if (TYPE(0) == block.man)\n"
   10161 									 "    {\n"
   10162 									 "        vs_tcs = block.boy;\n"
   10163 									 "    }\n"
   10164 									 "\n"
   10165 									 "    vs_tcs += in_vs;\n"
   10166 									 "}\n"
   10167 									 "\n";
   10168 
   10169 	std::string source;
   10170 	testCase&   test_case = m_test_cases[test_case_index];
   10171 
   10172 	if (test_case.m_stage == stage)
   10173 	{
   10174 		GLchar			   buffer[16];
   10175 		const GLuint	   alignment = test_case.m_alignment;
   10176 		const Utils::Type& type		 = test_case.m_type;
   10177 		const GLchar*	  type_name = type.GetGLSLTypeName();
   10178 		size_t			   position  = 0;
   10179 
   10180 		switch (stage)
   10181 		{
   10182 		case Utils::Shader::COMPUTE:
   10183 			source = cs;
   10184 			break;
   10185 		case Utils::Shader::FRAGMENT:
   10186 			source = fs_tested;
   10187 			break;
   10188 		case Utils::Shader::GEOMETRY:
   10189 			source = gs_tested;
   10190 			break;
   10191 		case Utils::Shader::TESS_CTRL:
   10192 			source = tcs_tested;
   10193 			break;
   10194 		case Utils::Shader::TESS_EVAL:
   10195 			source = tes_tested;
   10196 			break;
   10197 		case Utils::Shader::VERTEX:
   10198 			source = vs_tested;
   10199 			break;
   10200 		default:
   10201 			TCU_FAIL("Invalid enum");
   10202 		}
   10203 
   10204 		sprintf(buffer, "%d", alignment);
   10205 		Utils::replaceToken("ALIGN", position, buffer, source);
   10206 		Utils::replaceToken("TYPE", position, type_name, source);
   10207 		Utils::replaceToken("TYPE", position, type_name, source);
   10208 	}
   10209 	else
   10210 	{
   10211 		switch (stage)
   10212 		{
   10213 		case Utils::Shader::FRAGMENT:
   10214 			source = fs;
   10215 			break;
   10216 		case Utils::Shader::GEOMETRY:
   10217 			source = gs;
   10218 			break;
   10219 		case Utils::Shader::TESS_CTRL:
   10220 			source = tcs;
   10221 			break;
   10222 		case Utils::Shader::TESS_EVAL:
   10223 			source = tes;
   10224 			break;
   10225 		case Utils::Shader::VERTEX:
   10226 			source = vs;
   10227 			break;
   10228 		default:
   10229 			TCU_FAIL("Invalid enum");
   10230 		}
   10231 	}
   10232 
   10233 	return source;
   10234 }
   10235 
   10236 /** Get description of test case
   10237  *
   10238  * @param test_case_index Index of test case
   10239  *
   10240  * @return Type name and offset
   10241  **/
   10242 std::string UniformBlockMemberAlignNonPowerOf2Test::getTestCaseName(GLuint test_case_index)
   10243 {
   10244 	std::stringstream stream;
   10245 	testCase&		  test_case = m_test_cases[test_case_index];
   10246 
   10247 	stream << "Type: " << test_case.m_type.GetGLSLTypeName() << ", align: " << test_case.m_alignment;
   10248 
   10249 	return stream.str();
   10250 }
   10251 
   10252 /** Get number of test cases
   10253  *
   10254  * @return Number of test cases
   10255  **/
   10256 GLuint UniformBlockMemberAlignNonPowerOf2Test::getTestCaseNumber()
   10257 {
   10258 	return static_cast<GLuint>(m_test_cases.size());
   10259 }
   10260 
   10261 /** Selects if "compute" stage is relevant for test
   10262  *
   10263  * @param test_case_index Index of test case
   10264  *
   10265  * @return true when tested stage is compute
   10266  **/
   10267 bool UniformBlockMemberAlignNonPowerOf2Test::isComputeRelevant(GLuint test_case_index)
   10268 {
   10269 	return (Utils::Shader::COMPUTE == m_test_cases[test_case_index].m_stage);
   10270 }
   10271 
   10272 /** Checks if stage is supported
   10273  *
   10274  * @param ignored
   10275  *
   10276  * @return true
   10277  **/
   10278 bool UniformBlockMemberAlignNonPowerOf2Test::isStageSupported(Utils::Shader::STAGES /* stage */)
   10279 {
   10280 	return true;
   10281 }
   10282 
   10283 /** Selects if compilation failure is expected result
   10284  *
   10285  * @param test_case_index Index of test case
   10286  *
   10287  * @return should_fail field from testCase
   10288  **/
   10289 bool UniformBlockMemberAlignNonPowerOf2Test::isFailureExpected(GLuint test_case_index)
   10290 {
   10291 	return m_test_cases[test_case_index].m_should_fail;
   10292 }
   10293 
   10294 /** Prepare all test cases
   10295  *
   10296  **/
   10297 void UniformBlockMemberAlignNonPowerOf2Test::testInit()
   10298 {
   10299 	static const GLuint dmat4_size = 128;
   10300 	const GLuint		n_types	= getTypesNumber();
   10301 	bool				stage_support[Utils::Shader::STAGE_MAX];
   10302 
   10303 	for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   10304 	{
   10305 		stage_support[stage] = isStageSupported((Utils::Shader::STAGES)stage);
   10306 	}
   10307 
   10308 	for (GLuint j = 0; j < n_types; ++j)
   10309 	{
   10310 		const Utils::Type& type = getType(j);
   10311 
   10312 		for (GLuint align = 0; align <= dmat4_size; ++align)
   10313 		{
   10314 
   10315 #if WRKARD_UNIFORMBLOCKMEMBERALIGNNONPOWEROF2TEST
   10316 
   10317 			const bool should_fail = (0 == align) ? false : !isPowerOf2(align);
   10318 
   10319 #else /* WRKARD_UNIFORMBLOCKMEMBERALIGNNONPOWEROF2TEST */
   10320 
   10321 			const bool should_fail = !isPowerOf2(align);
   10322 
   10323 #endif /* WRKARD_UNIFORMBLOCKMEMBERALIGNNONPOWEROF2TEST */
   10324 
   10325 			for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   10326 			{
   10327 				if (false == stage_support[stage])
   10328 				{
   10329 					continue;
   10330 				}
   10331 
   10332 				testCase test_case = { align, type, should_fail, (Utils::Shader::STAGES)stage };
   10333 
   10334 				m_test_cases.push_back(test_case);
   10335 			}
   10336 		}
   10337 	}
   10338 }
   10339 
   10340 /** Check if value is power of 2
   10341  *
   10342  * @param val Tested value
   10343  *
   10344  * @return true if val is power of 2, false otherwise
   10345  **/
   10346 bool UniformBlockMemberAlignNonPowerOf2Test::isPowerOf2(GLuint val)
   10347 {
   10348 	if (0 == val)
   10349 	{
   10350 		return false;
   10351 	}
   10352 
   10353 	return (0 == (val & (val - 1)));
   10354 }
   10355 
   10356 /** Constructor
   10357  *
   10358  * @param context Test framework context
   10359  **/
   10360 UniformBlockAlignmentTest::UniformBlockAlignmentTest(deqp::Context& context)
   10361 	: TextureTestBase(context, "uniform_block_alignment", "Test verifies offset and alignment of uniform buffer")
   10362 {
   10363 }
   10364 
   10365 /** Get interface of program
   10366  *
   10367  * @param ignored
   10368  * @param program_interface Interface of program
   10369  * @param varying_passthrough Collection of connections between in and out variables
   10370  **/
   10371 void UniformBlockAlignmentTest::getProgramInterface(GLuint /* test_case_index */,
   10372 													Utils::ProgramInterface&   program_interface,
   10373 													Utils::VaryingPassthrough& varying_passthrough)
   10374 {
   10375 	static const Utils::Type vec4 = Utils::Type::vec4;
   10376 
   10377 #if WRKARD_UNIFORMBLOCKALIGNMENT
   10378 
   10379 	static const GLuint block_align = 16;
   10380 
   10381 #else /* WRKARD_UNIFORMBLOCKALIGNMENT */
   10382 
   10383 	static const GLuint block_align = 64;
   10384 
   10385 #endif /* WRKARD_UNIFORMBLOCKALIGNMENT */
   10386 
   10387 	static const GLuint vec4_stride = 16;
   10388 	static const GLuint data_stride = vec4_stride * 2; /* one vec4 + one scalar aligned to 16 */
   10389 
   10390 	/*Fixed a test issue, the fifth_offset should be calculated by block_align, instead of fifth_align, according to spec, the actual
   10391 	 alignment of a member will be the greater of the specified alignment and the base aligment for the member type
   10392 	 */
   10393 	const GLuint first_offset  = 0;																		/* vec4 at 0 */
   10394 	const GLuint second_offset = Utils::Type::GetActualOffset(first_offset + vec4_stride, block_align); /* Data at 32 */
   10395 	const GLuint third_offset =
   10396 		Utils::Type::GetActualOffset(second_offset + data_stride, block_align); /* Data[2] at 64 */
   10397 	const GLuint fourth_offset =
   10398 		Utils::Type::GetActualOffset(third_offset + data_stride * 2, block_align); /* vec4[3] at 96 */
   10399 	const GLuint fifth_offset =
   10400 		Utils::Type::GetActualOffset(fourth_offset + vec4_stride * 3, block_align); /* vec4[2] at 160 */
   10401 	const GLuint sixth_offset =
   10402 		Utils::Type::GetActualOffset(fifth_offset + vec4_stride * 2, block_align); /* Data at 192 */
   10403 
   10404 	Utils::Interface* structure = program_interface.Structure("Data");
   10405 
   10406 	structure->Member("vector", "", 0 /* expected_component */, 0 /* expected_location */, Utils::Type::vec4,
   10407 					  false /* normalized */, 0 /* n_array_elements */, Utils::Type::vec4.GetSize(), 0 /* offset */);
   10408 
   10409 	structure->Member("scalar", "", 0 /* expected_component */, 0 /* expected_location */, Utils::Type::_float,
   10410 					  false /* normalized */, 0 /* n_array_elements */, Utils::Type::_float.GetSize(),
   10411 					  Utils::Type::vec4.GetSize() /* offset */);
   10412 
   10413 	/* Prepare Block */
   10414 	Utils::Interface* vs_uni_block = program_interface.Block("vs_uni_Block");
   10415 
   10416 	vs_uni_block->Member("first", "", 0 /* expected_component */, 0 /* expected_location */, Utils::Type::vec4,
   10417 						 false /* normalized */, 0 /* n_array_elements */, vec4_stride, first_offset /* offset */);
   10418 
   10419 	vs_uni_block->Member("second", "", 0 /* expected_component */, 0 /* expected_location */, structure,
   10420 						 0 /* n_array_elements */, data_stride, second_offset);
   10421 
   10422 	vs_uni_block->Member("third", "", 0 /* expected_component */, 0 /* expected_location */, structure,
   10423 						 2 /* n_array_elements */, data_stride, third_offset);
   10424 
   10425 	vs_uni_block->Member("fourth", "", 0 /* expected_component */, 0 /* expected_location */, vec4,
   10426 						 false /* normalized */, 3 /* n_array_elements */, vec4_stride, fourth_offset);
   10427 
   10428 	vs_uni_block->Member("fifth", "layout(align = 64)", 0 /* expected_component */, 0 /* expected_location */, vec4,
   10429 						 false /* normalized */, 2 /* n_array_elements */, vec4_stride, fifth_offset);
   10430 
   10431 	vs_uni_block->Member("sixth", "", 0 /* expected_component */, 0 /* expected_location */, structure,
   10432 						 0 /* n_array_elements */, data_stride, sixth_offset);
   10433 
   10434 	const GLuint stride = calculateStride(*vs_uni_block);
   10435 	m_data.resize(stride);
   10436 	generateData(*vs_uni_block, 0, m_data);
   10437 
   10438 	Utils::ShaderInterface& vs_si = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   10439 
   10440 /* Add uniform BLOCK */
   10441 #if WRKARD_UNIFORMBLOCKALIGNMENT
   10442 	vs_si.Uniform("vs_uni_block", "layout (std140, binding = BINDING)", 0, 0, vs_uni_block, 0,
   10443 				  static_cast<GLuint>(m_data.size()), 0, &m_data[0], m_data.size());
   10444 #else  /* WRKARD_UNIFORMBLOCKALIGNMENT */
   10445 	vs_si.Uniform("vs_uni_block", "layout (std140, binding = BINDING, align = 64)", 0, 0, vs_uni_block, 0,
   10446 				  static_cast<GLuint>(m_data.size()), 0, &m_data[0], m_data.size());
   10447 #endif /* WRKARD_UNIFORMBLOCKALIGNMENT */
   10448 
   10449 	program_interface.CloneVertexInterface(varying_passthrough);
   10450 }
   10451 
   10452 /** Constructor
   10453  *
   10454  * @param context Test framework context
   10455  **/
   10456 SSBMemberOffsetAndAlignTest::SSBMemberOffsetAndAlignTest(deqp::Context& context)
   10457 	: TextureTestBase(context, "ssb_member_offset_and_align",
   10458 					  "Test verifies offsets and alignment of storage buffer members")
   10459 {
   10460 }
   10461 
   10462 /** Get interface of program
   10463  *
   10464  * @param test_case_index     Test case index
   10465  * @param program_interface   Interface of program
   10466  * @param varying_passthrough Collection of connections between in and out variables
   10467  **/
   10468 void SSBMemberOffsetAndAlignTest::getProgramInterface(GLuint					 test_case_index,
   10469 													  Utils::ProgramInterface&   program_interface,
   10470 													  Utils::VaryingPassthrough& varying_passthrough)
   10471 {
   10472 	std::string globals = "const int basic_size = BASIC_SIZE;\n"
   10473 						  "const int type_align = TYPE_ALIGN;\n"
   10474 						  "const int type_size  = TYPE_SIZE;\n";
   10475 
   10476 	Utils::Type  type		 = getType(test_case_index);
   10477 	GLuint		 basic_size  = Utils::Type::GetTypeSize(type.m_basic_type);
   10478 	const GLuint base_align  = type.GetBaseAlignment(false);
   10479 	const GLuint array_align = type.GetBaseAlignment(true);
   10480 	const GLuint base_stride = Utils::Type::CalculateStd140Stride(base_align, type.m_n_columns, 0);
   10481 	const GLuint type_align  = Utils::roundUpToPowerOf2(base_stride);
   10482 
   10483 	/* Calculate offsets */
   10484 	const GLuint first_offset  = 0;
   10485 	const GLuint second_offset = type.GetActualOffset(base_stride, basic_size / 2);
   10486 
   10487 #if WRKARD_UNIFORMBLOCKMEMBEROFFSETANDALIGNTEST
   10488 
   10489 	const GLuint third_offset   = type.GetActualOffset(second_offset + base_stride, base_align);
   10490 	const GLuint fourth_offset  = type.GetActualOffset(third_offset + base_stride, base_align);
   10491 	const GLuint fifth_offset   = type.GetActualOffset(fourth_offset + base_stride, base_align);
   10492 	const GLuint sixth_offset   = type.GetActualOffset(fifth_offset + base_stride, array_align);
   10493 	const GLuint seventh_offset = type.GetActualOffset(sixth_offset + base_stride, array_align);
   10494 	const GLuint eigth_offset   = type.GetActualOffset(seventh_offset + base_stride, array_align);
   10495 
   10496 #else /* WRKARD_UNIFORMBLOCKMEMBEROFFSETANDALIGNTEST */
   10497 
   10498 	const GLuint third_offset   = type.GetActualOffset(second_offset + base_stride, 2 * type_align);
   10499 	const GLuint fourth_offset  = type.GetActualOffset(3 * type_align + base_stride, base_align);
   10500 	const GLuint fifth_offset   = type.GetActualOffset(fourth_offset + base_stride, base_align);
   10501 	const GLuint sixth_offset   = type.GetActualOffset(fifth_offset + base_stride, array_align);
   10502 	const GLuint seventh_offset = type.GetActualOffset(sixth_offset + base_stride, array_align);
   10503 	const GLuint eigth_offset   = type.GetActualOffset(seventh_offset + base_stride, 8 * basic_size);
   10504 
   10505 #endif /* WRKARD_UNIFORMBLOCKMEMBEROFFSETANDALIGNTEST */
   10506 
   10507 	/* Prepare data */
   10508 	const std::vector<GLubyte>& first  = type.GenerateData();
   10509 	const std::vector<GLubyte>& second = type.GenerateData();
   10510 	const std::vector<GLubyte>& third  = type.GenerateData();
   10511 	const std::vector<GLubyte>& fourth = type.GenerateData();
   10512 
   10513 	m_data.resize(eigth_offset + base_stride);
   10514 	GLubyte* ptr = &m_data[0];
   10515 	memcpy(ptr + first_offset, &first[0], first.size());
   10516 	memcpy(ptr + second_offset, &second[0], second.size());
   10517 	memcpy(ptr + third_offset, &third[0], third.size());
   10518 	memcpy(ptr + fourth_offset, &fourth[0], fourth.size());
   10519 	memcpy(ptr + fifth_offset, &fourth[0], fourth.size());
   10520 	memcpy(ptr + sixth_offset, &third[0], third.size());
   10521 	memcpy(ptr + seventh_offset, &second[0], second.size());
   10522 	memcpy(ptr + eigth_offset, &first[0], first.size());
   10523 
   10524 	/* Prepare globals */
   10525 	size_t position = 0;
   10526 	GLchar buffer[16];
   10527 
   10528 	sprintf(buffer, "%d", basic_size);
   10529 	Utils::replaceToken("BASIC_SIZE", position, buffer, globals);
   10530 
   10531 	sprintf(buffer, "%d", type_align);
   10532 	Utils::replaceToken("TYPE_ALIGN", position, buffer, globals);
   10533 
   10534 	sprintf(buffer, "%d", base_stride);
   10535 	Utils::replaceToken("TYPE_SIZE", position, buffer, globals);
   10536 
   10537 	/* Prepare Block */
   10538 	Utils::Interface* vs_buf_block = program_interface.Block("vs_buf_Block");
   10539 
   10540 	vs_buf_block->Member("at_first_offset", "layout(offset = 0, align = 8 * basic_size)", 0 /* expected_component */,
   10541 						 0 /* expected_location */, type, false /* normalized */, 0 /* n_array_elements */, base_stride,
   10542 						 first_offset);
   10543 
   10544 	vs_buf_block->Member("at_second_offset", "layout(offset = type_size, align = basic_size / 2)",
   10545 						 0 /* expected_component */, 0 /* expected_location */, type, false /* normalized */,
   10546 						 0 /* n_array_elements */, base_stride, second_offset);
   10547 
   10548 	vs_buf_block->Member("at_third_offset", "layout(align = 2 * type_align)", 0 /* expected_component */,
   10549 						 0 /* expected_location */, type, false /* normalized */, 0 /* n_array_elements */, base_stride,
   10550 						 third_offset);
   10551 
   10552 	vs_buf_block->Member("at_fourth_offset", "layout(offset = 3 * type_align + type_size)", 0 /* expected_component */,
   10553 						 0 /* expected_location */, type, false /* normalized */, 0 /* n_array_elements */, base_stride,
   10554 						 fourth_offset);
   10555 
   10556 	vs_buf_block->Member("at_fifth_offset", "", 0 /* expected_component */, 0 /* expected_location */, type,
   10557 						 false /* normalized */, 0 /* n_array_elements */, base_stride, fifth_offset);
   10558 
   10559 	vs_buf_block->Member("at_sixth_offset", "", 0 /* expected_component */, 0 /* expected_location */, type,
   10560 						 false /* normalized */, 2 /* n_array_elements */, array_align * 2, sixth_offset);
   10561 
   10562 	vs_buf_block->Member("at_eigth_offset", "layout(align = 8 * basic_size)", 0 /* expected_component */,
   10563 						 0 /* expected_location */, type, false /* normalized */, 0 /* n_array_elements */, base_stride,
   10564 						 eigth_offset);
   10565 
   10566 	Utils::ShaderInterface& vs_si = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   10567 
   10568 	/* Add globals */
   10569 	vs_si.m_globals = globals;
   10570 
   10571 	/* Add uniform BLOCK */
   10572 	vs_si.SSB("vs_buf_block", "layout (std140, binding = BINDING)", 0, 0, vs_buf_block, 0,
   10573 			  static_cast<GLuint>(m_data.size()), 0, &m_data[0], m_data.size());
   10574 
   10575 	/* */
   10576 	program_interface.CloneVertexInterface(varying_passthrough);
   10577 }
   10578 
   10579 /** Get type name
   10580  *
   10581  * @param test_case_index Index of test case
   10582  *
   10583  * @return Name of type test in test_case_index
   10584  **/
   10585 std::string SSBMemberOffsetAndAlignTest::getTestCaseName(glw::GLuint test_case_index)
   10586 {
   10587 	return getTypeName(test_case_index);
   10588 }
   10589 
   10590 /** Returns number of types to test
   10591  *
   10592  * @return Number of types, 34
   10593  **/
   10594 glw::GLuint SSBMemberOffsetAndAlignTest::getTestCaseNumber()
   10595 {
   10596 	return getTypesNumber();
   10597 }
   10598 
   10599 /** Prepare code snippet that will verify in and uniform variables
   10600  *
   10601  * @param ignored
   10602  * @param ignored
   10603  * @param stage   Shader stage
   10604  *
   10605  * @return Code that verify variables
   10606  **/
   10607 std::string SSBMemberOffsetAndAlignTest::getVerificationSnippet(GLuint /* test_case_index */,
   10608 																Utils::ProgramInterface& /* program_interface */,
   10609 																Utils::Shader::STAGES stage)
   10610 {
   10611 	std::string verification = "if ( (PREFIXblock.at_first_offset  != PREFIXblock.at_eigth_offset   ) ||\n"
   10612 							   "         (PREFIXblock.at_second_offset != PREFIXblock.at_sixth_offset[1]) ||\n"
   10613 							   "         (PREFIXblock.at_third_offset  != PREFIXblock.at_sixth_offset[0]) ||\n"
   10614 							   "         (PREFIXblock.at_fourth_offset != PREFIXblock.at_fifth_offset   )  )\n"
   10615 							   "    {\n"
   10616 							   "        result = 0;\n"
   10617 							   "    }";
   10618 
   10619 	const GLchar* prefix = Utils::ProgramInterface::GetStagePrefix(stage, Utils::Variable::SSB);
   10620 
   10621 	Utils::replaceAllTokens("PREFIX", prefix, verification);
   10622 
   10623 	return verification;
   10624 }
   10625 
   10626 /** Selects if "draw" stages are relevant for test
   10627  *
   10628  * @param ignored
   10629  *
   10630  * @return true if all stages support shader storage buffers, false otherwise
   10631  **/
   10632 bool SSBMemberOffsetAndAlignTest::isDrawRelevant(GLuint /* test_case_index */)
   10633 {
   10634 	const Functions& gl					   = m_context.getRenderContext().getFunctions();
   10635 	GLint			 gs_supported_buffers  = 0;
   10636 	GLint			 tcs_supported_buffers = 0;
   10637 	GLint			 tes_supported_buffers = 0;
   10638 	GLint			 vs_supported_buffers  = 0;
   10639 
   10640 	gl.getIntegerv(GL_MAX_GEOMETRY_SHADER_STORAGE_BLOCKS, &gs_supported_buffers);
   10641 	gl.getIntegerv(GL_MAX_TESS_CONTROL_SHADER_STORAGE_BLOCKS, &tcs_supported_buffers);
   10642 	gl.getIntegerv(GL_MAX_TESS_EVALUATION_SHADER_STORAGE_BLOCKS, &tes_supported_buffers);
   10643 	gl.getIntegerv(GL_MAX_VERTEX_SHADER_STORAGE_BLOCKS, &vs_supported_buffers);
   10644 
   10645 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   10646 
   10647 	return ((1 <= gs_supported_buffers) && (1 <= tcs_supported_buffers) && (1 <= tes_supported_buffers) &&
   10648 			(1 <= vs_supported_buffers));
   10649 }
   10650 
   10651 /** Constructor
   10652  *
   10653  * @param context Test framework context
   10654  **/
   10655 SSBLayoutQualifierConflictTest::SSBLayoutQualifierConflictTest(deqp::Context& context)
   10656 	: NegativeTestBase(context, "ssb_layout_qualifier_conflict", "Test verifies that std140 or std430 is required when "
   10657 																 "offset and/or align qualifiers are used with storage "
   10658 																 "block")
   10659 {
   10660 	/* Nothing to be done here */
   10661 }
   10662 
   10663 /** Source for given test case and stage
   10664  *
   10665  * @param test_case_index Index of test case
   10666  * @param stage           Shader stage
   10667  *
   10668  * @return Shader source
   10669  **/
   10670 std::string SSBLayoutQualifierConflictTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   10671 {
   10672 	static const GLchar* cs = "#version 430 core\n"
   10673 							  "#extension GL_ARB_enhanced_layouts : require\n"
   10674 							  "\n"
   10675 							  "layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
   10676 							  "\n"
   10677 							  "layout (QUALIFIERbinding = BINDING) buffer cs_Block {\n"
   10678 							  "    layout(offset = 16) vec4 boy;\n"
   10679 							  "    layout(align  = 64) vec4 man;\n"
   10680 							  "} uni_block;\n"
   10681 							  "\n"
   10682 							  "writeonly uniform image2D uni_image;\n"
   10683 							  "\n"
   10684 							  "void main()\n"
   10685 							  "{\n"
   10686 							  "    vec4 result = uni_block.boy + uni_block.man;\n"
   10687 							  "\n"
   10688 							  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), result);\n"
   10689 							  "}\n"
   10690 							  "\n";
   10691 	static const GLchar* fs = "#version 430 core\n"
   10692 							  "#extension GL_ARB_enhanced_layouts : require\n"
   10693 							  "\n"
   10694 							  "layout (QUALIFIERbinding = BINDING) buffer Block {\n"
   10695 							  "    layout(offset = 16) vec4 boy;\n"
   10696 							  "    layout(align  = 64) vec4 man;\n"
   10697 							  "} uni_block;\n"
   10698 							  "\n"
   10699 							  "in  vec4 gs_fs;\n"
   10700 							  "out vec4 fs_out;\n"
   10701 							  "\n"
   10702 							  "void main()\n"
   10703 							  "{\n"
   10704 							  "    fs_out = gs_fs + uni_block.boy + uni_block.man;\n"
   10705 							  "}\n"
   10706 							  "\n";
   10707 	static const GLchar* gs = "#version 430 core\n"
   10708 							  "#extension GL_ARB_enhanced_layouts : require\n"
   10709 							  "\n"
   10710 							  "layout(points)                           in;\n"
   10711 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   10712 							  "\n"
   10713 							  "layout (QUALIFIERbinding = BINDING) buffer gs_Block {\n"
   10714 							  "    layout(offset = 16) vec4 boy;\n"
   10715 							  "    layout(align  = 64) vec4 man;\n"
   10716 							  "} uni_block;\n"
   10717 							  "\n"
   10718 							  "in  vec4 tes_gs[];\n"
   10719 							  "out vec4 gs_fs;\n"
   10720 							  "\n"
   10721 							  "void main()\n"
   10722 							  "{\n"
   10723 							  "    gs_fs = tes_gs[0] + uni_block.boy + uni_block.man;\n"
   10724 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   10725 							  "    EmitVertex();\n"
   10726 							  "    gs_fs = tes_gs[0] + uni_block.boy + uni_block.man;\n"
   10727 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   10728 							  "    EmitVertex();\n"
   10729 							  "    gs_fs = tes_gs[0] + uni_block.boy + uni_block.man;\n"
   10730 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   10731 							  "    EmitVertex();\n"
   10732 							  "    gs_fs = tes_gs[0] + uni_block.boy + uni_block.man;\n"
   10733 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   10734 							  "    EmitVertex();\n"
   10735 							  "}\n"
   10736 							  "\n";
   10737 	static const GLchar* tcs =
   10738 		"#version 430 core\n"
   10739 		"#extension GL_ARB_enhanced_layouts : require\n"
   10740 		"\n"
   10741 		"layout(vertices = 1) out;\n"
   10742 		"\n"
   10743 		"layout (QUALIFIERbinding = BINDING) buffer tcs_Block {\n"
   10744 		"    layout(offset = 16) vec4 boy;\n"
   10745 		"    layout(align  = 64) vec4 man;\n"
   10746 		"} uni_block;\n"
   10747 		"\n"
   10748 		"in  vec4 vs_tcs[];\n"
   10749 		"out vec4 tcs_tes[];\n"
   10750 		"\n"
   10751 		"void main()\n"
   10752 		"{\n"
   10753 		"\n"
   10754 		"    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID] + uni_block.boy + uni_block.man;\n"
   10755 		"\n"
   10756 		"    gl_TessLevelOuter[0] = 1.0;\n"
   10757 		"    gl_TessLevelOuter[1] = 1.0;\n"
   10758 		"    gl_TessLevelOuter[2] = 1.0;\n"
   10759 		"    gl_TessLevelOuter[3] = 1.0;\n"
   10760 		"    gl_TessLevelInner[0] = 1.0;\n"
   10761 		"    gl_TessLevelInner[1] = 1.0;\n"
   10762 		"}\n"
   10763 		"\n";
   10764 	static const GLchar* tes = "#version 430 core\n"
   10765 							   "#extension GL_ARB_enhanced_layouts : require\n"
   10766 							   "\n"
   10767 							   "layout(isolines, point_mode) in;\n"
   10768 							   "\n"
   10769 							   "layout (QUALIFIERbinding = BINDING) buffer tes_Block {\n"
   10770 							   "    layout(offset = 16) vec4 boy;\n"
   10771 							   "    layout(align  = 64) vec4 man;\n"
   10772 							   "} uni_block;\n"
   10773 							   "\n"
   10774 							   "in  vec4 tcs_tes[];\n"
   10775 							   "out vec4 tes_gs;\n"
   10776 							   "\n"
   10777 							   "void main()\n"
   10778 							   "{\n"
   10779 							   "    tes_gs = tcs_tes[0] + uni_block.boy + uni_block.man;\n"
   10780 							   "}\n"
   10781 							   "\n";
   10782 	static const GLchar* vs = "#version 430 core\n"
   10783 							  "#extension GL_ARB_enhanced_layouts : require\n"
   10784 							  "\n"
   10785 							  "layout (QUALIFIERbinding = BINDING) buffer vs_Block {\n"
   10786 							  "    layout(offset = 16) vec4 boy;\n"
   10787 							  "    layout(align  = 64) vec4 man;\n"
   10788 							  "} uni_block;\n"
   10789 							  "\n"
   10790 							  "in  vec4 in_vs;\n"
   10791 							  "out vec4 vs_tcs;\n"
   10792 							  "\n"
   10793 							  "void main()\n"
   10794 							  "{\n"
   10795 							  "    vs_tcs = in_vs + uni_block.boy + uni_block.man;\n"
   10796 							  "}\n"
   10797 							  "\n";
   10798 
   10799 	GLchar		buffer[16];
   10800 	size_t		position = 0;
   10801 	std::string source;
   10802 	testCase&   test_case = m_test_cases[test_case_index];
   10803 	std::string qualifier = getQualifierName(test_case.m_qualifier);
   10804 
   10805 	if (false == qualifier.empty())
   10806 	{
   10807 		qualifier.append(", ");
   10808 	}
   10809 
   10810 	sprintf(buffer, "%d", stage);
   10811 
   10812 	switch (stage)
   10813 	{
   10814 	case Utils::Shader::COMPUTE:
   10815 		source = cs;
   10816 		break;
   10817 	case Utils::Shader::FRAGMENT:
   10818 		source = fs;
   10819 		break;
   10820 	case Utils::Shader::GEOMETRY:
   10821 		source = gs;
   10822 		break;
   10823 	case Utils::Shader::TESS_CTRL:
   10824 		source = tcs;
   10825 		break;
   10826 	case Utils::Shader::TESS_EVAL:
   10827 		source = tes;
   10828 		break;
   10829 	case Utils::Shader::VERTEX:
   10830 		source = vs;
   10831 		break;
   10832 	default:
   10833 		TCU_FAIL("Invalid enum");
   10834 	}
   10835 
   10836 	if (test_case.m_stage == stage)
   10837 	{
   10838 		Utils::replaceToken("QUALIFIER", position, qualifier.c_str(), source);
   10839 	}
   10840 	else
   10841 	{
   10842 		Utils::replaceToken("QUALIFIER", position, "std140, ", source);
   10843 	}
   10844 
   10845 	Utils::replaceToken("BINDING", position, buffer, source);
   10846 
   10847 	return source;
   10848 }
   10849 
   10850 /** Get description of test case
   10851  *
   10852  * @param test_case_index Index of test case
   10853  *
   10854  * @return Qualifier name
   10855  **/
   10856 std::string SSBLayoutQualifierConflictTest::getTestCaseName(GLuint test_case_index)
   10857 {
   10858 	std::string result = getQualifierName(m_test_cases[test_case_index].m_qualifier);
   10859 
   10860 	return result;
   10861 }
   10862 
   10863 /** Get number of test cases
   10864  *
   10865  * @return Number of test cases
   10866  **/
   10867 GLuint SSBLayoutQualifierConflictTest::getTestCaseNumber()
   10868 {
   10869 	return static_cast<GLuint>(m_test_cases.size());
   10870 }
   10871 
   10872 /** Selects if "compute" stage is relevant for test
   10873  *
   10874  * @param test_case_index Index of test case
   10875  *
   10876  * @return true when tested stage is compute
   10877  **/
   10878 bool SSBLayoutQualifierConflictTest::isComputeRelevant(GLuint test_case_index)
   10879 {
   10880 	return (Utils::Shader::COMPUTE == m_test_cases[test_case_index].m_stage);
   10881 }
   10882 
   10883 /** Selects if compilation failure is expected result
   10884  *
   10885  * @param test_case_index Index of test case
   10886  *
   10887  * @return false for STD140 and STD430 cases, true otherwise
   10888  **/
   10889 bool SSBLayoutQualifierConflictTest::isFailureExpected(GLuint test_case_index)
   10890 {
   10891 	const QUALIFIERS qualifier = m_test_cases[test_case_index].m_qualifier;
   10892 
   10893 	return !((STD140 == qualifier) || (STD430 == qualifier));
   10894 }
   10895 
   10896 /** Checks if stage is supported
   10897  *
   10898  * @param stage Shader stage
   10899  *
   10900  * @return true if supported, false otherwise
   10901  **/
   10902 bool SSBLayoutQualifierConflictTest::isStageSupported(Utils::Shader::STAGES stage)
   10903 {
   10904 	const Functions& gl					   = m_context.getRenderContext().getFunctions();
   10905 	GLint			 max_supported_buffers = 0;
   10906 	GLenum			 pname				   = 0;
   10907 
   10908 	switch (stage)
   10909 	{
   10910 	case Utils::Shader::COMPUTE:
   10911 		pname = GL_MAX_COMPUTE_SHADER_STORAGE_BLOCKS;
   10912 		break;
   10913 	case Utils::Shader::FRAGMENT:
   10914 		pname = GL_MAX_FRAGMENT_SHADER_STORAGE_BLOCKS;
   10915 		break;
   10916 	case Utils::Shader::GEOMETRY:
   10917 		pname = GL_MAX_GEOMETRY_SHADER_STORAGE_BLOCKS;
   10918 		break;
   10919 	case Utils::Shader::TESS_CTRL:
   10920 		pname = GL_MAX_TESS_CONTROL_SHADER_STORAGE_BLOCKS;
   10921 		break;
   10922 	case Utils::Shader::TESS_EVAL:
   10923 		pname = GL_MAX_TESS_EVALUATION_SHADER_STORAGE_BLOCKS;
   10924 		break;
   10925 	case Utils::Shader::VERTEX:
   10926 		pname = GL_MAX_VERTEX_SHADER_STORAGE_BLOCKS;
   10927 		break;
   10928 	default:
   10929 		TCU_FAIL("Invalid enum");
   10930 	}
   10931 
   10932 	gl.getIntegerv(pname, &max_supported_buffers);
   10933 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   10934 
   10935 	return 1 <= max_supported_buffers;
   10936 }
   10937 
   10938 /** Prepare all test cases
   10939  *
   10940  **/
   10941 void SSBLayoutQualifierConflictTest::testInit()
   10942 {
   10943 	bool stage_support[Utils::Shader::STAGE_MAX];
   10944 
   10945 	for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   10946 	{
   10947 		stage_support[stage] = isStageSupported((Utils::Shader::STAGES)stage);
   10948 	}
   10949 
   10950 	for (GLuint qualifier = 0; qualifier < QUALIFIERS_MAX; ++qualifier)
   10951 	{
   10952 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   10953 		{
   10954 			if (false == stage_support[stage])
   10955 			{
   10956 				continue;
   10957 			}
   10958 
   10959 			testCase test_case = { (QUALIFIERS)qualifier, (Utils::Shader::STAGES)stage };
   10960 
   10961 			m_test_cases.push_back(test_case);
   10962 		}
   10963 	}
   10964 }
   10965 
   10966 /** Get name of glsl constant
   10967  *
   10968  * @param Constant id
   10969  *
   10970  * @return Name of constant used in GLSL
   10971  **/
   10972 const GLchar* SSBLayoutQualifierConflictTest::getQualifierName(QUALIFIERS qualifier)
   10973 {
   10974 	const GLchar* name = "";
   10975 
   10976 	switch (qualifier)
   10977 	{
   10978 	case DEFAULT:
   10979 		name = "";
   10980 		break;
   10981 	case STD140:
   10982 		name = "std140";
   10983 		break;
   10984 	case STD430:
   10985 		name = "std430";
   10986 		break;
   10987 	case SHARED:
   10988 		name = "shared";
   10989 		break;
   10990 	case PACKED:
   10991 		name = "packed";
   10992 		break;
   10993 	default:
   10994 		TCU_FAIL("Invalid enum");
   10995 	}
   10996 
   10997 	return name;
   10998 }
   10999 
   11000 /** Constructor
   11001  *
   11002  * @param context Test framework context
   11003  **/
   11004 SSBMemberInvalidOffsetAlignmentTest::SSBMemberInvalidOffsetAlignmentTest(deqp::Context& context)
   11005 	: UniformBlockMemberInvalidOffsetAlignmentTest(
   11006 		  context, "ssb_member_invalid_offset_alignment",
   11007 		  "Test verifies that invalid alignment of offset qualifiers cause compilation failure")
   11008 {
   11009 	/* Nothing to be done here */
   11010 }
   11011 
   11012 /** Get the maximum size for a shader storage block
   11013  *
   11014  * @return The maximum size in basic machine units of a shader storage block.
   11015  **/
   11016 GLint SSBMemberInvalidOffsetAlignmentTest::getMaxBlockSize()
   11017 {
   11018 	const Functions& gl		  = m_context.getRenderContext().getFunctions();
   11019 	GLint			 max_size = 0;
   11020 
   11021 	gl.getIntegerv(GL_MAX_SHADER_STORAGE_BLOCK_SIZE, &max_size);
   11022 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   11023 
   11024 	return max_size;
   11025 }
   11026 
   11027 /** Source for given test case and stage
   11028  *
   11029  * @param test_case_index Index of test case
   11030  * @param stage           Shader stage
   11031  *
   11032  * @return Shader source
   11033  **/
   11034 std::string SSBMemberInvalidOffsetAlignmentTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   11035 {
   11036 	static const GLchar* cs = "#version 430 core\n"
   11037 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11038 							  "\n"
   11039 							  "layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
   11040 							  "\n"
   11041 							  "layout (std140) buffer Block {\n"
   11042 							  "    layout (offset = OFFSET) TYPE member;\n"
   11043 							  "} block;\n"
   11044 							  "\n"
   11045 							  "writeonly uniform image2D uni_image;\n"
   11046 							  "\n"
   11047 							  "void main()\n"
   11048 							  "{\n"
   11049 							  "    vec4 result = vec4(1, 0, 0.5, 1);\n"
   11050 							  "\n"
   11051 							  "    if (TYPE(1) == block.member)\n"
   11052 							  "    {\n"
   11053 							  "        result = vec4(1, 1, 1, 1);\n"
   11054 							  "    }\n"
   11055 							  "\n"
   11056 							  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), result);\n"
   11057 							  "}\n"
   11058 							  "\n";
   11059 	static const GLchar* fs = "#version 430 core\n"
   11060 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11061 							  "\n"
   11062 							  "in  vec4 gs_fs;\n"
   11063 							  "out vec4 fs_out;\n"
   11064 							  "\n"
   11065 							  "void main()\n"
   11066 							  "{\n"
   11067 							  "    fs_out = gs_fs;\n"
   11068 							  "}\n"
   11069 							  "\n";
   11070 	static const GLchar* fs_tested = "#version 430 core\n"
   11071 									 "#extension GL_ARB_enhanced_layouts : require\n"
   11072 									 "\n"
   11073 									 "layout (std140) buffer Block {\n"
   11074 									 "    layout (offset = OFFSET) TYPE member;\n"
   11075 									 "} block;\n"
   11076 									 "\n"
   11077 									 "in  vec4 gs_fs;\n"
   11078 									 "out vec4 fs_out;\n"
   11079 									 "\n"
   11080 									 "void main()\n"
   11081 									 "{\n"
   11082 									 "    if (TYPE(1) == block.member)\n"
   11083 									 "    {\n"
   11084 									 "        fs_out = vec4(1, 1, 1, 1);\n"
   11085 									 "    }\n"
   11086 									 "\n"
   11087 									 "    fs_out += gs_fs;\n"
   11088 									 "}\n"
   11089 									 "\n";
   11090 	static const GLchar* gs = "#version 430 core\n"
   11091 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11092 							  "\n"
   11093 							  "layout(points)                           in;\n"
   11094 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   11095 							  "\n"
   11096 							  "in  vec4 tes_gs[];\n"
   11097 							  "out vec4 gs_fs;\n"
   11098 							  "\n"
   11099 							  "void main()\n"
   11100 							  "{\n"
   11101 							  "    gs_fs = tes_gs[0];\n"
   11102 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   11103 							  "    EmitVertex();\n"
   11104 							  "    gs_fs = tes_gs[0];\n"
   11105 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   11106 							  "    EmitVertex();\n"
   11107 							  "    gs_fs = tes_gs[0];\n"
   11108 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   11109 							  "    EmitVertex();\n"
   11110 							  "    gs_fs = tes_gs[0];\n"
   11111 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   11112 							  "    EmitVertex();\n"
   11113 							  "}\n"
   11114 							  "\n";
   11115 	static const GLchar* gs_tested = "#version 430 core\n"
   11116 									 "#extension GL_ARB_enhanced_layouts : require\n"
   11117 									 "\n"
   11118 									 "layout(points)                           in;\n"
   11119 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   11120 									 "\n"
   11121 									 "layout (std140) buffer Block {\n"
   11122 									 "    layout (offset = OFFSET) TYPE member;\n"
   11123 									 "} block;\n"
   11124 									 "\n"
   11125 									 "in  vec4 tes_gs[];\n"
   11126 									 "out vec4 gs_fs;\n"
   11127 									 "\n"
   11128 									 "void main()\n"
   11129 									 "{\n"
   11130 									 "    if (TYPE(1) == block.member)\n"
   11131 									 "    {\n"
   11132 									 "        gs_fs = vec4(1, 1, 1, 1);\n"
   11133 									 "    }\n"
   11134 									 "\n"
   11135 									 "    gs_fs += tes_gs[0];\n"
   11136 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   11137 									 "    EmitVertex();\n"
   11138 									 "    gs_fs += tes_gs[0];\n"
   11139 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   11140 									 "    EmitVertex();\n"
   11141 									 "    gs_fs += tes_gs[0];\n"
   11142 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   11143 									 "    EmitVertex();\n"
   11144 									 "    gs_fs += tes_gs[0];\n"
   11145 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   11146 									 "    EmitVertex();\n"
   11147 									 "}\n"
   11148 									 "\n";
   11149 	static const GLchar* tcs = "#version 430 core\n"
   11150 							   "#extension GL_ARB_enhanced_layouts : require\n"
   11151 							   "\n"
   11152 							   "layout(vertices = 1) out;\n"
   11153 							   "\n"
   11154 							   "in  vec4 vs_tcs[];\n"
   11155 							   "out vec4 tcs_tes[];\n"
   11156 							   "\n"
   11157 							   "void main()\n"
   11158 							   "{\n"
   11159 							   "\n"
   11160 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   11161 							   "\n"
   11162 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   11163 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   11164 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   11165 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   11166 							   "    gl_TessLevelInner[0] = 1.0;\n"
   11167 							   "    gl_TessLevelInner[1] = 1.0;\n"
   11168 							   "}\n"
   11169 							   "\n";
   11170 	static const GLchar* tcs_tested = "#version 430 core\n"
   11171 									  "#extension GL_ARB_enhanced_layouts : require\n"
   11172 									  "\n"
   11173 									  "layout(vertices = 1) out;\n"
   11174 									  "\n"
   11175 									  "layout (std140) buffer Block {\n"
   11176 									  "    layout (offset = OFFSET) TYPE member;\n"
   11177 									  "} block;\n"
   11178 									  "\n"
   11179 									  "in  vec4 vs_tcs[];\n"
   11180 									  "out vec4 tcs_tes[];\n"
   11181 									  "\n"
   11182 									  "void main()\n"
   11183 									  "{\n"
   11184 									  "    if (TYPE(1) == block.member)\n"
   11185 									  "    {\n"
   11186 									  "        tcs_tes[gl_InvocationID] = vec4(1, 1, 1, 1);\n"
   11187 									  "    }\n"
   11188 									  "\n"
   11189 									  "\n"
   11190 									  "    tcs_tes[gl_InvocationID] += vs_tcs[gl_InvocationID];\n"
   11191 									  "\n"
   11192 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   11193 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   11194 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   11195 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   11196 									  "    gl_TessLevelInner[0] = 1.0;\n"
   11197 									  "    gl_TessLevelInner[1] = 1.0;\n"
   11198 									  "}\n"
   11199 									  "\n";
   11200 	static const GLchar* tes = "#version 430 core\n"
   11201 							   "#extension GL_ARB_enhanced_layouts : require\n"
   11202 							   "\n"
   11203 							   "layout(isolines, point_mode) in;\n"
   11204 							   "\n"
   11205 							   "in  vec4 tcs_tes[];\n"
   11206 							   "out vec4 tes_gs;\n"
   11207 							   "\n"
   11208 							   "void main()\n"
   11209 							   "{\n"
   11210 							   "    tes_gs = tcs_tes[0];\n"
   11211 							   "}\n"
   11212 							   "\n";
   11213 	static const GLchar* tes_tested = "#version 430 core\n"
   11214 									  "#extension GL_ARB_enhanced_layouts : require\n"
   11215 									  "\n"
   11216 									  "layout(isolines, point_mode) in;\n"
   11217 									  "\n"
   11218 									  "layout (std140) buffer Block {\n"
   11219 									  "    layout (offset = OFFSET) TYPE member;\n"
   11220 									  "} block;\n"
   11221 									  "\n"
   11222 									  "in  vec4 tcs_tes[];\n"
   11223 									  "out vec4 tes_gs;\n"
   11224 									  "\n"
   11225 									  "void main()\n"
   11226 									  "{\n"
   11227 									  "    if (TYPE(1) == block.member)\n"
   11228 									  "    {\n"
   11229 									  "        tes_gs = vec4(1, 1, 1, 1);\n"
   11230 									  "    }\n"
   11231 									  "\n"
   11232 									  "    tes_gs += tcs_tes[0];\n"
   11233 									  "}\n"
   11234 									  "\n";
   11235 	static const GLchar* vs = "#version 430 core\n"
   11236 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11237 							  "\n"
   11238 							  "in  vec4 in_vs;\n"
   11239 							  "out vec4 vs_tcs;\n"
   11240 							  "\n"
   11241 							  "void main()\n"
   11242 							  "{\n"
   11243 							  "    vs_tcs = in_vs;\n"
   11244 							  "}\n"
   11245 							  "\n";
   11246 	static const GLchar* vs_tested = "#version 430 core\n"
   11247 									 "#extension GL_ARB_enhanced_layouts : require\n"
   11248 									 "\n"
   11249 									 "layout (std140) buffer Block {\n"
   11250 									 "    layout (offset = OFFSET) TYPE member;\n"
   11251 									 "} block;\n"
   11252 									 "\n"
   11253 									 "in  vec4 in_vs;\n"
   11254 									 "out vec4 vs_tcs;\n"
   11255 									 "\n"
   11256 									 "void main()\n"
   11257 									 "{\n"
   11258 									 "    if (TYPE(1) == block.member)\n"
   11259 									 "    {\n"
   11260 									 "        vs_tcs = vec4(1, 1, 1, 1);\n"
   11261 									 "    }\n"
   11262 									 "\n"
   11263 									 "    vs_tcs += in_vs;\n"
   11264 									 "}\n"
   11265 									 "\n";
   11266 
   11267 	std::string source;
   11268 	testCase&   test_case = m_test_cases[test_case_index];
   11269 
   11270 	if (test_case.m_stage == stage)
   11271 	{
   11272 		GLchar			   buffer[16];
   11273 		const GLuint	   offset	= test_case.m_offset;
   11274 		size_t			   position  = 0;
   11275 		const Utils::Type& type		 = test_case.m_type;
   11276 		const GLchar*	  type_name = type.GetGLSLTypeName();
   11277 
   11278 		sprintf(buffer, "%d", offset);
   11279 
   11280 		switch (stage)
   11281 		{
   11282 		case Utils::Shader::COMPUTE:
   11283 			source = cs;
   11284 			break;
   11285 		case Utils::Shader::FRAGMENT:
   11286 			source = fs_tested;
   11287 			break;
   11288 		case Utils::Shader::GEOMETRY:
   11289 			source = gs_tested;
   11290 			break;
   11291 		case Utils::Shader::TESS_CTRL:
   11292 			source = tcs_tested;
   11293 			break;
   11294 		case Utils::Shader::TESS_EVAL:
   11295 			source = tes_tested;
   11296 			break;
   11297 		case Utils::Shader::VERTEX:
   11298 			source = vs_tested;
   11299 			break;
   11300 		default:
   11301 			TCU_FAIL("Invalid enum");
   11302 		}
   11303 
   11304 		Utils::replaceToken("OFFSET", position, buffer, source);
   11305 		Utils::replaceToken("TYPE", position, type_name, source);
   11306 		Utils::replaceToken("TYPE", position, type_name, source);
   11307 	}
   11308 	else
   11309 	{
   11310 		switch (stage)
   11311 		{
   11312 		case Utils::Shader::FRAGMENT:
   11313 			source = fs;
   11314 			break;
   11315 		case Utils::Shader::GEOMETRY:
   11316 			source = gs;
   11317 			break;
   11318 		case Utils::Shader::TESS_CTRL:
   11319 			source = tcs;
   11320 			break;
   11321 		case Utils::Shader::TESS_EVAL:
   11322 			source = tes;
   11323 			break;
   11324 		case Utils::Shader::VERTEX:
   11325 			source = vs;
   11326 			break;
   11327 		default:
   11328 			TCU_FAIL("Invalid enum");
   11329 		}
   11330 	}
   11331 
   11332 	return source;
   11333 }
   11334 
   11335 /** Checks if stage is supported
   11336  *
   11337  * @param stage Shader stage
   11338  *
   11339  * @return true if supported, false otherwise
   11340  **/
   11341 bool SSBMemberInvalidOffsetAlignmentTest::isStageSupported(Utils::Shader::STAGES stage)
   11342 {
   11343 	const Functions& gl					   = m_context.getRenderContext().getFunctions();
   11344 	GLint			 max_supported_buffers = 0;
   11345 	GLenum			 pname				   = 0;
   11346 
   11347 	switch (stage)
   11348 	{
   11349 	case Utils::Shader::COMPUTE:
   11350 		pname = GL_MAX_COMPUTE_SHADER_STORAGE_BLOCKS;
   11351 		break;
   11352 	case Utils::Shader::FRAGMENT:
   11353 		pname = GL_MAX_FRAGMENT_SHADER_STORAGE_BLOCKS;
   11354 		break;
   11355 	case Utils::Shader::GEOMETRY:
   11356 		pname = GL_MAX_GEOMETRY_SHADER_STORAGE_BLOCKS;
   11357 		break;
   11358 	case Utils::Shader::TESS_CTRL:
   11359 		pname = GL_MAX_TESS_CONTROL_SHADER_STORAGE_BLOCKS;
   11360 		break;
   11361 	case Utils::Shader::TESS_EVAL:
   11362 		pname = GL_MAX_TESS_EVALUATION_SHADER_STORAGE_BLOCKS;
   11363 		break;
   11364 	case Utils::Shader::VERTEX:
   11365 		pname = GL_MAX_VERTEX_SHADER_STORAGE_BLOCKS;
   11366 		break;
   11367 	default:
   11368 		TCU_FAIL("Invalid enum");
   11369 	}
   11370 
   11371 	gl.getIntegerv(pname, &max_supported_buffers);
   11372 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   11373 
   11374 	return 1 <= max_supported_buffers;
   11375 }
   11376 
   11377 /** Constructor
   11378  *
   11379  * @param context Test framework context
   11380  **/
   11381 SSBMemberOverlappingOffsetsTest::SSBMemberOverlappingOffsetsTest(deqp::Context& context)
   11382 	: UniformBlockMemberOverlappingOffsetsTest(
   11383 		  context, "ssb_member_overlapping_offsets",
   11384 		  "Test verifies that overlapping offsets qualifiers cause compilation failure")
   11385 {
   11386 	/* Nothing to be done here */
   11387 }
   11388 
   11389 /** Source for given test case and stage
   11390  *
   11391  * @param test_case_index Index of test case
   11392  * @param stage           Shader stage
   11393  *
   11394  * @return Shader source
   11395  **/
   11396 std::string SSBMemberOverlappingOffsetsTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   11397 {
   11398 	static const GLchar* cs = "#version 430 core\n"
   11399 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11400 							  "\n"
   11401 							  "layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
   11402 							  "\n"
   11403 							  "layout (std140) buffer Block {\n"
   11404 							  "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   11405 							  "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   11406 							  "} block;\n"
   11407 							  "\n"
   11408 							  "writeonly uniform image2D uni_image;\n"
   11409 							  "\n"
   11410 							  "void main()\n"
   11411 							  "{\n"
   11412 							  "    vec4 result = vec4(1, 0, 0.5, 1);\n"
   11413 							  "\n"
   11414 							  "    if ((BOY_TYPE(1) == block.boy) ||\n"
   11415 							  "        (MAN_TYPE(0) == block.man) )\n"
   11416 							  "    {\n"
   11417 							  "        result = vec4(1, 1, 1, 1);\n"
   11418 							  "    }\n"
   11419 							  "\n"
   11420 							  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), result);\n"
   11421 							  "}\n"
   11422 							  "\n";
   11423 	static const GLchar* fs = "#version 430 core\n"
   11424 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11425 							  "\n"
   11426 							  "in  vec4 gs_fs;\n"
   11427 							  "out vec4 fs_out;\n"
   11428 							  "\n"
   11429 							  "void main()\n"
   11430 							  "{\n"
   11431 							  "    fs_out = gs_fs;\n"
   11432 							  "}\n"
   11433 							  "\n";
   11434 	static const GLchar* fs_tested = "#version 430 core\n"
   11435 									 "#extension GL_ARB_enhanced_layouts : require\n"
   11436 									 "\n"
   11437 									 "layout (std140) buffer Block {\n"
   11438 									 "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   11439 									 "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   11440 									 "} block;\n"
   11441 									 "\n"
   11442 									 "in  vec4 gs_fs;\n"
   11443 									 "out vec4 fs_out;\n"
   11444 									 "\n"
   11445 									 "void main()\n"
   11446 									 "{\n"
   11447 									 "    if ((BOY_TYPE(1) == block.boy) ||\n"
   11448 									 "        (MAN_TYPE(0) == block.man) )\n"
   11449 									 "    {\n"
   11450 									 "        fs_out = vec4(1, 1, 1, 1);\n"
   11451 									 "    }\n"
   11452 									 "\n"
   11453 									 "    fs_out += gs_fs;\n"
   11454 									 "}\n"
   11455 									 "\n";
   11456 	static const GLchar* gs = "#version 430 core\n"
   11457 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11458 							  "\n"
   11459 							  "layout(points)                           in;\n"
   11460 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   11461 							  "\n"
   11462 							  "in  vec4 tes_gs[];\n"
   11463 							  "out vec4 gs_fs;\n"
   11464 							  "\n"
   11465 							  "void main()\n"
   11466 							  "{\n"
   11467 							  "    gs_fs = tes_gs[0];\n"
   11468 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   11469 							  "    EmitVertex();\n"
   11470 							  "    gs_fs = tes_gs[0];\n"
   11471 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   11472 							  "    EmitVertex();\n"
   11473 							  "    gs_fs = tes_gs[0];\n"
   11474 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   11475 							  "    EmitVertex();\n"
   11476 							  "    gs_fs = tes_gs[0];\n"
   11477 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   11478 							  "    EmitVertex();\n"
   11479 							  "}\n"
   11480 							  "\n";
   11481 	static const GLchar* gs_tested = "#version 430 core\n"
   11482 									 "#extension GL_ARB_enhanced_layouts : require\n"
   11483 									 "\n"
   11484 									 "layout(points)                           in;\n"
   11485 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   11486 									 "\n"
   11487 									 "layout (std140) buffer Block {\n"
   11488 									 "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   11489 									 "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   11490 									 "} block;\n"
   11491 									 "\n"
   11492 									 "in  vec4 tes_gs[];\n"
   11493 									 "out vec4 gs_fs;\n"
   11494 									 "\n"
   11495 									 "void main()\n"
   11496 									 "{\n"
   11497 									 "    if ((BOY_TYPE(1) == block.boy) ||\n"
   11498 									 "        (MAN_TYPE(0) == block.man) )\n"
   11499 									 "    {\n"
   11500 									 "        gs_fs = vec4(1, 1, 1, 1);\n"
   11501 									 "    }\n"
   11502 									 "\n"
   11503 									 "    gs_fs += tes_gs[0];\n"
   11504 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   11505 									 "    EmitVertex();\n"
   11506 									 "    gs_fs += tes_gs[0];\n"
   11507 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   11508 									 "    EmitVertex();\n"
   11509 									 "    gs_fs += tes_gs[0];\n"
   11510 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   11511 									 "    EmitVertex();\n"
   11512 									 "    gs_fs += tes_gs[0];\n"
   11513 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   11514 									 "    EmitVertex();\n"
   11515 									 "}\n"
   11516 									 "\n";
   11517 	static const GLchar* tcs = "#version 430 core\n"
   11518 							   "#extension GL_ARB_enhanced_layouts : require\n"
   11519 							   "\n"
   11520 							   "layout(vertices = 1) out;\n"
   11521 							   "\n"
   11522 							   "in  vec4 vs_tcs[];\n"
   11523 							   "out vec4 tcs_tes[];\n"
   11524 							   "\n"
   11525 							   "void main()\n"
   11526 							   "{\n"
   11527 							   "\n"
   11528 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   11529 							   "\n"
   11530 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   11531 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   11532 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   11533 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   11534 							   "    gl_TessLevelInner[0] = 1.0;\n"
   11535 							   "    gl_TessLevelInner[1] = 1.0;\n"
   11536 							   "}\n"
   11537 							   "\n";
   11538 	static const GLchar* tcs_tested = "#version 430 core\n"
   11539 									  "#extension GL_ARB_enhanced_layouts : require\n"
   11540 									  "\n"
   11541 									  "layout(vertices = 1) out;\n"
   11542 									  "\n"
   11543 									  "layout (std140) buffer Block {\n"
   11544 									  "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   11545 									  "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   11546 									  "} block;\n"
   11547 									  "\n"
   11548 									  "in  vec4 vs_tcs[];\n"
   11549 									  "out vec4 tcs_tes[];\n"
   11550 									  "\n"
   11551 									  "void main()\n"
   11552 									  "{\n"
   11553 									  "    if ((BOY_TYPE(1) == block.boy) ||\n"
   11554 									  "        (MAN_TYPE(0) == block.man) )\n"
   11555 									  "    {\n"
   11556 									  "        tcs_tes[gl_InvocationID] = vec4(1, 1, 1, 1);\n"
   11557 									  "    }\n"
   11558 									  "\n"
   11559 									  "\n"
   11560 									  "    tcs_tes[gl_InvocationID] += vs_tcs[gl_InvocationID];\n"
   11561 									  "\n"
   11562 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   11563 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   11564 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   11565 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   11566 									  "    gl_TessLevelInner[0] = 1.0;\n"
   11567 									  "    gl_TessLevelInner[1] = 1.0;\n"
   11568 									  "}\n"
   11569 									  "\n";
   11570 	static const GLchar* tes = "#version 430 core\n"
   11571 							   "#extension GL_ARB_enhanced_layouts : require\n"
   11572 							   "\n"
   11573 							   "layout(isolines, point_mode) in;\n"
   11574 							   "\n"
   11575 							   "in  vec4 tcs_tes[];\n"
   11576 							   "out vec4 tes_gs;\n"
   11577 							   "\n"
   11578 							   "void main()\n"
   11579 							   "{\n"
   11580 							   "    tes_gs = tcs_tes[0];\n"
   11581 							   "}\n"
   11582 							   "\n";
   11583 	static const GLchar* tes_tested = "#version 430 core\n"
   11584 									  "#extension GL_ARB_enhanced_layouts : require\n"
   11585 									  "\n"
   11586 									  "layout(isolines, point_mode) in;\n"
   11587 									  "\n"
   11588 									  "layout (std140) buffer Block {\n"
   11589 									  "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   11590 									  "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   11591 									  "} block;\n"
   11592 									  "\n"
   11593 									  "in  vec4 tcs_tes[];\n"
   11594 									  "out vec4 tes_gs;\n"
   11595 									  "\n"
   11596 									  "void main()\n"
   11597 									  "{\n"
   11598 									  "    if ((BOY_TYPE(1) == block.boy) ||\n"
   11599 									  "        (MAN_TYPE(0) == block.man) )\n"
   11600 									  "    {\n"
   11601 									  "        tes_gs = vec4(1, 1, 1, 1);\n"
   11602 									  "    }\n"
   11603 									  "\n"
   11604 									  "    tes_gs += tcs_tes[0];\n"
   11605 									  "}\n"
   11606 									  "\n";
   11607 	static const GLchar* vs = "#version 430 core\n"
   11608 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11609 							  "\n"
   11610 							  "in  vec4 in_vs;\n"
   11611 							  "out vec4 vs_tcs;\n"
   11612 							  "\n"
   11613 							  "void main()\n"
   11614 							  "{\n"
   11615 							  "    vs_tcs = in_vs;\n"
   11616 							  "}\n"
   11617 							  "\n";
   11618 	static const GLchar* vs_tested = "#version 430 core\n"
   11619 									 "#extension GL_ARB_enhanced_layouts : require\n"
   11620 									 "\n"
   11621 									 "layout (std140) buffer Block {\n"
   11622 									 "    layout (offset = BOY_OFFSET) BOY_TYPE boy;\n"
   11623 									 "    layout (offset = MAN_OFFSET) MAN_TYPE man;\n"
   11624 									 "} block;\n"
   11625 									 "\n"
   11626 									 "in  vec4 in_vs;\n"
   11627 									 "out vec4 vs_tcs;\n"
   11628 									 "\n"
   11629 									 "void main()\n"
   11630 									 "{\n"
   11631 									 "    if ((BOY_TYPE(1) == block.boy) ||\n"
   11632 									 "        (MAN_TYPE(0) == block.man) )\n"
   11633 									 "    {\n"
   11634 									 "        vs_tcs = vec4(1, 1, 1, 1);\n"
   11635 									 "    }\n"
   11636 									 "\n"
   11637 									 "    vs_tcs += in_vs;\n"
   11638 									 "}\n"
   11639 									 "\n";
   11640 
   11641 	std::string source;
   11642 	testCase&   test_case = m_test_cases[test_case_index];
   11643 
   11644 	if (test_case.m_stage == stage)
   11645 	{
   11646 		GLchar			   buffer[16];
   11647 		const GLuint	   boy_offset	= test_case.m_boy_offset;
   11648 		const Utils::Type& boy_type		 = test_case.m_boy_type;
   11649 		const GLchar*	  boy_type_name = boy_type.GetGLSLTypeName();
   11650 		const GLuint	   man_offset	= test_case.m_man_offset;
   11651 		const Utils::Type& man_type		 = test_case.m_man_type;
   11652 		const GLchar*	  man_type_name = man_type.GetGLSLTypeName();
   11653 		size_t			   position		 = 0;
   11654 
   11655 		switch (stage)
   11656 		{
   11657 		case Utils::Shader::COMPUTE:
   11658 			source = cs;
   11659 			break;
   11660 		case Utils::Shader::FRAGMENT:
   11661 			source = fs_tested;
   11662 			break;
   11663 		case Utils::Shader::GEOMETRY:
   11664 			source = gs_tested;
   11665 			break;
   11666 		case Utils::Shader::TESS_CTRL:
   11667 			source = tcs_tested;
   11668 			break;
   11669 		case Utils::Shader::TESS_EVAL:
   11670 			source = tes_tested;
   11671 			break;
   11672 		case Utils::Shader::VERTEX:
   11673 			source = vs_tested;
   11674 			break;
   11675 		default:
   11676 			TCU_FAIL("Invalid enum");
   11677 		}
   11678 
   11679 		sprintf(buffer, "%d", boy_offset);
   11680 		Utils::replaceToken("BOY_OFFSET", position, buffer, source);
   11681 		Utils::replaceToken("BOY_TYPE", position, boy_type_name, source);
   11682 		sprintf(buffer, "%d", man_offset);
   11683 		Utils::replaceToken("MAN_OFFSET", position, buffer, source);
   11684 		Utils::replaceToken("MAN_TYPE", position, man_type_name, source);
   11685 		Utils::replaceToken("BOY_TYPE", position, boy_type_name, source);
   11686 		Utils::replaceToken("MAN_TYPE", position, man_type_name, source);
   11687 	}
   11688 	else
   11689 	{
   11690 		switch (stage)
   11691 		{
   11692 		case Utils::Shader::FRAGMENT:
   11693 			source = fs;
   11694 			break;
   11695 		case Utils::Shader::GEOMETRY:
   11696 			source = gs;
   11697 			break;
   11698 		case Utils::Shader::TESS_CTRL:
   11699 			source = tcs;
   11700 			break;
   11701 		case Utils::Shader::TESS_EVAL:
   11702 			source = tes;
   11703 			break;
   11704 		case Utils::Shader::VERTEX:
   11705 			source = vs;
   11706 			break;
   11707 		default:
   11708 			TCU_FAIL("Invalid enum");
   11709 		}
   11710 	}
   11711 
   11712 	return source;
   11713 }
   11714 
   11715 /** Checks if stage is supported
   11716  *
   11717  * @param stage Shader stage
   11718  *
   11719  * @return true if supported, false otherwise
   11720  **/
   11721 bool SSBMemberOverlappingOffsetsTest::isStageSupported(Utils::Shader::STAGES stage)
   11722 {
   11723 	const Functions& gl					   = m_context.getRenderContext().getFunctions();
   11724 	GLint			 max_supported_buffers = 0;
   11725 	GLenum			 pname				   = 0;
   11726 
   11727 	switch (stage)
   11728 	{
   11729 	case Utils::Shader::COMPUTE:
   11730 		pname = GL_MAX_COMPUTE_SHADER_STORAGE_BLOCKS;
   11731 		break;
   11732 	case Utils::Shader::FRAGMENT:
   11733 		pname = GL_MAX_FRAGMENT_SHADER_STORAGE_BLOCKS;
   11734 		break;
   11735 	case Utils::Shader::GEOMETRY:
   11736 		pname = GL_MAX_GEOMETRY_SHADER_STORAGE_BLOCKS;
   11737 		break;
   11738 	case Utils::Shader::TESS_CTRL:
   11739 		pname = GL_MAX_TESS_CONTROL_SHADER_STORAGE_BLOCKS;
   11740 		break;
   11741 	case Utils::Shader::TESS_EVAL:
   11742 		pname = GL_MAX_TESS_EVALUATION_SHADER_STORAGE_BLOCKS;
   11743 		break;
   11744 	case Utils::Shader::VERTEX:
   11745 		pname = GL_MAX_VERTEX_SHADER_STORAGE_BLOCKS;
   11746 		break;
   11747 	default:
   11748 		TCU_FAIL("Invalid enum");
   11749 	}
   11750 
   11751 	gl.getIntegerv(pname, &max_supported_buffers);
   11752 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   11753 
   11754 	return 1 <= max_supported_buffers;
   11755 }
   11756 
   11757 /** Constructor
   11758  *
   11759  * @param context Test framework context
   11760  **/
   11761 SSBMemberAlignNonPowerOf2Test::SSBMemberAlignNonPowerOf2Test(deqp::Context& context)
   11762 	: UniformBlockMemberAlignNonPowerOf2Test(context, "ssb_member_align_non_power_of_2",
   11763 											 "Test verifies that align qualifier requires value that is a power of 2")
   11764 {
   11765 	/* Nothing to be done here */
   11766 }
   11767 
   11768 /** Source for given test case and stage
   11769  *
   11770  * @param test_case_index Index of test case
   11771  * @param stage           Shader stage
   11772  *
   11773  * @return Shader source
   11774  **/
   11775 std::string SSBMemberAlignNonPowerOf2Test::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   11776 {
   11777 	static const GLchar* cs = "#version 430 core\n"
   11778 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11779 							  "\n"
   11780 							  "layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
   11781 							  "\n"
   11782 							  "layout (std140) buffer Block {\n"
   11783 							  "    vec4 boy;\n"
   11784 							  "    layout (align = ALIGN) TYPE man;\n"
   11785 							  "} block;\n"
   11786 							  "\n"
   11787 							  "writeonly uniform image2D uni_image;\n"
   11788 							  "\n"
   11789 							  "void main()\n"
   11790 							  "{\n"
   11791 							  "    vec4 result = vec4(1, 0, 0.5, 1);\n"
   11792 							  "\n"
   11793 							  "    if (TYPE(0) == block.man)\n"
   11794 							  "    {\n"
   11795 							  "        result = vec4(1, 1, 1, 1) - block.boy;\n"
   11796 							  "    }\n"
   11797 							  "\n"
   11798 							  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), result);\n"
   11799 							  "}\n"
   11800 							  "\n";
   11801 	static const GLchar* fs = "#version 430 core\n"
   11802 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11803 							  "\n"
   11804 							  "in  vec4 gs_fs;\n"
   11805 							  "out vec4 fs_out;\n"
   11806 							  "\n"
   11807 							  "void main()\n"
   11808 							  "{\n"
   11809 							  "    fs_out = gs_fs;\n"
   11810 							  "}\n"
   11811 							  "\n";
   11812 	static const GLchar* fs_tested = "#version 430 core\n"
   11813 									 "#extension GL_ARB_enhanced_layouts : require\n"
   11814 									 "\n"
   11815 									 "layout (std140) buffer Block {\n"
   11816 									 "    vec4 boy;\n"
   11817 									 "    layout (align = ALIGN) TYPE man;\n"
   11818 									 "} block;\n"
   11819 									 "\n"
   11820 									 "in  vec4 gs_fs;\n"
   11821 									 "out vec4 fs_out;\n"
   11822 									 "\n"
   11823 									 "void main()\n"
   11824 									 "{\n"
   11825 									 "    if (TYPE(0) == block.man)\n"
   11826 									 "    {\n"
   11827 									 "        fs_out = block.boy;\n"
   11828 									 "    }\n"
   11829 									 "\n"
   11830 									 "    fs_out += gs_fs;\n"
   11831 									 "}\n"
   11832 									 "\n";
   11833 	static const GLchar* gs = "#version 430 core\n"
   11834 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11835 							  "\n"
   11836 							  "layout(points)                           in;\n"
   11837 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   11838 							  "\n"
   11839 							  "in  vec4 tes_gs[];\n"
   11840 							  "out vec4 gs_fs;\n"
   11841 							  "\n"
   11842 							  "void main()\n"
   11843 							  "{\n"
   11844 							  "    gs_fs = tes_gs[0];\n"
   11845 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   11846 							  "    EmitVertex();\n"
   11847 							  "    gs_fs = tes_gs[0];\n"
   11848 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   11849 							  "    EmitVertex();\n"
   11850 							  "    gs_fs = tes_gs[0];\n"
   11851 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   11852 							  "    EmitVertex();\n"
   11853 							  "    gs_fs = tes_gs[0];\n"
   11854 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   11855 							  "    EmitVertex();\n"
   11856 							  "}\n"
   11857 							  "\n";
   11858 	static const GLchar* gs_tested = "#version 430 core\n"
   11859 									 "#extension GL_ARB_enhanced_layouts : require\n"
   11860 									 "\n"
   11861 									 "layout(points)                           in;\n"
   11862 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   11863 									 "\n"
   11864 									 "layout (std140) buffer Block {\n"
   11865 									 "    vec4 boy;\n"
   11866 									 "    layout (align = ALIGN) TYPE man;\n"
   11867 									 "} block;\n"
   11868 									 "\n"
   11869 									 "in  vec4 tes_gs[];\n"
   11870 									 "out vec4 gs_fs;\n"
   11871 									 "\n"
   11872 									 "void main()\n"
   11873 									 "{\n"
   11874 									 "    if (TYPE(0) == block.man)\n"
   11875 									 "    {\n"
   11876 									 "        gs_fs = block.boy;\n"
   11877 									 "    }\n"
   11878 									 "\n"
   11879 									 "    gs_fs += tes_gs[0];\n"
   11880 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   11881 									 "    EmitVertex();\n"
   11882 									 "    gs_fs += tes_gs[0];\n"
   11883 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   11884 									 "    EmitVertex();\n"
   11885 									 "    gs_fs += tes_gs[0];\n"
   11886 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   11887 									 "    EmitVertex();\n"
   11888 									 "    gs_fs += tes_gs[0];\n"
   11889 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   11890 									 "    EmitVertex();\n"
   11891 									 "}\n"
   11892 									 "\n";
   11893 	static const GLchar* tcs = "#version 430 core\n"
   11894 							   "#extension GL_ARB_enhanced_layouts : require\n"
   11895 							   "\n"
   11896 							   "layout(vertices = 1) out;\n"
   11897 							   "\n"
   11898 							   "in  vec4 vs_tcs[];\n"
   11899 							   "out vec4 tcs_tes[];\n"
   11900 							   "\n"
   11901 							   "void main()\n"
   11902 							   "{\n"
   11903 							   "\n"
   11904 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   11905 							   "\n"
   11906 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   11907 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   11908 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   11909 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   11910 							   "    gl_TessLevelInner[0] = 1.0;\n"
   11911 							   "    gl_TessLevelInner[1] = 1.0;\n"
   11912 							   "}\n"
   11913 							   "\n";
   11914 	static const GLchar* tcs_tested = "#version 430 core\n"
   11915 									  "#extension GL_ARB_enhanced_layouts : require\n"
   11916 									  "\n"
   11917 									  "layout(vertices = 1) out;\n"
   11918 									  "\n"
   11919 									  "layout (std140) buffer Block {\n"
   11920 									  "    vec4 boy;\n"
   11921 									  "    layout (align = ALIGN) TYPE man;\n"
   11922 									  "} block;\n"
   11923 									  "\n"
   11924 									  "in  vec4 vs_tcs[];\n"
   11925 									  "out vec4 tcs_tes[];\n"
   11926 									  "\n"
   11927 									  "void main()\n"
   11928 									  "{\n"
   11929 									  "    if (TYPE(0) == block.man)\n"
   11930 									  "    {\n"
   11931 									  "        tcs_tes[gl_InvocationID] = block.boy;\n"
   11932 									  "    }\n"
   11933 									  "\n"
   11934 									  "\n"
   11935 									  "    tcs_tes[gl_InvocationID] += vs_tcs[gl_InvocationID];\n"
   11936 									  "\n"
   11937 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   11938 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   11939 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   11940 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   11941 									  "    gl_TessLevelInner[0] = 1.0;\n"
   11942 									  "    gl_TessLevelInner[1] = 1.0;\n"
   11943 									  "}\n"
   11944 									  "\n";
   11945 	static const GLchar* tes = "#version 430 core\n"
   11946 							   "#extension GL_ARB_enhanced_layouts : require\n"
   11947 							   "\n"
   11948 							   "layout(isolines, point_mode) in;\n"
   11949 							   "\n"
   11950 							   "in  vec4 tcs_tes[];\n"
   11951 							   "out vec4 tes_gs;\n"
   11952 							   "\n"
   11953 							   "void main()\n"
   11954 							   "{\n"
   11955 							   "    tes_gs = tcs_tes[0];\n"
   11956 							   "}\n"
   11957 							   "\n";
   11958 	static const GLchar* tes_tested = "#version 430 core\n"
   11959 									  "#extension GL_ARB_enhanced_layouts : require\n"
   11960 									  "\n"
   11961 									  "layout(isolines, point_mode) in;\n"
   11962 									  "\n"
   11963 									  "layout (std140) buffer Block {\n"
   11964 									  "    vec4 boy;\n"
   11965 									  "    layout (align = ALIGN) TYPE man;\n"
   11966 									  "} block;\n"
   11967 									  "\n"
   11968 									  "in  vec4 tcs_tes[];\n"
   11969 									  "out vec4 tes_gs;\n"
   11970 									  "\n"
   11971 									  "void main()\n"
   11972 									  "{\n"
   11973 									  "    if (TYPE(0) == block.man)\n"
   11974 									  "    {\n"
   11975 									  "        tes_gs = block.boy;\n"
   11976 									  "    }\n"
   11977 									  "\n"
   11978 									  "    tes_gs += tcs_tes[0];\n"
   11979 									  "}\n"
   11980 									  "\n";
   11981 	static const GLchar* vs = "#version 430 core\n"
   11982 							  "#extension GL_ARB_enhanced_layouts : require\n"
   11983 							  "\n"
   11984 							  "in  vec4 in_vs;\n"
   11985 							  "out vec4 vs_tcs;\n"
   11986 							  "\n"
   11987 							  "void main()\n"
   11988 							  "{\n"
   11989 							  "    vs_tcs = in_vs;\n"
   11990 							  "}\n"
   11991 							  "\n";
   11992 	static const GLchar* vs_tested = "#version 430 core\n"
   11993 									 "#extension GL_ARB_enhanced_layouts : require\n"
   11994 									 "\n"
   11995 									 "layout (std140) buffer Block {\n"
   11996 									 "    vec4 boy;\n"
   11997 									 "    layout (align = ALIGN) TYPE man;\n"
   11998 									 "} block;\n"
   11999 									 "\n"
   12000 									 "in  vec4 in_vs;\n"
   12001 									 "out vec4 vs_tcs;\n"
   12002 									 "\n"
   12003 									 "void main()\n"
   12004 									 "{\n"
   12005 									 "    if (TYPE(0) == block.man)\n"
   12006 									 "    {\n"
   12007 									 "        vs_tcs = block.boy;\n"
   12008 									 "    }\n"
   12009 									 "\n"
   12010 									 "    vs_tcs += in_vs;\n"
   12011 									 "}\n"
   12012 									 "\n";
   12013 
   12014 	std::string source;
   12015 	testCase&   test_case = m_test_cases[test_case_index];
   12016 
   12017 	if (test_case.m_stage == stage)
   12018 	{
   12019 		GLchar			   buffer[16];
   12020 		const GLuint	   alignment = test_case.m_alignment;
   12021 		const Utils::Type& type		 = test_case.m_type;
   12022 		const GLchar*	  type_name = type.GetGLSLTypeName();
   12023 		size_t			   position  = 0;
   12024 
   12025 		switch (stage)
   12026 		{
   12027 		case Utils::Shader::COMPUTE:
   12028 			source = cs;
   12029 			break;
   12030 		case Utils::Shader::FRAGMENT:
   12031 			source = fs_tested;
   12032 			break;
   12033 		case Utils::Shader::GEOMETRY:
   12034 			source = gs_tested;
   12035 			break;
   12036 		case Utils::Shader::TESS_CTRL:
   12037 			source = tcs_tested;
   12038 			break;
   12039 		case Utils::Shader::TESS_EVAL:
   12040 			source = tes_tested;
   12041 			break;
   12042 		case Utils::Shader::VERTEX:
   12043 			source = vs_tested;
   12044 			break;
   12045 		default:
   12046 			TCU_FAIL("Invalid enum");
   12047 		}
   12048 
   12049 		sprintf(buffer, "%d", alignment);
   12050 		Utils::replaceToken("ALIGN", position, buffer, source);
   12051 		Utils::replaceToken("TYPE", position, type_name, source);
   12052 		Utils::replaceToken("TYPE", position, type_name, source);
   12053 	}
   12054 	else
   12055 	{
   12056 		switch (stage)
   12057 		{
   12058 		case Utils::Shader::FRAGMENT:
   12059 			source = fs;
   12060 			break;
   12061 		case Utils::Shader::GEOMETRY:
   12062 			source = gs;
   12063 			break;
   12064 		case Utils::Shader::TESS_CTRL:
   12065 			source = tcs;
   12066 			break;
   12067 		case Utils::Shader::TESS_EVAL:
   12068 			source = tes;
   12069 			break;
   12070 		case Utils::Shader::VERTEX:
   12071 			source = vs;
   12072 			break;
   12073 		default:
   12074 			TCU_FAIL("Invalid enum");
   12075 		}
   12076 	}
   12077 
   12078 	return source;
   12079 }
   12080 
   12081 /** Checks if stage is supported
   12082  *
   12083  * @param stage Shader stage
   12084  *
   12085  * @return true if supported, false otherwise
   12086  **/
   12087 bool SSBMemberAlignNonPowerOf2Test::isStageSupported(Utils::Shader::STAGES stage)
   12088 {
   12089 	const Functions& gl					   = m_context.getRenderContext().getFunctions();
   12090 	GLint			 max_supported_buffers = 0;
   12091 	GLenum			 pname				   = 0;
   12092 
   12093 	switch (stage)
   12094 	{
   12095 	case Utils::Shader::COMPUTE:
   12096 		pname = GL_MAX_COMPUTE_SHADER_STORAGE_BLOCKS;
   12097 		break;
   12098 	case Utils::Shader::FRAGMENT:
   12099 		pname = GL_MAX_FRAGMENT_SHADER_STORAGE_BLOCKS;
   12100 		break;
   12101 	case Utils::Shader::GEOMETRY:
   12102 		pname = GL_MAX_GEOMETRY_SHADER_STORAGE_BLOCKS;
   12103 		break;
   12104 	case Utils::Shader::TESS_CTRL:
   12105 		pname = GL_MAX_TESS_CONTROL_SHADER_STORAGE_BLOCKS;
   12106 		break;
   12107 	case Utils::Shader::TESS_EVAL:
   12108 		pname = GL_MAX_TESS_EVALUATION_SHADER_STORAGE_BLOCKS;
   12109 		break;
   12110 	case Utils::Shader::VERTEX:
   12111 		pname = GL_MAX_VERTEX_SHADER_STORAGE_BLOCKS;
   12112 		break;
   12113 	default:
   12114 		TCU_FAIL("Invalid enum");
   12115 	}
   12116 
   12117 	gl.getIntegerv(pname, &max_supported_buffers);
   12118 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   12119 
   12120 	return 1 <= max_supported_buffers;
   12121 }
   12122 
   12123 /** Constructor
   12124  *
   12125  * @param context Test framework context
   12126  **/
   12127 SSBAlignmentTest::SSBAlignmentTest(deqp::Context& context)
   12128 	: TextureTestBase(context, "ssb_alignment", "Test verifies offset and alignment of ssb buffer")
   12129 {
   12130 }
   12131 
   12132 /** Get interface of program
   12133  *
   12134  * @param ignored
   12135  * @param program_interface Interface of program
   12136  * @param varying_passthrough Collection of connections between in and out variables
   12137  **/
   12138 void SSBAlignmentTest::getProgramInterface(GLuint /* test_case_index */, Utils::ProgramInterface& program_interface,
   12139 										   Utils::VaryingPassthrough& varying_passthrough)
   12140 {
   12141 	static const Utils::Type vec4 = Utils::Type::vec4;
   12142 
   12143 #if WRKARD_UNIFORMBLOCKALIGNMENT
   12144 
   12145 	static const GLuint block_align = 16;
   12146 
   12147 #else /* WRKARD_UNIFORMBLOCKALIGNMENT */
   12148 
   12149 	static const GLuint block_align = 64;
   12150 
   12151 #endif /* WRKARD_UNIFORMBLOCKALIGNMENT */
   12152 
   12153 	static const GLuint fifth_align = 16;
   12154 	static const GLuint vec4_stride = 16;
   12155 	static const GLuint data_stride = vec4_stride * 2; /* one vec4 + one scalar aligned to 16 */
   12156 
   12157 	const GLuint first_offset  = 0;																		/* vec4 at 0 */
   12158 	const GLuint second_offset = Utils::Type::GetActualOffset(first_offset + vec4_stride, block_align); /* Data at 32 */
   12159 	const GLuint third_offset =
   12160 		Utils::Type::GetActualOffset(second_offset + data_stride, block_align); /* Data[2] at 64 */
   12161 	const GLuint fourth_offset =
   12162 		Utils::Type::GetActualOffset(third_offset + data_stride * 2, block_align); /* vec4[3] at 96 */
   12163 	const GLuint fifth_offset =
   12164 		Utils::Type::GetActualOffset(fourth_offset + vec4_stride * 3, fifth_align); /* vec4[2] at 160 */
   12165 	const GLuint sixth_offset =
   12166 		Utils::Type::GetActualOffset(fifth_offset + vec4_stride * 2, block_align); /* Data at 192 */
   12167 
   12168 	Utils::Interface* structure = program_interface.Structure("Data");
   12169 
   12170 	structure->Member("vector", "", 0 /* expected_component */, 0 /* expected_location */, Utils::Type::vec4,
   12171 					  false /* normalized */, 0 /* n_array_elements */, Utils::Type::vec4.GetSize(), 0 /* offset */);
   12172 
   12173 	structure->Member("scalar", "", 0 /* expected_component */, 0 /* expected_location */, Utils::Type::_float,
   12174 					  false /* normalized */, 0 /* n_array_elements */, Utils::Type::_float.GetSize(),
   12175 					  Utils::Type::vec4.GetSize() /* offset */);
   12176 
   12177 	/* Prepare Block */
   12178 	Utils::Interface* vs_buf_Block = program_interface.Block("vs_buf_Block");
   12179 
   12180 	vs_buf_Block->Member("first", "", 0 /* expected_component */, 0 /* expected_location */, Utils::Type::vec4,
   12181 						 false /* normalized */, 0 /* n_array_elements */, vec4_stride, first_offset /* offset */);
   12182 
   12183 	vs_buf_Block->Member("second", "", 0 /* expected_component */, 0 /* expected_location */, structure,
   12184 						 0 /* n_array_elements */, data_stride, second_offset);
   12185 
   12186 	vs_buf_Block->Member("third", "", 0 /* expected_component */, 0 /* expected_location */, structure,
   12187 						 2 /* n_array_elements */, data_stride, third_offset);
   12188 
   12189 	vs_buf_Block->Member("fourth", "", 0 /* expected_component */, 0 /* expected_location */, vec4,
   12190 						 false /* normalized */, 3 /* n_array_elements */, vec4_stride, fourth_offset);
   12191 
   12192 	vs_buf_Block->Member("fifth", "layout(align = 16)", 0 /* expected_component */, 0 /* expected_location */, vec4,
   12193 						 false /* normalized */, 2 /* n_array_elements */, vec4_stride, fifth_offset);
   12194 
   12195 	vs_buf_Block->Member("sixth", "", 0 /* expected_component */, 0 /* expected_location */, structure,
   12196 						 0 /* n_array_elements */, data_stride, sixth_offset);
   12197 
   12198 	const GLuint stride = calculateStride(*vs_buf_Block);
   12199 	m_data.resize(stride);
   12200 	generateData(*vs_buf_Block, 0, m_data);
   12201 
   12202 	Utils::ShaderInterface& vs_si = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   12203 
   12204 /* Add uniform BLOCK */
   12205 #if WRKARD_UNIFORMBLOCKALIGNMENT
   12206 	vs_si.SSB("vs_buf_block", "layout (std140, binding = BINDING)", 0, 0, vs_buf_Block, 0,
   12207 			  static_cast<GLuint>(m_data.size()), 0, &m_data[0], m_data.size());
   12208 #else  /* WRKARD_UNIFORMBLOCKALIGNMENT */
   12209 	vs_si.SSB("vs_buf_block", "layout (std140, binding = BINDING, align = 64)", 0, 0, vs_buf_Block, 0,
   12210 			  static_cast<GLuint>(m_data.size()), 0, &m_data[0], m_data.size());
   12211 #endif /* WRKARD_UNIFORMBLOCKALIGNMENT */
   12212 
   12213 	program_interface.CloneVertexInterface(varying_passthrough);
   12214 }
   12215 
   12216 /** Selects if "draw" stages are relevant for test
   12217  *
   12218  * @param ignored
   12219  *
   12220  * @return true if all stages support shader storage buffers, false otherwise
   12221  **/
   12222 bool SSBAlignmentTest::isDrawRelevant(GLuint /* test_case_index */)
   12223 {
   12224 	const Functions& gl					   = m_context.getRenderContext().getFunctions();
   12225 	GLint			 gs_supported_buffers  = 0;
   12226 	GLint			 tcs_supported_buffers = 0;
   12227 	GLint			 tes_supported_buffers = 0;
   12228 	GLint			 vs_supported_buffers  = 0;
   12229 
   12230 	gl.getIntegerv(GL_MAX_GEOMETRY_SHADER_STORAGE_BLOCKS, &gs_supported_buffers);
   12231 	gl.getIntegerv(GL_MAX_TESS_CONTROL_SHADER_STORAGE_BLOCKS, &tcs_supported_buffers);
   12232 	gl.getIntegerv(GL_MAX_TESS_EVALUATION_SHADER_STORAGE_BLOCKS, &tes_supported_buffers);
   12233 	gl.getIntegerv(GL_MAX_VERTEX_SHADER_STORAGE_BLOCKS, &vs_supported_buffers);
   12234 
   12235 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   12236 
   12237 	return ((1 <= gs_supported_buffers) && (1 <= tcs_supported_buffers) && (1 <= tes_supported_buffers) &&
   12238 			(1 <= vs_supported_buffers));
   12239 }
   12240 
   12241 /** Constructor
   12242  *
   12243  * @param context Test framework context
   12244  **/
   12245 VaryingLocationsTest::VaryingLocationsTest(deqp::Context& context)
   12246 	: TextureTestBase(context, "varying_locations", "Test verifies that input and output locations are respected")
   12247 {
   12248 }
   12249 
   12250 /** Constructor
   12251  *
   12252  * @param context          Test context
   12253  * @param test_name        Name of test
   12254  * @param test_description Description of test
   12255  **/
   12256 VaryingLocationsTest::VaryingLocationsTest(deqp::Context& context, const glw::GLchar* test_name,
   12257 										   const glw::GLchar* test_description)
   12258 	: TextureTestBase(context, test_name, test_description)
   12259 {
   12260 }
   12261 
   12262 /** Get interface of program
   12263  *
   12264  * @param test_case_index     Test case
   12265  * @param program_interface   Interface of program
   12266  * @param varying_passthrough Collection of connections between in and out variables
   12267  **/
   12268 void VaryingLocationsTest::getProgramInterface(GLuint test_case_index, Utils::ProgramInterface& program_interface,
   12269 											   Utils::VaryingPassthrough& varying_passthrough)
   12270 {
   12271 	const Utils::Type type = getType(test_case_index);
   12272 
   12273 	m_first_data = type.GenerateDataPacked();
   12274 	m_last_data  = type.GenerateDataPacked();
   12275 
   12276 	prepareShaderStage(Utils::Shader::FRAGMENT, type, program_interface, varying_passthrough);
   12277 	prepareShaderStage(Utils::Shader::GEOMETRY, type, program_interface, varying_passthrough);
   12278 	prepareShaderStage(Utils::Shader::TESS_CTRL, type, program_interface, varying_passthrough);
   12279 	prepareShaderStage(Utils::Shader::TESS_EVAL, type, program_interface, varying_passthrough);
   12280 	prepareShaderStage(Utils::Shader::VERTEX, type, program_interface, varying_passthrough);
   12281 }
   12282 
   12283 /** Get type name
   12284  *
   12285  * @param test_case_index Index of test case
   12286  *
   12287  * @return Name of type test in test_case_index
   12288  **/
   12289 std::string VaryingLocationsTest::getTestCaseName(glw::GLuint test_case_index)
   12290 {
   12291 	return getTypeName(test_case_index);
   12292 }
   12293 
   12294 /** Returns number of types to test
   12295  *
   12296  * @return Number of types, 34
   12297  **/
   12298 glw::GLuint VaryingLocationsTest::getTestCaseNumber()
   12299 {
   12300 	return getTypesNumber();
   12301 }
   12302 
   12303 /** Selects if "compute" stage is relevant for test
   12304  *
   12305  * @param ignored
   12306  *
   12307  * @return false
   12308  **/
   12309 bool VaryingLocationsTest::isComputeRelevant(GLuint /* test_case_index */)
   12310 {
   12311 	return false;
   12312 }
   12313 
   12314 /**
   12315  *
   12316  *
   12317  **/
   12318 std::string VaryingLocationsTest::prepareGlobals(GLint last_in_loc, GLint last_out_loc)
   12319 {
   12320 	GLchar		buffer[16];
   12321 	std::string globals = "const uint first_input_location  = 0u;\n"
   12322 						  "const uint first_output_location = 0u;\n"
   12323 						  "const uint last_input_location   = LAST_INPUTu;\n"
   12324 						  "const uint last_output_location  = LAST_OUTPUTu;\n";
   12325 	size_t position = 100; /* Skip first part */
   12326 
   12327 	sprintf(buffer, "%d", last_in_loc);
   12328 	Utils::replaceToken("LAST_INPUT", position, buffer, globals);
   12329 
   12330 	sprintf(buffer, "%d", last_out_loc);
   12331 	Utils::replaceToken("LAST_OUTPUT", position, buffer, globals);
   12332 
   12333 	return globals;
   12334 }
   12335 
   12336 /**
   12337  *
   12338  **/
   12339 void VaryingLocationsTest::prepareShaderStage(Utils::Shader::STAGES stage, const Utils::Type& type,
   12340 											  Utils::ProgramInterface&   program_interface,
   12341 											  Utils::VaryingPassthrough& varying_passthrough)
   12342 {
   12343 	const GLuint array_length  = 1;
   12344 	const GLuint first_in_loc  = 0;
   12345 	const GLuint first_out_loc = 0;
   12346 	const GLuint last_in_loc   = getLastInputLocation(stage, type, array_length);
   12347 	size_t		 position	  = 0;
   12348 
   12349 	const GLchar* prefix_in = Utils::ProgramInterface::GetStagePrefix(stage, Utils::Variable::VARYING_INPUT);
   12350 
   12351 	const GLchar* prefix_out = Utils::ProgramInterface::GetStagePrefix(stage, Utils::Variable::VARYING_OUTPUT);
   12352 
   12353 	const GLchar* qual_first_in  = "layout (location = first_input_location)";
   12354 	const GLchar* qual_first_out = "layout (location = first_output_location)";
   12355 	const GLchar* qual_last_in   = "layout (location = last_input_location)";
   12356 	const GLchar* qual_last_out  = "layout (location = last_output_location)";
   12357 
   12358 	Utils::ShaderInterface& si		  = program_interface.GetShaderInterface(stage);
   12359 	const GLuint			type_size = type.GetSize();
   12360 
   12361 	std::string first_in_name  = "PREFIXfirst";
   12362 	std::string first_out_name = "PREFIXfirst";
   12363 	std::string last_in_name   = "PREFIXlast";
   12364 	std::string last_out_name  = "PREFIXlast";
   12365 
   12366 	Utils::replaceToken("PREFIX", position, prefix_in, first_in_name);
   12367 	position = 0;
   12368 	Utils::replaceToken("PREFIX", position, prefix_out, first_out_name);
   12369 	position = 0;
   12370 	Utils::replaceToken("PREFIX", position, prefix_in, last_in_name);
   12371 	position = 0;
   12372 	Utils::replaceToken("PREFIX", position, prefix_out, last_out_name);
   12373 
   12374 	if (Utils::Shader::FRAGMENT == stage)
   12375 	{
   12376 		qual_first_in = "layout (location = first_input_location) flat";
   12377 		qual_last_in  = "layout (location = last_input_location)  flat";
   12378 	}
   12379 	if (Utils::Shader::GEOMETRY == stage)
   12380 	{
   12381 		qual_first_out = "layout (location = first_output_location) flat";
   12382 		qual_last_out  = "layout (location = last_output_location)  flat";
   12383 	}
   12384 
   12385 	Utils::Variable* first_in = si.Input(
   12386 		first_in_name.c_str(), qual_first_in /* qualifiers */, 0 /* expected_componenet */,
   12387 		first_in_loc /* expected_location */, type /* type */, GL_FALSE /* normalized */, 0u /* n_array_elements */,
   12388 		0u /* stride */, 0u /* offset */, (GLvoid*)&m_first_data[0] /* data */, m_first_data.size() /* data_size */);
   12389 
   12390 	Utils::Variable* last_in =
   12391 		si.Input(last_in_name.c_str(), qual_last_in /* qualifiers */, 0 /* expected_componenet */,
   12392 				 last_in_loc /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   12393 				 0u /* n_array_elements */, 0u /* stride */, type_size /* offset */,
   12394 				 (GLvoid*)&m_last_data[0] /* data */, m_last_data.size() /* data_size */);
   12395 
   12396 	if (Utils::Shader::FRAGMENT != stage)
   12397 	{
   12398 		const GLuint last_out_loc = getLastOutputLocation(stage, type, array_length);
   12399 
   12400 		Utils::Variable* first_out =
   12401 			si.Output(first_out_name.c_str(), qual_first_out /* qualifiers */, 0 /* expected_componenet */,
   12402 					  first_out_loc /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   12403 					  0u /* n_array_elements */, 0u /* stride */, 0u /* offset */, (GLvoid*)&m_first_data[0] /* data */,
   12404 					  m_first_data.size() /* data_size */);
   12405 
   12406 		Utils::Variable* last_out = si.Output(
   12407 			last_out_name.c_str(), qual_last_out /* qualifiers */, 0 /* expected_componenet */,
   12408 			last_out_loc /* expected_location */, type /* type */, GL_FALSE /* normalized */, 0u /* n_array_elements */,
   12409 			0u /* stride */, 0u /* offset */, (GLvoid*)&m_last_data[0] /* data */, m_last_data.size() /* data_size */);
   12410 
   12411 		si.m_globals = prepareGlobals(last_in_loc, last_out_loc);
   12412 
   12413 		varying_passthrough.Add(stage, first_in, first_out);
   12414 		varying_passthrough.Add(stage, last_in, last_out);
   12415 	}
   12416 	else
   12417 	{
   12418 		/* No outputs for fragment shader, so last_output_location can be 0 */
   12419 		si.m_globals = prepareGlobals(last_in_loc, 0);
   12420 	}
   12421 }
   12422 
   12423 /** This test should be run with separable programs
   12424  *
   12425  * @param ignored
   12426  *
   12427  * @return true
   12428  **/
   12429 bool VaryingLocationsTest::useMonolithicProgram(GLuint /* test_case_index */)
   12430 {
   12431 	return false;
   12432 }
   12433 
   12434 /* Constants used by VertexAttribLocationsTest */
   12435 const GLuint VertexAttribLocationsTest::m_base_vertex   = 4;
   12436 const GLuint VertexAttribLocationsTest::m_base_instance = 2;
   12437 const GLuint VertexAttribLocationsTest::m_loc_vertex	= 2;
   12438 const GLuint VertexAttribLocationsTest::m_loc_instance  = 5;
   12439 const GLuint VertexAttribLocationsTest::m_n_instances   = 4;
   12440 
   12441 /** Constructor
   12442  *
   12443  * @param context Test framework context
   12444  **/
   12445 VertexAttribLocationsTest::VertexAttribLocationsTest(deqp::Context& context)
   12446 	: TextureTestBase(context, "vertex_attrib_locations",
   12447 					  "Test verifies that attribute locations are respected by drawing operations")
   12448 {
   12449 }
   12450 
   12451 /** Execute proper draw command for test case
   12452  *
   12453  * @param test_case_index Index of test case
   12454  **/
   12455 void VertexAttribLocationsTest::executeDrawCall(GLuint test_case_index)
   12456 {
   12457 	const Functions& gl = m_context.getRenderContext().getFunctions();
   12458 
   12459 	switch (test_case_index)
   12460 	{
   12461 	case DRAWARRAYS:
   12462 		gl.drawArrays(GL_PATCHES, 0 /* first */, 1 /* count */);
   12463 		GLU_EXPECT_NO_ERROR(gl.getError(), "DrawArrays");
   12464 		break;
   12465 	case DRAWARRAYSINSTANCED:
   12466 		gl.drawArraysInstanced(GL_PATCHES, 0 /* first */, 1 /* count */, m_n_instances);
   12467 		GLU_EXPECT_NO_ERROR(gl.getError(), "DrawArraysInstanced");
   12468 		break;
   12469 	case DRAWELEMENTS:
   12470 		gl.drawElements(GL_PATCHES, 1 /* count */, GL_UNSIGNED_BYTE, DE_NULL);
   12471 		GLU_EXPECT_NO_ERROR(gl.getError(), "DrawElements");
   12472 		break;
   12473 	case DRAWELEMENTSBASEVERTEX:
   12474 		gl.drawElementsBaseVertex(GL_PATCHES, 1 /* count */, GL_UNSIGNED_BYTE, DE_NULL, m_base_vertex);
   12475 		GLU_EXPECT_NO_ERROR(gl.getError(), "DrawElementsBaseVertex");
   12476 		break;
   12477 	case DRAWELEMENTSINSTANCED:
   12478 		gl.drawElementsInstanced(GL_PATCHES, 1 /* count */, GL_UNSIGNED_BYTE, DE_NULL, m_n_instances);
   12479 		GLU_EXPECT_NO_ERROR(gl.getError(), "DrawElementsInstanced");
   12480 		break;
   12481 	case DRAWELEMENTSINSTANCEDBASEINSTANCE:
   12482 		gl.drawElementsInstancedBaseInstance(GL_PATCHES, 1 /* count */, GL_UNSIGNED_BYTE, DE_NULL, m_n_instances,
   12483 											 m_base_instance);
   12484 		GLU_EXPECT_NO_ERROR(gl.getError(), "DrawElementsInstancedBaseInstance");
   12485 		break;
   12486 	case DRAWELEMENTSINSTANCEDBASEVERTEX:
   12487 		gl.drawElementsInstancedBaseVertex(GL_PATCHES, 1 /* count */, GL_UNSIGNED_BYTE, DE_NULL, m_n_instances,
   12488 										   m_base_vertex);
   12489 		GLU_EXPECT_NO_ERROR(gl.getError(), "DrawElementsInstancedBaseVertex");
   12490 		break;
   12491 	case DRAWELEMENTSINSTANCEDBASEVERTEXBASEINSTANCE:
   12492 		gl.drawElementsInstancedBaseVertexBaseInstance(GL_PATCHES, 1 /* count */, GL_UNSIGNED_BYTE, DE_NULL,
   12493 													   m_n_instances, m_base_vertex, m_base_instance);
   12494 		GLU_EXPECT_NO_ERROR(gl.getError(), "DrawElementsInstancedBaseVertexBaseInstance");
   12495 		break;
   12496 	default:
   12497 		TCU_FAIL("Invalid enum");
   12498 	}
   12499 }
   12500 
   12501 /** Get interface of program
   12502  *
   12503  * @param ignored
   12504  * @param program_interface   Interface of program
   12505  * @param ignored
   12506  **/
   12507 void VertexAttribLocationsTest::getProgramInterface(GLuint /* test_case_index */,
   12508 													Utils::ProgramInterface& program_interface,
   12509 													Utils::VaryingPassthrough& /* varying_passthrough */)
   12510 {
   12511 	Utils::ShaderInterface& si = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   12512 
   12513 	/* Globals */
   12514 	si.m_globals = "const uint vertex_index_location   = 2;\n"
   12515 				   "const uint instance_index_location = 5;\n";
   12516 
   12517 	/* Attributes */
   12518 	si.Input("vertex_index" /* name */, "layout (location = vertex_index_location)" /* qualifiers */,
   12519 			 0 /* expected_componenet */, m_loc_vertex /* expected_location */, Utils::Type::uint /* type */,
   12520 			 GL_FALSE /* normalized */, 0u /* n_array_elements */, 16 /* stride */, 0u /* offset */,
   12521 			 (GLvoid*)0 /* data */, 0 /* data_size */);
   12522 	si.Input("instance_index" /* name */, "layout (location = instance_index_location)" /* qualifiers */,
   12523 			 0 /* expected_componenet */, m_loc_instance /* expected_location */, Utils::Type::uint /* type */,
   12524 			 GL_FALSE /* normalized */, 0u /* n_array_elements */, 16 /* stride */, 16u /* offset */,
   12525 			 (GLvoid*)0 /* data */, 0 /* data_size */);
   12526 }
   12527 
   12528 /** Get name of test case
   12529  *
   12530  * @param test_case_index Index of test case
   12531  *
   12532  * @return Name of test case
   12533  **/
   12534 std::string VertexAttribLocationsTest::getTestCaseName(glw::GLuint test_case_index)
   12535 {
   12536 	std::string result;
   12537 
   12538 	switch (test_case_index)
   12539 	{
   12540 	case DRAWARRAYS:
   12541 		result = "DrawArrays";
   12542 		break;
   12543 	case DRAWARRAYSINSTANCED:
   12544 		result = "DrawArraysInstanced";
   12545 		break;
   12546 	case DRAWELEMENTS:
   12547 		result = "DrawElements";
   12548 		break;
   12549 	case DRAWELEMENTSBASEVERTEX:
   12550 		result = "DrawElementsBaseVertex";
   12551 		break;
   12552 	case DRAWELEMENTSINSTANCED:
   12553 		result = "DrawElementsInstanced";
   12554 		break;
   12555 	case DRAWELEMENTSINSTANCEDBASEINSTANCE:
   12556 		result = "DrawElementsInstancedBaseInstance";
   12557 		break;
   12558 	case DRAWELEMENTSINSTANCEDBASEVERTEX:
   12559 		result = "DrawElementsInstancedBaseVertex";
   12560 		break;
   12561 	case DRAWELEMENTSINSTANCEDBASEVERTEXBASEINSTANCE:
   12562 		result = "DrawElementsInstancedBaseVertexBaseInstance";
   12563 		break;
   12564 	default:
   12565 		TCU_FAIL("Invalid enum");
   12566 	}
   12567 
   12568 	return result;
   12569 }
   12570 
   12571 /** Get number of test cases
   12572  *
   12573  * @return Number of test cases
   12574  **/
   12575 GLuint VertexAttribLocationsTest::getTestCaseNumber()
   12576 {
   12577 	return TESTCASES_MAX;
   12578 }
   12579 
   12580 /** Prepare code snippet that will verify in and uniform variables
   12581  *
   12582  * @param ignored
   12583  * @param ignored
   12584  * @param stage   Shader stage
   12585  *
   12586  * @return Code that verify variables
   12587  **/
   12588 std::string VertexAttribLocationsTest::getVerificationSnippet(GLuint /* test_case_index */,
   12589 															  Utils::ProgramInterface& /* program_interface */,
   12590 															  Utils::Shader::STAGES stage)
   12591 {
   12592 	std::string verification;
   12593 
   12594 	if (Utils::Shader::VERTEX == stage)
   12595 	{
   12596 
   12597 #if DEBUG_VERTEX_ATTRIB_LOCATIONS_TEST_VARIABLE
   12598 
   12599 		verification = "if (gl_InstanceID != instance_index)\n"
   12600 					   "    {\n"
   12601 					   "        result = 12u;\n"
   12602 					   "    }\n"
   12603 					   "    else if (gl_VertexID != vertex_index)\n"
   12604 					   "    {\n"
   12605 					   "        result = 11u;\n"
   12606 					   "    }\n";
   12607 
   12608 #else
   12609 
   12610 		verification = "if ((gl_VertexID   != vertex_index)  ||\n"
   12611 					   "        (gl_InstanceID != instance_index) )\n"
   12612 					   "    {\n"
   12613 					   "        result = 0u;\n"
   12614 					   "    }\n";
   12615 
   12616 #endif
   12617 	}
   12618 	else
   12619 	{
   12620 		verification = "";
   12621 	}
   12622 
   12623 	return verification;
   12624 }
   12625 
   12626 /** Selects if "compute" stage is relevant for test
   12627  *
   12628  * @param ignored
   12629  *
   12630  * @return false
   12631  **/
   12632 bool VertexAttribLocationsTest::isComputeRelevant(GLuint /* test_case_index */)
   12633 {
   12634 	return false;
   12635 }
   12636 
   12637 /** Prepare attributes, vertex array object and array buffer
   12638  *
   12639  * @param ignored
   12640  * @param ignored Interface of program
   12641  * @param buffer  Array buffer
   12642  * @param vao     Vertex array object
   12643  **/
   12644 void VertexAttribLocationsTest::prepareAttributes(GLuint test_case_index /* test_case_index */,
   12645 												  Utils::ProgramInterface& /* program_interface */,
   12646 												  Utils::Buffer& buffer, Utils::VertexArray& vao)
   12647 {
   12648 	static const GLuint vertex_index_data[8]   = { 0, 1, 2, 3, 4, 5, 6, 7 };
   12649 	static const GLuint instance_index_data[8] = { 0, 1, 2, 3, 4, 5, 6, 7 };
   12650 
   12651 	std::vector<GLuint> buffer_data;
   12652 	buffer_data.resize(8 + 8); /* vertex_index_data + instance_index_data */
   12653 
   12654 	GLubyte* ptr = (GLubyte*)&buffer_data[0];
   12655 
   12656 	/*
   12657 	 When case index >=2, the test calls glDrawElement*(), such as glDrawElementsBaseVertex(), glDrawElementsInstanced(), glDrawElementsInstancedBaseInstance() and so on,
   12658 	 So we need to change the buffer type as GL_ELEMENT_ARRAY_BUFFER
   12659 	 */
   12660 	if (test_case_index >= 2)
   12661 	{
   12662 		buffer.m_buffer = Utils::Buffer::Element;
   12663 	}
   12664 	vao.Bind();
   12665 	buffer.Bind();
   12666 
   12667 	vao.Attribute(m_loc_vertex /* vertex_index */, Utils::Type::uint, 0 /* array_elements */, false /* normalized */,
   12668 				  0 /* stride */, 0 /* offset */);
   12669 
   12670 	vao.Attribute(m_loc_instance /* instance_index */, Utils::Type::uint, 0 /* array_elements */,
   12671 				  false /* normalized */, 0 /* stride */, (GLvoid*)sizeof(vertex_index_data) /* offset */);
   12672 	// when test_case_index is 5 or 7, the draw call is glDrawElementsInstancedBaseInstance, glDrawElementsInstancedBaseVertexBaseInstance
   12673 	// the instancecount is 4, the baseinstance is 2, the divisor should be set 2
   12674 	bool isBaseInstanced = (test_case_index == DRAWELEMENTSINSTANCEDBASEINSTANCE ||
   12675 							test_case_index == DRAWELEMENTSINSTANCEDBASEVERTEXBASEINSTANCE);
   12676 	vao.Divisor(m_context.getRenderContext().getFunctions() /* gl */, m_loc_instance /* instance_index */,
   12677 				isBaseInstanced ? 2 : 1 /* divisor. 1 - advance once per instance */);
   12678 
   12679 	memcpy(ptr + 0, vertex_index_data, sizeof(vertex_index_data));
   12680 	memcpy(ptr + sizeof(vertex_index_data), instance_index_data, sizeof(instance_index_data));
   12681 
   12682 	buffer.Data(Utils::Buffer::StaticDraw, buffer_data.size() * sizeof(GLuint), ptr);
   12683 }
   12684 
   12685 /** This test should be run with separable programs
   12686  *
   12687  * @param ignored
   12688  *
   12689  * @return true
   12690  **/
   12691 bool VertexAttribLocationsTest::useMonolithicProgram(GLuint /* test_case_index */)
   12692 {
   12693 	return false;
   12694 }
   12695 
   12696 /** Constructor
   12697  *
   12698  * @param context Test framework context
   12699  **/
   12700 VaryingArrayLocationsTest::VaryingArrayLocationsTest(deqp::Context& context)
   12701 	: VaryingLocationsTest(context, "varying_array_locations",
   12702 						   "Test verifies that input and output locations are respected for arrays")
   12703 {
   12704 }
   12705 
   12706 /**
   12707  *
   12708  **/
   12709 void VaryingArrayLocationsTest::prepareShaderStage(Utils::Shader::STAGES stage, const Utils::Type& type,
   12710 												   Utils::ProgramInterface&   program_interface,
   12711 												   Utils::VaryingPassthrough& varying_passthrough)
   12712 {
   12713 	const GLuint array_length  = 1u;
   12714 	const GLuint first_in_loc  = 0;
   12715 	const GLuint first_out_loc = 0;
   12716 	const GLuint last_in_loc   = getLastInputLocation(stage, type, array_length);
   12717 	size_t		 position	  = 0;
   12718 
   12719 	const GLchar* prefix_in = Utils::ProgramInterface::GetStagePrefix(stage, Utils::Variable::VARYING_INPUT);
   12720 
   12721 	const GLchar* prefix_out = Utils::ProgramInterface::GetStagePrefix(stage, Utils::Variable::VARYING_OUTPUT);
   12722 
   12723 	const GLchar* qual_first_in  = "layout (location = first_input_location)";
   12724 	const GLchar* qual_first_out = "layout (location = first_output_location)";
   12725 	const GLchar* qual_last_in   = "layout (location = last_input_location)";
   12726 	const GLchar* qual_last_out  = "layout (location = last_output_location)";
   12727 
   12728 	Utils::ShaderInterface& si		  = program_interface.GetShaderInterface(stage);
   12729 	const GLuint			type_size = type.GetSize();
   12730 
   12731 	std::string first_in_name  = "PREFIXfirst";
   12732 	std::string first_out_name = "PREFIXfirst";
   12733 	std::string last_in_name   = "PREFIXlast";
   12734 	std::string last_out_name  = "PREFIXlast";
   12735 
   12736 	Utils::replaceToken("PREFIX", position, prefix_in, first_in_name);
   12737 	position = 0;
   12738 	Utils::replaceToken("PREFIX", position, prefix_out, first_out_name);
   12739 	position = 0;
   12740 	Utils::replaceToken("PREFIX", position, prefix_in, last_in_name);
   12741 	position = 0;
   12742 	Utils::replaceToken("PREFIX", position, prefix_out, last_out_name);
   12743 
   12744 	if (Utils::Shader::FRAGMENT == stage)
   12745 	{
   12746 		qual_first_in = "layout (location = first_input_location) flat";
   12747 		qual_last_in  = "layout (location = last_input_location)  flat";
   12748 	}
   12749 	if (Utils::Shader::GEOMETRY == stage)
   12750 	{
   12751 		qual_first_out = "layout (location = first_output_location) flat";
   12752 		qual_last_out  = "layout (location = last_output_location)  flat";
   12753 	}
   12754 
   12755 	Utils::Variable* first_in =
   12756 		si.Input(first_in_name.c_str(), qual_first_in /* qualifiers */, 0 /* expected_componenet */,
   12757 				 first_in_loc /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   12758 				 array_length /* n_array_elements */, 0u /* stride */, 0u /* offset */,
   12759 				 (GLvoid*)&m_first_data[0] /* data */, m_first_data.size() /* data_size */);
   12760 
   12761 	Utils::Variable* last_in =
   12762 		si.Input(last_in_name.c_str(), qual_last_in /* qualifiers */, 0 /* expected_componenet */,
   12763 				 last_in_loc /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   12764 				 array_length /* n_array_elements */, 0u /* stride */, type_size /* offset */,
   12765 				 (GLvoid*)&m_last_data[0] /* data */, m_last_data.size() /* data_size */);
   12766 
   12767 	if (Utils::Shader::FRAGMENT != stage)
   12768 	{
   12769 		const GLuint last_out_loc = getLastOutputLocation(stage, type, array_length);
   12770 
   12771 		Utils::Variable* first_out =
   12772 			si.Output(first_out_name.c_str(), qual_first_out /* qualifiers */, 0 /* expected_componenet */,
   12773 					  first_out_loc /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   12774 					  array_length /* n_array_elements */, 0u /* stride */, 0u /* offset */,
   12775 					  (GLvoid*)&m_first_data[0] /* data */, m_first_data.size() /* data_size */);
   12776 
   12777 		Utils::Variable* last_out =
   12778 			si.Output(last_out_name.c_str(), qual_last_out /* qualifiers */, 0 /* expected_componenet */,
   12779 					  last_out_loc /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   12780 					  array_length /* n_array_elements */, 0u /* stride */, 0u /* offset */,
   12781 					  (GLvoid*)&m_last_data[0] /* data */, m_last_data.size() /* data_size */);
   12782 
   12783 		si.m_globals = prepareGlobals(last_in_loc, last_out_loc);
   12784 
   12785 		varying_passthrough.Add(stage, first_in, first_out);
   12786 		varying_passthrough.Add(stage, last_in, last_out);
   12787 	}
   12788 	else
   12789 	{
   12790 		/* No outputs for fragment shader, so last_output_location can be 0 */
   12791 		si.m_globals = prepareGlobals(last_in_loc, 0);
   12792 	}
   12793 }
   12794 
   12795 /** Constructor
   12796  *
   12797  * @param context Test framework context
   12798  **/
   12799 VaryingStructureLocationsTest::VaryingStructureLocationsTest(deqp::Context& context)
   12800 	: TextureTestBase(context, "varying_structure_locations",
   12801 					  "Test verifies that locations are respected when structures are used as in and out ")
   12802 {
   12803 }
   12804 
   12805 /** Prepare code snippet that will pass in variables to out variables
   12806  *
   12807  * @param ignored
   12808  * @param varying_passthrough Collection of connections between in and out variables
   12809  * @param stage               Shader stage
   12810  *
   12811  * @return Code that pass in variables to next stage
   12812  **/
   12813 std::string VaryingStructureLocationsTest::getPassSnippet(GLuint /* test_case_index */,
   12814 														  Utils::VaryingPassthrough& varying_passthrough,
   12815 														  Utils::Shader::STAGES		 stage)
   12816 {
   12817 	std::string result;
   12818 
   12819 	if (Utils::Shader::VERTEX != stage)
   12820 	{
   12821 		result = TextureTestBase::getPassSnippet(0, varying_passthrough, stage);
   12822 	}
   12823 	else
   12824 	{
   12825 		result = "    vs_tcs_output[0].single   = vs_in_single[0];\n"
   12826 				 "    vs_tcs_output[0].array[0] = vs_in_array[0];\n";
   12827 	}
   12828 
   12829 	return result;
   12830 }
   12831 
   12832 /** Get interface of program
   12833  *
   12834  * @param test_case_index     Test case
   12835  * @param program_interface   Interface of program
   12836  * @param varying_passthrough Collection of connections between in and out variables
   12837  **/
   12838 void VaryingStructureLocationsTest::getProgramInterface(GLuint					   test_case_index,
   12839 														Utils::ProgramInterface&   program_interface,
   12840 														Utils::VaryingPassthrough& varying_passthrough)
   12841 {
   12842 	Utils::ShaderInterface& si   = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   12843 	const Utils::Type		type = getType(test_case_index);
   12844 
   12845 	/* Prepare data */
   12846 	// We should call GenerateDataPacked() to generate data, which can make sure the data in shader is correct
   12847 	m_single_data = type.GenerateDataPacked();
   12848 	m_array_data  = type.GenerateDataPacked();
   12849 
   12850 	m_data.resize(m_single_data.size() + m_array_data.size());
   12851 	GLubyte* ptr = (GLubyte*)&m_data[0];
   12852 	memcpy(ptr, &m_single_data[0], m_single_data.size());
   12853 	memcpy(ptr + m_single_data.size(), &m_array_data[0], m_array_data.size());
   12854 
   12855 	Utils::Interface* structure = program_interface.Structure("Data");
   12856 
   12857 	structure->Member("single", "" /* qualifiers */, 0 /* component */, 0 /* location */, type, false /* normalized */,
   12858 					  0u /* n_array_elements */, 0u /* stride */, 0u /* offset */);
   12859 
   12860 	// the second struct member 's location should not be 0, it is based on by how many the locations the first struct member consumed.
   12861 	structure->Member("array", "" /* qualifiers */, 0 /* component */, type.GetLocations() /* location */, type,
   12862 					  false /* normalized */, 1u /* n_array_elements */, 0u /* stride */, type.GetSize() /* offset */);
   12863 
   12864 	si.Input("vs_in_single", "layout (location = 0)", 0 /* component */, 0 /* location */, type, false /* normalized */,
   12865 			 1u /* n_array_elements */, 0u /* stride */, 0u /* offset */, (GLvoid*)&m_single_data[0] /* data */,
   12866 			 m_single_data.size() /* data_size */);
   12867 
   12868 	si.Input("vs_in_array", "layout (location = 8)", 0 /* component */, 8 /* location */, type, false /* normalized */,
   12869 			 1u /* n_array_elements */, 0u /* stride */, type.GetSize() /* offset */,
   12870 			 (GLvoid*)&m_array_data[0] /* data */, m_array_data.size() /* data_size */);
   12871 
   12872 	si.Output("vs_tcs_output", "layout (location = 0)", 0 /* component */, 0 /* location */, structure,
   12873 			  1u /* n_array_elements */, 0u /* stride */, 0u /* offset */, (GLvoid*)&m_data[0] /* data */,
   12874 			  m_data.size() /* data_size */);
   12875 
   12876 	program_interface.CloneVertexInterface(varying_passthrough);
   12877 }
   12878 
   12879 /** Get type name
   12880  *
   12881  * @param test_case_index Index of test case
   12882  *
   12883  * @return Name of type test in test_case_index
   12884  **/
   12885 std::string VaryingStructureLocationsTest::getTestCaseName(glw::GLuint test_case_index)
   12886 {
   12887 	return getTypeName(test_case_index);
   12888 }
   12889 
   12890 /** Returns number of types to test
   12891  *
   12892  * @return Number of types, 34
   12893  **/
   12894 glw::GLuint VaryingStructureLocationsTest::getTestCaseNumber()
   12895 {
   12896 	return getTypesNumber();
   12897 }
   12898 
   12899 /** Selects if "compute" stage is relevant for test
   12900  *
   12901  * @param ignored
   12902  *
   12903  * @return false
   12904  **/
   12905 bool VaryingStructureLocationsTest::isComputeRelevant(GLuint /* test_case_index */)
   12906 {
   12907 	return false;
   12908 }
   12909 
   12910 /** This test should be run with separable programs
   12911  *
   12912  * @param ignored
   12913  *
   12914  * @return true
   12915  **/
   12916 bool VaryingStructureLocationsTest::useMonolithicProgram(GLuint /* test_case_index */)
   12917 {
   12918 	return false;
   12919 }
   12920 
   12921 /** Constructor
   12922  *
   12923  * @param context          Test context
   12924  * @param test_name        Name of test
   12925  * @param test_description Description of test
   12926  **/
   12927 VaryingStructureMemberLocationTest::VaryingStructureMemberLocationTest(deqp::Context& context)
   12928 	: NegativeTestBase(context, "varying_structure_member_location",
   12929 					   "Test verifies that compiler does not allow location qualifier on member of strucure")
   12930 {
   12931 }
   12932 
   12933 /** Source for given test case and stage
   12934  *
   12935  * @param test_case_index Index of test case
   12936  * @param stage           Shader stage
   12937  *
   12938  * @return Shader source
   12939  **/
   12940 std::string VaryingStructureMemberLocationTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   12941 {
   12942 	static const GLchar* struct_definition = "struct Data {\n"
   12943 											 "    vec4 gohan;\n"
   12944 											 "    layout (location = 4) vec4 goten;\n"
   12945 											 "};\n";
   12946 	static const GLchar* input_var  = "in Data data;\n";
   12947 	static const GLchar* output_var = "out Data data;\n";
   12948 	static const GLchar* input_use  = "    result += data.gohan + data.goten;\n";
   12949 	static const GLchar* output_use = "    data.gohan = result / 2;\n"
   12950 									  "    data.goten = result / 4 - data.gohan;\n";
   12951 	static const GLchar* fs = "#version 430 core\n"
   12952 							  "#extension GL_ARB_enhanced_layouts : require\n"
   12953 							  "\n"
   12954 							  "in  vec4 gs_fs;\n"
   12955 							  "out vec4 fs_out;\n"
   12956 							  "\n"
   12957 							  "void main()\n"
   12958 							  "{\n"
   12959 							  "    fs_out = gs_fs;\n"
   12960 							  "}\n"
   12961 							  "\n";
   12962 	static const GLchar* fs_tested = "#version 430 core\n"
   12963 									 "#extension GL_ARB_enhanced_layouts : require\n"
   12964 									 "\n"
   12965 									 "STRUCT_DEFINITION"
   12966 									 "\n"
   12967 									 "VARIABLE_DEFINITION"
   12968 									 "\n"
   12969 									 "in  vec4 gs_fs;\n"
   12970 									 "out vec4 fs_out;\n"
   12971 									 "\n"
   12972 									 "void main()\n"
   12973 									 "{\n"
   12974 									 "    vec4 result = gs_fs;\n"
   12975 									 "\n"
   12976 									 "VARIABLE_USE"
   12977 									 "\n"
   12978 									 "    fs_out += result;\n"
   12979 									 "}\n"
   12980 									 "\n";
   12981 	static const GLchar* gs = "#version 430 core\n"
   12982 							  "#extension GL_ARB_enhanced_layouts : require\n"
   12983 							  "\n"
   12984 							  "layout(points)                           in;\n"
   12985 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   12986 							  "\n"
   12987 							  "in  vec4 tes_gs[];\n"
   12988 							  "out vec4 gs_fs;\n"
   12989 							  "\n"
   12990 							  "void main()\n"
   12991 							  "{\n"
   12992 							  "    gs_fs = tes_gs[0];\n"
   12993 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   12994 							  "    EmitVertex();\n"
   12995 							  "    gs_fs = tes_gs[0];\n"
   12996 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   12997 							  "    EmitVertex();\n"
   12998 							  "    gs_fs = tes_gs[0];\n"
   12999 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   13000 							  "    EmitVertex();\n"
   13001 							  "    gs_fs = tes_gs[0];\n"
   13002 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   13003 							  "    EmitVertex();\n"
   13004 							  "}\n"
   13005 							  "\n";
   13006 	static const GLchar* gs_tested = "#version 430 core\n"
   13007 									 "#extension GL_ARB_enhanced_layouts : require\n"
   13008 									 "\n"
   13009 									 "layout(points)                           in;\n"
   13010 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   13011 									 "\n"
   13012 									 "STRUCT_DEFINITION"
   13013 									 "\n"
   13014 									 "VARIABLE_DEFINITION"
   13015 									 "\n"
   13016 									 "in  vec4 tes_gs[];\n"
   13017 									 "out vec4 gs_fs;\n"
   13018 									 "\n"
   13019 									 "void main()\n"
   13020 									 "{\n"
   13021 									 "    vec4 result = tes_gs[0];\n"
   13022 									 "\n"
   13023 									 "VARIABLE_USE"
   13024 									 "\n"
   13025 									 "    gs_fs = result;\n"
   13026 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   13027 									 "    EmitVertex();\n"
   13028 									 "    gs_fs = result;\n"
   13029 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   13030 									 "    EmitVertex();\n"
   13031 									 "    gs_fs = result;\n"
   13032 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   13033 									 "    EmitVertex();\n"
   13034 									 "    gs_fs = result;\n"
   13035 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   13036 									 "    EmitVertex();\n"
   13037 									 "}\n"
   13038 									 "\n";
   13039 	static const GLchar* tcs = "#version 430 core\n"
   13040 							   "#extension GL_ARB_enhanced_layouts : require\n"
   13041 							   "\n"
   13042 							   "layout(vertices = 1) out;\n"
   13043 							   "\n"
   13044 							   "in  vec4 vs_tcs[];\n"
   13045 							   "out vec4 tcs_tes[];\n"
   13046 							   "\n"
   13047 							   "void main()\n"
   13048 							   "{\n"
   13049 							   "\n"
   13050 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   13051 							   "\n"
   13052 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   13053 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   13054 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   13055 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   13056 							   "    gl_TessLevelInner[0] = 1.0;\n"
   13057 							   "    gl_TessLevelInner[1] = 1.0;\n"
   13058 							   "}\n"
   13059 							   "\n";
   13060 	static const GLchar* tcs_tested = "#version 430 core\n"
   13061 									  "#extension GL_ARB_enhanced_layouts : require\n"
   13062 									  "\n"
   13063 									  "layout(vertices = 1) out;\n"
   13064 									  "\n"
   13065 									  "STRUCT_DEFINITION"
   13066 									  "\n"
   13067 									  "VARIABLE_DEFINITION"
   13068 									  "\n"
   13069 									  "in  vec4 vs_tcs[];\n"
   13070 									  "out vec4 tcs_tes[];\n"
   13071 									  "\n"
   13072 									  "void main()\n"
   13073 									  "{\n"
   13074 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   13075 									  "\n"
   13076 									  "VARIABLE_USE"
   13077 									  "\n"
   13078 									  "    tcs_tes[gl_InvocationID] = result;\n"
   13079 									  "\n"
   13080 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   13081 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   13082 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   13083 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   13084 									  "    gl_TessLevelInner[0] = 1.0;\n"
   13085 									  "    gl_TessLevelInner[1] = 1.0;\n"
   13086 									  "}\n"
   13087 									  "\n";
   13088 	static const GLchar* tes = "#version 430 core\n"
   13089 							   "#extension GL_ARB_enhanced_layouts : require\n"
   13090 							   "\n"
   13091 							   "layout(isolines, point_mode) in;\n"
   13092 							   "\n"
   13093 							   "in  vec4 tcs_tes[];\n"
   13094 							   "out vec4 tes_gs;\n"
   13095 							   "\n"
   13096 							   "void main()\n"
   13097 							   "{\n"
   13098 							   "    tes_gs = tcs_tes[0];\n"
   13099 							   "}\n"
   13100 							   "\n";
   13101 	static const GLchar* tes_tested = "#version 430 core\n"
   13102 									  "#extension GL_ARB_enhanced_layouts : require\n"
   13103 									  "\n"
   13104 									  "layout(isolines, point_mode) in;\n"
   13105 									  "\n"
   13106 									  "STRUCT_DEFINITION"
   13107 									  "\n"
   13108 									  "VARIABLE_DEFINITION"
   13109 									  "\n"
   13110 									  "in  vec4 tcs_tes[];\n"
   13111 									  "out vec4 tes_gs;\n"
   13112 									  "\n"
   13113 									  "void main()\n"
   13114 									  "{\n"
   13115 									  "    vec4 result = tcs_tes[0];\n"
   13116 									  "\n"
   13117 									  "VARIABLE_USE"
   13118 									  "\n"
   13119 									  "    tes_gs += result;\n"
   13120 									  "}\n"
   13121 									  "\n";
   13122 	static const GLchar* vs = "#version 430 core\n"
   13123 							  "#extension GL_ARB_enhanced_layouts : require\n"
   13124 							  "\n"
   13125 							  "in  vec4 in_vs;\n"
   13126 							  "out vec4 vs_tcs;\n"
   13127 							  "\n"
   13128 							  "void main()\n"
   13129 							  "{\n"
   13130 							  "    vs_tcs = in_vs;\n"
   13131 							  "}\n"
   13132 							  "\n";
   13133 	static const GLchar* vs_tested = "#version 430 core\n"
   13134 									 "#extension GL_ARB_enhanced_layouts : require\n"
   13135 									 "\n"
   13136 									 "STRUCT_DEFINITION"
   13137 									 "\n"
   13138 									 "VARIABLE_DEFINITION"
   13139 									 "\n"
   13140 									 "in  vec4 in_vs;\n"
   13141 									 "out vec4 vs_tcs;\n"
   13142 									 "\n"
   13143 									 "void main()\n"
   13144 									 "{\n"
   13145 									 "    vec4 result = in_vs;\n"
   13146 									 "\n"
   13147 									 "VARIABLE_USE"
   13148 									 "\n"
   13149 									 "    vs_tcs += result;\n"
   13150 									 "}\n"
   13151 									 "\n";
   13152 
   13153 	std::string   source;
   13154 	testCase&	 test_case		 = m_test_cases[test_case_index];
   13155 	const GLchar* var_definition = 0;
   13156 	const GLchar* var_use		 = 0;
   13157 
   13158 	if (true == test_case.m_is_input)
   13159 	{
   13160 		var_definition = input_var;
   13161 		var_use		   = input_use;
   13162 	}
   13163 	else
   13164 	{
   13165 		var_definition = output_var;
   13166 		var_use		   = output_use;
   13167 	}
   13168 
   13169 	if (test_case.m_stage == stage)
   13170 	{
   13171 		size_t position = 0;
   13172 
   13173 		switch (stage)
   13174 		{
   13175 		case Utils::Shader::FRAGMENT:
   13176 			source = fs_tested;
   13177 			break;
   13178 		case Utils::Shader::GEOMETRY:
   13179 			source = gs_tested;
   13180 			break;
   13181 		case Utils::Shader::TESS_CTRL:
   13182 			source = tcs_tested;
   13183 			break;
   13184 		case Utils::Shader::TESS_EVAL:
   13185 			source = tes_tested;
   13186 			break;
   13187 		case Utils::Shader::VERTEX:
   13188 			source = vs_tested;
   13189 			break;
   13190 		default:
   13191 			TCU_FAIL("Invalid enum");
   13192 		}
   13193 
   13194 		Utils::replaceToken("STRUCT_DEFINITION", position, struct_definition, source);
   13195 		Utils::replaceToken("VARIABLE_DEFINITION", position, var_definition, source);
   13196 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   13197 	}
   13198 	else
   13199 	{
   13200 		switch (stage)
   13201 		{
   13202 		case Utils::Shader::FRAGMENT:
   13203 			source = fs;
   13204 			break;
   13205 		case Utils::Shader::GEOMETRY:
   13206 			source = gs;
   13207 			break;
   13208 		case Utils::Shader::TESS_CTRL:
   13209 			source = tcs;
   13210 			break;
   13211 		case Utils::Shader::TESS_EVAL:
   13212 			source = tes;
   13213 			break;
   13214 		case Utils::Shader::VERTEX:
   13215 			source = vs;
   13216 			break;
   13217 		default:
   13218 			TCU_FAIL("Invalid enum");
   13219 		}
   13220 	}
   13221 
   13222 	return source;
   13223 }
   13224 
   13225 /** Get description of test case
   13226  *
   13227  * @param test_case_index Index of test case
   13228  *
   13229  * @return Test case description
   13230  **/
   13231 std::string VaryingStructureMemberLocationTest::getTestCaseName(GLuint test_case_index)
   13232 {
   13233 	std::stringstream stream;
   13234 	testCase&		  test_case = m_test_cases[test_case_index];
   13235 
   13236 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage) << ", direction: ";
   13237 
   13238 	if (true == test_case.m_is_input)
   13239 	{
   13240 		stream << "input";
   13241 	}
   13242 	else
   13243 	{
   13244 		stream << "output";
   13245 	}
   13246 
   13247 	return stream.str();
   13248 }
   13249 
   13250 /** Get number of test cases
   13251  *
   13252  * @return Number of test cases
   13253  **/
   13254 GLuint VaryingStructureMemberLocationTest::getTestCaseNumber()
   13255 {
   13256 	return static_cast<GLuint>(m_test_cases.size());
   13257 }
   13258 
   13259 /** Selects if "compute" stage is relevant for test
   13260  *
   13261  * @param ignored
   13262  *
   13263  * @return false
   13264  **/
   13265 bool VaryingStructureMemberLocationTest::isComputeRelevant(GLuint /* test_case_index */)
   13266 {
   13267 	return false;
   13268 }
   13269 
   13270 /** Prepare all test cases
   13271  *
   13272  **/
   13273 void VaryingStructureMemberLocationTest::testInit()
   13274 {
   13275 	for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   13276 	{
   13277 		if (Utils::Shader::COMPUTE == stage)
   13278 		{
   13279 			continue;
   13280 		}
   13281 
   13282 		testCase test_case_in  = { true, (Utils::Shader::STAGES)stage };
   13283 		testCase test_case_out = { false, (Utils::Shader::STAGES)stage };
   13284 
   13285 		m_test_cases.push_back(test_case_in);
   13286 
   13287 		if (Utils::Shader::FRAGMENT != stage)
   13288 		{
   13289 			m_test_cases.push_back(test_case_out);
   13290 		}
   13291 	}
   13292 }
   13293 
   13294 /** Constructor
   13295  *
   13296  * @param context Test framework context
   13297  **/
   13298 VaryingBlockLocationsTest::VaryingBlockLocationsTest(deqp::Context& context)
   13299 	: TextureTestBase(context, "varying_block_locations",
   13300 					  "Test verifies that locations are respected when blocks are used as in and out ")
   13301 {
   13302 }
   13303 
   13304 /** Prepare code snippet that will pass in variables to out variables
   13305  *
   13306  * @param ignored
   13307  * @param varying_passthrough Collection of connections between in and out variables
   13308  * @param stage               Shader stage
   13309  *
   13310  * @return Code that pass in variables to next stage
   13311  **/
   13312 std::string VaryingBlockLocationsTest::getPassSnippet(GLuint /* test_case_index */,
   13313 													  Utils::VaryingPassthrough& varying_passthrough,
   13314 													  Utils::Shader::STAGES		 stage)
   13315 {
   13316 	std::string result;
   13317 
   13318 	if (Utils::Shader::VERTEX != stage)
   13319 	{
   13320 		result = TextureTestBase::getPassSnippet(0, varying_passthrough, stage);
   13321 	}
   13322 	else
   13323 	{
   13324 		result = "vs_tcs_block.third  = vs_in_third;\n"
   13325 				 "    vs_tcs_block.fourth = vs_in_fourth;\n"
   13326 				 "    vs_tcs_block.fifth  = vs_in_fifth;\n";
   13327 	}
   13328 
   13329 	return result;
   13330 }
   13331 
   13332 /** Get interface of program
   13333  *
   13334  * @param ignored
   13335  * @param program_interface   Interface of program
   13336  * @param varying_passthrough Collection of connections between in and out variables
   13337  **/
   13338 void VaryingBlockLocationsTest::getProgramInterface(GLuint /* test_case_index */,
   13339 													Utils::ProgramInterface&   program_interface,
   13340 													Utils::VaryingPassthrough& varying_passthrough)
   13341 {
   13342 	Utils::ShaderInterface& si   = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   13343 	const Utils::Type		vec4 = Utils::Type::vec4;
   13344 
   13345 	/* Prepare data */
   13346 	m_third_data  = vec4.GenerateData();
   13347 	m_fourth_data = vec4.GenerateData();
   13348 	m_fifth_data  = vec4.GenerateData();
   13349 
   13350 	/* Memory layout is different from location layout */
   13351 	const GLuint fifth_offset  = 0u;
   13352 	const GLuint third_offset  = static_cast<GLuint>(fifth_offset + m_fifth_data.size());
   13353 	const GLuint fourth_offset = static_cast<GLuint>(third_offset + m_fourth_data.size());
   13354 
   13355 	m_data.resize(fourth_offset + m_fourth_data.size());
   13356 	GLubyte* ptr = (GLubyte*)&m_data[0];
   13357 	memcpy(ptr + third_offset, &m_third_data[0], m_third_data.size());
   13358 	memcpy(ptr + fourth_offset, &m_fourth_data[0], m_fourth_data.size());
   13359 	memcpy(ptr + fifth_offset, &m_fifth_data[0], m_fifth_data.size());
   13360 
   13361 	Utils::Interface* block = program_interface.Block("vs_tcs_Block");
   13362 
   13363 	block->Member("fifth", "" /* qualifiers */, 0 /* component */, 4 /* location */, vec4, false /* normalized */,
   13364 				  0u /* n_array_elements */, 0u /* stride */, fifth_offset /* offset */);
   13365 
   13366 	block->Member("third", "layout (location = 2)" /* qualifiers */, 0 /* component */, 2 /* location */, vec4,
   13367 				  false /* normalized */, 0u /* n_array_elements */, 0u /* stride */, third_offset /* offset */);
   13368 
   13369 	block->Member("fourth", "" /* qualifiers */, 0 /* component */, 3 /* location */, vec4, false /* normalized */,
   13370 				  0u /* n_array_elements */, 0u /* stride */, fourth_offset /* offset */);
   13371 
   13372 	si.Output("vs_tcs_block", "layout (location = 4)", 0 /* component */, 4 /* location */, block,
   13373 			  0u /* n_array_elements */, 0u /* stride */, 0u /* offset */, (GLvoid*)&m_data[0] /* data */,
   13374 			  m_data.size() /* data_size */);
   13375 
   13376 	si.Input("vs_in_third", "layout (location = 0)", 0 /* component */, 0 /* location */, vec4, false /* normalized */,
   13377 			 0u /* n_array_elements */, 0u /* stride */, third_offset /* offset */,
   13378 			 (GLvoid*)&m_third_data[0] /* data */, m_third_data.size() /* data_size */);
   13379 
   13380 	si.Input("vs_in_fourth", "layout (location = 1)", 0 /* component */, 1 /* location */, vec4, false /* normalized */,
   13381 			 0u /* n_array_elements */, 0u /* stride */, fourth_offset /* offset */,
   13382 			 (GLvoid*)&m_fourth_data[0] /* data */, m_fourth_data.size() /* data_size */);
   13383 
   13384 	si.Input("vs_in_fifth", "layout (location = 2)", 0 /* component */, 2 /* location */, vec4, false /* normalized */,
   13385 			 0u /* n_array_elements */, 0u /* stride */, fifth_offset /* offset */,
   13386 			 (GLvoid*)&m_fifth_data[0] /* data */, m_fifth_data.size() /* data_size */);
   13387 
   13388 	program_interface.CloneVertexInterface(varying_passthrough);
   13389 }
   13390 
   13391 /** Selects if "compute" stage is relevant for test
   13392  *
   13393  * @param ignored
   13394  *
   13395  * @return false
   13396  **/
   13397 bool VaryingBlockLocationsTest::isComputeRelevant(GLuint /* test_case_index */)
   13398 {
   13399 	return false;
   13400 }
   13401 
   13402 /** This test should be run with separable programs
   13403  *
   13404  * @param ignored
   13405  *
   13406  * @return true
   13407  **/
   13408 bool VaryingBlockLocationsTest::useMonolithicProgram(GLuint /* test_case_index */)
   13409 {
   13410 	return false;
   13411 }
   13412 
   13413 /** Constructor
   13414  *
   13415  * @param context Test framework context
   13416  **/
   13417 VaryingBlockMemberLocationsTest::VaryingBlockMemberLocationsTest(deqp::Context& context)
   13418 	: NegativeTestBase(
   13419 		  context, "varying_block_member_locations",
   13420 		  "Test verifies that compilation error is reported when not all members of block are qualified with location")
   13421 {
   13422 }
   13423 
   13424 /** Source for given test case and stage
   13425  *
   13426  * @param test_case_index Index of test case
   13427  * @param stage           Shader stage
   13428  *
   13429  * @return Shader source
   13430  **/
   13431 std::string VaryingBlockMemberLocationsTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   13432 {
   13433 	static const GLchar* block_definition_all = "Goku {\n"
   13434 												"    layout (location = 2) vec4 gohan;\n"
   13435 												"    layout (location = 4) vec4 goten;\n"
   13436 												"    layout (location = 6) vec4 chichi;\n"
   13437 												"} gokuARRAY;\n";
   13438 	static const GLchar* block_definition_default = "Goku {\n"
   13439 													"    vec4 gohan;\n"
   13440 													"    vec4 goten;\n"
   13441 													"    vec4 chichi;\n"
   13442 													"} gokuARRAY;\n";
   13443 	static const GLchar* block_definition_one = "Goku {\n"
   13444 												"    vec4 gohan;\n"
   13445 												"    layout (location = 4) vec4 goten;\n"
   13446 												"    vec4 chichi;\n"
   13447 												"} gokuARRAY;\n";
   13448 	static const GLchar* input_use  = "    result += gokuINDEX.gohan + gokuINDEX.goten + gokuINDEX.chichi;\n";
   13449 	static const GLchar* output_use = "    gokuINDEX.gohan  = result / 2;\n"
   13450 									  "    gokuINDEX.goten  = result / 4 - gokuINDEX.gohan;\n"
   13451 									  "    gokuINDEX.chichi = result / 8 - gokuINDEX.goten;\n";
   13452 	static const GLchar* fs = "#version 430 core\n"
   13453 							  "#extension GL_ARB_enhanced_layouts : require\n"
   13454 							  "\n"
   13455 							  "in  vec4 gs_fs;\n"
   13456 							  "out vec4 fs_out;\n"
   13457 							  "\n"
   13458 							  "void main()\n"
   13459 							  "{\n"
   13460 							  "    fs_out = gs_fs;\n"
   13461 							  "}\n"
   13462 							  "\n";
   13463 	static const GLchar* fs_tested = "#version 430 core\n"
   13464 									 "#extension GL_ARB_enhanced_layouts : require\n"
   13465 									 "\n"
   13466 									 "DIRECTION BLOCK_DEFINITION"
   13467 									 "\n"
   13468 									 "in  vec4 gs_fs;\n"
   13469 									 "out vec4 fs_out;\n"
   13470 									 "\n"
   13471 									 "void main()\n"
   13472 									 "{\n"
   13473 									 "    vec4 result = gs_fs;\n"
   13474 									 "\n"
   13475 									 "VARIABLE_USE"
   13476 									 "\n"
   13477 									 "    fs_out = result;\n"
   13478 									 "}\n"
   13479 									 "\n";
   13480 	static const GLchar* gs = "#version 430 core\n"
   13481 							  "#extension GL_ARB_enhanced_layouts : require\n"
   13482 							  "\n"
   13483 							  "layout(points)                           in;\n"
   13484 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   13485 							  "\n"
   13486 							  "in  vec4 tes_gs[];\n"
   13487 							  "out vec4 gs_fs;\n"
   13488 							  "\n"
   13489 							  "void main()\n"
   13490 							  "{\n"
   13491 							  "    gs_fs = tes_gs[0];\n"
   13492 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   13493 							  "    EmitVertex();\n"
   13494 							  "    gs_fs = tes_gs[0];\n"
   13495 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   13496 							  "    EmitVertex();\n"
   13497 							  "    gs_fs = tes_gs[0];\n"
   13498 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   13499 							  "    EmitVertex();\n"
   13500 							  "    gs_fs = tes_gs[0];\n"
   13501 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   13502 							  "    EmitVertex();\n"
   13503 							  "}\n"
   13504 							  "\n";
   13505 	static const GLchar* gs_tested = "#version 430 core\n"
   13506 									 "#extension GL_ARB_enhanced_layouts : require\n"
   13507 									 "\n"
   13508 									 "layout(points)                           in;\n"
   13509 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   13510 									 "\n"
   13511 									 "DIRECTION BLOCK_DEFINITION"
   13512 									 "\n"
   13513 									 "in  vec4 tes_gs[];\n"
   13514 									 "out vec4 gs_fs;\n"
   13515 									 "\n"
   13516 									 "void main()\n"
   13517 									 "{\n"
   13518 									 "    vec4 result = tes_gs[0];\n"
   13519 									 "\n"
   13520 									 "VARIABLE_USE"
   13521 									 "\n"
   13522 									 "    gs_fs = result;\n"
   13523 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   13524 									 "    EmitVertex();\n"
   13525 									 "    gs_fs = result;\n"
   13526 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   13527 									 "    EmitVertex();\n"
   13528 									 "    gs_fs = result;\n"
   13529 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   13530 									 "    EmitVertex();\n"
   13531 									 "    gs_fs = result;\n"
   13532 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   13533 									 "    EmitVertex();\n"
   13534 									 "}\n"
   13535 									 "\n";
   13536 	static const GLchar* tcs = "#version 430 core\n"
   13537 							   "#extension GL_ARB_enhanced_layouts : require\n"
   13538 							   "\n"
   13539 							   "layout(vertices = 1) out;\n"
   13540 							   "\n"
   13541 							   "in  vec4 vs_tcs[];\n"
   13542 							   "out vec4 tcs_tes[];\n"
   13543 							   "\n"
   13544 							   "void main()\n"
   13545 							   "{\n"
   13546 							   "\n"
   13547 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   13548 							   "\n"
   13549 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   13550 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   13551 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   13552 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   13553 							   "    gl_TessLevelInner[0] = 1.0;\n"
   13554 							   "    gl_TessLevelInner[1] = 1.0;\n"
   13555 							   "}\n"
   13556 							   "\n";
   13557 	static const GLchar* tcs_tested = "#version 430 core\n"
   13558 									  "#extension GL_ARB_enhanced_layouts : require\n"
   13559 									  "\n"
   13560 									  "layout(vertices = 1) out;\n"
   13561 									  "\n"
   13562 									  "DIRECTION BLOCK_DEFINITION"
   13563 									  "\n"
   13564 									  "in  vec4 vs_tcs[];\n"
   13565 									  "out vec4 tcs_tes[];\n"
   13566 									  "\n"
   13567 									  "void main()\n"
   13568 									  "{\n"
   13569 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   13570 									  "\n"
   13571 									  "VARIABLE_USE"
   13572 									  "\n"
   13573 									  "    tcs_tes[gl_InvocationID] = result;\n"
   13574 									  "\n"
   13575 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   13576 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   13577 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   13578 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   13579 									  "    gl_TessLevelInner[0] = 1.0;\n"
   13580 									  "    gl_TessLevelInner[1] = 1.0;\n"
   13581 									  "}\n"
   13582 									  "\n";
   13583 	static const GLchar* tes = "#version 430 core\n"
   13584 							   "#extension GL_ARB_enhanced_layouts : require\n"
   13585 							   "\n"
   13586 							   "layout(isolines, point_mode) in;\n"
   13587 							   "\n"
   13588 							   "in  vec4 tcs_tes[];\n"
   13589 							   "out vec4 tes_gs;\n"
   13590 							   "\n"
   13591 							   "void main()\n"
   13592 							   "{\n"
   13593 							   "    tes_gs = tcs_tes[0];\n"
   13594 							   "}\n"
   13595 							   "\n";
   13596 	static const GLchar* tes_tested = "#version 430 core\n"
   13597 									  "#extension GL_ARB_enhanced_layouts : require\n"
   13598 									  "\n"
   13599 									  "layout(isolines, point_mode) in;\n"
   13600 									  "\n"
   13601 									  "DIRECTION BLOCK_DEFINITION"
   13602 									  "\n"
   13603 									  "in  vec4 tcs_tes[];\n"
   13604 									  "out vec4 tes_gs;\n"
   13605 									  "\n"
   13606 									  "void main()\n"
   13607 									  "{\n"
   13608 									  "    vec4 result = tcs_tes[0];\n"
   13609 									  "\n"
   13610 									  "VARIABLE_USE"
   13611 									  "\n"
   13612 									  "    tes_gs = result;\n"
   13613 									  "}\n"
   13614 									  "\n";
   13615 	static const GLchar* vs = "#version 430 core\n"
   13616 							  "#extension GL_ARB_enhanced_layouts : require\n"
   13617 							  "\n"
   13618 							  "in  vec4 in_vs;\n"
   13619 							  "out vec4 vs_tcs;\n"
   13620 							  "\n"
   13621 							  "void main()\n"
   13622 							  "{\n"
   13623 							  "    vs_tcs = in_vs;\n"
   13624 							  "}\n"
   13625 							  "\n";
   13626 	static const GLchar* vs_tested = "#version 430 core\n"
   13627 									 "#extension GL_ARB_enhanced_layouts : require\n"
   13628 									 "\n"
   13629 									 "DIRECTION BLOCK_DEFINITION"
   13630 									 "\n"
   13631 									 "in  vec4 in_vs;\n"
   13632 									 "out vec4 vs_tcs;\n"
   13633 									 "\n"
   13634 									 "void main()\n"
   13635 									 "{\n"
   13636 									 "    vec4 result = in_vs;\n"
   13637 									 "\n"
   13638 									 "VARIABLE_USE"
   13639 									 "\n"
   13640 									 "    vs_tcs = result;\n"
   13641 									 "}\n"
   13642 									 "\n";
   13643 
   13644 	static const GLchar* shaders_in[6][6] = { /* cs  */ { 0, 0, 0, 0, 0, 0 },
   13645 											  /* vs  */ { 0, vs_tested, tcs, tes, gs, fs },
   13646 											  /* tcs */ { 0, vs_tested, tcs_tested, tes, gs, fs },
   13647 											  /* tes */ { 0, vs, tcs_tested, tes_tested, gs, fs },
   13648 											  /* gs  */ { 0, vs, tcs, tes_tested, gs_tested, fs },
   13649 											  /* fs  */ { 0, vs, tcs, tes, gs_tested, fs_tested } };
   13650 
   13651 	static const GLchar* shaders_out[6][6] = { /* cs  */ { 0, 0, 0, 0, 0, 0 },
   13652 											   /* vs  */ { 0, vs_tested, tcs_tested, tes, gs, fs },
   13653 											   /* tcs */ { 0, vs, tcs_tested, tes_tested, gs, fs },
   13654 											   /* tes */ { 0, vs, tcs, tes_tested, gs_tested, fs },
   13655 											   /* gs  */ { 0, vs, tcs, tes, gs_tested, fs_tested },
   13656 											   /* fs  */ { 0, 0, 0, 0, 0, 0 } };
   13657 
   13658 	static const bool require_modifications_in[6][6] = {
   13659 		/* cs  */ { false, false, false, false, false, false },
   13660 		/* vs  */ { false, true, false, false, false, false },
   13661 		/* tcs */ { false, true, true, false, false, false },
   13662 		/* tes */ { false, false, true, true, false, false },
   13663 		/* gs  */ { false, false, false, true, true, false },
   13664 		/* fs  */ { false, false, false, false, true, true }
   13665 	};
   13666 
   13667 	static const bool require_modifications_out[6][6] = {
   13668 		/* cs  */ { false, false, false, false, false, false },
   13669 		/* vs  */ { false, true, true, false, false, false },
   13670 		/* tcs */ { false, false, true, true, false, false },
   13671 		/* tes */ { false, false, false, true, true, false },
   13672 		/* gs  */ { false, false, false, false, true, true },
   13673 		/* fs  */ { false, false, false, false, false, false }
   13674 	};
   13675 
   13676 	const GLchar* array					= "";
   13677 	const GLchar* definition			= block_definition_default;
   13678 	const GLchar* direction				= "out";
   13679 	const GLchar* index					= "";
   13680 	bool		  require_modifications = false;
   13681 	std::string   source;
   13682 	testCase&	 test_case = m_test_cases[test_case_index];
   13683 	const GLchar* var_use   = output_use;
   13684 
   13685 	if (true == test_case.m_is_input)
   13686 	{
   13687 		require_modifications = require_modifications_in[test_case.m_stage][stage];
   13688 		source				  = shaders_in[test_case.m_stage][stage];
   13689 
   13690 		if (test_case.m_stage == stage)
   13691 		{
   13692 			direction = "in";
   13693 			var_use   = input_use;
   13694 		}
   13695 	}
   13696 	else
   13697 	{
   13698 		require_modifications = require_modifications_out[test_case.m_stage][stage];
   13699 		source				  = shaders_out[test_case.m_stage][stage];
   13700 
   13701 		if (test_case.m_stage != stage)
   13702 		{
   13703 			direction = "in";
   13704 			var_use   = input_use;
   13705 		}
   13706 	}
   13707 
   13708 	if (test_case.m_stage == stage)
   13709 	{
   13710 		if (true == test_case.m_qualify_all)
   13711 		{
   13712 			definition = block_definition_all;
   13713 		}
   13714 		else
   13715 		{
   13716 			definition = block_definition_one;
   13717 		}
   13718 	}
   13719 
   13720 	// Geometry shader inputs, tessellation control shader inputs and outputs, and tessellation evaluation
   13721 	// inputs all have an additional level of arrayness relative to other shader inputs and outputs.
   13722 	switch (stage)
   13723 	{
   13724 	case Utils::Shader::FRAGMENT:
   13725 		break;
   13726 	case Utils::Shader::TESS_CTRL:
   13727 		array = "[]";
   13728 		index = "[gl_InvocationID]";
   13729 		break;
   13730 	// geometry shader's input must have one more dimension than tessellation evaluation shader's output,
   13731 	// the GS input block is an array, so the DS output can't be declared as an array
   13732 	case Utils::Shader::GEOMETRY:
   13733 	case Utils::Shader::TESS_EVAL:
   13734 	{
   13735 		if (std::string(direction) == std::string("in")) // match HS output and DS input
   13736 		{
   13737 			array = "[]";
   13738 			index = "[0]";
   13739 		}
   13740 		else // match DS output and GS input
   13741 		{
   13742 			array = "";
   13743 			index = "";
   13744 		}
   13745 	}
   13746 	break;
   13747 	case Utils::Shader::VERTEX:
   13748 		break;
   13749 	default:
   13750 		TCU_FAIL("Invalid enum");
   13751 	}
   13752 
   13753 	if (true == require_modifications)
   13754 	{
   13755 		size_t position = 0;
   13756 		size_t temp;
   13757 
   13758 		Utils::replaceToken("DIRECTION", position, direction, source);
   13759 		temp = position;
   13760 		Utils::replaceToken("BLOCK_DEFINITION", position, definition, source);
   13761 		position = temp;
   13762 		Utils::replaceToken("ARRAY", position, array, source);
   13763 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   13764 
   13765 		Utils::replaceAllTokens("INDEX", index, source);
   13766 	}
   13767 	else
   13768 	{
   13769 		switch (stage)
   13770 		{
   13771 		case Utils::Shader::FRAGMENT:
   13772 			source = fs;
   13773 			break;
   13774 		case Utils::Shader::GEOMETRY:
   13775 			source = gs;
   13776 			break;
   13777 		case Utils::Shader::TESS_CTRL:
   13778 			source = tcs;
   13779 			break;
   13780 		case Utils::Shader::TESS_EVAL:
   13781 			source = tes;
   13782 			break;
   13783 		case Utils::Shader::VERTEX:
   13784 			source = vs;
   13785 			break;
   13786 		default:
   13787 			TCU_FAIL("Invalid enum");
   13788 		}
   13789 	}
   13790 
   13791 	return source;
   13792 }
   13793 
   13794 /** Get description of test case
   13795  *
   13796  * @param test_case_index Index of test case
   13797  *
   13798  * @return Test case description
   13799  **/
   13800 std::string VaryingBlockMemberLocationsTest::getTestCaseName(GLuint test_case_index)
   13801 {
   13802 	std::stringstream stream;
   13803 	testCase&		  test_case = m_test_cases[test_case_index];
   13804 
   13805 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage) << ", direction: ";
   13806 
   13807 	if (true == test_case.m_is_input)
   13808 	{
   13809 		stream << "input";
   13810 	}
   13811 	else
   13812 	{
   13813 		stream << "output";
   13814 	}
   13815 
   13816 	if (true == test_case.m_qualify_all)
   13817 	{
   13818 		stream << ", all members qualified";
   13819 	}
   13820 	else
   13821 	{
   13822 		stream << ", not all members qualified";
   13823 	}
   13824 
   13825 	return stream.str();
   13826 }
   13827 
   13828 /** Get number of test cases
   13829  *
   13830  * @return Number of test cases
   13831  **/
   13832 GLuint VaryingBlockMemberLocationsTest::getTestCaseNumber()
   13833 {
   13834 	return static_cast<GLuint>(m_test_cases.size());
   13835 }
   13836 
   13837 /** Selects if "compute" stage is relevant for test
   13838  *
   13839  * @param ignored
   13840  *
   13841  * @return false
   13842  **/
   13843 bool VaryingBlockMemberLocationsTest::isComputeRelevant(GLuint /* test_case_index */)
   13844 {
   13845 	return false;
   13846 }
   13847 
   13848 /** Selects if compilation failure is expected result
   13849  *
   13850  * @param test_case_index Index of test case
   13851  *
   13852  * @return false when all members are qualified, true otherwise
   13853  **/
   13854 bool VaryingBlockMemberLocationsTest::isFailureExpected(GLuint test_case_index)
   13855 {
   13856 	return (true != m_test_cases[test_case_index].m_qualify_all);
   13857 }
   13858 
   13859 /** Prepare all test cases
   13860  *
   13861  **/
   13862 void VaryingBlockMemberLocationsTest::testInit()
   13863 {
   13864 	for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   13865 	{
   13866 		if (Utils::Shader::COMPUTE == stage)
   13867 		{
   13868 			continue;
   13869 		}
   13870 
   13871 		testCase test_case_in_all  = { true, true, (Utils::Shader::STAGES)stage };
   13872 		testCase test_case_in_one  = { true, false, (Utils::Shader::STAGES)stage };
   13873 		testCase test_case_out_all = { false, true, (Utils::Shader::STAGES)stage };
   13874 		testCase test_case_out_one = { false, false, (Utils::Shader::STAGES)stage };
   13875 
   13876 		if (Utils::Shader::VERTEX != stage)
   13877 		{
   13878 			m_test_cases.push_back(test_case_in_all);
   13879 			m_test_cases.push_back(test_case_in_one);
   13880 		}
   13881 
   13882 		if (Utils::Shader::FRAGMENT != stage)
   13883 		{
   13884 			m_test_cases.push_back(test_case_out_all);
   13885 			m_test_cases.push_back(test_case_out_one);
   13886 		}
   13887 	}
   13888 }
   13889 
   13890 /** Constructor
   13891  *
   13892  * @param context Test framework context
   13893  **/
   13894 VaryingBlockAutomaticMemberLocationsTest::VaryingBlockAutomaticMemberLocationsTest(deqp::Context& context)
   13895 	: NegativeTestBase(
   13896 		  context, "varying_block_automatic_member_locations",
   13897 		  "Test verifies that compiler assigns subsequent locations to block members, even if this causes errors")
   13898 {
   13899 }
   13900 
   13901 /** Source for given test case and stage
   13902  *
   13903  * @param test_case_index Index of test case
   13904  * @param stage           Shader stage
   13905  *
   13906  * @return Shader source
   13907  **/
   13908 std::string VaryingBlockAutomaticMemberLocationsTest::getShaderSource(GLuint				test_case_index,
   13909 																	  Utils::Shader::STAGES stage)
   13910 {
   13911 	static const GLchar* block_definition = "layout (location = 2) DIRECTION DBZ {\n"
   13912 											"    vec4 goku;\n"
   13913 											"    vec4 gohan[4];\n"
   13914 											"    vec4 goten;\n"
   13915 											"    layout (location = 1) vec4 chichi;\n"
   13916 											"    vec4 pan;\n"
   13917 											"} dbzARRAY;\n";
   13918 	static const GLchar* input_use = "    result += dbzINDEX.goku + dbzINDEX.gohan[0] + dbzINDEX.gohan[1] + "
   13919 									 "dbzINDEX.gohan[3] + dbzINDEX.gohan[2] + dbzINDEX.goten + dbzINDEX.chichi + "
   13920 									 "dbzINDEX.pan;\n";
   13921 	static const GLchar* output_use = "    dbzINDEX.goku     = result;\n"
   13922 									  "    dbzINDEX.gohan[0] = result / 2;\n"
   13923 									  "    dbzINDEX.gohan[1] = result / 2.25;\n"
   13924 									  "    dbzINDEX.gohan[2] = result / 2.5;\n"
   13925 									  "    dbzINDEX.gohan[3] = result / 2.75;\n"
   13926 									  "    dbzINDEX.goten    = result / 4  - dbzINDEX.gohan[0] - dbzINDEX.gohan[1] - "
   13927 									  "dbzINDEX.gohan[2] - dbzINDEX.gohan[3];\n"
   13928 									  "    dbzINDEX.chichi   = result / 8  - dbzINDEX.goten;\n"
   13929 									  "    dbzINDEX.pan      = result / 16 - dbzINDEX.chichi;\n";
   13930 	static const GLchar* fs = "#version 430 core\n"
   13931 							  "#extension GL_ARB_enhanced_layouts : require\n"
   13932 							  "\n"
   13933 							  "in  vec4 gs_fs;\n"
   13934 							  "out vec4 fs_out;\n"
   13935 							  "\n"
   13936 							  "void main()\n"
   13937 							  "{\n"
   13938 							  "    fs_out = gs_fs;\n"
   13939 							  "}\n"
   13940 							  "\n";
   13941 	static const GLchar* fs_tested = "#version 430 core\n"
   13942 									 "#extension GL_ARB_enhanced_layouts : require\n"
   13943 									 "\n"
   13944 									 "BLOCK_DEFINITION"
   13945 									 "\n"
   13946 									 "in  vec4 gs_fs;\n"
   13947 									 "out vec4 fs_out;\n"
   13948 									 "\n"
   13949 									 "void main()\n"
   13950 									 "{\n"
   13951 									 "    vec4 result = gs_fs;\n"
   13952 									 "\n"
   13953 									 "VARIABLE_USE"
   13954 									 "\n"
   13955 									 "    fs_out += result;\n"
   13956 									 "}\n"
   13957 									 "\n";
   13958 	static const GLchar* gs = "#version 430 core\n"
   13959 							  "#extension GL_ARB_enhanced_layouts : require\n"
   13960 							  "\n"
   13961 							  "layout(points)                           in;\n"
   13962 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   13963 							  "\n"
   13964 							  "in  vec4 tes_gs[];\n"
   13965 							  "out vec4 gs_fs;\n"
   13966 							  "\n"
   13967 							  "void main()\n"
   13968 							  "{\n"
   13969 							  "    gs_fs = tes_gs[0];\n"
   13970 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   13971 							  "    EmitVertex();\n"
   13972 							  "    gs_fs = tes_gs[0];\n"
   13973 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   13974 							  "    EmitVertex();\n"
   13975 							  "    gs_fs = tes_gs[0];\n"
   13976 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   13977 							  "    EmitVertex();\n"
   13978 							  "    gs_fs = tes_gs[0];\n"
   13979 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   13980 							  "    EmitVertex();\n"
   13981 							  "}\n"
   13982 							  "\n";
   13983 	static const GLchar* gs_tested = "#version 430 core\n"
   13984 									 "#extension GL_ARB_enhanced_layouts : require\n"
   13985 									 "\n"
   13986 									 "layout(points)                           in;\n"
   13987 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   13988 									 "\n"
   13989 									 "BLOCK_DEFINITION"
   13990 									 "\n"
   13991 									 "in  vec4 tes_gs[];\n"
   13992 									 "out vec4 gs_fs;\n"
   13993 									 "\n"
   13994 									 "void main()\n"
   13995 									 "{\n"
   13996 									 "    vec4 result = tes_gs[0];\n"
   13997 									 "\n"
   13998 									 "VARIABLE_USE"
   13999 									 "\n"
   14000 									 "    gs_fs = result;\n"
   14001 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   14002 									 "    EmitVertex();\n"
   14003 									 "    gs_fs = result;\n"
   14004 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   14005 									 "    EmitVertex();\n"
   14006 									 "    gs_fs = result;\n"
   14007 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   14008 									 "    EmitVertex();\n"
   14009 									 "    gs_fs = result;\n"
   14010 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   14011 									 "    EmitVertex();\n"
   14012 									 "}\n"
   14013 									 "\n";
   14014 	static const GLchar* tcs = "#version 430 core\n"
   14015 							   "#extension GL_ARB_enhanced_layouts : require\n"
   14016 							   "\n"
   14017 							   "layout(vertices = 1) out;\n"
   14018 							   "\n"
   14019 							   "in  vec4 vs_tcs[];\n"
   14020 							   "out vec4 tcs_tes[];\n"
   14021 							   "\n"
   14022 							   "void main()\n"
   14023 							   "{\n"
   14024 							   "\n"
   14025 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   14026 							   "\n"
   14027 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   14028 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   14029 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   14030 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   14031 							   "    gl_TessLevelInner[0] = 1.0;\n"
   14032 							   "    gl_TessLevelInner[1] = 1.0;\n"
   14033 							   "}\n"
   14034 							   "\n";
   14035 	static const GLchar* tcs_tested = "#version 430 core\n"
   14036 									  "#extension GL_ARB_enhanced_layouts : require\n"
   14037 									  "\n"
   14038 									  "layout(vertices = 1) out;\n"
   14039 									  "\n"
   14040 									  "BLOCK_DEFINITION"
   14041 									  "\n"
   14042 									  "in  vec4 vs_tcs[];\n"
   14043 									  "out vec4 tcs_tes[];\n"
   14044 									  "\n"
   14045 									  "void main()\n"
   14046 									  "{\n"
   14047 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   14048 									  "\n"
   14049 									  "VARIABLE_USE"
   14050 									  "\n"
   14051 									  "    tcs_tes[gl_InvocationID] = result;\n"
   14052 									  "\n"
   14053 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   14054 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   14055 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   14056 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   14057 									  "    gl_TessLevelInner[0] = 1.0;\n"
   14058 									  "    gl_TessLevelInner[1] = 1.0;\n"
   14059 									  "}\n"
   14060 									  "\n";
   14061 	static const GLchar* tes = "#version 430 core\n"
   14062 							   "#extension GL_ARB_enhanced_layouts : require\n"
   14063 							   "\n"
   14064 							   "layout(isolines, point_mode) in;\n"
   14065 							   "\n"
   14066 							   "in  vec4 tcs_tes[];\n"
   14067 							   "out vec4 tes_gs;\n"
   14068 							   "\n"
   14069 							   "void main()\n"
   14070 							   "{\n"
   14071 							   "    tes_gs = tcs_tes[0];\n"
   14072 							   "}\n"
   14073 							   "\n";
   14074 	static const GLchar* tes_tested = "#version 430 core\n"
   14075 									  "#extension GL_ARB_enhanced_layouts : require\n"
   14076 									  "\n"
   14077 									  "layout(isolines, point_mode) in;\n"
   14078 									  "\n"
   14079 									  "BLOCK_DEFINITION"
   14080 									  "\n"
   14081 									  "in  vec4 tcs_tes[];\n"
   14082 									  "out vec4 tes_gs;\n"
   14083 									  "\n"
   14084 									  "void main()\n"
   14085 									  "{\n"
   14086 									  "    vec4 result = tcs_tes[0];\n"
   14087 									  "\n"
   14088 									  "VARIABLE_USE"
   14089 									  "\n"
   14090 									  "    tes_gs += result;\n"
   14091 									  "}\n"
   14092 									  "\n";
   14093 	static const GLchar* vs = "#version 430 core\n"
   14094 							  "#extension GL_ARB_enhanced_layouts : require\n"
   14095 							  "\n"
   14096 							  "in  vec4 in_vs;\n"
   14097 							  "out vec4 vs_tcs;\n"
   14098 							  "\n"
   14099 							  "void main()\n"
   14100 							  "{\n"
   14101 							  "    vs_tcs = in_vs;\n"
   14102 							  "}\n"
   14103 							  "\n";
   14104 	static const GLchar* vs_tested = "#version 430 core\n"
   14105 									 "#extension GL_ARB_enhanced_layouts : require\n"
   14106 									 "\n"
   14107 									 "BLOCK_DEFINITION"
   14108 									 "\n"
   14109 									 "in  vec4 in_vs;\n"
   14110 									 "out vec4 vs_tcs;\n"
   14111 									 "\n"
   14112 									 "void main()\n"
   14113 									 "{\n"
   14114 									 "    vec4 result = in_vs;\n"
   14115 									 "\n"
   14116 									 "VARIABLE_USE"
   14117 									 "\n"
   14118 									 "    vs_tcs += result;\n"
   14119 									 "}\n"
   14120 									 "\n";
   14121 
   14122 	const GLchar* array		= "";
   14123 	const GLchar* direction = "out";
   14124 	const GLchar* index		= "";
   14125 	std::string   source;
   14126 	testCase&	 test_case = m_test_cases[test_case_index];
   14127 	const GLchar* var_use   = output_use;
   14128 
   14129 	if (true == test_case.m_is_input)
   14130 	{
   14131 		direction = "in ";
   14132 		var_use   = input_use;
   14133 	}
   14134 
   14135 	if (test_case.m_stage == stage)
   14136 	{
   14137 		size_t position = 0;
   14138 		size_t temp;
   14139 
   14140 		switch (stage)
   14141 		{
   14142 		case Utils::Shader::FRAGMENT:
   14143 			source = fs_tested;
   14144 			break;
   14145 		case Utils::Shader::GEOMETRY:
   14146 			source = gs_tested;
   14147 			array  = "[]";
   14148 			index  = "[0]";
   14149 			break;
   14150 		case Utils::Shader::TESS_CTRL:
   14151 			source = tcs_tested;
   14152 			array  = "[]";
   14153 			index  = "[gl_InvocationID]";
   14154 			break;
   14155 		case Utils::Shader::TESS_EVAL:
   14156 			source = tes_tested;
   14157 			array  = "[]";
   14158 			index  = "[0]";
   14159 			break;
   14160 		case Utils::Shader::VERTEX:
   14161 			source = vs_tested;
   14162 			break;
   14163 		default:
   14164 			TCU_FAIL("Invalid enum");
   14165 		}
   14166 
   14167 		temp = position;
   14168 		Utils::replaceToken("BLOCK_DEFINITION", position, block_definition, source);
   14169 		position = temp;
   14170 		Utils::replaceToken("DIRECTION", position, direction, source);
   14171 		Utils::replaceToken("ARRAY", position, array, source);
   14172 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   14173 
   14174 		Utils::replaceAllTokens("INDEX", index, source);
   14175 	}
   14176 	else
   14177 	{
   14178 		switch (stage)
   14179 		{
   14180 		case Utils::Shader::FRAGMENT:
   14181 			source = fs;
   14182 			break;
   14183 		case Utils::Shader::GEOMETRY:
   14184 			source = gs;
   14185 			break;
   14186 		case Utils::Shader::TESS_CTRL:
   14187 			source = tcs;
   14188 			break;
   14189 		case Utils::Shader::TESS_EVAL:
   14190 			source = tes;
   14191 			break;
   14192 		case Utils::Shader::VERTEX:
   14193 			source = vs;
   14194 			break;
   14195 		default:
   14196 			TCU_FAIL("Invalid enum");
   14197 		}
   14198 	}
   14199 
   14200 	return source;
   14201 }
   14202 
   14203 /** Get description of test case
   14204  *
   14205  * @param test_case_index Index of test case
   14206  *
   14207  * @return Test case description
   14208  **/
   14209 std::string VaryingBlockAutomaticMemberLocationsTest::getTestCaseName(GLuint test_case_index)
   14210 {
   14211 	std::stringstream stream;
   14212 	testCase&		  test_case = m_test_cases[test_case_index];
   14213 
   14214 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage) << ", direction: ";
   14215 
   14216 	if (true == test_case.m_is_input)
   14217 	{
   14218 		stream << "input";
   14219 	}
   14220 	else
   14221 	{
   14222 		stream << "output";
   14223 	}
   14224 
   14225 	return stream.str();
   14226 }
   14227 
   14228 /** Get number of test cases
   14229  *
   14230  * @return Number of test cases
   14231  **/
   14232 GLuint VaryingBlockAutomaticMemberLocationsTest::getTestCaseNumber()
   14233 {
   14234 	return static_cast<GLuint>(m_test_cases.size());
   14235 }
   14236 
   14237 /** Selects if "compute" stage is relevant for test
   14238  *
   14239  * @param ignored
   14240  *
   14241  * @return false
   14242  **/
   14243 bool VaryingBlockAutomaticMemberLocationsTest::isComputeRelevant(GLuint /* test_case_index */)
   14244 {
   14245 	return false;
   14246 }
   14247 
   14248 /** Prepare all test cases
   14249  *
   14250  **/
   14251 void VaryingBlockAutomaticMemberLocationsTest::testInit()
   14252 {
   14253 	for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   14254 	{
   14255 		if (Utils::Shader::COMPUTE == stage)
   14256 		{
   14257 			continue;
   14258 		}
   14259 
   14260 		testCase test_case_in  = { true, (Utils::Shader::STAGES)stage };
   14261 		testCase test_case_out = { false, (Utils::Shader::STAGES)stage };
   14262 
   14263 		if (Utils::Shader::VERTEX != stage)
   14264 		{
   14265 			m_test_cases.push_back(test_case_in);
   14266 		}
   14267 
   14268 		if (Utils::Shader::FRAGMENT != stage)
   14269 		{
   14270 			m_test_cases.push_back(test_case_out);
   14271 		}
   14272 	}
   14273 }
   14274 
   14275 /** Constructor
   14276  *
   14277  * @param context Test framework context
   14278  **/
   14279 VaryingLocationLimitTest::VaryingLocationLimitTest(deqp::Context& context)
   14280 	: NegativeTestBase(context, "varying_location_limit",
   14281 					   "Test verifies that compiler reports error when location qualifier exceed limits")
   14282 {
   14283 }
   14284 
   14285 /** Source for given test case and stage
   14286  *
   14287  * @param test_case_index Index of test case
   14288  * @param stage           Shader stage
   14289  *
   14290  * @return Shader source
   14291  **/
   14292 std::string VaryingLocationLimitTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   14293 {
   14294 	static const GLchar* var_definition = "layout (location = LAST + 1) FLAT DIRECTION TYPE gokuARRAY;\n";
   14295 	static const GLchar* input_use		= "    if (TYPE(0) == gokuINDEX)\n"
   14296 									 "    {\n"
   14297 									 "        result += vec4(1, 0.5, 0.25, 0.125);\n"
   14298 									 "    }\n";
   14299 	static const GLchar* output_use = "    gokuINDEX = TYPE(0);\n"
   14300 									  "    if (vec4(0) == result)\n"
   14301 									  "    {\n"
   14302 									  "        gokuINDEX = TYPE(1);\n"
   14303 									  "    }\n";
   14304 	static const GLchar* fs = "#version 430 core\n"
   14305 							  "#extension GL_ARB_enhanced_layouts : require\n"
   14306 							  "\n"
   14307 							  "in  vec4 gs_fs;\n"
   14308 							  "out vec4 fs_out;\n"
   14309 							  "\n"
   14310 							  "void main()\n"
   14311 							  "{\n"
   14312 							  "    fs_out = gs_fs;\n"
   14313 							  "}\n"
   14314 							  "\n";
   14315 	static const GLchar* fs_tested = "#version 430 core\n"
   14316 									 "#extension GL_ARB_enhanced_layouts : require\n"
   14317 									 "\n"
   14318 									 "VAR_DEFINITION"
   14319 									 "\n"
   14320 									 "in  vec4 gs_fs;\n"
   14321 									 "out vec4 fs_out;\n"
   14322 									 "\n"
   14323 									 "void main()\n"
   14324 									 "{\n"
   14325 									 "    vec4 result = gs_fs;\n"
   14326 									 "\n"
   14327 									 "VARIABLE_USE"
   14328 									 "\n"
   14329 									 "    fs_out += result;\n"
   14330 									 "}\n"
   14331 									 "\n";
   14332 	static const GLchar* gs = "#version 430 core\n"
   14333 							  "#extension GL_ARB_enhanced_layouts : require\n"
   14334 							  "\n"
   14335 							  "layout(points)                           in;\n"
   14336 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   14337 							  "\n"
   14338 							  "in  vec4 tes_gs[];\n"
   14339 							  "out vec4 gs_fs;\n"
   14340 							  "\n"
   14341 							  "void main()\n"
   14342 							  "{\n"
   14343 							  "    gs_fs = tes_gs[0];\n"
   14344 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   14345 							  "    EmitVertex();\n"
   14346 							  "    gs_fs = tes_gs[0];\n"
   14347 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   14348 							  "    EmitVertex();\n"
   14349 							  "    gs_fs = tes_gs[0];\n"
   14350 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   14351 							  "    EmitVertex();\n"
   14352 							  "    gs_fs = tes_gs[0];\n"
   14353 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   14354 							  "    EmitVertex();\n"
   14355 							  "}\n"
   14356 							  "\n";
   14357 	static const GLchar* gs_tested = "#version 430 core\n"
   14358 									 "#extension GL_ARB_enhanced_layouts : require\n"
   14359 									 "\n"
   14360 									 "layout(points)                           in;\n"
   14361 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   14362 									 "\n"
   14363 									 "VAR_DEFINITION"
   14364 									 "\n"
   14365 									 "in  vec4 tes_gs[];\n"
   14366 									 "out vec4 gs_fs;\n"
   14367 									 "\n"
   14368 									 "void main()\n"
   14369 									 "{\n"
   14370 									 "    vec4 result = tes_gs[0];\n"
   14371 									 "\n"
   14372 									 "VARIABLE_USE"
   14373 									 "\n"
   14374 									 "    gs_fs = result;\n"
   14375 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   14376 									 "    EmitVertex();\n"
   14377 									 "    gs_fs = result;\n"
   14378 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   14379 									 "    EmitVertex();\n"
   14380 									 "    gs_fs = result;\n"
   14381 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   14382 									 "    EmitVertex();\n"
   14383 									 "    gs_fs = result;\n"
   14384 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   14385 									 "    EmitVertex();\n"
   14386 									 "}\n"
   14387 									 "\n";
   14388 	static const GLchar* tcs = "#version 430 core\n"
   14389 							   "#extension GL_ARB_enhanced_layouts : require\n"
   14390 							   "\n"
   14391 							   "layout(vertices = 1) out;\n"
   14392 							   "\n"
   14393 							   "in  vec4 vs_tcs[];\n"
   14394 							   "out vec4 tcs_tes[];\n"
   14395 							   "\n"
   14396 							   "void main()\n"
   14397 							   "{\n"
   14398 							   "\n"
   14399 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   14400 							   "\n"
   14401 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   14402 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   14403 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   14404 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   14405 							   "    gl_TessLevelInner[0] = 1.0;\n"
   14406 							   "    gl_TessLevelInner[1] = 1.0;\n"
   14407 							   "}\n"
   14408 							   "\n";
   14409 	static const GLchar* tcs_tested = "#version 430 core\n"
   14410 									  "#extension GL_ARB_enhanced_layouts : require\n"
   14411 									  "\n"
   14412 									  "layout(vertices = 1) out;\n"
   14413 									  "\n"
   14414 									  "VAR_DEFINITION"
   14415 									  "\n"
   14416 									  "in  vec4 vs_tcs[];\n"
   14417 									  "out vec4 tcs_tes[];\n"
   14418 									  "\n"
   14419 									  "void main()\n"
   14420 									  "{\n"
   14421 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   14422 									  "\n"
   14423 									  "VARIABLE_USE"
   14424 									  "\n"
   14425 									  "    tcs_tes[gl_InvocationID] = result;\n"
   14426 									  "\n"
   14427 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   14428 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   14429 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   14430 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   14431 									  "    gl_TessLevelInner[0] = 1.0;\n"
   14432 									  "    gl_TessLevelInner[1] = 1.0;\n"
   14433 									  "}\n"
   14434 									  "\n";
   14435 	static const GLchar* tes = "#version 430 core\n"
   14436 							   "#extension GL_ARB_enhanced_layouts : require\n"
   14437 							   "\n"
   14438 							   "layout(isolines, point_mode) in;\n"
   14439 							   "\n"
   14440 							   "in  vec4 tcs_tes[];\n"
   14441 							   "out vec4 tes_gs;\n"
   14442 							   "\n"
   14443 							   "void main()\n"
   14444 							   "{\n"
   14445 							   "    tes_gs = tcs_tes[0];\n"
   14446 							   "}\n"
   14447 							   "\n";
   14448 	static const GLchar* tes_tested = "#version 430 core\n"
   14449 									  "#extension GL_ARB_enhanced_layouts : require\n"
   14450 									  "\n"
   14451 									  "layout(isolines, point_mode) in;\n"
   14452 									  "\n"
   14453 									  "VAR_DEFINITION"
   14454 									  "\n"
   14455 									  "in  vec4 tcs_tes[];\n"
   14456 									  "out vec4 tes_gs;\n"
   14457 									  "\n"
   14458 									  "void main()\n"
   14459 									  "{\n"
   14460 									  "    vec4 result = tcs_tes[0];\n"
   14461 									  "\n"
   14462 									  "VARIABLE_USE"
   14463 									  "\n"
   14464 									  "    tes_gs += result;\n"
   14465 									  "}\n"
   14466 									  "\n";
   14467 	static const GLchar* vs = "#version 430 core\n"
   14468 							  "#extension GL_ARB_enhanced_layouts : require\n"
   14469 							  "\n"
   14470 							  "in  vec4 in_vs;\n"
   14471 							  "out vec4 vs_tcs;\n"
   14472 							  "\n"
   14473 							  "void main()\n"
   14474 							  "{\n"
   14475 							  "    vs_tcs = in_vs;\n"
   14476 							  "}\n"
   14477 							  "\n";
   14478 	static const GLchar* vs_tested = "#version 430 core\n"
   14479 									 "#extension GL_ARB_enhanced_layouts : require\n"
   14480 									 "\n"
   14481 									 "VAR_DEFINITION"
   14482 									 "\n"
   14483 									 "in  vec4 in_vs;\n"
   14484 									 "out vec4 vs_tcs;\n"
   14485 									 "\n"
   14486 									 "void main()\n"
   14487 									 "{\n"
   14488 									 "    vec4 result = in_vs;\n"
   14489 									 "\n"
   14490 									 "VARIABLE_USE"
   14491 									 "\n"
   14492 									 "    vs_tcs += result;\n"
   14493 									 "}\n"
   14494 									 "\n";
   14495 
   14496 	std::string source;
   14497 	testCase&   test_case = m_test_cases[test_case_index];
   14498 
   14499 	if (test_case.m_stage == stage)
   14500 	{
   14501 		const GLchar*			 array = "";
   14502 		GLchar					 buffer[16];
   14503 		const GLchar*			 direction = "in ";
   14504 		const GLchar*			 flat	  = "";
   14505 		const GLchar*			 index	 = "";
   14506 		GLuint					 last	  = getLastInputLocation(stage, test_case.m_type, 0);
   14507 		size_t					 position  = 0;
   14508 		size_t					 temp;
   14509 		const GLchar*			 type_name = test_case.m_type.GetGLSLTypeName();
   14510 		Utils::Variable::STORAGE storage   = Utils::Variable::VARYING_INPUT;
   14511 		const GLchar*			 var_use   = input_use;
   14512 
   14513 		if (false == test_case.m_is_input)
   14514 		{
   14515 			direction = "out";
   14516 			last	  = getLastOutputLocation(stage, test_case.m_type, 0);
   14517 			storage   = Utils::Variable::VARYING_OUTPUT;
   14518 			var_use   = output_use;
   14519 		}
   14520 
   14521 		if (true == isFlatRequired(stage, test_case.m_type, storage))
   14522 		{
   14523 			flat = "flat";
   14524 		}
   14525 
   14526 		sprintf(buffer, "%d", last);
   14527 
   14528 		switch (stage)
   14529 		{
   14530 		case Utils::Shader::FRAGMENT:
   14531 			source = fs_tested;
   14532 			break;
   14533 		case Utils::Shader::GEOMETRY:
   14534 			source = gs_tested;
   14535 			array  = "[]";
   14536 			index  = "[0]";
   14537 			break;
   14538 		case Utils::Shader::TESS_CTRL:
   14539 			source = tcs_tested;
   14540 			array  = "[]";
   14541 			index  = "[gl_InvocationID]";
   14542 			break;
   14543 		case Utils::Shader::TESS_EVAL:
   14544 			source = tes_tested;
   14545 			array  = "[]";
   14546 			index  = "[0]";
   14547 			break;
   14548 		case Utils::Shader::VERTEX:
   14549 			source = vs_tested;
   14550 			break;
   14551 		default:
   14552 			TCU_FAIL("Invalid enum");
   14553 		}
   14554 
   14555 		temp = position;
   14556 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   14557 		position = temp;
   14558 		Utils::replaceToken("LAST", position, buffer, source);
   14559 		Utils::replaceToken("FLAT", position, flat, source);
   14560 		Utils::replaceToken("DIRECTION", position, direction, source);
   14561 		Utils::replaceToken("ARRAY", position, array, source);
   14562 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   14563 
   14564 		Utils::replaceAllTokens("TYPE", type_name, source);
   14565 		Utils::replaceAllTokens("INDEX", index, source);
   14566 	}
   14567 	else
   14568 	{
   14569 		switch (stage)
   14570 		{
   14571 		case Utils::Shader::FRAGMENT:
   14572 			source = fs;
   14573 			break;
   14574 		case Utils::Shader::GEOMETRY:
   14575 			source = gs;
   14576 			break;
   14577 		case Utils::Shader::TESS_CTRL:
   14578 			source = tcs;
   14579 			break;
   14580 		case Utils::Shader::TESS_EVAL:
   14581 			source = tes;
   14582 			break;
   14583 		case Utils::Shader::VERTEX:
   14584 			source = vs;
   14585 			break;
   14586 		default:
   14587 			TCU_FAIL("Invalid enum");
   14588 		}
   14589 	}
   14590 
   14591 	return source;
   14592 }
   14593 
   14594 /** Get description of test case
   14595  *
   14596  * @param test_case_index Index of test case
   14597  *
   14598  * @return Test case description
   14599  **/
   14600 std::string VaryingLocationLimitTest::getTestCaseName(GLuint test_case_index)
   14601 {
   14602 	std::stringstream stream;
   14603 	testCase&		  test_case = m_test_cases[test_case_index];
   14604 
   14605 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage)
   14606 		   << " type: " << test_case.m_type.GetGLSLTypeName() << ", direction: ";
   14607 
   14608 	if (true == test_case.m_is_input)
   14609 	{
   14610 		stream << "input";
   14611 	}
   14612 	else
   14613 	{
   14614 		stream << "output";
   14615 	}
   14616 
   14617 	return stream.str();
   14618 }
   14619 
   14620 /** Get number of test cases
   14621  *
   14622  * @return Number of test cases
   14623  **/
   14624 GLuint VaryingLocationLimitTest::getTestCaseNumber()
   14625 {
   14626 	return static_cast<GLuint>(m_test_cases.size());
   14627 }
   14628 
   14629 /** Selects if "compute" stage is relevant for test
   14630  *
   14631  * @param ignored
   14632  *
   14633  * @return false
   14634  **/
   14635 bool VaryingLocationLimitTest::isComputeRelevant(GLuint /* test_case_index */)
   14636 {
   14637 	return false;
   14638 }
   14639 
   14640 /** Prepare all test cases
   14641  *
   14642  **/
   14643 void VaryingLocationLimitTest::testInit()
   14644 {
   14645 	const GLuint n_types = getTypesNumber();
   14646 
   14647 	for (GLuint i = 0; i < n_types; ++i)
   14648 	{
   14649 		const Utils::Type& type = getType(i);
   14650 
   14651 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   14652 		{
   14653 			if (Utils::Shader::COMPUTE == stage)
   14654 			{
   14655 				continue;
   14656 			}
   14657 
   14658 			testCase test_case_in  = { true, type, (Utils::Shader::STAGES)stage };
   14659 			testCase test_case_out = { false, type, (Utils::Shader::STAGES)stage };
   14660 
   14661 			m_test_cases.push_back(test_case_in);
   14662 
   14663 			if (Utils::Shader::FRAGMENT != stage)
   14664 			{
   14665 				m_test_cases.push_back(test_case_out);
   14666 			}
   14667 		}
   14668 	}
   14669 }
   14670 
   14671 /** Constructor
   14672  *
   14673  * @param context Test framework context
   14674  **/
   14675 VaryingComponentsTest::VaryingComponentsTest(deqp::Context& context)
   14676 	: VaryingLocationsTest(context, "varying_components",
   14677 						   "Test verifies that input and output components are respected")
   14678 {
   14679 }
   14680 
   14681 /** Constructor
   14682  *
   14683  * @param context          Test framework context
   14684  * @param test_name        Name of test
   14685  * @param test_description Description of test
   14686  **/
   14687 VaryingComponentsTest::VaryingComponentsTest(deqp::Context& context, const glw::GLchar* test_name,
   14688 											 const glw::GLchar* test_description)
   14689 	: VaryingLocationsTest(context, test_name, test_description)
   14690 {
   14691 }
   14692 
   14693 /** Get interface of program
   14694  *
   14695  * @param test_case_index     Test case
   14696  * @param program_interface   Interface of program
   14697  * @param varying_passthrough Collection of connections between in and out variables
   14698  **/
   14699 void VaryingComponentsTest::getProgramInterface(GLuint test_case_index, Utils::ProgramInterface& program_interface,
   14700 												Utils::VaryingPassthrough& varying_passthrough)
   14701 {
   14702 	GLuint				   array_length = getArrayLength();
   14703 	const testCase&		   test_case	= m_test_cases[test_case_index];
   14704 	const Utils::Type	  vector_type  = Utils::Type::GetType(test_case.m_type, 1, 4);
   14705 	Utils::ShaderInterface si			= program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   14706 
   14707 	/* Zero means no array, however we still need at least 1 slot of data */
   14708 	if (0 == array_length)
   14709 	{
   14710 		array_length += 1;
   14711 	}
   14712 
   14713 	/* Generate data */
   14714 	const std::vector<GLubyte>& data	  = vector_type.GenerateDataPacked();
   14715 	const size_t				data_size = data.size();
   14716 
   14717 	/* Prepare data for variables */
   14718 	m_data.resize(array_length * data_size);
   14719 
   14720 	GLubyte*	   dst = &m_data[0];
   14721 	const GLubyte* src = &data[0];
   14722 
   14723 	for (GLuint i = 0; i < array_length; ++i)
   14724 	{
   14725 		memcpy(dst + data_size * i, src, data_size);
   14726 	}
   14727 
   14728 	/* Prepare interface for each stage */
   14729 	prepareShaderStage(Utils::Shader::FRAGMENT, vector_type, program_interface, test_case, varying_passthrough);
   14730 	prepareShaderStage(Utils::Shader::GEOMETRY, vector_type, program_interface, test_case, varying_passthrough);
   14731 	prepareShaderStage(Utils::Shader::TESS_CTRL, vector_type, program_interface, test_case, varying_passthrough);
   14732 	prepareShaderStage(Utils::Shader::TESS_EVAL, vector_type, program_interface, test_case, varying_passthrough);
   14733 	prepareShaderStage(Utils::Shader::VERTEX, vector_type, program_interface, test_case, varying_passthrough);
   14734 }
   14735 
   14736 /** Get type name
   14737  *
   14738  * @param test_case_index Index of test case
   14739  *
   14740  * @return Name of type test in test_case_index
   14741  **/
   14742 std::string VaryingComponentsTest::getTestCaseName(glw::GLuint test_case_index)
   14743 {
   14744 	std::string name;
   14745 
   14746 	const testCase& test_case = m_test_cases[test_case_index];
   14747 
   14748 	name = "Type: ";
   14749 
   14750 	switch (test_case.m_type)
   14751 	{
   14752 	case Utils::Type::Double:
   14753 		name.append(Utils::Type::_double.GetGLSLTypeName());
   14754 		break;
   14755 	case Utils::Type::Float:
   14756 		name.append(Utils::Type::_float.GetGLSLTypeName());
   14757 		break;
   14758 	case Utils::Type::Int:
   14759 		name.append(Utils::Type::_int.GetGLSLTypeName());
   14760 		break;
   14761 	case Utils::Type::Uint:
   14762 		name.append(Utils::Type::uint.GetGLSLTypeName());
   14763 		break;
   14764 	}
   14765 
   14766 	name.append(", layout: ");
   14767 
   14768 	switch (test_case.m_layout)
   14769 	{
   14770 	case GVEC4:
   14771 		name.append("GVEC4");
   14772 		break;
   14773 	case SCALAR_GVEC3:
   14774 		name.append("SCALAR_GVEC3");
   14775 		break;
   14776 	case GVEC3_SCALAR:
   14777 		name.append("GVEC3_SCALAR");
   14778 		break;
   14779 	case GVEC2_GVEC2:
   14780 		name.append("GVEC2_GVEC2");
   14781 		break;
   14782 	case GVEC2_SCALAR_SCALAR:
   14783 		name.append("GVEC2_SCALAR_SCALAR");
   14784 		break;
   14785 	case SCALAR_GVEC2_SCALAR:
   14786 		name.append("SCALAR_GVEC2_SCALAR");
   14787 		break;
   14788 	case SCALAR_SCALAR_GVEC2:
   14789 		name.append("SCALAR_SCALAR_GVEC2");
   14790 		break;
   14791 	case SCALAR_SCALAR_SCALAR_SCALAR:
   14792 		name.append("SCALAR_SCALAR_SCALAR_SCALAR");
   14793 		break;
   14794 	}
   14795 
   14796 	return name;
   14797 }
   14798 
   14799 /** Returns number of types to test
   14800  *
   14801  * @return Number of types, 34
   14802  **/
   14803 glw::GLuint VaryingComponentsTest::getTestCaseNumber()
   14804 {
   14805 	return static_cast<GLuint>(m_test_cases.size());
   14806 }
   14807 
   14808 /* Prepare test cases */
   14809 void VaryingComponentsTest::testInit()
   14810 {
   14811 	m_test_cases.push_back(testCase(GVEC4, Utils::Type::Double));
   14812 	m_test_cases.push_back(testCase(SCALAR_GVEC3, Utils::Type::Double));
   14813 	m_test_cases.push_back(testCase(GVEC3_SCALAR, Utils::Type::Double));
   14814 	m_test_cases.push_back(testCase(GVEC2_GVEC2, Utils::Type::Double));
   14815 	m_test_cases.push_back(testCase(GVEC2_SCALAR_SCALAR, Utils::Type::Double));
   14816 	m_test_cases.push_back(testCase(SCALAR_GVEC2_SCALAR, Utils::Type::Double));
   14817 	m_test_cases.push_back(testCase(SCALAR_SCALAR_GVEC2, Utils::Type::Double));
   14818 	m_test_cases.push_back(testCase(SCALAR_SCALAR_SCALAR_SCALAR, Utils::Type::Double));
   14819 
   14820 	m_test_cases.push_back(testCase(GVEC4, Utils::Type::Float));
   14821 	m_test_cases.push_back(testCase(SCALAR_GVEC3, Utils::Type::Float));
   14822 	m_test_cases.push_back(testCase(GVEC3_SCALAR, Utils::Type::Float));
   14823 	m_test_cases.push_back(testCase(GVEC2_GVEC2, Utils::Type::Float));
   14824 	m_test_cases.push_back(testCase(GVEC2_SCALAR_SCALAR, Utils::Type::Float));
   14825 	m_test_cases.push_back(testCase(SCALAR_GVEC2_SCALAR, Utils::Type::Float));
   14826 	m_test_cases.push_back(testCase(SCALAR_SCALAR_GVEC2, Utils::Type::Float));
   14827 	m_test_cases.push_back(testCase(SCALAR_SCALAR_SCALAR_SCALAR, Utils::Type::Float));
   14828 
   14829 	m_test_cases.push_back(testCase(GVEC4, Utils::Type::Int));
   14830 	m_test_cases.push_back(testCase(SCALAR_GVEC3, Utils::Type::Int));
   14831 	m_test_cases.push_back(testCase(GVEC3_SCALAR, Utils::Type::Int));
   14832 	m_test_cases.push_back(testCase(GVEC2_GVEC2, Utils::Type::Int));
   14833 	m_test_cases.push_back(testCase(GVEC2_SCALAR_SCALAR, Utils::Type::Int));
   14834 	m_test_cases.push_back(testCase(SCALAR_GVEC2_SCALAR, Utils::Type::Int));
   14835 	m_test_cases.push_back(testCase(SCALAR_SCALAR_GVEC2, Utils::Type::Int));
   14836 	m_test_cases.push_back(testCase(SCALAR_SCALAR_SCALAR_SCALAR, Utils::Type::Int));
   14837 
   14838 	m_test_cases.push_back(testCase(GVEC4, Utils::Type::Uint));
   14839 	m_test_cases.push_back(testCase(SCALAR_GVEC3, Utils::Type::Uint));
   14840 	m_test_cases.push_back(testCase(GVEC3_SCALAR, Utils::Type::Uint));
   14841 	m_test_cases.push_back(testCase(GVEC2_GVEC2, Utils::Type::Uint));
   14842 	m_test_cases.push_back(testCase(GVEC2_SCALAR_SCALAR, Utils::Type::Uint));
   14843 	m_test_cases.push_back(testCase(SCALAR_GVEC2_SCALAR, Utils::Type::Uint));
   14844 	m_test_cases.push_back(testCase(SCALAR_SCALAR_GVEC2, Utils::Type::Uint));
   14845 	m_test_cases.push_back(testCase(SCALAR_SCALAR_SCALAR_SCALAR, Utils::Type::Uint));
   14846 }
   14847 
   14848 /** Inform that test use components
   14849  *
   14850  * @param ignored
   14851  *
   14852  * @return true
   14853  **/
   14854 bool VaryingComponentsTest::useComponentQualifier(glw::GLuint /* test_case_index */)
   14855 {
   14856 	return true;
   14857 }
   14858 
   14859 /** Get length of arrays that should be used during test
   14860  *
   14861  * @return 0u - no array at all
   14862  **/
   14863 GLuint VaryingComponentsTest::getArrayLength()
   14864 {
   14865 	return 0;
   14866 }
   14867 
   14868 std::string VaryingComponentsTest::prepareGlobals(GLuint last_in_location, GLuint last_out_location)
   14869 {
   14870 	std::string globals = VaryingLocationsTest::prepareGlobals(last_in_location, last_out_location);
   14871 
   14872 	globals.append("const uint comp_x = 0u;\n"
   14873 				   "const uint comp_y = 1u;\n"
   14874 				   "const uint comp_z = 2u;\n"
   14875 				   "const uint comp_w = 3u;\n");
   14876 
   14877 	return globals;
   14878 }
   14879 
   14880 /**
   14881  *
   14882  **/
   14883 std::string VaryingComponentsTest::prepareName(const glw::GLchar* name, glw::GLint location, glw::GLint component,
   14884 											   Utils::Shader::STAGES stage, Utils::Variable::STORAGE storage)
   14885 {
   14886 	GLchar		  buffer[16];
   14887 	std::string   result   = "PREFIXNAME_lLOCATION_cCOMPONENT";
   14888 	size_t		  position = 0;
   14889 	const GLchar* prefix   = Utils::ProgramInterface::GetStagePrefix(stage, storage);
   14890 
   14891 	Utils::replaceToken("PREFIX", position, prefix, result);
   14892 	Utils::replaceToken("NAME", position, name, result);
   14893 
   14894 	sprintf(buffer, "%d", location);
   14895 	Utils::replaceToken("LOCATION", position, buffer, result);
   14896 
   14897 	sprintf(buffer, "%d", component);
   14898 	Utils::replaceToken("COMPONENT", position, buffer, result);
   14899 
   14900 	return result;
   14901 }
   14902 
   14903 std::string VaryingComponentsTest::prepareQualifiers(const glw::GLchar* location, const glw::GLchar* component,
   14904 													 const glw::GLchar* interpolation)
   14905 {
   14906 	size_t		position   = 0;
   14907 	std::string qualifiers = "layout (location = LOCATION, component = COMPONENT) INTERPOLATION";
   14908 
   14909 	Utils::replaceToken("LOCATION", position, location, qualifiers);
   14910 	Utils::replaceToken("COMPONENT", position, component, qualifiers);
   14911 	Utils::replaceToken("INTERPOLATION", position, interpolation, qualifiers);
   14912 
   14913 	return qualifiers;
   14914 }
   14915 
   14916 /**
   14917  *
   14918  **/
   14919 void VaryingComponentsTest::prepareShaderStage(Utils::Shader::STAGES stage, const Utils::Type& vector_type,
   14920 											   Utils::ProgramInterface& program_interface, const testCase& test_case,
   14921 											   Utils::VaryingPassthrough& varying_passthrough)
   14922 {
   14923 	const GLuint			array_length = getArrayLength();
   14924 	const Utils::Type&		basic_type = Utils::Type::GetType(vector_type.m_basic_type, 1 /* n_cols */, 1 /* n_rows */);
   14925 	descriptor				desc_in[8];
   14926 	descriptor				desc_out[8];
   14927 	const GLuint			first_in_loc  = 0;
   14928 	const GLuint			first_out_loc = 0;
   14929 	const GLchar*			interpolation = "";
   14930 	const GLuint			last_in_loc   = getLastInputLocation(stage, vector_type, array_length);
   14931 	GLuint					last_out_loc  = 0;
   14932 	GLuint					n_desc		  = 0;
   14933 	Utils::ShaderInterface& si			  = program_interface.GetShaderInterface(stage);
   14934 
   14935 	/* Select interpolation */
   14936 	if ((Utils::Shader::FRAGMENT == stage) || (Utils::Shader::GEOMETRY == stage))
   14937 	{
   14938 		interpolation = " flat";
   14939 	}
   14940 
   14941 	if (Utils::Shader::FRAGMENT != stage)
   14942 	{
   14943 		last_out_loc = getLastOutputLocation(stage, vector_type, array_length);
   14944 	}
   14945 
   14946 	switch (test_case.m_layout)
   14947 	{
   14948 	case GVEC4:
   14949 		n_desc = 2;
   14950 		desc_in[0].assign(0, "comp_x", first_in_loc, "first_input_location", 4, "gvec4");
   14951 		desc_in[1].assign(0, "comp_x", last_in_loc, "last_input_location", 4, "gvec4");
   14952 
   14953 		desc_out[0].assign(0, "comp_x", first_out_loc, "first_output_location", 4, "gvec4");
   14954 		desc_out[1].assign(0, "comp_x", last_out_loc, "last_output_location", 4, "gvec4");
   14955 		break;
   14956 	case SCALAR_GVEC3:
   14957 		n_desc = 4;
   14958 		desc_in[0].assign(0, "comp_x", first_in_loc, "first_input_location", 1, "scalar");
   14959 		desc_in[1].assign(0, "comp_x", last_in_loc, "last_input_location", 1, "scalar");
   14960 		desc_in[2].assign(1, "comp_y", first_in_loc, "first_input_location", 3, "gvec3");
   14961 		desc_in[3].assign(1, "comp_y", last_in_loc, "last_input_location", 3, "gvec3");
   14962 
   14963 		desc_out[0].assign(0, "comp_x", first_out_loc, "first_output_location", 1, "scalar");
   14964 		desc_out[1].assign(0, "comp_x", last_out_loc, "last_output_location", 1, "scalar");
   14965 		desc_out[2].assign(1, "comp_y", first_out_loc, "first_output_location", 3, "gvec3");
   14966 		desc_out[3].assign(1, "comp_y", last_out_loc, "last_output_location", 3, "gvec3");
   14967 		break;
   14968 	case GVEC3_SCALAR:
   14969 		n_desc = 4;
   14970 		desc_in[0].assign(0, "comp_x", first_in_loc, "first_input_location", 3, "gvec3");
   14971 		desc_in[1].assign(0, "comp_x", last_in_loc, "last_input_location", 3, "gvec3");
   14972 		desc_in[2].assign(3, "comp_w", first_in_loc, "first_input_location", 1, "scalar");
   14973 		desc_in[3].assign(3, "comp_w", last_in_loc, "last_input_location", 1, "scalar");
   14974 
   14975 		desc_out[0].assign(0, "comp_x", first_out_loc, "first_output_location", 3, "gvec3");
   14976 		desc_out[1].assign(0, "comp_x", last_out_loc, "last_output_location", 3, "gvec3");
   14977 		desc_out[2].assign(3, "comp_w", first_out_loc, "first_output_location", 1, "scalar");
   14978 		desc_out[3].assign(3, "comp_w", last_out_loc, "last_output_location", 1, "scalar");
   14979 		break;
   14980 	case GVEC2_GVEC2:
   14981 		n_desc = 4;
   14982 		desc_in[0].assign(0, "comp_x", first_in_loc, "first_input_location", 2, "gvec2");
   14983 		desc_in[1].assign(0, "comp_x", last_in_loc, "last_input_location", 2, "gvec2");
   14984 		desc_in[2].assign(2, "comp_z", first_in_loc, "first_input_location", 2, "gvec2");
   14985 		desc_in[3].assign(2, "comp_z", last_in_loc, "last_input_location", 2, "gvec2");
   14986 
   14987 		desc_out[0].assign(0, "comp_x", first_out_loc, "first_output_location", 2, "gvec2");
   14988 		desc_out[1].assign(0, "comp_x", last_out_loc, "last_output_location", 2, "gvec2");
   14989 		desc_out[2].assign(2, "comp_z", first_out_loc, "first_output_location", 2, "gvec2");
   14990 		desc_out[3].assign(2, "comp_z", last_out_loc, "last_output_location", 2, "gvec2");
   14991 		break;
   14992 	case GVEC2_SCALAR_SCALAR:
   14993 		n_desc = 6;
   14994 		desc_in[0].assign(0, "comp_x", first_in_loc, "first_input_location", 2, "gvec2");
   14995 		desc_in[1].assign(0, "comp_x", last_in_loc, "last_input_location", 2, "gvec2");
   14996 		desc_in[2].assign(2, "comp_z", first_in_loc, "first_input_location", 1, "scalar");
   14997 		desc_in[3].assign(2, "comp_z", last_in_loc, "last_input_location", 1, "scalar");
   14998 		desc_in[4].assign(3, "comp_w", first_in_loc, "first_input_location", 1, "scalar");
   14999 		desc_in[5].assign(3, "comp_w", last_in_loc, "last_input_location", 1, "scalar");
   15000 
   15001 		desc_out[0].assign(0, "comp_x", first_out_loc, "first_output_location", 2, "gvec2");
   15002 		desc_out[1].assign(0, "comp_x", last_out_loc, "last_output_location", 2, "gvec2");
   15003 		desc_out[2].assign(2, "comp_z", first_out_loc, "first_output_location", 1, "scalar");
   15004 		desc_out[3].assign(2, "comp_z", last_out_loc, "last_output_location", 1, "scalar");
   15005 		desc_out[4].assign(3, "comp_w", first_out_loc, "first_output_location", 1, "scalar");
   15006 		desc_out[5].assign(3, "comp_w", last_out_loc, "last_output_location", 1, "scalar");
   15007 		break;
   15008 	case SCALAR_GVEC2_SCALAR:
   15009 		n_desc = 6;
   15010 		desc_in[0].assign(0, "comp_x", first_in_loc, "first_input_location", 1, "scalar");
   15011 		desc_in[1].assign(0, "comp_x", last_in_loc, "last_input_location", 1, "scalar");
   15012 		desc_in[2].assign(1, "comp_y", first_in_loc, "first_input_location", 2, "gvec2");
   15013 		desc_in[3].assign(1, "comp_y", last_in_loc, "last_input_location", 2, "gvec2");
   15014 		desc_in[4].assign(3, "comp_w", first_in_loc, "first_input_location", 1, "scalar");
   15015 		desc_in[5].assign(3, "comp_w", last_in_loc, "last_input_location", 1, "scalar");
   15016 
   15017 		desc_out[0].assign(0, "comp_x", first_out_loc, "first_output_location", 1, "scalar");
   15018 		desc_out[1].assign(0, "comp_x", last_out_loc, "last_output_location", 1, "scalar");
   15019 		desc_out[2].assign(1, "comp_y", first_out_loc, "first_output_location", 2, "gvec2");
   15020 		desc_out[3].assign(1, "comp_y", last_out_loc, "last_output_location", 2, "gvec2");
   15021 		desc_out[4].assign(3, "comp_w", first_out_loc, "first_output_location", 1, "scalar");
   15022 		desc_out[5].assign(3, "comp_w", last_out_loc, "last_output_location", 1, "scalar");
   15023 		break;
   15024 	case SCALAR_SCALAR_GVEC2:
   15025 		n_desc = 6;
   15026 		desc_in[0].assign(0, "comp_x", first_in_loc, "first_input_location", 1, "scalar");
   15027 		desc_in[1].assign(0, "comp_x", last_in_loc, "last_input_location", 1, "scalar");
   15028 		desc_in[2].assign(1, "comp_y", first_in_loc, "first_input_location", 1, "scalar");
   15029 		desc_in[3].assign(1, "comp_y", last_in_loc, "last_input_location", 1, "scalar");
   15030 		desc_in[4].assign(2, "comp_z", first_in_loc, "first_input_location", 2, "gvec2");
   15031 		desc_in[5].assign(2, "comp_z", last_in_loc, "last_input_location", 2, "gvec2");
   15032 
   15033 		desc_out[0].assign(0, "comp_x", first_out_loc, "first_output_location", 1, "scalar");
   15034 		desc_out[1].assign(0, "comp_x", last_out_loc, "last_output_location", 1, "scalar");
   15035 		desc_out[2].assign(1, "comp_y", first_out_loc, "first_output_location", 1, "scalar");
   15036 		desc_out[3].assign(1, "comp_y", last_out_loc, "last_output_location", 1, "scalar");
   15037 		desc_out[4].assign(2, "comp_z", first_out_loc, "first_output_location", 2, "gvec2");
   15038 		desc_out[5].assign(2, "comp_z", last_out_loc, "last_output_location", 2, "gvec2");
   15039 		break;
   15040 	case SCALAR_SCALAR_SCALAR_SCALAR:
   15041 		n_desc = 8;
   15042 		desc_in[0].assign(0, "comp_x", first_in_loc, "first_input_location", 1, "scalar");
   15043 		desc_in[1].assign(0, "comp_x", last_in_loc, "last_input_location", 1, "scalar");
   15044 		desc_in[2].assign(1, "comp_y", first_in_loc, "first_input_location", 1, "scalar");
   15045 		desc_in[3].assign(1, "comp_y", last_in_loc, "last_input_location", 1, "scalar");
   15046 		desc_in[4].assign(2, "comp_z", first_in_loc, "first_input_location", 1, "scalar");
   15047 		desc_in[5].assign(2, "comp_z", last_in_loc, "last_input_location", 1, "scalar");
   15048 		desc_in[6].assign(3, "comp_w", first_in_loc, "first_input_location", 1, "scalar");
   15049 		desc_in[7].assign(3, "comp_w", last_in_loc, "last_input_location", 1, "scalar");
   15050 
   15051 		desc_out[0].assign(0, "comp_x", first_out_loc, "first_output_location", 1, "scalar");
   15052 		desc_out[1].assign(0, "comp_x", last_out_loc, "last_output_location", 1, "scalar");
   15053 		desc_out[2].assign(1, "comp_y", first_out_loc, "first_output_location", 1, "scalar");
   15054 		desc_out[3].assign(1, "comp_y", last_out_loc, "last_output_location", 1, "scalar");
   15055 		desc_out[4].assign(2, "comp_z", first_out_loc, "first_output_location", 1, "scalar");
   15056 		desc_out[5].assign(2, "comp_z", last_out_loc, "last_output_location", 1, "scalar");
   15057 		desc_out[6].assign(3, "comp_w", first_out_loc, "first_output_location", 1, "scalar");
   15058 		desc_out[7].assign(3, "comp_w", last_out_loc, "last_output_location", 1, "scalar");
   15059 		break;
   15060 	}
   15061 
   15062 	for (GLuint i = 0; i < n_desc; ++i)
   15063 	{
   15064 		const descriptor& in_desc = desc_in[i];
   15065 
   15066 		Utils::Variable* in =
   15067 			prepareVarying(basic_type, in_desc, interpolation, si, stage, Utils::Variable::VARYING_INPUT);
   15068 
   15069 		if (Utils::Shader::FRAGMENT != stage)
   15070 		{
   15071 			const descriptor& out_desc = desc_out[i];
   15072 
   15073 			Utils::Variable* out =
   15074 				prepareVarying(basic_type, out_desc, interpolation, si, stage, Utils::Variable::VARYING_OUTPUT);
   15075 
   15076 			varying_passthrough.Add(stage, in, out);
   15077 		}
   15078 	}
   15079 
   15080 	si.m_globals = prepareGlobals(last_in_loc, last_out_loc);
   15081 }
   15082 
   15083 /**
   15084  *
   15085  **/
   15086 Utils::Variable* VaryingComponentsTest::prepareVarying(const Utils::Type& basic_type, const descriptor& desc,
   15087 													   const GLchar* interpolation, Utils::ShaderInterface& si,
   15088 													   Utils::Shader::STAGES stage, Utils::Variable::STORAGE storage)
   15089 {
   15090 	const GLuint	   array_length   = getArrayLength();
   15091 	const GLuint	   component_size = basic_type.GetSize();
   15092 	const std::string& name			  = prepareName(desc.m_name, desc.m_location, desc.m_component, stage, storage);
   15093 	const GLuint	   offset		  = desc.m_component * component_size;
   15094 	const std::string& qual			  = prepareQualifiers(desc.m_location_str, desc.m_component_str, interpolation);
   15095 	const GLuint	   size			  = desc.m_n_rows * component_size;
   15096 	const Utils::Type& type			  = Utils::Type::GetType(basic_type.m_basic_type, 1 /* n_columns */, desc.m_n_rows);
   15097 	Utils::Variable*   var			  = 0;
   15098 
   15099 	if (Utils::Variable::VARYING_INPUT == storage)
   15100 	{
   15101 		var = si.Input(name.c_str(), qual.c_str() /* qualifiers */, desc.m_component /* expected_componenet */,
   15102 					   desc.m_location /* expected_location */, type, /* built_in_type */
   15103 					   GL_FALSE /* normalized */, array_length /* n_array_elements */, 0u /* stride */,
   15104 					   offset /* offset */, (GLvoid*)&m_data[offset] /* data */, size /* data_size */);
   15105 	}
   15106 	else
   15107 	{
   15108 		var = si.Output(name.c_str(), qual.c_str() /* qualifiers */, desc.m_component /* expected_componenet */,
   15109 						desc.m_location /* expected_location */, type, /* built_in_type */
   15110 						GL_FALSE /* normalized */, array_length /* n_array_elements */, 0u /* stride */,
   15111 						offset /* offset */, (GLvoid*)&m_data[offset] /* data */, size /* data_size */);
   15112 	}
   15113 
   15114 	return var;
   15115 }
   15116 
   15117 void VaryingComponentsTest::descriptor::assign(glw::GLint component, const glw::GLchar* component_str,
   15118 											   glw::GLint location, const glw::GLchar* location_str, glw::GLuint n_rows,
   15119 											   const glw::GLchar* name)
   15120 {
   15121 	m_component		= component;
   15122 	m_component_str = component_str;
   15123 	m_location		= location;
   15124 	m_location_str  = location_str;
   15125 	m_n_rows		= n_rows;
   15126 	m_name			= name;
   15127 }
   15128 
   15129 VaryingComponentsTest::testCase::testCase(COMPONENTS_LAYOUT layout, Utils::Type::TYPES type)
   15130 	: m_layout(layout), m_type(type)
   15131 {
   15132 }
   15133 
   15134 /** Constructor
   15135  *
   15136  * @param context Test framework context
   15137  **/
   15138 VaryingArrayComponentsTest::VaryingArrayComponentsTest(deqp::Context& context)
   15139 	: VaryingComponentsTest(context, "varying_array_components",
   15140 							"Test verifies that input and output components are respected for arrays")
   15141 {
   15142 }
   15143 
   15144 /** Get length of arrays that should be used during test
   15145  *
   15146  * @return 4u
   15147  **/
   15148 GLuint VaryingArrayComponentsTest::getArrayLength()
   15149 {
   15150 	return 4u;
   15151 }
   15152 
   15153 /** Constructor
   15154  *
   15155  * @param context Test framework context
   15156  **/
   15157 VaryingExceedingComponentsTest::VaryingExceedingComponentsTest(deqp::Context& context)
   15158 	: NegativeTestBase(context, "varying_exceeding_components",
   15159 					   "Test verifies that compiler reports error when component qualifier exceed limits")
   15160 {
   15161 }
   15162 
   15163 /** Source for given test case and stage
   15164  *
   15165  * @param test_case_index Index of test case
   15166  * @param stage           Shader stage
   15167  *
   15168  * @return Shader source
   15169  **/
   15170 std::string VaryingExceedingComponentsTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   15171 {
   15172 	static const GLchar* var_definition_arr =
   15173 		"layout (location = 1, component = COMPONENT) flat DIRECTION TYPE gokuARRAY[1];\n";
   15174 	static const GLchar* var_definition_one =
   15175 		"layout (location = 1, component = COMPONENT) flat DIRECTION TYPE gokuARRAY;\n";
   15176 	static const GLchar* input_use_arr = "    if (TYPE(0) == gokuINDEX[0])\n"
   15177 										 "    {\n"
   15178 										 "        result += vec4(1, 0.5, 0.25, 0.125);\n"
   15179 										 "    }\n";
   15180 	static const GLchar* input_use_one = "    if (TYPE(0) == gokuINDEX)\n"
   15181 										 "    {\n"
   15182 										 "        result += vec4(1, 0.5, 0.25, 0.125);\n"
   15183 										 "    }\n";
   15184 	static const GLchar* output_use_arr = "    gokuINDEX[0] = TYPE(0);\n"
   15185 										  "    if (vec4(0) == result)\n"
   15186 										  "    {\n"
   15187 										  "        gokuINDEX[0] = TYPE(1);\n"
   15188 										  "    }\n";
   15189 	static const GLchar* output_use_one = "    gokuINDEX = TYPE(0);\n"
   15190 										  "    if (vec4(0) == result)\n"
   15191 										  "    {\n"
   15192 										  "        gokuINDEX = TYPE(1);\n"
   15193 										  "    }\n";
   15194 	static const GLchar* fs = "#version 430 core\n"
   15195 							  "#extension GL_ARB_enhanced_layouts : require\n"
   15196 							  "\n"
   15197 							  "in  vec4 gs_fs;\n"
   15198 							  "out vec4 fs_out;\n"
   15199 							  "\n"
   15200 							  "void main()\n"
   15201 							  "{\n"
   15202 							  "    fs_out = gs_fs;\n"
   15203 							  "}\n"
   15204 							  "\n";
   15205 	static const GLchar* fs_tested = "#version 430 core\n"
   15206 									 "#extension GL_ARB_enhanced_layouts : require\n"
   15207 									 "\n"
   15208 									 "VAR_DEFINITION"
   15209 									 "\n"
   15210 									 "in  vec4 gs_fs;\n"
   15211 									 "out vec4 fs_out;\n"
   15212 									 "\n"
   15213 									 "void main()\n"
   15214 									 "{\n"
   15215 									 "    vec4 result = gs_fs;\n"
   15216 									 "\n"
   15217 									 "VARIABLE_USE"
   15218 									 "\n"
   15219 									 "    fs_out += result;\n"
   15220 									 "}\n"
   15221 									 "\n";
   15222 	static const GLchar* gs = "#version 430 core\n"
   15223 							  "#extension GL_ARB_enhanced_layouts : require\n"
   15224 							  "\n"
   15225 							  "layout(points)                           in;\n"
   15226 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   15227 							  "\n"
   15228 							  "in  vec4 tes_gs[];\n"
   15229 							  "out vec4 gs_fs;\n"
   15230 							  "\n"
   15231 							  "void main()\n"
   15232 							  "{\n"
   15233 							  "    gs_fs = tes_gs[0];\n"
   15234 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   15235 							  "    EmitVertex();\n"
   15236 							  "    gs_fs = tes_gs[0];\n"
   15237 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   15238 							  "    EmitVertex();\n"
   15239 							  "    gs_fs = tes_gs[0];\n"
   15240 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   15241 							  "    EmitVertex();\n"
   15242 							  "    gs_fs = tes_gs[0];\n"
   15243 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   15244 							  "    EmitVertex();\n"
   15245 							  "}\n"
   15246 							  "\n";
   15247 	static const GLchar* gs_tested = "#version 430 core\n"
   15248 									 "#extension GL_ARB_enhanced_layouts : require\n"
   15249 									 "\n"
   15250 									 "layout(points)                           in;\n"
   15251 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   15252 									 "\n"
   15253 									 "VAR_DEFINITION"
   15254 									 "\n"
   15255 									 "in  vec4 tes_gs[];\n"
   15256 									 "out vec4 gs_fs;\n"
   15257 									 "\n"
   15258 									 "void main()\n"
   15259 									 "{\n"
   15260 									 "    vec4 result = tes_gs[0];\n"
   15261 									 "\n"
   15262 									 "VARIABLE_USE"
   15263 									 "\n"
   15264 									 "    gs_fs = result;\n"
   15265 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   15266 									 "    EmitVertex();\n"
   15267 									 "    gs_fs = result;\n"
   15268 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   15269 									 "    EmitVertex();\n"
   15270 									 "    gs_fs = result;\n"
   15271 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   15272 									 "    EmitVertex();\n"
   15273 									 "    gs_fs = result;\n"
   15274 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   15275 									 "    EmitVertex();\n"
   15276 									 "}\n"
   15277 									 "\n";
   15278 	static const GLchar* tcs = "#version 430 core\n"
   15279 							   "#extension GL_ARB_enhanced_layouts : require\n"
   15280 							   "\n"
   15281 							   "layout(vertices = 1) out;\n"
   15282 							   "\n"
   15283 							   "in  vec4 vs_tcs[];\n"
   15284 							   "out vec4 tcs_tes[];\n"
   15285 							   "\n"
   15286 							   "void main()\n"
   15287 							   "{\n"
   15288 							   "\n"
   15289 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   15290 							   "\n"
   15291 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   15292 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   15293 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   15294 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   15295 							   "    gl_TessLevelInner[0] = 1.0;\n"
   15296 							   "    gl_TessLevelInner[1] = 1.0;\n"
   15297 							   "}\n"
   15298 							   "\n";
   15299 	static const GLchar* tcs_tested = "#version 430 core\n"
   15300 									  "#extension GL_ARB_enhanced_layouts : require\n"
   15301 									  "\n"
   15302 									  "layout(vertices = 1) out;\n"
   15303 									  "\n"
   15304 									  "VAR_DEFINITION"
   15305 									  "\n"
   15306 									  "in  vec4 vs_tcs[];\n"
   15307 									  "out vec4 tcs_tes[];\n"
   15308 									  "\n"
   15309 									  "void main()\n"
   15310 									  "{\n"
   15311 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   15312 									  "\n"
   15313 									  "VARIABLE_USE"
   15314 									  "\n"
   15315 									  "    tcs_tes[gl_InvocationID] = result;\n"
   15316 									  "\n"
   15317 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   15318 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   15319 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   15320 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   15321 									  "    gl_TessLevelInner[0] = 1.0;\n"
   15322 									  "    gl_TessLevelInner[1] = 1.0;\n"
   15323 									  "}\n"
   15324 									  "\n";
   15325 	static const GLchar* tes = "#version 430 core\n"
   15326 							   "#extension GL_ARB_enhanced_layouts : require\n"
   15327 							   "\n"
   15328 							   "layout(isolines, point_mode) in;\n"
   15329 							   "\n"
   15330 							   "in  vec4 tcs_tes[];\n"
   15331 							   "out vec4 tes_gs;\n"
   15332 							   "\n"
   15333 							   "void main()\n"
   15334 							   "{\n"
   15335 							   "    tes_gs = tcs_tes[0];\n"
   15336 							   "}\n"
   15337 							   "\n";
   15338 	static const GLchar* tes_tested = "#version 430 core\n"
   15339 									  "#extension GL_ARB_enhanced_layouts : require\n"
   15340 									  "\n"
   15341 									  "layout(isolines, point_mode) in;\n"
   15342 									  "\n"
   15343 									  "VAR_DEFINITION"
   15344 									  "\n"
   15345 									  "in  vec4 tcs_tes[];\n"
   15346 									  "out vec4 tes_gs;\n"
   15347 									  "\n"
   15348 									  "void main()\n"
   15349 									  "{\n"
   15350 									  "    vec4 result = tcs_tes[0];\n"
   15351 									  "\n"
   15352 									  "VARIABLE_USE"
   15353 									  "\n"
   15354 									  "    tes_gs += result;\n"
   15355 									  "}\n"
   15356 									  "\n";
   15357 	static const GLchar* vs = "#version 430 core\n"
   15358 							  "#extension GL_ARB_enhanced_layouts : require\n"
   15359 							  "\n"
   15360 							  "in  vec4 in_vs;\n"
   15361 							  "out vec4 vs_tcs;\n"
   15362 							  "\n"
   15363 							  "void main()\n"
   15364 							  "{\n"
   15365 							  "    vs_tcs = in_vs;\n"
   15366 							  "}\n"
   15367 							  "\n";
   15368 	static const GLchar* vs_tested = "#version 430 core\n"
   15369 									 "#extension GL_ARB_enhanced_layouts : require\n"
   15370 									 "\n"
   15371 									 "VAR_DEFINITION"
   15372 									 "\n"
   15373 									 "in  vec4 in_vs;\n"
   15374 									 "out vec4 vs_tcs;\n"
   15375 									 "\n"
   15376 									 "void main()\n"
   15377 									 "{\n"
   15378 									 "    vec4 result = in_vs;\n"
   15379 									 "\n"
   15380 									 "VARIABLE_USE"
   15381 									 "\n"
   15382 									 "    vs_tcs += result;\n"
   15383 									 "}\n"
   15384 									 "\n";
   15385 
   15386 	std::string source;
   15387 	testCase&   test_case = m_test_cases[test_case_index];
   15388 
   15389 	if (test_case.m_stage == stage)
   15390 	{
   15391 		const GLchar* array = "";
   15392 		GLchar		  buffer[16];
   15393 		const GLchar* var_definition = 0;
   15394 		const GLchar* direction		 = "in ";
   15395 		const GLchar* index			 = "";
   15396 		size_t		  position		 = 0;
   15397 		size_t		  temp;
   15398 		const GLchar* type_name = test_case.m_type.GetGLSLTypeName();
   15399 		const GLchar* var_use   = 0;
   15400 
   15401 		if (false == test_case.m_is_input)
   15402 		{
   15403 			direction = "out";
   15404 
   15405 			if (false == test_case.m_is_array)
   15406 			{
   15407 				var_definition = var_definition_one;
   15408 				var_use		   = output_use_one;
   15409 			}
   15410 			else
   15411 			{
   15412 				var_definition = var_definition_arr;
   15413 				var_use		   = output_use_arr;
   15414 			}
   15415 		}
   15416 		else
   15417 		{
   15418 			if (false == test_case.m_is_array)
   15419 			{
   15420 				var_definition = var_definition_one;
   15421 				var_use		   = input_use_one;
   15422 			}
   15423 			else
   15424 			{
   15425 				var_definition = var_definition_arr;
   15426 				var_use		   = input_use_arr;
   15427 			}
   15428 		}
   15429 
   15430 		sprintf(buffer, "%d", test_case.m_component);
   15431 
   15432 		switch (stage)
   15433 		{
   15434 		case Utils::Shader::FRAGMENT:
   15435 			source = fs_tested;
   15436 			break;
   15437 		case Utils::Shader::GEOMETRY:
   15438 			source = gs_tested;
   15439 			array  = "[]";
   15440 			index  = "[0]";
   15441 			break;
   15442 		case Utils::Shader::TESS_CTRL:
   15443 			source = tcs_tested;
   15444 			array  = "[]";
   15445 			index  = "[gl_InvocationID]";
   15446 			break;
   15447 		case Utils::Shader::TESS_EVAL:
   15448 			source = tes_tested;
   15449 			array  = "[]";
   15450 			index  = "[0]";
   15451 			break;
   15452 		case Utils::Shader::VERTEX:
   15453 			source = vs_tested;
   15454 			break;
   15455 		default:
   15456 			TCU_FAIL("Invalid enum");
   15457 		}
   15458 
   15459 		temp = position;
   15460 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   15461 		position = temp;
   15462 		Utils::replaceToken("COMPONENT", position, buffer, source);
   15463 		Utils::replaceToken("DIRECTION", position, direction, source);
   15464 		Utils::replaceToken("ARRAY", position, array, source);
   15465 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   15466 
   15467 		Utils::replaceAllTokens("TYPE", type_name, source);
   15468 		Utils::replaceAllTokens("INDEX", index, source);
   15469 	}
   15470 	else
   15471 	{
   15472 		switch (stage)
   15473 		{
   15474 		case Utils::Shader::FRAGMENT:
   15475 			source = fs;
   15476 			break;
   15477 		case Utils::Shader::GEOMETRY:
   15478 			source = gs;
   15479 			break;
   15480 		case Utils::Shader::TESS_CTRL:
   15481 			source = tcs;
   15482 			break;
   15483 		case Utils::Shader::TESS_EVAL:
   15484 			source = tes;
   15485 			break;
   15486 		case Utils::Shader::VERTEX:
   15487 			source = vs;
   15488 			break;
   15489 		default:
   15490 			TCU_FAIL("Invalid enum");
   15491 		}
   15492 	}
   15493 
   15494 	return source;
   15495 }
   15496 
   15497 /** Get description of test case
   15498  *
   15499  * @param test_case_index Index of test case
   15500  *
   15501  * @return Test case description
   15502  **/
   15503 std::string VaryingExceedingComponentsTest::getTestCaseName(GLuint test_case_index)
   15504 {
   15505 	std::stringstream stream;
   15506 	testCase&		  test_case = m_test_cases[test_case_index];
   15507 
   15508 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage)
   15509 		   << " type: " << test_case.m_type.GetGLSLTypeName();
   15510 
   15511 	if (true == test_case.m_is_array)
   15512 	{
   15513 		stream << "[1]";
   15514 	}
   15515 
   15516 	stream << ", direction: ";
   15517 
   15518 	if (true == test_case.m_is_input)
   15519 	{
   15520 		stream << "input";
   15521 	}
   15522 	else
   15523 	{
   15524 		stream << "output";
   15525 	}
   15526 
   15527 	stream << ", component: " << test_case.m_component;
   15528 
   15529 	return stream.str();
   15530 }
   15531 
   15532 /** Get number of test cases
   15533  *
   15534  * @return Number of test cases
   15535  **/
   15536 GLuint VaryingExceedingComponentsTest::getTestCaseNumber()
   15537 {
   15538 	return static_cast<GLuint>(m_test_cases.size());
   15539 }
   15540 
   15541 /** Selects if "compute" stage is relevant for test
   15542  *
   15543  * @param ignored
   15544  *
   15545  * @return false
   15546  **/
   15547 bool VaryingExceedingComponentsTest::isComputeRelevant(GLuint /* test_case_index */)
   15548 {
   15549 	return false;
   15550 }
   15551 
   15552 /** Prepare all test cases
   15553  *
   15554  **/
   15555 void VaryingExceedingComponentsTest::testInit()
   15556 {
   15557 	static const GLuint n_components_per_location = 4;
   15558 	const GLuint		n_types					  = getTypesNumber();
   15559 
   15560 	for (GLuint i = 0; i < n_types; ++i)
   15561 	{
   15562 		const Utils::Type& type				 = getType(i);
   15563 		const GLuint	   n_req_components  = type.m_n_rows;
   15564 		const GLuint	   valid_component   = n_components_per_location - n_req_components;
   15565 		const GLuint	   invalid_component = valid_component + 1;
   15566 
   15567 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   15568 		{
   15569 			if (Utils::Shader::COMPUTE == stage)
   15570 			{
   15571 				continue;
   15572 			}
   15573 
   15574 			/* Component cannot be used for matrices */
   15575 			if (1 != type.m_n_columns)
   15576 			{
   15577 				continue;
   15578 			}
   15579 
   15580 			testCase test_case_in_arr  = { invalid_component, true, true, (Utils::Shader::STAGES)stage, type };
   15581 			testCase test_case_in_one  = { invalid_component, true, false, (Utils::Shader::STAGES)stage, type };
   15582 			testCase test_case_out_arr = { invalid_component, false, true, (Utils::Shader::STAGES)stage, type };
   15583 			testCase test_case_out_one = { invalid_component, false, false, (Utils::Shader::STAGES)stage, type };
   15584 
   15585 			m_test_cases.push_back(test_case_in_arr);
   15586 			m_test_cases.push_back(test_case_in_one);
   15587 
   15588 			if (Utils::Shader::FRAGMENT != stage)
   15589 			{
   15590 				m_test_cases.push_back(test_case_out_arr);
   15591 				m_test_cases.push_back(test_case_out_one);
   15592 			}
   15593 		}
   15594 	}
   15595 }
   15596 
   15597 /** Constructor
   15598  *
   15599  * @param context Test framework context
   15600  **/
   15601 VaryingComponentWithoutLocationTest::VaryingComponentWithoutLocationTest(deqp::Context& context)
   15602 	: NegativeTestBase(context, "varying_component_without_location",
   15603 					   "Test verifies that compiler reports error when component qualifier is used without location")
   15604 {
   15605 }
   15606 
   15607 /** Source for given test case and stage
   15608  *
   15609  * @param test_case_index Index of test case
   15610  * @param stage           Shader stage
   15611  *
   15612  * @return Shader source
   15613  **/
   15614 std::string VaryingComponentWithoutLocationTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   15615 {
   15616 	static const GLchar* var_definition = "layout (component = COMPONENT) FLAT DIRECTION TYPE gokuARRAY;\n";
   15617 	static const GLchar* input_use		= "    if (TYPE(0) == gokuINDEX)\n"
   15618 									 "    {\n"
   15619 									 "        result += vec4(1, 0.5, 0.25, 0.125);\n"
   15620 									 "    }\n";
   15621 	static const GLchar* output_use = "    gokuINDEX = TYPE(0);\n"
   15622 									  "    if (vec4(0) == result)\n"
   15623 									  "    {\n"
   15624 									  "        gokuINDEX = TYPE(1);\n"
   15625 									  "    }\n";
   15626 	static const GLchar* fs = "#version 430 core\n"
   15627 							  "#extension GL_ARB_enhanced_layouts : require\n"
   15628 							  "\n"
   15629 							  "in  vec4 gs_fs;\n"
   15630 							  "out vec4 fs_out;\n"
   15631 							  "\n"
   15632 							  "void main()\n"
   15633 							  "{\n"
   15634 							  "    fs_out = gs_fs;\n"
   15635 							  "}\n"
   15636 							  "\n";
   15637 	static const GLchar* fs_tested = "#version 430 core\n"
   15638 									 "#extension GL_ARB_enhanced_layouts : require\n"
   15639 									 "\n"
   15640 									 "VAR_DEFINITION"
   15641 									 "\n"
   15642 									 "in  vec4 gs_fs;\n"
   15643 									 "out vec4 fs_out;\n"
   15644 									 "\n"
   15645 									 "void main()\n"
   15646 									 "{\n"
   15647 									 "    vec4 result = gs_fs;\n"
   15648 									 "\n"
   15649 									 "VARIABLE_USE"
   15650 									 "\n"
   15651 									 "    fs_out = result;\n"
   15652 									 "}\n"
   15653 									 "\n";
   15654 	static const GLchar* gs = "#version 430 core\n"
   15655 							  "#extension GL_ARB_enhanced_layouts : require\n"
   15656 							  "\n"
   15657 							  "layout(points)                           in;\n"
   15658 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   15659 							  "\n"
   15660 							  "in  vec4 tes_gs[];\n"
   15661 							  "out vec4 gs_fs;\n"
   15662 							  "\n"
   15663 							  "void main()\n"
   15664 							  "{\n"
   15665 							  "    gs_fs = tes_gs[0];\n"
   15666 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   15667 							  "    EmitVertex();\n"
   15668 							  "    gs_fs = tes_gs[0];\n"
   15669 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   15670 							  "    EmitVertex();\n"
   15671 							  "    gs_fs = tes_gs[0];\n"
   15672 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   15673 							  "    EmitVertex();\n"
   15674 							  "    gs_fs = tes_gs[0];\n"
   15675 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   15676 							  "    EmitVertex();\n"
   15677 							  "}\n"
   15678 							  "\n";
   15679 	static const GLchar* gs_tested = "#version 430 core\n"
   15680 									 "#extension GL_ARB_enhanced_layouts : require\n"
   15681 									 "\n"
   15682 									 "layout(points)                           in;\n"
   15683 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   15684 									 "\n"
   15685 									 "VAR_DEFINITION"
   15686 									 "\n"
   15687 									 "in  vec4 tes_gs[];\n"
   15688 									 "out vec4 gs_fs;\n"
   15689 									 "\n"
   15690 									 "void main()\n"
   15691 									 "{\n"
   15692 									 "    vec4 result = tes_gs[0];\n"
   15693 									 "\n"
   15694 									 "VARIABLE_USE"
   15695 									 "\n"
   15696 									 "    gs_fs = result;\n"
   15697 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   15698 									 "    EmitVertex();\n"
   15699 									 "    gs_fs = result;\n"
   15700 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   15701 									 "    EmitVertex();\n"
   15702 									 "    gs_fs = result;\n"
   15703 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   15704 									 "    EmitVertex();\n"
   15705 									 "    gs_fs = result;\n"
   15706 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   15707 									 "    EmitVertex();\n"
   15708 									 "}\n"
   15709 									 "\n";
   15710 	static const GLchar* tcs = "#version 430 core\n"
   15711 							   "#extension GL_ARB_enhanced_layouts : require\n"
   15712 							   "\n"
   15713 							   "layout(vertices = 1) out;\n"
   15714 							   "\n"
   15715 							   "in  vec4 vs_tcs[];\n"
   15716 							   "out vec4 tcs_tes[];\n"
   15717 							   "\n"
   15718 							   "void main()\n"
   15719 							   "{\n"
   15720 							   "\n"
   15721 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   15722 							   "\n"
   15723 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   15724 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   15725 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   15726 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   15727 							   "    gl_TessLevelInner[0] = 1.0;\n"
   15728 							   "    gl_TessLevelInner[1] = 1.0;\n"
   15729 							   "}\n"
   15730 							   "\n";
   15731 	static const GLchar* tcs_tested = "#version 430 core\n"
   15732 									  "#extension GL_ARB_enhanced_layouts : require\n"
   15733 									  "\n"
   15734 									  "layout(vertices = 1) out;\n"
   15735 									  "\n"
   15736 									  "VAR_DEFINITION"
   15737 									  "\n"
   15738 									  "in  vec4 vs_tcs[];\n"
   15739 									  "out vec4 tcs_tes[];\n"
   15740 									  "\n"
   15741 									  "void main()\n"
   15742 									  "{\n"
   15743 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   15744 									  "\n"
   15745 									  "VARIABLE_USE"
   15746 									  "\n"
   15747 									  "    tcs_tes[gl_InvocationID] = result;\n"
   15748 									  "\n"
   15749 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   15750 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   15751 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   15752 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   15753 									  "    gl_TessLevelInner[0] = 1.0;\n"
   15754 									  "    gl_TessLevelInner[1] = 1.0;\n"
   15755 									  "}\n"
   15756 									  "\n";
   15757 	static const GLchar* tes = "#version 430 core\n"
   15758 							   "#extension GL_ARB_enhanced_layouts : require\n"
   15759 							   "\n"
   15760 							   "layout(isolines, point_mode) in;\n"
   15761 							   "\n"
   15762 							   "in  vec4 tcs_tes[];\n"
   15763 							   "out vec4 tes_gs;\n"
   15764 							   "\n"
   15765 							   "void main()\n"
   15766 							   "{\n"
   15767 							   "    tes_gs = tcs_tes[0];\n"
   15768 							   "}\n"
   15769 							   "\n";
   15770 	static const GLchar* tes_tested = "#version 430 core\n"
   15771 									  "#extension GL_ARB_enhanced_layouts : require\n"
   15772 									  "\n"
   15773 									  "layout(isolines, point_mode) in;\n"
   15774 									  "\n"
   15775 									  "VAR_DEFINITION"
   15776 									  "\n"
   15777 									  "in  vec4 tcs_tes[];\n"
   15778 									  "out vec4 tes_gs;\n"
   15779 									  "\n"
   15780 									  "void main()\n"
   15781 									  "{\n"
   15782 									  "    vec4 result = tcs_tes[0];\n"
   15783 									  "\n"
   15784 									  "VARIABLE_USE"
   15785 									  "\n"
   15786 									  "    tes_gs = result;\n"
   15787 									  "}\n"
   15788 									  "\n";
   15789 	static const GLchar* vs = "#version 430 core\n"
   15790 							  "#extension GL_ARB_enhanced_layouts : require\n"
   15791 							  "\n"
   15792 							  "in  vec4 in_vs;\n"
   15793 							  "out vec4 vs_tcs;\n"
   15794 							  "\n"
   15795 							  "void main()\n"
   15796 							  "{\n"
   15797 							  "    vs_tcs = in_vs;\n"
   15798 							  "}\n"
   15799 							  "\n";
   15800 	static const GLchar* vs_tested = "#version 430 core\n"
   15801 									 "#extension GL_ARB_enhanced_layouts : require\n"
   15802 									 "\n"
   15803 									 "VAR_DEFINITION"
   15804 									 "\n"
   15805 									 "in  vec4 in_vs;\n"
   15806 									 "out vec4 vs_tcs;\n"
   15807 									 "\n"
   15808 									 "void main()\n"
   15809 									 "{\n"
   15810 									 "    vec4 result = in_vs;\n"
   15811 									 "\n"
   15812 									 "VARIABLE_USE"
   15813 									 "\n"
   15814 									 "    vs_tcs = result;\n"
   15815 									 "}\n"
   15816 									 "\n";
   15817 
   15818 	std::string source;
   15819 	testCase&   test_case = m_test_cases[test_case_index];
   15820 
   15821 	if (test_case.m_stage == stage)
   15822 	{
   15823 		const GLchar* array = "";
   15824 		GLchar		  buffer[16];
   15825 		const GLchar* direction = "in ";
   15826 		const GLchar* index		= "";
   15827 		size_t		  position  = 0;
   15828 		size_t		  temp;
   15829 		const GLchar* type_name = test_case.m_type.GetGLSLTypeName();
   15830 		const GLchar* var_use   = input_use;
   15831 		const GLchar* flat		= "flat";
   15832 
   15833 		if (false == test_case.m_is_input)
   15834 		{
   15835 			direction = "out";
   15836 			var_use   = output_use;
   15837 		}
   15838 
   15839 		sprintf(buffer, "%d", test_case.m_component);
   15840 
   15841 		switch (stage)
   15842 		{
   15843 		case Utils::Shader::FRAGMENT:
   15844 			source = fs_tested;
   15845 			break;
   15846 		case Utils::Shader::GEOMETRY:
   15847 			source = gs_tested;
   15848 			array  = "[]";
   15849 			index  = "[0]";
   15850 			break;
   15851 		case Utils::Shader::TESS_CTRL:
   15852 			source = tcs_tested;
   15853 			array  = "[]";
   15854 			index  = "[gl_InvocationID]";
   15855 			break;
   15856 		case Utils::Shader::TESS_EVAL:
   15857 			source = tes_tested;
   15858 			array  = "[]";
   15859 			index  = "[0]";
   15860 			break;
   15861 		case Utils::Shader::VERTEX:
   15862 			source = vs_tested;
   15863 			flat   = "";
   15864 			break;
   15865 		default:
   15866 			TCU_FAIL("Invalid enum");
   15867 		}
   15868 
   15869 		temp = position;
   15870 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   15871 		position = temp;
   15872 		Utils::replaceToken("COMPONENT", position, buffer, source);
   15873 		Utils::replaceToken("FLAT", position, flat, source);
   15874 		Utils::replaceToken("DIRECTION", position, direction, source);
   15875 		Utils::replaceToken("ARRAY", position, array, source);
   15876 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   15877 
   15878 		Utils::replaceAllTokens("TYPE", type_name, source);
   15879 		Utils::replaceAllTokens("INDEX", index, source);
   15880 	}
   15881 	else
   15882 	{
   15883 		switch (stage)
   15884 		{
   15885 		case Utils::Shader::FRAGMENT:
   15886 			source = fs;
   15887 			break;
   15888 		case Utils::Shader::GEOMETRY:
   15889 			source = gs;
   15890 			break;
   15891 		case Utils::Shader::TESS_CTRL:
   15892 			source = tcs;
   15893 			break;
   15894 		case Utils::Shader::TESS_EVAL:
   15895 			source = tes;
   15896 			break;
   15897 		case Utils::Shader::VERTEX:
   15898 			source = vs;
   15899 			break;
   15900 		default:
   15901 			TCU_FAIL("Invalid enum");
   15902 		}
   15903 	}
   15904 
   15905 	return source;
   15906 }
   15907 
   15908 /** Get description of test case
   15909  *
   15910  * @param test_case_index Index of test case
   15911  *
   15912  * @return Test case description
   15913  **/
   15914 std::string VaryingComponentWithoutLocationTest::getTestCaseName(GLuint test_case_index)
   15915 {
   15916 	std::stringstream stream;
   15917 	testCase&		  test_case = m_test_cases[test_case_index];
   15918 
   15919 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage)
   15920 		   << " type: " << test_case.m_type.GetGLSLTypeName() << ", direction: ";
   15921 
   15922 	if (true == test_case.m_is_input)
   15923 	{
   15924 		stream << "input";
   15925 	}
   15926 	else
   15927 	{
   15928 		stream << "output";
   15929 	}
   15930 
   15931 	stream << ", component: " << test_case.m_component;
   15932 
   15933 	return stream.str();
   15934 }
   15935 
   15936 /** Get number of test cases
   15937  *
   15938  * @return Number of test cases
   15939  **/
   15940 GLuint VaryingComponentWithoutLocationTest::getTestCaseNumber()
   15941 {
   15942 	return static_cast<GLuint>(m_test_cases.size());
   15943 }
   15944 
   15945 /** Selects if "compute" stage is relevant for test
   15946  *
   15947  * @param ignored
   15948  *
   15949  * @return false
   15950  **/
   15951 bool VaryingComponentWithoutLocationTest::isComputeRelevant(GLuint /* test_case_index */)
   15952 {
   15953 	return false;
   15954 }
   15955 
   15956 /** Prepare all test cases
   15957  *
   15958  **/
   15959 void VaryingComponentWithoutLocationTest::testInit()
   15960 {
   15961 	static const GLuint n_components_per_location = 4;
   15962 	const GLuint		n_types					  = getTypesNumber();
   15963 
   15964 	for (GLuint i = 0; i < n_types; ++i)
   15965 	{
   15966 		const Utils::Type& type				= getType(i);
   15967 		const GLuint	   n_req_components = type.m_n_rows;
   15968 		const GLuint	   valid_component  = n_components_per_location - n_req_components;
   15969 
   15970 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   15971 		{
   15972 			if (Utils::Shader::COMPUTE == stage)
   15973 			{
   15974 				continue;
   15975 			}
   15976 
   15977 			/* Component cannot be used for matrices */
   15978 			if (1 != type.m_n_columns)
   15979 			{
   15980 				continue;
   15981 			}
   15982 
   15983 			testCase test_case_in  = { valid_component, true, (Utils::Shader::STAGES)stage, type };
   15984 			testCase test_case_out = { valid_component, false, (Utils::Shader::STAGES)stage, type };
   15985 
   15986 			m_test_cases.push_back(test_case_in);
   15987 
   15988 			if (Utils::Shader::FRAGMENT != stage)
   15989 			{
   15990 				m_test_cases.push_back(test_case_out);
   15991 			}
   15992 		}
   15993 	}
   15994 }
   15995 
   15996 /** Constructor
   15997  *
   15998  * @param context Test framework context
   15999  **/
   16000 VaryingComponentOfInvalidTypeTest::VaryingComponentOfInvalidTypeTest(deqp::Context& context)
   16001 	: NegativeTestBase(context, "varying_component_of_invalid_type",
   16002 					   "Test verifies that compiler reports error when component qualifier is used for invalid type")
   16003 {
   16004 }
   16005 
   16006 /** Source for given test case and stage
   16007  *
   16008  * @param test_case_index Index of test case
   16009  * @param stage           Shader stage
   16010  *
   16011  * @return Shader source
   16012  **/
   16013 std::string VaryingComponentOfInvalidTypeTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   16014 {
   16015 	static const GLchar* block_definition_arr = "layout (location = 1, component = COMPONENT) flat DIRECTION Goku {\n"
   16016 												"    TYPE member;\n"
   16017 												"} gokuARRAY[1];\n";
   16018 	static const GLchar* block_definition_one = "layout (location = 1, component = COMPONENT) flat DIRECTION Goku {\n"
   16019 												"    TYPE member;\n"
   16020 												"} gokuARRAY;\n";
   16021 	static const GLchar* matrix_definition_arr =
   16022 		"layout (location = 1, component = COMPONENT) flat DIRECTION TYPE gokuARRAY[1];\n";
   16023 	static const GLchar* matrix_definition_one =
   16024 		"layout (location = 1, component = COMPONENT) flat DIRECTION TYPE gokuARRAY;\n";
   16025 	static const GLchar* struct_definition_arr =
   16026 		"struct Goku {\n"
   16027 		"    TYPE member;\n"
   16028 		"};\n"
   16029 		"\n"
   16030 		"layout (location = 1, component = COMPONENT) flat DIRECTION Goku gokuARRAY[1];\n";
   16031 	static const GLchar* struct_definition_one =
   16032 		"struct Goku {\n"
   16033 		"    TYPE member;\n"
   16034 		"};\n"
   16035 		"\n"
   16036 		"layout (location = 1, component = COMPONENT) flat DIRECTION Goku gokuARRAY;\n";
   16037 	static const GLchar* matrix_input_use_arr = "    if (TYPE(0) == gokuINDEX[0])\n"
   16038 												"    {\n"
   16039 												"        result += vec4(1, 0.5, 0.25, 0.125);\n"
   16040 												"    }\n";
   16041 	static const GLchar* matrix_input_use_one = "    if (TYPE(0) == gokuINDEX)\n"
   16042 												"    {\n"
   16043 												"        result += vec4(1, 0.5, 0.25, 0.125);\n"
   16044 												"    }\n";
   16045 	static const GLchar* matrix_output_use_arr = "    gokuINDEX[0] = TYPE(0);\n"
   16046 												 "    if (vec4(0) == result)\n"
   16047 												 "    {\n"
   16048 												 "        gokuINDEX[0] = TYPE(1);\n"
   16049 												 "    }\n";
   16050 	static const GLchar* matrix_output_use_one = "    gokuINDEX = TYPE(0);\n"
   16051 												 "    if (vec4(0) == result)\n"
   16052 												 "    {\n"
   16053 												 "        gokuINDEX = TYPE(1);\n"
   16054 												 "    }\n";
   16055 	static const GLchar* member_input_use_arr = "    if (TYPE(0) == gokuINDEX[0].member)\n"
   16056 												"    {\n"
   16057 												"        result += vec4(1, 0.5, 0.25, 0.125);\n"
   16058 												"    }\n";
   16059 	static const GLchar* member_input_use_one = "    if (TYPE(0) == gokuINDEX.member)\n"
   16060 												"    {\n"
   16061 												"        result += vec4(1, 0.5, 0.25, 0.125);\n"
   16062 												"    }\n";
   16063 	static const GLchar* member_output_use_arr = "    gokuINDEX[0].member = TYPE(0);\n"
   16064 												 "    if (vec4(0) == result)\n"
   16065 												 "    {\n"
   16066 												 "        gokuINDEX[0].member = TYPE(1);\n"
   16067 												 "    }\n";
   16068 	static const GLchar* member_output_use_one = "    gokuINDEX.member = TYPE(0);\n"
   16069 												 "    if (vec4(0) == result)\n"
   16070 												 "    {\n"
   16071 												 "        gokuINDEX.member = TYPE(1);\n"
   16072 												 "    }\n";
   16073 	static const GLchar* fs = "#version 430 core\n"
   16074 							  "#extension GL_ARB_enhanced_layouts : require\n"
   16075 							  "\n"
   16076 							  "in  vec4 gs_fs;\n"
   16077 							  "out vec4 fs_out;\n"
   16078 							  "\n"
   16079 							  "void main()\n"
   16080 							  "{\n"
   16081 							  "    fs_out = gs_fs;\n"
   16082 							  "}\n"
   16083 							  "\n";
   16084 	static const GLchar* fs_tested = "#version 430 core\n"
   16085 									 "#extension GL_ARB_enhanced_layouts : require\n"
   16086 									 "\n"
   16087 									 "VAR_DEFINITION"
   16088 									 "\n"
   16089 									 "in  vec4 gs_fs;\n"
   16090 									 "out vec4 fs_out;\n"
   16091 									 "\n"
   16092 									 "void main()\n"
   16093 									 "{\n"
   16094 									 "    vec4 result = gs_fs;\n"
   16095 									 "\n"
   16096 									 "VARIABLE_USE"
   16097 									 "\n"
   16098 									 "    fs_out += result;\n"
   16099 									 "}\n"
   16100 									 "\n";
   16101 	static const GLchar* gs = "#version 430 core\n"
   16102 							  "#extension GL_ARB_enhanced_layouts : require\n"
   16103 							  "\n"
   16104 							  "layout(points)                           in;\n"
   16105 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   16106 							  "\n"
   16107 							  "in  vec4 tes_gs[];\n"
   16108 							  "out vec4 gs_fs;\n"
   16109 							  "\n"
   16110 							  "void main()\n"
   16111 							  "{\n"
   16112 							  "    gs_fs = tes_gs[0];\n"
   16113 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   16114 							  "    EmitVertex();\n"
   16115 							  "    gs_fs = tes_gs[0];\n"
   16116 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   16117 							  "    EmitVertex();\n"
   16118 							  "    gs_fs = tes_gs[0];\n"
   16119 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   16120 							  "    EmitVertex();\n"
   16121 							  "    gs_fs = tes_gs[0];\n"
   16122 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   16123 							  "    EmitVertex();\n"
   16124 							  "}\n"
   16125 							  "\n";
   16126 	static const GLchar* gs_tested = "#version 430 core\n"
   16127 									 "#extension GL_ARB_enhanced_layouts : require\n"
   16128 									 "\n"
   16129 									 "layout(points)                           in;\n"
   16130 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   16131 									 "\n"
   16132 									 "VAR_DEFINITION"
   16133 									 "\n"
   16134 									 "in  vec4 tes_gs[];\n"
   16135 									 "out vec4 gs_fs;\n"
   16136 									 "\n"
   16137 									 "void main()\n"
   16138 									 "{\n"
   16139 									 "    vec4 result = tes_gs[0];\n"
   16140 									 "\n"
   16141 									 "VARIABLE_USE"
   16142 									 "\n"
   16143 									 "    gs_fs = result;\n"
   16144 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   16145 									 "    EmitVertex();\n"
   16146 									 "    gs_fs = result;\n"
   16147 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   16148 									 "    EmitVertex();\n"
   16149 									 "    gs_fs = result;\n"
   16150 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   16151 									 "    EmitVertex();\n"
   16152 									 "    gs_fs = result;\n"
   16153 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   16154 									 "    EmitVertex();\n"
   16155 									 "}\n"
   16156 									 "\n";
   16157 	static const GLchar* tcs = "#version 430 core\n"
   16158 							   "#extension GL_ARB_enhanced_layouts : require\n"
   16159 							   "\n"
   16160 							   "layout(vertices = 1) out;\n"
   16161 							   "\n"
   16162 							   "in  vec4 vs_tcs[];\n"
   16163 							   "out vec4 tcs_tes[];\n"
   16164 							   "\n"
   16165 							   "void main()\n"
   16166 							   "{\n"
   16167 							   "\n"
   16168 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   16169 							   "\n"
   16170 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   16171 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   16172 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   16173 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   16174 							   "    gl_TessLevelInner[0] = 1.0;\n"
   16175 							   "    gl_TessLevelInner[1] = 1.0;\n"
   16176 							   "}\n"
   16177 							   "\n";
   16178 	static const GLchar* tcs_tested = "#version 430 core\n"
   16179 									  "#extension GL_ARB_enhanced_layouts : require\n"
   16180 									  "\n"
   16181 									  "layout(vertices = 1) out;\n"
   16182 									  "\n"
   16183 									  "VAR_DEFINITION"
   16184 									  "\n"
   16185 									  "in  vec4 vs_tcs[];\n"
   16186 									  "out vec4 tcs_tes[];\n"
   16187 									  "\n"
   16188 									  "void main()\n"
   16189 									  "{\n"
   16190 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   16191 									  "\n"
   16192 									  "VARIABLE_USE"
   16193 									  "\n"
   16194 									  "    tcs_tes[gl_InvocationID] = result;\n"
   16195 									  "\n"
   16196 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   16197 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   16198 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   16199 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   16200 									  "    gl_TessLevelInner[0] = 1.0;\n"
   16201 									  "    gl_TessLevelInner[1] = 1.0;\n"
   16202 									  "}\n"
   16203 									  "\n";
   16204 	static const GLchar* tes = "#version 430 core\n"
   16205 							   "#extension GL_ARB_enhanced_layouts : require\n"
   16206 							   "\n"
   16207 							   "layout(isolines, point_mode) in;\n"
   16208 							   "\n"
   16209 							   "in  vec4 tcs_tes[];\n"
   16210 							   "out vec4 tes_gs;\n"
   16211 							   "\n"
   16212 							   "void main()\n"
   16213 							   "{\n"
   16214 							   "    tes_gs = tcs_tes[0];\n"
   16215 							   "}\n"
   16216 							   "\n";
   16217 	static const GLchar* tes_tested = "#version 430 core\n"
   16218 									  "#extension GL_ARB_enhanced_layouts : require\n"
   16219 									  "\n"
   16220 									  "layout(isolines, point_mode) in;\n"
   16221 									  "\n"
   16222 									  "VAR_DEFINITION"
   16223 									  "\n"
   16224 									  "in  vec4 tcs_tes[];\n"
   16225 									  "out vec4 tes_gs;\n"
   16226 									  "\n"
   16227 									  "void main()\n"
   16228 									  "{\n"
   16229 									  "    vec4 result = tcs_tes[0];\n"
   16230 									  "\n"
   16231 									  "VARIABLE_USE"
   16232 									  "\n"
   16233 									  "    tes_gs += result;\n"
   16234 									  "}\n"
   16235 									  "\n";
   16236 	static const GLchar* vs = "#version 430 core\n"
   16237 							  "#extension GL_ARB_enhanced_layouts : require\n"
   16238 							  "\n"
   16239 							  "in  vec4 in_vs;\n"
   16240 							  "out vec4 vs_tcs;\n"
   16241 							  "\n"
   16242 							  "void main()\n"
   16243 							  "{\n"
   16244 							  "    vs_tcs = in_vs;\n"
   16245 							  "}\n"
   16246 							  "\n";
   16247 	static const GLchar* vs_tested = "#version 430 core\n"
   16248 									 "#extension GL_ARB_enhanced_layouts : require\n"
   16249 									 "\n"
   16250 									 "VAR_DEFINITION"
   16251 									 "\n"
   16252 									 "in  vec4 in_vs;\n"
   16253 									 "out vec4 vs_tcs;\n"
   16254 									 "\n"
   16255 									 "void main()\n"
   16256 									 "{\n"
   16257 									 "    vec4 result = in_vs;\n"
   16258 									 "\n"
   16259 									 "VARIABLE_USE"
   16260 									 "\n"
   16261 									 "    vs_tcs += result;\n"
   16262 									 "}\n"
   16263 									 "\n";
   16264 
   16265 	std::string source;
   16266 	testCase&   test_case = m_test_cases[test_case_index];
   16267 
   16268 	if (test_case.m_stage == stage)
   16269 	{
   16270 		const GLchar* array = "";
   16271 		GLchar		  buffer[16];
   16272 		const GLchar* var_definition = 0;
   16273 		const GLchar* direction		 = "in ";
   16274 		const GLchar* index			 = "";
   16275 		size_t		  position		 = 0;
   16276 		size_t		  temp;
   16277 		const GLchar* type_name = test_case.m_type.GetGLSLTypeName();
   16278 		const GLchar* var_use   = 0;
   16279 
   16280 		if (false == test_case.m_is_input)
   16281 		{
   16282 			direction = "out";
   16283 
   16284 			if (false == test_case.m_is_array)
   16285 			{
   16286 				switch (test_case.m_case)
   16287 				{
   16288 				case BLOCK:
   16289 					var_definition = block_definition_one;
   16290 					var_use		   = member_output_use_one;
   16291 					break;
   16292 				case MATRIX:
   16293 					var_definition = matrix_definition_one;
   16294 					var_use		   = matrix_output_use_one;
   16295 					break;
   16296 				case STRUCT:
   16297 					var_definition = struct_definition_one;
   16298 					var_use		   = member_output_use_one;
   16299 					break;
   16300 				default:
   16301 					TCU_FAIL("Invalid enum");
   16302 				}
   16303 			}
   16304 			else
   16305 			{
   16306 				switch (test_case.m_case)
   16307 				{
   16308 				case BLOCK:
   16309 					var_definition = block_definition_arr;
   16310 					var_use		   = member_output_use_arr;
   16311 					break;
   16312 				case MATRIX:
   16313 					var_definition = matrix_definition_arr;
   16314 					var_use		   = matrix_output_use_arr;
   16315 					break;
   16316 				case STRUCT:
   16317 					var_definition = struct_definition_arr;
   16318 					var_use		   = member_output_use_arr;
   16319 					break;
   16320 				default:
   16321 					TCU_FAIL("Invalid enum");
   16322 				}
   16323 			}
   16324 		}
   16325 		else
   16326 		{
   16327 			if (false == test_case.m_is_array)
   16328 			{
   16329 				switch (test_case.m_case)
   16330 				{
   16331 				case BLOCK:
   16332 					var_definition = block_definition_one;
   16333 					var_use		   = member_input_use_one;
   16334 					break;
   16335 				case MATRIX:
   16336 					var_definition = matrix_definition_one;
   16337 					var_use		   = matrix_input_use_one;
   16338 					break;
   16339 				case STRUCT:
   16340 					var_definition = struct_definition_one;
   16341 					var_use		   = member_input_use_one;
   16342 					break;
   16343 				default:
   16344 					TCU_FAIL("Invalid enum");
   16345 				}
   16346 			}
   16347 			else
   16348 			{
   16349 				switch (test_case.m_case)
   16350 				{
   16351 				case BLOCK:
   16352 					var_definition = block_definition_arr;
   16353 					var_use		   = member_input_use_arr;
   16354 					break;
   16355 				case MATRIX:
   16356 					var_definition = matrix_definition_arr;
   16357 					var_use		   = matrix_input_use_arr;
   16358 					break;
   16359 				case STRUCT:
   16360 					var_definition = struct_definition_arr;
   16361 					var_use		   = member_input_use_arr;
   16362 					break;
   16363 				default:
   16364 					TCU_FAIL("Invalid enum");
   16365 				}
   16366 			}
   16367 		}
   16368 
   16369 		sprintf(buffer, "%d", test_case.m_component);
   16370 
   16371 		switch (stage)
   16372 		{
   16373 		case Utils::Shader::FRAGMENT:
   16374 			source = fs_tested;
   16375 			break;
   16376 		case Utils::Shader::GEOMETRY:
   16377 			source = gs_tested;
   16378 			array  = "[]";
   16379 			index  = "[0]";
   16380 			break;
   16381 		case Utils::Shader::TESS_CTRL:
   16382 			source = tcs_tested;
   16383 			array  = "[]";
   16384 			index  = "[gl_InvocationID]";
   16385 			break;
   16386 		case Utils::Shader::TESS_EVAL:
   16387 			source = tes_tested;
   16388 			array  = "[]";
   16389 			index  = "[0]";
   16390 			break;
   16391 		case Utils::Shader::VERTEX:
   16392 			source = vs_tested;
   16393 			break;
   16394 		default:
   16395 			TCU_FAIL("Invalid enum");
   16396 		}
   16397 
   16398 		temp = position;
   16399 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   16400 		position = temp;
   16401 		Utils::replaceToken("COMPONENT", position, buffer, source);
   16402 		Utils::replaceToken("DIRECTION", position, direction, source);
   16403 		Utils::replaceToken("ARRAY", position, array, source);
   16404 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   16405 
   16406 		Utils::replaceAllTokens("TYPE", type_name, source);
   16407 		Utils::replaceAllTokens("INDEX", index, source);
   16408 	}
   16409 	else
   16410 	{
   16411 		switch (stage)
   16412 		{
   16413 		case Utils::Shader::FRAGMENT:
   16414 			source = fs;
   16415 			break;
   16416 		case Utils::Shader::GEOMETRY:
   16417 			source = gs;
   16418 			break;
   16419 		case Utils::Shader::TESS_CTRL:
   16420 			source = tcs;
   16421 			break;
   16422 		case Utils::Shader::TESS_EVAL:
   16423 			source = tes;
   16424 			break;
   16425 		case Utils::Shader::VERTEX:
   16426 			source = vs;
   16427 			break;
   16428 		default:
   16429 			TCU_FAIL("Invalid enum");
   16430 		}
   16431 	}
   16432 
   16433 	return source;
   16434 }
   16435 
   16436 /** Get description of test case
   16437  *
   16438  * @param test_case_index Index of test case
   16439  *
   16440  * @return Test case description
   16441  **/
   16442 std::string VaryingComponentOfInvalidTypeTest::getTestCaseName(GLuint test_case_index)
   16443 {
   16444 	std::stringstream stream;
   16445 	testCase&		  test_case = m_test_cases[test_case_index];
   16446 
   16447 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage)
   16448 		   << " type: " << test_case.m_type.GetGLSLTypeName();
   16449 
   16450 	if (true == test_case.m_is_array)
   16451 	{
   16452 		stream << "[1]";
   16453 	}
   16454 
   16455 	stream << ", direction: ";
   16456 
   16457 	if (true == test_case.m_is_input)
   16458 	{
   16459 		stream << "input";
   16460 	}
   16461 	else
   16462 	{
   16463 		stream << "output";
   16464 	}
   16465 
   16466 	stream << ", component: " << test_case.m_component;
   16467 
   16468 	return stream.str();
   16469 }
   16470 
   16471 /** Get number of test cases
   16472  *
   16473  * @return Number of test cases
   16474  **/
   16475 GLuint VaryingComponentOfInvalidTypeTest::getTestCaseNumber()
   16476 {
   16477 	return static_cast<GLuint>(m_test_cases.size());
   16478 }
   16479 
   16480 /** Selects if "compute" stage is relevant for test
   16481  *
   16482  * @param ignored
   16483  *
   16484  * @return false
   16485  **/
   16486 bool VaryingComponentOfInvalidTypeTest::isComputeRelevant(GLuint /* test_case_index */)
   16487 {
   16488 	return false;
   16489 }
   16490 
   16491 /** Prepare all test cases
   16492  *
   16493  **/
   16494 void VaryingComponentOfInvalidTypeTest::testInit()
   16495 {
   16496 	static const GLuint n_components_per_location = 4;
   16497 	const GLuint		n_types					  = getTypesNumber();
   16498 
   16499 	for (GLuint i = 0; i < n_types; ++i)
   16500 	{
   16501 		const Utils::Type& type				= getType(i);
   16502 		const GLuint	   n_req_components = type.m_n_rows;
   16503 		const GLuint	   valid_component  = n_components_per_location - n_req_components;
   16504 
   16505 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   16506 		{
   16507 			if (Utils::Shader::COMPUTE == stage)
   16508 			{
   16509 				continue;
   16510 			}
   16511 
   16512 			/* Use different CASE for matrices */
   16513 			if (1 != type.m_n_columns)
   16514 			{
   16515 				testCase test_case_in_arr = { MATRIX, valid_component, true, true, (Utils::Shader::STAGES)stage, type };
   16516 				testCase test_case_in_one = {
   16517 					MATRIX, valid_component, false, true, (Utils::Shader::STAGES)stage, type
   16518 				};
   16519 				testCase test_case_out_arr = {
   16520 					MATRIX, valid_component, true, false, (Utils::Shader::STAGES)stage, type
   16521 				};
   16522 				testCase test_case_out_one = {
   16523 					MATRIX, valid_component, false, false, (Utils::Shader::STAGES)stage, type
   16524 				};
   16525 
   16526 				m_test_cases.push_back(test_case_in_arr);
   16527 				m_test_cases.push_back(test_case_in_one);
   16528 
   16529 				if (Utils::Shader::FRAGMENT != stage)
   16530 				{
   16531 					m_test_cases.push_back(test_case_out_arr);
   16532 					m_test_cases.push_back(test_case_out_one);
   16533 				}
   16534 			}
   16535 			else
   16536 			{
   16537 				for (GLuint c = BLOCK; c < MAX_CASES; ++c)
   16538 				{
   16539 					testCase test_case_in_arr = { (CASES)c, valid_component, true, true, (Utils::Shader::STAGES)stage,
   16540 												  type };
   16541 					testCase test_case_in_one = { (CASES)c, valid_component, false, true, (Utils::Shader::STAGES)stage,
   16542 												  type };
   16543 					testCase test_case_out_arr = { (CASES)c, valid_component, true, false, (Utils::Shader::STAGES)stage,
   16544 												   type };
   16545 					testCase test_case_out_one = {
   16546 						(CASES)c, valid_component, false, false, (Utils::Shader::STAGES)stage, type
   16547 					};
   16548 
   16549 					if (Utils::Shader::VERTEX != stage)
   16550 					{
   16551 						m_test_cases.push_back(test_case_in_arr);
   16552 						m_test_cases.push_back(test_case_in_one);
   16553 					}
   16554 
   16555 					if (Utils::Shader::FRAGMENT != stage)
   16556 					{
   16557 						m_test_cases.push_back(test_case_out_arr);
   16558 						m_test_cases.push_back(test_case_out_one);
   16559 					}
   16560 				}
   16561 			}
   16562 		}
   16563 	}
   16564 }
   16565 
   16566 /** Constructor
   16567  *
   16568  * @param context Test framework context
   16569  **/
   16570 InputComponentAliasingTest::InputComponentAliasingTest(deqp::Context& context)
   16571 	: NegativeTestBase(context, "input_component_aliasing",
   16572 					   "Test verifies that compiler reports component aliasing as error")
   16573 {
   16574 }
   16575 
   16576 /** Source for given test case and stage
   16577  *
   16578  * @param test_case_index Index of test case
   16579  * @param stage           Shader stage
   16580  *
   16581  * @return Shader source
   16582  **/
   16583 std::string InputComponentAliasingTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   16584 {
   16585 	static const GLchar* var_definition = "layout (location = 1, component = COMPONENT) FLAT in TYPE gohanARRAY;\n"
   16586 										  "layout (location = 1, component = COMPONENT) FLAT in TYPE gotenARRAY;\n";
   16587 	static const GLchar* test_one = "    if (TYPE(0) == gohanINDEX)\n"
   16588 									"    {\n"
   16589 									"        result += vec4(1, 0.5, 0.25, 0.125);\n"
   16590 									"    }\n";
   16591 	static const GLchar* fs = "#version 430 core\n"
   16592 							  "#extension GL_ARB_enhanced_layouts : require\n"
   16593 							  "\n"
   16594 							  "in  vec4 gs_fs;\n"
   16595 							  "out vec4 fs_out;\n"
   16596 							  "\n"
   16597 							  "void main()\n"
   16598 							  "{\n"
   16599 							  "    fs_out = gs_fs;\n"
   16600 							  "}\n"
   16601 							  "\n";
   16602 	static const GLchar* fs_tested = "#version 430 core\n"
   16603 									 "#extension GL_ARB_enhanced_layouts : require\n"
   16604 									 "\n"
   16605 									 "VAR_DEFINITION"
   16606 									 "\n"
   16607 									 "in  vec4 gs_fs;\n"
   16608 									 "out vec4 fs_out;\n"
   16609 									 "\n"
   16610 									 "void main()\n"
   16611 									 "{\n"
   16612 									 "    vec4 result = gs_fs;\n"
   16613 									 "\n"
   16614 									 "VARIABLE_USE"
   16615 									 "\n"
   16616 									 "    fs_out += result;\n"
   16617 									 "}\n"
   16618 									 "\n";
   16619 	static const GLchar* gs = "#version 430 core\n"
   16620 							  "#extension GL_ARB_enhanced_layouts : require\n"
   16621 							  "\n"
   16622 							  "layout(points)                           in;\n"
   16623 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   16624 							  "\n"
   16625 							  "in  vec4 tes_gs[];\n"
   16626 							  "out vec4 gs_fs;\n"
   16627 							  "\n"
   16628 							  "void main()\n"
   16629 							  "{\n"
   16630 							  "    gs_fs = tes_gs[0];\n"
   16631 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   16632 							  "    EmitVertex();\n"
   16633 							  "    gs_fs = tes_gs[0];\n"
   16634 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   16635 							  "    EmitVertex();\n"
   16636 							  "    gs_fs = tes_gs[0];\n"
   16637 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   16638 							  "    EmitVertex();\n"
   16639 							  "    gs_fs = tes_gs[0];\n"
   16640 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   16641 							  "    EmitVertex();\n"
   16642 							  "}\n"
   16643 							  "\n";
   16644 	static const GLchar* gs_tested = "#version 430 core\n"
   16645 									 "#extension GL_ARB_enhanced_layouts : require\n"
   16646 									 "\n"
   16647 									 "layout(points)                           in;\n"
   16648 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   16649 									 "\n"
   16650 									 "VAR_DEFINITION"
   16651 									 "\n"
   16652 									 "in  vec4 tes_gs[];\n"
   16653 									 "out vec4 gs_fs;\n"
   16654 									 "\n"
   16655 									 "void main()\n"
   16656 									 "{\n"
   16657 									 "    vec4 result = tes_gs[0];\n"
   16658 									 "\n"
   16659 									 "VARIABLE_USE"
   16660 									 "\n"
   16661 									 "    gs_fs = result;\n"
   16662 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   16663 									 "    EmitVertex();\n"
   16664 									 "    gs_fs = result;\n"
   16665 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   16666 									 "    EmitVertex();\n"
   16667 									 "    gs_fs = result;\n"
   16668 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   16669 									 "    EmitVertex();\n"
   16670 									 "    gs_fs = result;\n"
   16671 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   16672 									 "    EmitVertex();\n"
   16673 									 "}\n"
   16674 									 "\n";
   16675 	static const GLchar* tcs = "#version 430 core\n"
   16676 							   "#extension GL_ARB_enhanced_layouts : require\n"
   16677 							   "\n"
   16678 							   "layout(vertices = 1) out;\n"
   16679 							   "\n"
   16680 							   "in  vec4 vs_tcs[];\n"
   16681 							   "out vec4 tcs_tes[];\n"
   16682 							   "\n"
   16683 							   "void main()\n"
   16684 							   "{\n"
   16685 							   "\n"
   16686 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   16687 							   "\n"
   16688 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   16689 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   16690 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   16691 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   16692 							   "    gl_TessLevelInner[0] = 1.0;\n"
   16693 							   "    gl_TessLevelInner[1] = 1.0;\n"
   16694 							   "}\n"
   16695 							   "\n";
   16696 	static const GLchar* tcs_tested = "#version 430 core\n"
   16697 									  "#extension GL_ARB_enhanced_layouts : require\n"
   16698 									  "\n"
   16699 									  "layout(vertices = 1) out;\n"
   16700 									  "\n"
   16701 									  "VAR_DEFINITION"
   16702 									  "\n"
   16703 									  "in  vec4 vs_tcs[];\n"
   16704 									  "out vec4 tcs_tes[];\n"
   16705 									  "\n"
   16706 									  "void main()\n"
   16707 									  "{\n"
   16708 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   16709 									  "\n"
   16710 									  "VARIABLE_USE"
   16711 									  "\n"
   16712 									  "    tcs_tes[gl_InvocationID] = result;\n"
   16713 									  "\n"
   16714 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   16715 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   16716 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   16717 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   16718 									  "    gl_TessLevelInner[0] = 1.0;\n"
   16719 									  "    gl_TessLevelInner[1] = 1.0;\n"
   16720 									  "}\n"
   16721 									  "\n";
   16722 	static const GLchar* tes = "#version 430 core\n"
   16723 							   "#extension GL_ARB_enhanced_layouts : require\n"
   16724 							   "\n"
   16725 							   "layout(isolines, point_mode) in;\n"
   16726 							   "\n"
   16727 							   "in  vec4 tcs_tes[];\n"
   16728 							   "out vec4 tes_gs;\n"
   16729 							   "\n"
   16730 							   "void main()\n"
   16731 							   "{\n"
   16732 							   "    tes_gs = tcs_tes[0];\n"
   16733 							   "}\n"
   16734 							   "\n";
   16735 	static const GLchar* tes_tested = "#version 430 core\n"
   16736 									  "#extension GL_ARB_enhanced_layouts : require\n"
   16737 									  "\n"
   16738 									  "layout(isolines, point_mode) in;\n"
   16739 									  "\n"
   16740 									  "VAR_DEFINITION"
   16741 									  "\n"
   16742 									  "in  vec4 tcs_tes[];\n"
   16743 									  "out vec4 tes_gs;\n"
   16744 									  "\n"
   16745 									  "void main()\n"
   16746 									  "{\n"
   16747 									  "    vec4 result = tcs_tes[0];\n"
   16748 									  "\n"
   16749 									  "VARIABLE_USE"
   16750 									  "\n"
   16751 									  "    tes_gs += result;\n"
   16752 									  "}\n"
   16753 									  "\n";
   16754 	static const GLchar* vs = "#version 430 core\n"
   16755 							  "#extension GL_ARB_enhanced_layouts : require\n"
   16756 							  "\n"
   16757 							  "in  vec4 in_vs;\n"
   16758 							  "out vec4 vs_tcs;\n"
   16759 							  "\n"
   16760 							  "void main()\n"
   16761 							  "{\n"
   16762 							  "    vs_tcs = in_vs;\n"
   16763 							  "}\n"
   16764 							  "\n";
   16765 	static const GLchar* vs_tested = "#version 430 core\n"
   16766 									 "#extension GL_ARB_enhanced_layouts : require\n"
   16767 									 "\n"
   16768 									 "VAR_DEFINITION"
   16769 									 "\n"
   16770 									 "in  vec4 in_vs;\n"
   16771 									 "out vec4 vs_tcs;\n"
   16772 									 "\n"
   16773 									 "void main()\n"
   16774 									 "{\n"
   16775 									 "    vec4 result = in_vs;\n"
   16776 									 "\n"
   16777 									 "VARIABLE_USE"
   16778 									 "\n"
   16779 									 "    vs_tcs += result;\n"
   16780 									 "}\n"
   16781 									 "\n";
   16782 
   16783 	std::string source;
   16784 	testCase&   test_case = m_test_cases[test_case_index];
   16785 
   16786 	if (test_case.m_stage == stage)
   16787 	{
   16788 		const GLchar* array = "";
   16789 		GLchar		  buffer_gohan[16];
   16790 		GLchar		  buffer_goten[16];
   16791 		const GLchar* flat		  = "";
   16792 		const GLchar* index		  = "";
   16793 		const bool	is_flat_req = isFlatRequired(stage, test_case.m_type, Utils::Variable::VARYING_INPUT);
   16794 		size_t		  position	= 0;
   16795 		size_t		  temp;
   16796 		const GLchar* type_name = test_case.m_type.GetGLSLTypeName();
   16797 		const GLchar* var_use   = test_one;
   16798 
   16799 		if (true == is_flat_req)
   16800 		{
   16801 			flat = "flat";
   16802 		}
   16803 
   16804 		sprintf(buffer_gohan, "%d", test_case.m_component_gohan);
   16805 		sprintf(buffer_goten, "%d", test_case.m_component_goten);
   16806 
   16807 		switch (stage)
   16808 		{
   16809 		case Utils::Shader::FRAGMENT:
   16810 			source = fs_tested;
   16811 			break;
   16812 		case Utils::Shader::GEOMETRY:
   16813 			source = gs_tested;
   16814 			array  = "[]";
   16815 			index  = "[0]";
   16816 			break;
   16817 		case Utils::Shader::TESS_CTRL:
   16818 			source = tcs_tested;
   16819 			array  = "[]";
   16820 			index  = "[gl_InvocationID]";
   16821 			break;
   16822 		case Utils::Shader::TESS_EVAL:
   16823 			source = tes_tested;
   16824 			array  = "[]";
   16825 			index  = "[0]";
   16826 			break;
   16827 		case Utils::Shader::VERTEX:
   16828 			source = vs_tested;
   16829 			break;
   16830 		default:
   16831 			TCU_FAIL("Invalid enum");
   16832 		}
   16833 
   16834 		temp = position;
   16835 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   16836 		position = temp;
   16837 		Utils::replaceToken("COMPONENT", position, buffer_gohan, source);
   16838 		Utils::replaceToken("ARRAY", position, array, source);
   16839 		Utils::replaceToken("COMPONENT", position, buffer_goten, source);
   16840 		Utils::replaceToken("ARRAY", position, array, source);
   16841 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   16842 
   16843 		Utils::replaceAllTokens("FLAT", flat, source);
   16844 		Utils::replaceAllTokens("TYPE", type_name, source);
   16845 		Utils::replaceAllTokens("INDEX", index, source);
   16846 	}
   16847 	else
   16848 	{
   16849 		switch (stage)
   16850 		{
   16851 		case Utils::Shader::FRAGMENT:
   16852 			source = fs;
   16853 			break;
   16854 		case Utils::Shader::GEOMETRY:
   16855 			source = gs;
   16856 			break;
   16857 		case Utils::Shader::TESS_CTRL:
   16858 			source = tcs;
   16859 			break;
   16860 		case Utils::Shader::TESS_EVAL:
   16861 			source = tes;
   16862 			break;
   16863 		case Utils::Shader::VERTEX:
   16864 			source = vs;
   16865 			break;
   16866 		default:
   16867 			TCU_FAIL("Invalid enum");
   16868 		}
   16869 	}
   16870 
   16871 	return source;
   16872 }
   16873 
   16874 /** Get description of test case
   16875  *
   16876  * @param test_case_index Index of test case
   16877  *
   16878  * @return Test case description
   16879  **/
   16880 std::string InputComponentAliasingTest::getTestCaseName(GLuint test_case_index)
   16881 {
   16882 	std::stringstream stream;
   16883 	testCase&		  test_case = m_test_cases[test_case_index];
   16884 
   16885 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage)
   16886 		   << " type: " << test_case.m_type.GetGLSLTypeName() << ", components: " << test_case.m_component_gohan
   16887 		   << " & " << test_case.m_component_goten;
   16888 
   16889 	return stream.str();
   16890 }
   16891 
   16892 /** Get number of test cases
   16893  *
   16894  * @return Number of test cases
   16895  **/
   16896 GLuint InputComponentAliasingTest::getTestCaseNumber()
   16897 {
   16898 	return static_cast<GLuint>(m_test_cases.size());
   16899 }
   16900 
   16901 /** Selects if "compute" stage is relevant for test
   16902  *
   16903  * @param ignored
   16904  *
   16905  * @return false
   16906  **/
   16907 bool InputComponentAliasingTest::isComputeRelevant(GLuint /* test_case_index */)
   16908 {
   16909 	return false;
   16910 }
   16911 
   16912 /** Selects if compilation failure is expected result
   16913  *
   16914  * @param test_case_index Index of test case
   16915  *
   16916  * @return false for VS that use only single variable, true otherwise
   16917  **/
   16918 bool InputComponentAliasingTest::isFailureExpected(GLuint test_case_index)
   16919 {
   16920 	testCase& test_case = m_test_cases[test_case_index];
   16921 
   16922 	return (Utils::Shader::VERTEX != test_case.m_stage);
   16923 }
   16924 
   16925 /** Prepare all test cases
   16926  *
   16927  **/
   16928 void InputComponentAliasingTest::testInit()
   16929 {
   16930 	const GLuint		n_types					  = getTypesNumber();
   16931 
   16932 	for (GLuint i = 0; i < n_types; ++i)
   16933 	{
   16934 		const Utils::Type& type						 = getType(i);
   16935 		const bool		   use_double				 = (Utils::Type::Double == type.m_basic_type);
   16936 		const GLuint	   n_components_per_location = use_double ? 2 : 4;
   16937 		const GLuint	   n_req_components			 = type.m_n_rows;
   16938 		const GLint		   valid_component			 = (GLint)n_components_per_location - (GLint)n_req_components;
   16939 		const GLuint	   component_size			 = use_double ? 2 : 1;
   16940 		/* Skip matrices */
   16941 		if (1 != type.m_n_columns)
   16942 		{
   16943 			continue;
   16944 		}
   16945 		/* Skip dvec3/dvec4 which doesn't support the component qualifier */
   16946 		if (valid_component < 0)
   16947 		{
   16948 			continue;
   16949 		}
   16950 
   16951 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   16952 		{
   16953 			if (Utils::Shader::COMPUTE == stage)
   16954 			{
   16955 				continue;
   16956 			}
   16957 
   16958 			for (GLuint gohan = 0; gohan <= (GLuint)valid_component; ++gohan)
   16959 			{
   16960 				const GLint first_aliasing = gohan - n_req_components + 1;
   16961 				const GLint last_aliasing  = gohan + n_req_components - 1;
   16962 
   16963 				const GLuint goten_start = std::max(0, first_aliasing);
   16964 				const GLuint goten_stop  = std::min(valid_component, last_aliasing);
   16965 
   16966 				for (GLuint goten = goten_start; goten <= goten_stop; ++goten)
   16967 				{
   16968 					testCase test_case = { gohan * component_size, goten * component_size, (Utils::Shader::STAGES)stage,
   16969 										   type };
   16970 
   16971 					m_test_cases.push_back(test_case);
   16972 				}
   16973 			}
   16974 		}
   16975 	}
   16976 }
   16977 
   16978 /** Constructor
   16979  *
   16980  * @param context Test framework context
   16981  **/
   16982 OutputComponentAliasingTest::OutputComponentAliasingTest(deqp::Context& context)
   16983 	: NegativeTestBase(context, "output_component_aliasing",
   16984 					   "Test verifies that compiler reports component aliasing as error")
   16985 {
   16986 }
   16987 
   16988 /** Source for given test case and stage
   16989  *
   16990  * @param test_case_index Index of test case
   16991  * @param stage           Shader stage
   16992  *
   16993  * @return Shader source
   16994  **/
   16995 std::string OutputComponentAliasingTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   16996 {
   16997 	static const GLchar* var_definition = "layout (location = 1, component = COMPONENT) flat out TYPE gohanARRAY;\n"
   16998 										  "layout (location = 1, component = COMPONENT) flat out TYPE gotenARRAY;\n";
   16999 	static const GLchar* l_test = "    gohanINDEX = TYPE(1);\n"
   17000 								  "    gotenINDEX = TYPE(0);\n";
   17001 	static const GLchar* fs = "#version 430 core\n"
   17002 							  "#extension GL_ARB_enhanced_layouts : require\n"
   17003 							  "\n"
   17004 							  "in  vec4 gs_fs;\n"
   17005 							  "out vec4 fs_out;\n"
   17006 							  "\n"
   17007 							  "void main()\n"
   17008 							  "{\n"
   17009 							  "    fs_out = gs_fs;\n"
   17010 							  "}\n"
   17011 							  "\n";
   17012 	static const GLchar* fs_tested = "#version 430 core\n"
   17013 									 "#extension GL_ARB_enhanced_layouts : require\n"
   17014 									 "\n"
   17015 									 "VAR_DEFINITION"
   17016 									 "\n"
   17017 									 "in  vec4 gs_fs;\n"
   17018 									 "out vec4 fs_out;\n"
   17019 									 "\n"
   17020 									 "void main()\n"
   17021 									 "{\n"
   17022 									 "    vec4 result = gs_fs;\n"
   17023 									 "\n"
   17024 									 "VARIABLE_USE"
   17025 									 "\n"
   17026 									 "    fs_out += result;\n"
   17027 									 "}\n"
   17028 									 "\n";
   17029 	static const GLchar* gs = "#version 430 core\n"
   17030 							  "#extension GL_ARB_enhanced_layouts : require\n"
   17031 							  "\n"
   17032 							  "layout(points)                           in;\n"
   17033 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   17034 							  "\n"
   17035 							  "in  vec4 tes_gs[];\n"
   17036 							  "out vec4 gs_fs;\n"
   17037 							  "\n"
   17038 							  "void main()\n"
   17039 							  "{\n"
   17040 							  "    gs_fs = tes_gs[0];\n"
   17041 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   17042 							  "    EmitVertex();\n"
   17043 							  "    gs_fs = tes_gs[0];\n"
   17044 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   17045 							  "    EmitVertex();\n"
   17046 							  "    gs_fs = tes_gs[0];\n"
   17047 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   17048 							  "    EmitVertex();\n"
   17049 							  "    gs_fs = tes_gs[0];\n"
   17050 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   17051 							  "    EmitVertex();\n"
   17052 							  "}\n"
   17053 							  "\n";
   17054 	static const GLchar* gs_tested = "#version 430 core\n"
   17055 									 "#extension GL_ARB_enhanced_layouts : require\n"
   17056 									 "\n"
   17057 									 "layout(points)                           in;\n"
   17058 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   17059 									 "\n"
   17060 									 "VAR_DEFINITION"
   17061 									 "\n"
   17062 									 "in  vec4 tes_gs[];\n"
   17063 									 "out vec4 gs_fs;\n"
   17064 									 "\n"
   17065 									 "void main()\n"
   17066 									 "{\n"
   17067 									 "    vec4 result = tes_gs[0];\n"
   17068 									 "\n"
   17069 									 "VARIABLE_USE"
   17070 									 "\n"
   17071 									 "    gs_fs = result;\n"
   17072 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   17073 									 "    EmitVertex();\n"
   17074 									 "    gs_fs = result;\n"
   17075 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   17076 									 "    EmitVertex();\n"
   17077 									 "    gs_fs = result;\n"
   17078 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   17079 									 "    EmitVertex();\n"
   17080 									 "    gs_fs = result;\n"
   17081 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   17082 									 "    EmitVertex();\n"
   17083 									 "}\n"
   17084 									 "\n";
   17085 	static const GLchar* tcs = "#version 430 core\n"
   17086 							   "#extension GL_ARB_enhanced_layouts : require\n"
   17087 							   "\n"
   17088 							   "layout(vertices = 1) out;\n"
   17089 							   "\n"
   17090 							   "in  vec4 vs_tcs[];\n"
   17091 							   "out vec4 tcs_tes[];\n"
   17092 							   "\n"
   17093 							   "void main()\n"
   17094 							   "{\n"
   17095 							   "\n"
   17096 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   17097 							   "\n"
   17098 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   17099 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   17100 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   17101 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   17102 							   "    gl_TessLevelInner[0] = 1.0;\n"
   17103 							   "    gl_TessLevelInner[1] = 1.0;\n"
   17104 							   "}\n"
   17105 							   "\n";
   17106 	static const GLchar* tcs_tested = "#version 430 core\n"
   17107 									  "#extension GL_ARB_enhanced_layouts : require\n"
   17108 									  "\n"
   17109 									  "layout(vertices = 1) out;\n"
   17110 									  "\n"
   17111 									  "VAR_DEFINITION"
   17112 									  "\n"
   17113 									  "in  vec4 vs_tcs[];\n"
   17114 									  "out vec4 tcs_tes[];\n"
   17115 									  "\n"
   17116 									  "void main()\n"
   17117 									  "{\n"
   17118 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   17119 									  "\n"
   17120 									  "VARIABLE_USE"
   17121 									  "\n"
   17122 									  "    tcs_tes[gl_InvocationID] = result;\n"
   17123 									  "\n"
   17124 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   17125 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   17126 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   17127 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   17128 									  "    gl_TessLevelInner[0] = 1.0;\n"
   17129 									  "    gl_TessLevelInner[1] = 1.0;\n"
   17130 									  "}\n"
   17131 									  "\n";
   17132 	static const GLchar* tes = "#version 430 core\n"
   17133 							   "#extension GL_ARB_enhanced_layouts : require\n"
   17134 							   "\n"
   17135 							   "layout(isolines, point_mode) in;\n"
   17136 							   "\n"
   17137 							   "in  vec4 tcs_tes[];\n"
   17138 							   "out vec4 tes_gs;\n"
   17139 							   "\n"
   17140 							   "void main()\n"
   17141 							   "{\n"
   17142 							   "    tes_gs = tcs_tes[0];\n"
   17143 							   "}\n"
   17144 							   "\n";
   17145 	static const GLchar* tes_tested = "#version 430 core\n"
   17146 									  "#extension GL_ARB_enhanced_layouts : require\n"
   17147 									  "\n"
   17148 									  "layout(isolines, point_mode) in;\n"
   17149 									  "\n"
   17150 									  "VAR_DEFINITION"
   17151 									  "\n"
   17152 									  "in  vec4 tcs_tes[];\n"
   17153 									  "out vec4 tes_gs;\n"
   17154 									  "\n"
   17155 									  "void main()\n"
   17156 									  "{\n"
   17157 									  "    vec4 result = tcs_tes[0];\n"
   17158 									  "\n"
   17159 									  "VARIABLE_USE"
   17160 									  "\n"
   17161 									  "    tes_gs += result;\n"
   17162 									  "}\n"
   17163 									  "\n";
   17164 	static const GLchar* vs = "#version 430 core\n"
   17165 							  "#extension GL_ARB_enhanced_layouts : require\n"
   17166 							  "\n"
   17167 							  "in  vec4 in_vs;\n"
   17168 							  "out vec4 vs_tcs;\n"
   17169 							  "\n"
   17170 							  "void main()\n"
   17171 							  "{\n"
   17172 							  "    vs_tcs = in_vs;\n"
   17173 							  "}\n"
   17174 							  "\n";
   17175 	static const GLchar* vs_tested = "#version 430 core\n"
   17176 									 "#extension GL_ARB_enhanced_layouts : require\n"
   17177 									 "\n"
   17178 									 "VAR_DEFINITION"
   17179 									 "\n"
   17180 									 "in  vec4 in_vs;\n"
   17181 									 "out vec4 vs_tcs;\n"
   17182 									 "\n"
   17183 									 "void main()\n"
   17184 									 "{\n"
   17185 									 "    vec4 result = in_vs;\n"
   17186 									 "\n"
   17187 									 "VARIABLE_USE"
   17188 									 "\n"
   17189 									 "    vs_tcs += result;\n"
   17190 									 "}\n"
   17191 									 "\n";
   17192 
   17193 	std::string source;
   17194 	testCase&   test_case = m_test_cases[test_case_index];
   17195 
   17196 	if (test_case.m_stage == stage)
   17197 	{
   17198 		const GLchar* array = "";
   17199 		GLchar		  buffer_gohan[16];
   17200 		GLchar		  buffer_goten[16];
   17201 		const GLchar* index	= "";
   17202 		size_t		  position = 0;
   17203 		size_t		  temp;
   17204 		const GLchar* type_name = test_case.m_type.GetGLSLTypeName();
   17205 
   17206 		sprintf(buffer_gohan, "%d", test_case.m_component_gohan);
   17207 		sprintf(buffer_goten, "%d", test_case.m_component_goten);
   17208 
   17209 		switch (stage)
   17210 		{
   17211 		case Utils::Shader::FRAGMENT:
   17212 			source = fs_tested;
   17213 			break;
   17214 		case Utils::Shader::GEOMETRY:
   17215 			source = gs_tested;
   17216 			array  = "[]";
   17217 			index  = "[0]";
   17218 			break;
   17219 		case Utils::Shader::TESS_CTRL:
   17220 			source = tcs_tested;
   17221 			array  = "[]";
   17222 			index  = "[gl_InvocationID]";
   17223 			break;
   17224 		case Utils::Shader::TESS_EVAL:
   17225 			source = tes_tested;
   17226 			array  = "[]";
   17227 			index  = "[0]";
   17228 			break;
   17229 		case Utils::Shader::VERTEX:
   17230 			source = vs_tested;
   17231 			break;
   17232 		default:
   17233 			TCU_FAIL("Invalid enum");
   17234 		}
   17235 
   17236 		temp = position;
   17237 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   17238 		position = temp;
   17239 		Utils::replaceToken("COMPONENT", position, buffer_gohan, source);
   17240 		Utils::replaceToken("ARRAY", position, array, source);
   17241 		Utils::replaceToken("COMPONENT", position, buffer_goten, source);
   17242 		Utils::replaceToken("ARRAY", position, array, source);
   17243 		Utils::replaceToken("VARIABLE_USE", position, l_test, source);
   17244 
   17245 		Utils::replaceAllTokens("TYPE", type_name, source);
   17246 		Utils::replaceAllTokens("INDEX", index, source);
   17247 	}
   17248 	else
   17249 	{
   17250 		switch (stage)
   17251 		{
   17252 		case Utils::Shader::FRAGMENT:
   17253 			source = fs;
   17254 			break;
   17255 		case Utils::Shader::GEOMETRY:
   17256 			source = gs;
   17257 			break;
   17258 		case Utils::Shader::TESS_CTRL:
   17259 			source = tcs;
   17260 			break;
   17261 		case Utils::Shader::TESS_EVAL:
   17262 			source = tes;
   17263 			break;
   17264 		case Utils::Shader::VERTEX:
   17265 			source = vs;
   17266 			break;
   17267 		default:
   17268 			TCU_FAIL("Invalid enum");
   17269 		}
   17270 	}
   17271 
   17272 	return source;
   17273 }
   17274 
   17275 /** Get description of test case
   17276  *
   17277  * @param test_case_index Index of test case
   17278  *
   17279  * @return Test case description
   17280  **/
   17281 std::string OutputComponentAliasingTest::getTestCaseName(GLuint test_case_index)
   17282 {
   17283 	std::stringstream stream;
   17284 	testCase&		  test_case = m_test_cases[test_case_index];
   17285 
   17286 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage)
   17287 		   << " type: " << test_case.m_type.GetGLSLTypeName() << ", components: " << test_case.m_component_gohan
   17288 		   << " & " << test_case.m_component_goten;
   17289 
   17290 	return stream.str();
   17291 }
   17292 
   17293 /** Get number of test cases
   17294  *
   17295  * @return Number of test cases
   17296  **/
   17297 GLuint OutputComponentAliasingTest::getTestCaseNumber()
   17298 {
   17299 	return static_cast<GLuint>(m_test_cases.size());
   17300 }
   17301 
   17302 /** Selects if "compute" stage is relevant for test
   17303  *
   17304  * @param ignored
   17305  *
   17306  * @return false
   17307  **/
   17308 bool OutputComponentAliasingTest::isComputeRelevant(GLuint /* test_case_index */)
   17309 {
   17310 	return false;
   17311 }
   17312 
   17313 /** Prepare all test cases
   17314  *
   17315  **/
   17316 void OutputComponentAliasingTest::testInit()
   17317 {
   17318 	static const GLuint n_components_per_location = 4;
   17319 	const GLuint		n_types					  = getTypesNumber();
   17320 
   17321 	for (GLuint i = 0; i < n_types; ++i)
   17322 	{
   17323 		const Utils::Type& type				= getType(i);
   17324 		const GLuint	   n_req_components = type.m_n_rows;
   17325 		const GLuint	   valid_component  = n_components_per_location - n_req_components;
   17326 
   17327 		/* Skip matrices */
   17328 		if (1 != type.m_n_columns)
   17329 		{
   17330 			continue;
   17331 		}
   17332 
   17333 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   17334 		{
   17335 			if (Utils::Shader::COMPUTE == stage)
   17336 			{
   17337 				continue;
   17338 			}
   17339 
   17340 			if ((Utils::Shader::FRAGMENT == stage) && (Utils::Type::Double == type.m_basic_type))
   17341 			{
   17342 				continue;
   17343 			}
   17344 
   17345 			for (GLuint gohan = 0; gohan <= valid_component; ++gohan)
   17346 			{
   17347 				const GLint first_aliasing = gohan - n_req_components + 1;
   17348 				const GLint last_aliasing  = gohan + n_req_components - 1;
   17349 
   17350 				const GLuint goten_start = std::max(0, first_aliasing);
   17351 				const GLuint goten_stop  = std::min((GLint)valid_component, last_aliasing);
   17352 
   17353 				for (GLuint goten = goten_start; goten <= goten_stop; ++goten)
   17354 				{
   17355 					testCase test_case = { gohan, goten, (Utils::Shader::STAGES)stage, type };
   17356 
   17357 					m_test_cases.push_back(test_case);
   17358 				}
   17359 			}
   17360 		}
   17361 	}
   17362 }
   17363 
   17364 /** Constructor
   17365  *
   17366  * @param context Test framework context
   17367  **/
   17368 VaryingLocationAliasingWithMixedTypesTest::VaryingLocationAliasingWithMixedTypesTest(deqp::Context& context)
   17369 	: NegativeTestBase(context, "varying_location_aliasing_with_mixed_types",
   17370 					   "Test verifies that compiler reports error when float/int types are mixed at one location")
   17371 {
   17372 }
   17373 
   17374 /** Source for given test case and stage
   17375  *
   17376  * @param test_case_index Index of test case
   17377  * @param stage           Shader stage
   17378  *
   17379  * @return Shader source
   17380  **/
   17381 std::string VaryingLocationAliasingWithMixedTypesTest::getShaderSource(GLuint				 test_case_index,
   17382 																	   Utils::Shader::STAGES stage)
   17383 {
   17384 	static const GLchar* var_definition =
   17385 		"layout (location = 1, component = COMPONENT) FLAT DIRECTION TYPE gohanARRAY;\n"
   17386 		"layout (location = 1, component = COMPONENT) FLAT DIRECTION TYPE gotenARRAY;\n";
   17387 	static const GLchar* input_use = "    if ((TYPE(0) == gohanINDEX) &&\n"
   17388 									 "        (TYPE(1) == gotenINDEX) )\n"
   17389 									 "    {\n"
   17390 									 "        result += vec4(1, 0.5, 0.25, 0.125);\n"
   17391 									 "    }\n";
   17392 	static const GLchar* output_use = "    gohanINDEX = TYPE(0);\n"
   17393 									  "    gotenINDEX = TYPE(1);\n"
   17394 									  "    if (vec4(0) == result)\n"
   17395 									  "    {\n"
   17396 									  "        gohanINDEX = TYPE(1);\n"
   17397 									  "        gotenINDEX = TYPE(0);\n"
   17398 									  "    }\n";
   17399 	static const GLchar* fs = "#version 430 core\n"
   17400 							  "#extension GL_ARB_enhanced_layouts : require\n"
   17401 							  "\n"
   17402 							  "in  vec4 gs_fs;\n"
   17403 							  "out vec4 fs_out;\n"
   17404 							  "\n"
   17405 							  "void main()\n"
   17406 							  "{\n"
   17407 							  "    fs_out = gs_fs;\n"
   17408 							  "}\n"
   17409 							  "\n";
   17410 	static const GLchar* fs_tested = "#version 430 core\n"
   17411 									 "#extension GL_ARB_enhanced_layouts : require\n"
   17412 									 "\n"
   17413 									 "VAR_DEFINITION"
   17414 									 "\n"
   17415 									 "in  vec4 gs_fs;\n"
   17416 									 "out vec4 fs_out;\n"
   17417 									 "\n"
   17418 									 "void main()\n"
   17419 									 "{\n"
   17420 									 "    vec4 result = gs_fs;\n"
   17421 									 "\n"
   17422 									 "VARIABLE_USE"
   17423 									 "\n"
   17424 									 "    fs_out += result;\n"
   17425 									 "}\n"
   17426 									 "\n";
   17427 	static const GLchar* gs = "#version 430 core\n"
   17428 							  "#extension GL_ARB_enhanced_layouts : require\n"
   17429 							  "\n"
   17430 							  "layout(points)                           in;\n"
   17431 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   17432 							  "\n"
   17433 							  "in  vec4 tes_gs[];\n"
   17434 							  "out vec4 gs_fs;\n"
   17435 							  "\n"
   17436 							  "void main()\n"
   17437 							  "{\n"
   17438 							  "    gs_fs = tes_gs[0];\n"
   17439 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   17440 							  "    EmitVertex();\n"
   17441 							  "    gs_fs = tes_gs[0];\n"
   17442 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   17443 							  "    EmitVertex();\n"
   17444 							  "    gs_fs = tes_gs[0];\n"
   17445 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   17446 							  "    EmitVertex();\n"
   17447 							  "    gs_fs = tes_gs[0];\n"
   17448 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   17449 							  "    EmitVertex();\n"
   17450 							  "}\n"
   17451 							  "\n";
   17452 	static const GLchar* gs_tested = "#version 430 core\n"
   17453 									 "#extension GL_ARB_enhanced_layouts : require\n"
   17454 									 "\n"
   17455 									 "layout(points)                           in;\n"
   17456 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   17457 									 "\n"
   17458 									 "VAR_DEFINITION"
   17459 									 "\n"
   17460 									 "in  vec4 tes_gs[];\n"
   17461 									 "out vec4 gs_fs;\n"
   17462 									 "\n"
   17463 									 "void main()\n"
   17464 									 "{\n"
   17465 									 "    vec4 result = tes_gs[0];\n"
   17466 									 "\n"
   17467 									 "VARIABLE_USE"
   17468 									 "\n"
   17469 									 "    gs_fs = result;\n"
   17470 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   17471 									 "    EmitVertex();\n"
   17472 									 "    gs_fs = result;\n"
   17473 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   17474 									 "    EmitVertex();\n"
   17475 									 "    gs_fs = result;\n"
   17476 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   17477 									 "    EmitVertex();\n"
   17478 									 "    gs_fs = result;\n"
   17479 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   17480 									 "    EmitVertex();\n"
   17481 									 "}\n"
   17482 									 "\n";
   17483 	static const GLchar* tcs = "#version 430 core\n"
   17484 							   "#extension GL_ARB_enhanced_layouts : require\n"
   17485 							   "\n"
   17486 							   "layout(vertices = 1) out;\n"
   17487 							   "\n"
   17488 							   "in  vec4 vs_tcs[];\n"
   17489 							   "out vec4 tcs_tes[];\n"
   17490 							   "\n"
   17491 							   "void main()\n"
   17492 							   "{\n"
   17493 							   "\n"
   17494 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   17495 							   "\n"
   17496 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   17497 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   17498 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   17499 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   17500 							   "    gl_TessLevelInner[0] = 1.0;\n"
   17501 							   "    gl_TessLevelInner[1] = 1.0;\n"
   17502 							   "}\n"
   17503 							   "\n";
   17504 	static const GLchar* tcs_tested = "#version 430 core\n"
   17505 									  "#extension GL_ARB_enhanced_layouts : require\n"
   17506 									  "\n"
   17507 									  "layout(vertices = 1) out;\n"
   17508 									  "\n"
   17509 									  "VAR_DEFINITION"
   17510 									  "\n"
   17511 									  "in  vec4 vs_tcs[];\n"
   17512 									  "out vec4 tcs_tes[];\n"
   17513 									  "\n"
   17514 									  "void main()\n"
   17515 									  "{\n"
   17516 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   17517 									  "\n"
   17518 									  "VARIABLE_USE"
   17519 									  "\n"
   17520 									  "    tcs_tes[gl_InvocationID] = result;\n"
   17521 									  "\n"
   17522 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   17523 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   17524 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   17525 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   17526 									  "    gl_TessLevelInner[0] = 1.0;\n"
   17527 									  "    gl_TessLevelInner[1] = 1.0;\n"
   17528 									  "}\n"
   17529 									  "\n";
   17530 	static const GLchar* tes = "#version 430 core\n"
   17531 							   "#extension GL_ARB_enhanced_layouts : require\n"
   17532 							   "\n"
   17533 							   "layout(isolines, point_mode) in;\n"
   17534 							   "\n"
   17535 							   "in  vec4 tcs_tes[];\n"
   17536 							   "out vec4 tes_gs;\n"
   17537 							   "\n"
   17538 							   "void main()\n"
   17539 							   "{\n"
   17540 							   "    tes_gs = tcs_tes[0];\n"
   17541 							   "}\n"
   17542 							   "\n";
   17543 	static const GLchar* tes_tested = "#version 430 core\n"
   17544 									  "#extension GL_ARB_enhanced_layouts : require\n"
   17545 									  "\n"
   17546 									  "layout(isolines, point_mode) in;\n"
   17547 									  "\n"
   17548 									  "VAR_DEFINITION"
   17549 									  "\n"
   17550 									  "in  vec4 tcs_tes[];\n"
   17551 									  "out vec4 tes_gs;\n"
   17552 									  "\n"
   17553 									  "void main()\n"
   17554 									  "{\n"
   17555 									  "    vec4 result = tcs_tes[0];\n"
   17556 									  "\n"
   17557 									  "VARIABLE_USE"
   17558 									  "\n"
   17559 									  "    tes_gs += result;\n"
   17560 									  "}\n"
   17561 									  "\n";
   17562 	static const GLchar* vs = "#version 430 core\n"
   17563 							  "#extension GL_ARB_enhanced_layouts : require\n"
   17564 							  "\n"
   17565 							  "in  vec4 in_vs;\n"
   17566 							  "out vec4 vs_tcs;\n"
   17567 							  "\n"
   17568 							  "void main()\n"
   17569 							  "{\n"
   17570 							  "    vs_tcs = in_vs;\n"
   17571 							  "}\n"
   17572 							  "\n";
   17573 	static const GLchar* vs_tested = "#version 430 core\n"
   17574 									 "#extension GL_ARB_enhanced_layouts : require\n"
   17575 									 "\n"
   17576 									 "VAR_DEFINITION"
   17577 									 "\n"
   17578 									 "in  vec4 in_vs;\n"
   17579 									 "out vec4 vs_tcs;\n"
   17580 									 "\n"
   17581 									 "void main()\n"
   17582 									 "{\n"
   17583 									 "    vec4 result = in_vs;\n"
   17584 									 "\n"
   17585 									 "VARIABLE_USE"
   17586 									 "\n"
   17587 									 "    vs_tcs += result;\n"
   17588 									 "}\n"
   17589 									 "\n";
   17590 
   17591 	std::string source;
   17592 	testCase&   test_case = m_test_cases[test_case_index];
   17593 
   17594 	if (test_case.m_stage == stage)
   17595 	{
   17596 		const GLchar*			 array = "";
   17597 		GLchar					 buffer_gohan[16];
   17598 		GLchar					 buffer_goten[16];
   17599 		const GLchar*			 direction  = "in ";
   17600 		const GLchar*			 flat_gohan = "";
   17601 		const GLchar*			 flat_goten = "";
   17602 		const GLchar*			 index		= "";
   17603 		size_t					 position   = 0;
   17604 		size_t					 temp;
   17605 		const GLchar*			 type_gohan_name = test_case.m_type_gohan.GetGLSLTypeName();
   17606 		const GLchar*			 type_goten_name = test_case.m_type_goten.GetGLSLTypeName();
   17607 		Utils::Variable::STORAGE storage		 = Utils::Variable::VARYING_INPUT;
   17608 		const GLchar*			 var_use		 = input_use;
   17609 
   17610 		if (false == test_case.m_is_input)
   17611 		{
   17612 			direction = "out";
   17613 			storage   = Utils::Variable::VARYING_OUTPUT;
   17614 			var_use   = output_use;
   17615 		}
   17616 
   17617 		if (true == isFlatRequired(stage, test_case.m_type_gohan, storage))
   17618 		{
   17619 			flat_gohan = "flat";
   17620 		}
   17621 
   17622 		if (true == isFlatRequired(stage, test_case.m_type_goten, storage))
   17623 		{
   17624 			flat_goten = "flat";
   17625 		}
   17626 
   17627 		sprintf(buffer_gohan, "%d", test_case.m_component_gohan);
   17628 		sprintf(buffer_goten, "%d", test_case.m_component_goten);
   17629 
   17630 		switch (stage)
   17631 		{
   17632 		case Utils::Shader::FRAGMENT:
   17633 			source = fs_tested;
   17634 			break;
   17635 		case Utils::Shader::GEOMETRY:
   17636 			source = gs_tested;
   17637 			array  = "[]";
   17638 			index  = "[0]";
   17639 			break;
   17640 		case Utils::Shader::TESS_CTRL:
   17641 			source = tcs_tested;
   17642 			array  = "[]";
   17643 			index  = "[gl_InvocationID]";
   17644 			break;
   17645 		case Utils::Shader::TESS_EVAL:
   17646 			source = tes_tested;
   17647 			array  = "[]";
   17648 			index  = "[0]";
   17649 			break;
   17650 		case Utils::Shader::VERTEX:
   17651 			source = vs_tested;
   17652 			break;
   17653 		default:
   17654 			TCU_FAIL("Invalid enum");
   17655 		}
   17656 
   17657 		temp = position;
   17658 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   17659 		position = temp;
   17660 		Utils::replaceToken("COMPONENT", position, buffer_gohan, source);
   17661 		Utils::replaceToken("FLAT", position, flat_gohan, source);
   17662 		Utils::replaceToken("DIRECTION", position, direction, source);
   17663 		Utils::replaceToken("TYPE", position, type_gohan_name, source);
   17664 		Utils::replaceToken("ARRAY", position, array, source);
   17665 		Utils::replaceToken("COMPONENT", position, buffer_goten, source);
   17666 		Utils::replaceToken("FLAT", position, flat_goten, source);
   17667 		Utils::replaceToken("DIRECTION", position, direction, source);
   17668 		Utils::replaceToken("TYPE", position, type_goten_name, source);
   17669 		Utils::replaceToken("ARRAY", position, array, source);
   17670 
   17671 		temp = position;
   17672 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   17673 		position = temp;
   17674 		if (true == test_case.m_is_input)
   17675 		{
   17676 			Utils::replaceToken("TYPE", position, type_gohan_name, source);
   17677 			Utils::replaceToken("TYPE", position, type_goten_name, source);
   17678 		}
   17679 		else
   17680 		{
   17681 			Utils::replaceToken("TYPE", position, type_gohan_name, source);
   17682 			Utils::replaceToken("TYPE", position, type_goten_name, source);
   17683 			Utils::replaceToken("TYPE", position, type_gohan_name, source);
   17684 			Utils::replaceToken("TYPE", position, type_goten_name, source);
   17685 		}
   17686 
   17687 		Utils::replaceAllTokens("INDEX", index, source);
   17688 	}
   17689 	else
   17690 	{
   17691 		switch (stage)
   17692 		{
   17693 		case Utils::Shader::FRAGMENT:
   17694 			source = fs;
   17695 			break;
   17696 		case Utils::Shader::GEOMETRY:
   17697 			source = gs;
   17698 			break;
   17699 		case Utils::Shader::TESS_CTRL:
   17700 			source = tcs;
   17701 			break;
   17702 		case Utils::Shader::TESS_EVAL:
   17703 			source = tes;
   17704 			break;
   17705 		case Utils::Shader::VERTEX:
   17706 			source = vs;
   17707 			break;
   17708 		default:
   17709 			TCU_FAIL("Invalid enum");
   17710 		}
   17711 	}
   17712 
   17713 	return source;
   17714 }
   17715 
   17716 /** Get description of test case
   17717  *
   17718  * @param test_case_index Index of test case
   17719  *
   17720  * @return Test case description
   17721  **/
   17722 std::string VaryingLocationAliasingWithMixedTypesTest::getTestCaseName(GLuint test_case_index)
   17723 {
   17724 	std::stringstream stream;
   17725 	testCase&		  test_case = m_test_cases[test_case_index];
   17726 
   17727 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage) << ", "
   17728 		   << test_case.m_type_gohan.GetGLSLTypeName() << " at " << test_case.m_component_gohan << ", "
   17729 		   << test_case.m_type_goten.GetGLSLTypeName() << " at " << test_case.m_component_goten << ". Direction: ";
   17730 
   17731 	if (true == test_case.m_is_input)
   17732 	{
   17733 		stream << "input";
   17734 	}
   17735 	else
   17736 	{
   17737 		stream << "output";
   17738 	}
   17739 
   17740 	return stream.str();
   17741 }
   17742 
   17743 /** Get number of test cases
   17744  *
   17745  * @return Number of test cases
   17746  **/
   17747 GLuint VaryingLocationAliasingWithMixedTypesTest::getTestCaseNumber()
   17748 {
   17749 	return static_cast<GLuint>(m_test_cases.size());
   17750 }
   17751 
   17752 /** Selects if "compute" stage is relevant for test
   17753  *
   17754  * @param ignored
   17755  *
   17756  * @return false
   17757  **/
   17758 bool VaryingLocationAliasingWithMixedTypesTest::isComputeRelevant(GLuint /* test_case_index */)
   17759 {
   17760 	return false;
   17761 }
   17762 
   17763 /** Prepare all test cases
   17764  *
   17765  **/
   17766 void VaryingLocationAliasingWithMixedTypesTest::testInit()
   17767 {
   17768 	static const GLuint n_components_per_location = 4;
   17769 	const GLuint		n_types					  = getTypesNumber();
   17770 
   17771 	for (GLuint i = 0; i < n_types; ++i)
   17772 	{
   17773 		const Utils::Type& type_gohan		   = getType(i);
   17774 		const bool		   is_float_type_gohan = isFloatType(type_gohan);
   17775 
   17776 		/* Skip matrices */
   17777 		if (1 != type_gohan.m_n_columns)
   17778 		{
   17779 			continue;
   17780 		}
   17781 
   17782 		for (GLuint j = 0; j < n_types; ++j)
   17783 		{
   17784 			const Utils::Type& type_goten		   = getType(j);
   17785 			const bool		   is_float_type_goten = isFloatType(type_goten);
   17786 
   17787 			/* Skip matrices */
   17788 			if (1 != type_goten.m_n_columns)
   17789 			{
   17790 				continue;
   17791 			}
   17792 
   17793 			/* Skip valid combinations */
   17794 			if (is_float_type_gohan == is_float_type_goten)
   17795 			{
   17796 				continue;
   17797 			}
   17798 
   17799 			const GLuint n_req_components_gohan = type_gohan.m_n_rows;
   17800 			const GLuint n_req_components_goten = type_goten.m_n_rows;
   17801 			const GLuint valid_component_gohan  = n_components_per_location - n_req_components_gohan;
   17802 			const GLuint valid_component_goten  = n_components_per_location - n_req_components_goten;
   17803 
   17804 			/* Skip pairs that cannot fit into one location */
   17805 			if (n_components_per_location < (n_req_components_gohan + n_req_components_goten))
   17806 			{
   17807 				continue;
   17808 			}
   17809 
   17810 			for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   17811 			{
   17812 				/* Skip compute shader */
   17813 				if (Utils::Shader::COMPUTE == stage)
   17814 				{
   17815 					continue;
   17816 				}
   17817 
   17818 				for (GLuint gohan = 0; gohan <= valid_component_gohan; ++gohan)
   17819 				{
   17820 					const GLint first_aliasing = gohan - n_req_components_goten + 1;
   17821 					const GLint last_aliasing  = gohan + n_req_components_gohan - 1;
   17822 
   17823 					const GLuint goten_lower_limit = std::max(0, first_aliasing);
   17824 					const GLuint goten_upper_limit = last_aliasing + 1;
   17825 
   17826 					/* Compoennets before gohan */
   17827 					for (GLuint goten = 0; goten < goten_lower_limit; ++goten)
   17828 					{
   17829 						testCase test_case_in = { gohan,	  goten,	 true, (Utils::Shader::STAGES)stage,
   17830 												  type_gohan, type_goten };
   17831 						testCase test_case_out = { gohan,	  goten,	 false, (Utils::Shader::STAGES)stage,
   17832 												   type_gohan, type_goten };
   17833 
   17834 						m_test_cases.push_back(test_case_in);
   17835 
   17836 						/* Skip double outputs in fragment shader */
   17837 						if ((Utils::Shader::FRAGMENT != stage) || ((Utils::Type::Double != type_gohan.m_basic_type) &&
   17838 																   (Utils::Type::Double != type_goten.m_basic_type)))
   17839 						{
   17840 							m_test_cases.push_back(test_case_out);
   17841 						}
   17842 					}
   17843 
   17844 					/* Components after gohan */
   17845 					for (GLuint goten = goten_upper_limit; goten <= valid_component_goten; ++goten)
   17846 					{
   17847 						testCase test_case_in = { gohan,	  goten,	 true, (Utils::Shader::STAGES)stage,
   17848 												  type_gohan, type_goten };
   17849 						testCase test_case_out = { gohan,	  goten,	 false, (Utils::Shader::STAGES)stage,
   17850 												   type_gohan, type_goten };
   17851 
   17852 						m_test_cases.push_back(test_case_in);
   17853 
   17854 						/* Skip double outputs in fragment shader */
   17855 						if ((Utils::Shader::FRAGMENT != stage) || ((Utils::Type::Double != type_gohan.m_basic_type) &&
   17856 																   (Utils::Type::Double != type_goten.m_basic_type)))
   17857 						{
   17858 							m_test_cases.push_back(test_case_out);
   17859 						}
   17860 					}
   17861 				}
   17862 			}
   17863 		}
   17864 	}
   17865 }
   17866 
   17867 /** Check if given type is float
   17868  *
   17869  * @param type Type in question
   17870  *
   17871  * @return true if tpye is float, false otherwise
   17872  **/
   17873 bool VaryingLocationAliasingWithMixedTypesTest::isFloatType(const Utils::Type& type)
   17874 {
   17875 	bool is_float = false;
   17876 
   17877 	if ((Utils::Type::Double == type.m_basic_type) || (Utils::Type::Float == type.m_basic_type))
   17878 	{
   17879 		is_float = true;
   17880 	}
   17881 
   17882 	return is_float;
   17883 }
   17884 
   17885 /** Constructor
   17886  *
   17887  * @param context Test framework context
   17888  **/
   17889 VaryingLocationAliasingWithMixedInterpolationTest::VaryingLocationAliasingWithMixedInterpolationTest(
   17890 	deqp::Context& context)
   17891 	: NegativeTestBase(
   17892 		  context, "varying_location_aliasing_with_mixed_interpolation",
   17893 		  "Test verifies that compiler reports error when interpolation qualifiers are mixed at one location")
   17894 {
   17895 }
   17896 
   17897 /** Source for given test case and stage
   17898  *
   17899  * @param test_case_index Index of test case
   17900  * @param stage           Shader stage
   17901  *
   17902  * @return Shader source
   17903  **/
   17904 std::string VaryingLocationAliasingWithMixedInterpolationTest::getShaderSource(GLuint				 test_case_index,
   17905 																			   Utils::Shader::STAGES stage)
   17906 {
   17907 	static const GLchar* var_definition =
   17908 		"layout (location = 1, component = COMPONENT) INTERPOLATION DIRECTION TYPE gohanARRAY;\n"
   17909 		"layout (location = 1, component = COMPONENT) INTERPOLATION DIRECTION TYPE gotenARRAY;\n";
   17910 	static const GLchar* input_use = "    if ((TYPE(0) == gohanINDEX) &&\n"
   17911 									 "        (TYPE(1) == gotenINDEX) )\n"
   17912 									 "    {\n"
   17913 									 "        result += vec4(1, 0.5, 0.25, 0.125);\n"
   17914 									 "    }\n";
   17915 	static const GLchar* output_use = "    gohanINDEX = TYPE(0);\n"
   17916 									  "    gotenINDEX = TYPE(1);\n"
   17917 									  "    if (vec4(0) == result)\n"
   17918 									  "    {\n"
   17919 									  "        gohanINDEX = TYPE(1);\n"
   17920 									  "        gotenINDEX = TYPE(0);\n"
   17921 									  "    }\n";
   17922 	static const GLchar* fs = "#version 430 core\n"
   17923 							  "#extension GL_ARB_enhanced_layouts : require\n"
   17924 							  "\n"
   17925 							  "in  vec4 gs_fs;\n"
   17926 							  "out vec4 fs_out;\n"
   17927 							  "\n"
   17928 							  "void main()\n"
   17929 							  "{\n"
   17930 							  "    fs_out = gs_fs;\n"
   17931 							  "}\n"
   17932 							  "\n";
   17933 	static const GLchar* fs_tested = "#version 430 core\n"
   17934 									 "#extension GL_ARB_enhanced_layouts : require\n"
   17935 									 "\n"
   17936 									 "VAR_DEFINITION"
   17937 									 "\n"
   17938 									 "in  vec4 gs_fs;\n"
   17939 									 "out vec4 fs_out;\n"
   17940 									 "\n"
   17941 									 "void main()\n"
   17942 									 "{\n"
   17943 									 "    vec4 result = gs_fs;\n"
   17944 									 "\n"
   17945 									 "VARIABLE_USE"
   17946 									 "\n"
   17947 									 "    fs_out = result;\n"
   17948 									 "}\n"
   17949 									 "\n";
   17950 	static const GLchar* gs = "#version 430 core\n"
   17951 							  "#extension GL_ARB_enhanced_layouts : require\n"
   17952 							  "\n"
   17953 							  "layout(points)                           in;\n"
   17954 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   17955 							  "\n"
   17956 							  "in  vec4 tes_gs[];\n"
   17957 							  "out vec4 gs_fs;\n"
   17958 							  "\n"
   17959 							  "void main()\n"
   17960 							  "{\n"
   17961 							  "    gs_fs = tes_gs[0];\n"
   17962 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   17963 							  "    EmitVertex();\n"
   17964 							  "    gs_fs = tes_gs[0];\n"
   17965 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   17966 							  "    EmitVertex();\n"
   17967 							  "    gs_fs = tes_gs[0];\n"
   17968 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   17969 							  "    EmitVertex();\n"
   17970 							  "    gs_fs = tes_gs[0];\n"
   17971 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   17972 							  "    EmitVertex();\n"
   17973 							  "}\n"
   17974 							  "\n";
   17975 	static const GLchar* gs_tested = "#version 430 core\n"
   17976 									 "#extension GL_ARB_enhanced_layouts : require\n"
   17977 									 "\n"
   17978 									 "layout(points)                           in;\n"
   17979 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   17980 									 "\n"
   17981 									 "VAR_DEFINITION"
   17982 									 "\n"
   17983 									 "in  vec4 tes_gs[];\n"
   17984 									 "out vec4 gs_fs;\n"
   17985 									 "\n"
   17986 									 "void main()\n"
   17987 									 "{\n"
   17988 									 "    vec4 result = tes_gs[0];\n"
   17989 									 "\n"
   17990 									 "VARIABLE_USE"
   17991 									 "\n"
   17992 									 "    gs_fs = result;\n"
   17993 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   17994 									 "    EmitVertex();\n"
   17995 									 "    gs_fs = result;\n"
   17996 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   17997 									 "    EmitVertex();\n"
   17998 									 "    gs_fs = result;\n"
   17999 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   18000 									 "    EmitVertex();\n"
   18001 									 "    gs_fs = result;\n"
   18002 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   18003 									 "    EmitVertex();\n"
   18004 									 "}\n"
   18005 									 "\n";
   18006 	static const GLchar* tcs = "#version 430 core\n"
   18007 							   "#extension GL_ARB_enhanced_layouts : require\n"
   18008 							   "\n"
   18009 							   "layout(vertices = 1) out;\n"
   18010 							   "\n"
   18011 							   "in  vec4 vs_tcs[];\n"
   18012 							   "out vec4 tcs_tes[];\n"
   18013 							   "\n"
   18014 							   "void main()\n"
   18015 							   "{\n"
   18016 							   "\n"
   18017 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   18018 							   "\n"
   18019 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   18020 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   18021 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   18022 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   18023 							   "    gl_TessLevelInner[0] = 1.0;\n"
   18024 							   "    gl_TessLevelInner[1] = 1.0;\n"
   18025 							   "}\n"
   18026 							   "\n";
   18027 	static const GLchar* tcs_tested = "#version 430 core\n"
   18028 									  "#extension GL_ARB_enhanced_layouts : require\n"
   18029 									  "\n"
   18030 									  "layout(vertices = 1) out;\n"
   18031 									  "\n"
   18032 									  "VAR_DEFINITION"
   18033 									  "\n"
   18034 									  "in  vec4 vs_tcs[];\n"
   18035 									  "out vec4 tcs_tes[];\n"
   18036 									  "\n"
   18037 									  "void main()\n"
   18038 									  "{\n"
   18039 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   18040 									  "\n"
   18041 									  "VARIABLE_USE"
   18042 									  "\n"
   18043 									  "    tcs_tes[gl_InvocationID] = result;\n"
   18044 									  "\n"
   18045 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   18046 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   18047 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   18048 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   18049 									  "    gl_TessLevelInner[0] = 1.0;\n"
   18050 									  "    gl_TessLevelInner[1] = 1.0;\n"
   18051 									  "}\n"
   18052 									  "\n";
   18053 	static const GLchar* tes = "#version 430 core\n"
   18054 							   "#extension GL_ARB_enhanced_layouts : require\n"
   18055 							   "\n"
   18056 							   "layout(isolines, point_mode) in;\n"
   18057 							   "\n"
   18058 							   "in  vec4 tcs_tes[];\n"
   18059 							   "out vec4 tes_gs;\n"
   18060 							   "\n"
   18061 							   "void main()\n"
   18062 							   "{\n"
   18063 							   "    tes_gs = tcs_tes[0];\n"
   18064 							   "}\n"
   18065 							   "\n";
   18066 	static const GLchar* tes_tested = "#version 430 core\n"
   18067 									  "#extension GL_ARB_enhanced_layouts : require\n"
   18068 									  "\n"
   18069 									  "layout(isolines, point_mode) in;\n"
   18070 									  "\n"
   18071 									  "VAR_DEFINITION"
   18072 									  "\n"
   18073 									  "in  vec4 tcs_tes[];\n"
   18074 									  "out vec4 tes_gs;\n"
   18075 									  "\n"
   18076 									  "void main()\n"
   18077 									  "{\n"
   18078 									  "    vec4 result = tcs_tes[0];\n"
   18079 									  "\n"
   18080 									  "VARIABLE_USE"
   18081 									  "\n"
   18082 									  "    tes_gs += result;\n"
   18083 									  "}\n"
   18084 									  "\n";
   18085 	static const GLchar* vs = "#version 430 core\n"
   18086 							  "#extension GL_ARB_enhanced_layouts : require\n"
   18087 							  "\n"
   18088 							  "in  vec4 in_vs;\n"
   18089 							  "out vec4 vs_tcs;\n"
   18090 							  "\n"
   18091 							  "void main()\n"
   18092 							  "{\n"
   18093 							  "    vs_tcs = in_vs;\n"
   18094 							  "}\n"
   18095 							  "\n";
   18096 	static const GLchar* vs_tested = "#version 430 core\n"
   18097 									 "#extension GL_ARB_enhanced_layouts : require\n"
   18098 									 "\n"
   18099 									 "VAR_DEFINITION"
   18100 									 "\n"
   18101 									 "in  vec4 in_vs;\n"
   18102 									 "out vec4 vs_tcs;\n"
   18103 									 "\n"
   18104 									 "void main()\n"
   18105 									 "{\n"
   18106 									 "    vec4 result = in_vs;\n"
   18107 									 "\n"
   18108 									 "VARIABLE_USE"
   18109 									 "\n"
   18110 									 "    vs_tcs += result;\n"
   18111 									 "}\n"
   18112 									 "\n";
   18113 
   18114 	std::string source;
   18115 	testCase&   test_case = m_test_cases[test_case_index];
   18116 
   18117 	if (test_case.m_stage == stage)
   18118 	{
   18119 		const GLchar* array = "";
   18120 		GLchar		  buffer_gohan[16];
   18121 		GLchar		  buffer_goten[16];
   18122 		const GLchar* direction = "in ";
   18123 		const GLchar* index		= "";
   18124 		const GLchar* int_gohan = getInterpolationQualifier(test_case.m_interpolation_gohan);
   18125 		const GLchar* int_goten = getInterpolationQualifier(test_case.m_interpolation_goten);
   18126 		size_t		  position  = 0;
   18127 		size_t		  temp;
   18128 		const GLchar* type_gohan_name = test_case.m_type_gohan.GetGLSLTypeName();
   18129 		const GLchar* type_goten_name = test_case.m_type_goten.GetGLSLTypeName();
   18130 		const GLchar* var_use		  = input_use;
   18131 
   18132 		if (false == test_case.m_is_input)
   18133 		{
   18134 			direction = "out";
   18135 
   18136 			var_use = output_use;
   18137 		}
   18138 
   18139 		sprintf(buffer_gohan, "%d", test_case.m_component_gohan);
   18140 		sprintf(buffer_goten, "%d", test_case.m_component_goten);
   18141 
   18142 		switch (stage)
   18143 		{
   18144 		case Utils::Shader::FRAGMENT:
   18145 			source = fs_tested;
   18146 			break;
   18147 		case Utils::Shader::GEOMETRY:
   18148 			source = gs_tested;
   18149 			array  = "[]";
   18150 			index  = "[0]";
   18151 			break;
   18152 		case Utils::Shader::TESS_CTRL:
   18153 			source = tcs_tested;
   18154 			array  = "[]";
   18155 			index  = "[gl_InvocationID]";
   18156 			break;
   18157 		case Utils::Shader::TESS_EVAL:
   18158 			source = tes_tested;
   18159 			array  = "[]";
   18160 			index  = "[0]";
   18161 			break;
   18162 		case Utils::Shader::VERTEX:
   18163 			source = vs_tested;
   18164 			break;
   18165 		default:
   18166 			TCU_FAIL("Invalid enum");
   18167 		}
   18168 
   18169 		temp = position;
   18170 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   18171 		position = temp;
   18172 		Utils::replaceToken("COMPONENT", position, buffer_gohan, source);
   18173 		Utils::replaceToken("INTERPOLATION", position, int_gohan, source);
   18174 		Utils::replaceToken("DIRECTION", position, direction, source);
   18175 		Utils::replaceToken("TYPE", position, type_gohan_name, source);
   18176 		Utils::replaceToken("ARRAY", position, array, source);
   18177 		Utils::replaceToken("COMPONENT", position, buffer_goten, source);
   18178 		Utils::replaceToken("INTERPOLATION", position, int_goten, source);
   18179 		Utils::replaceToken("DIRECTION", position, direction, source);
   18180 		Utils::replaceToken("TYPE", position, type_goten_name, source);
   18181 		Utils::replaceToken("ARRAY", position, array, source);
   18182 
   18183 		temp = position;
   18184 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   18185 		position = temp;
   18186 		if (true == test_case.m_is_input)
   18187 		{
   18188 			Utils::replaceToken("TYPE", position, type_gohan_name, source);
   18189 			Utils::replaceToken("TYPE", position, type_goten_name, source);
   18190 		}
   18191 		else
   18192 		{
   18193 			Utils::replaceToken("TYPE", position, type_gohan_name, source);
   18194 			Utils::replaceToken("TYPE", position, type_goten_name, source);
   18195 			Utils::replaceToken("TYPE", position, type_gohan_name, source);
   18196 			Utils::replaceToken("TYPE", position, type_goten_name, source);
   18197 		}
   18198 
   18199 		Utils::replaceAllTokens("INDEX", index, source);
   18200 	}
   18201 	else
   18202 	{
   18203 		switch (stage)
   18204 		{
   18205 		case Utils::Shader::FRAGMENT:
   18206 			source = fs;
   18207 			break;
   18208 		case Utils::Shader::GEOMETRY:
   18209 			source = gs;
   18210 			break;
   18211 		case Utils::Shader::TESS_CTRL:
   18212 			source = tcs;
   18213 			break;
   18214 		case Utils::Shader::TESS_EVAL:
   18215 			source = tes;
   18216 			break;
   18217 		case Utils::Shader::VERTEX:
   18218 			source = vs;
   18219 			break;
   18220 		default:
   18221 			TCU_FAIL("Invalid enum");
   18222 		}
   18223 	}
   18224 
   18225 	return source;
   18226 }
   18227 
   18228 /** Get description of test case
   18229  *
   18230  * @param test_case_index Index of test case
   18231  *
   18232  * @return Test case description
   18233  **/
   18234 std::string VaryingLocationAliasingWithMixedInterpolationTest::getTestCaseName(GLuint test_case_index)
   18235 {
   18236 	std::stringstream stream;
   18237 	testCase&		  test_case = m_test_cases[test_case_index];
   18238 
   18239 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage) << ", "
   18240 		   << getInterpolationQualifier(test_case.m_interpolation_gohan) << " "
   18241 		   << test_case.m_type_gohan.GetGLSLTypeName() << " at " << test_case.m_component_gohan << ", "
   18242 		   << getInterpolationQualifier(test_case.m_interpolation_goten) << " "
   18243 		   << test_case.m_type_goten.GetGLSLTypeName() << " at " << test_case.m_component_goten << ". Direction: ";
   18244 
   18245 	if (true == test_case.m_is_input)
   18246 	{
   18247 		stream << "input";
   18248 	}
   18249 	else
   18250 	{
   18251 		stream << "output";
   18252 	}
   18253 
   18254 	return stream.str();
   18255 }
   18256 
   18257 /** Get number of test cases
   18258  *
   18259  * @return Number of test cases
   18260  **/
   18261 GLuint VaryingLocationAliasingWithMixedInterpolationTest::getTestCaseNumber()
   18262 {
   18263 	return static_cast<GLuint>(m_test_cases.size());
   18264 }
   18265 
   18266 /** Selects if "compute" stage is relevant for test
   18267  *
   18268  * @param ignored
   18269  *
   18270  * @return false
   18271  **/
   18272 bool VaryingLocationAliasingWithMixedInterpolationTest::isComputeRelevant(GLuint /* test_case_index */)
   18273 {
   18274 	return false;
   18275 }
   18276 
   18277 /** Prepare all test cases
   18278  *
   18279  **/
   18280 void VaryingLocationAliasingWithMixedInterpolationTest::testInit()
   18281 {
   18282 	static const GLuint n_components_per_location = 4;
   18283 	const GLuint		n_types					  = getTypesNumber();
   18284 
   18285 	for (GLuint i = 0; i < n_types; ++i)
   18286 	{
   18287 		const Utils::Type& type_gohan		   = getType(i);
   18288 		const bool		   is_float_type_gohan = isFloatType(type_gohan);
   18289 
   18290 		/* Skip matrices */
   18291 		if (1 != type_gohan.m_n_columns)
   18292 		{
   18293 			continue;
   18294 		}
   18295 
   18296 		for (GLuint j = 0; j < n_types; ++j)
   18297 		{
   18298 			const Utils::Type& type_goten		   = getType(j);
   18299 			const bool		   is_float_type_goten = isFloatType(type_goten);
   18300 
   18301 			/* Skip matrices */
   18302 			if (1 != type_goten.m_n_columns)
   18303 			{
   18304 				continue;
   18305 			}
   18306 
   18307 			/* Skip invalid combinations */
   18308 			if (is_float_type_gohan != is_float_type_goten)
   18309 			{
   18310 				continue;
   18311 			}
   18312 
   18313 			const GLuint n_req_components_gohan = type_gohan.m_n_rows;
   18314 			const GLuint n_req_components_goten = type_goten.m_n_rows;
   18315 
   18316 			/* Skip pairs that cannot fit into one location */
   18317 			if (n_components_per_location < (n_req_components_gohan + n_req_components_goten))
   18318 			{
   18319 				continue;
   18320 			}
   18321 
   18322 			for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   18323 			{
   18324 				/* Skip compute shader */
   18325 				if (Utils::Shader::COMPUTE == stage)
   18326 				{
   18327 					continue;
   18328 				}
   18329 
   18330 				const GLuint gohan = 0;
   18331 				const GLuint goten = gohan + n_req_components_gohan;
   18332 
   18333 				for (GLuint int_gohan = 0; int_gohan < INTERPOLATION_MAX; ++int_gohan)
   18334 				{
   18335 					for (GLuint int_goten = 0; int_goten < INTERPOLATION_MAX; ++int_goten)
   18336 					{
   18337 						const bool is_gohan_double = (Utils::Type::Double == type_gohan.m_basic_type) ? true : false;
   18338 						const bool is_goten_double = (Utils::Type::Double == type_goten.m_basic_type) ? true : false;
   18339 						const bool is_gohan_flat   = (FLAT == int_gohan) ? true : false;
   18340 						const bool is_goten_flat   = (FLAT == int_goten) ? true : false;
   18341 						const bool is_gohan_accepted_as_fs_in =
   18342 							(is_gohan_double && is_gohan_flat) || (!is_gohan_double);
   18343 						const bool is_goten_accepted_as_fs_in =
   18344 							(is_goten_double && is_goten_flat) || (!is_goten_double);
   18345 						const bool is_comb_accepted_as_fs_in = is_gohan_accepted_as_fs_in && is_goten_accepted_as_fs_in;
   18346 
   18347 						/* Skip when both are the same */
   18348 						if (int_gohan == int_goten)
   18349 						{
   18350 							continue;
   18351 						}
   18352 
   18353 						testCase test_case_in = { gohan,
   18354 												  goten,
   18355 												  (INTERPOLATIONS)int_gohan,
   18356 												  (INTERPOLATIONS)int_goten,
   18357 												  true,
   18358 												  (Utils::Shader::STAGES)stage,
   18359 												  type_gohan,
   18360 												  type_goten };
   18361 
   18362 						testCase test_case_out = { gohan,
   18363 												   goten,
   18364 												   (INTERPOLATIONS)int_gohan,
   18365 												   (INTERPOLATIONS)int_goten,
   18366 												   false,
   18367 												   (Utils::Shader::STAGES)stage,
   18368 												   type_gohan,
   18369 												   type_goten };
   18370 
   18371 						/* Skip inputs in:
   18372 						 * vertex shader,
   18373 						 * fragment shader when not flat double is used
   18374 						 */
   18375 						if ((Utils::Shader::VERTEX != stage) &&
   18376 							((Utils::Shader::FRAGMENT != stage) || (true == is_comb_accepted_as_fs_in)))
   18377 						{
   18378 							m_test_cases.push_back(test_case_in);
   18379 						}
   18380 
   18381 						/* Skip outputs in fragment shader */
   18382 						if (Utils::Shader::FRAGMENT != stage)
   18383 						{
   18384 							m_test_cases.push_back(test_case_out);
   18385 						}
   18386 					}
   18387 				}
   18388 			}
   18389 		}
   18390 	}
   18391 }
   18392 
   18393 /** Get interpolation qualifier
   18394  *
   18395  * @param interpolation Enumeration
   18396  *
   18397  * @return GLSL qualifier
   18398  **/
   18399 const GLchar* VaryingLocationAliasingWithMixedInterpolationTest::getInterpolationQualifier(INTERPOLATIONS interpolation)
   18400 {
   18401 	const GLchar* result = 0;
   18402 
   18403 	switch (interpolation)
   18404 	{
   18405 	case SMOOTH:
   18406 		result = "smooth";
   18407 		break;
   18408 	case FLAT:
   18409 		result = "flat";
   18410 		break;
   18411 	case NO_PERSPECTIVE:
   18412 		result = "noperspective";
   18413 		break;
   18414 	default:
   18415 		TCU_FAIL("Invalid enum");
   18416 	}
   18417 
   18418 	return result;
   18419 }
   18420 
   18421 /** Check if given type is float
   18422  *
   18423  * @param type Type in question
   18424  *
   18425  * @return true if tpye is float, false otherwise
   18426  **/
   18427 bool VaryingLocationAliasingWithMixedInterpolationTest::isFloatType(const Utils::Type& type)
   18428 {
   18429 	bool is_float = false;
   18430 
   18431 	if ((Utils::Type::Double == type.m_basic_type) || (Utils::Type::Float == type.m_basic_type))
   18432 	{
   18433 		is_float = true;
   18434 	}
   18435 
   18436 	return is_float;
   18437 }
   18438 
   18439 /** Constructor
   18440  *
   18441  * @param context Test framework context
   18442  **/
   18443 VaryingLocationAliasingWithMixedAuxiliaryStorageTest::VaryingLocationAliasingWithMixedAuxiliaryStorageTest(
   18444 	deqp::Context& context)
   18445 	: NegativeTestBase(
   18446 		  context, "varying_location_aliasing_with_mixed_auxiliary_storage",
   18447 		  "Test verifies that compiler reports error when auxiliary storage qualifiers are mixed at one location")
   18448 {
   18449 }
   18450 
   18451 /** Source for given test case and stage
   18452  *
   18453  * @param test_case_index Index of test case
   18454  * @param stage           Shader stage
   18455  *
   18456  * @return Shader source
   18457  **/
   18458 std::string VaryingLocationAliasingWithMixedAuxiliaryStorageTest::getShaderSource(GLuint				test_case_index,
   18459 																				  Utils::Shader::STAGES stage)
   18460 {
   18461 	static const GLchar* var_definition =
   18462 		"layout (location = 1, component = COMPONENT) AUX INTERPOLATION DIRECTION TYPE gohanARRAY;\n"
   18463 		"layout (location = 1, component = COMPONENT) AUX INTERPOLATION DIRECTION TYPE gotenARRAY;\n";
   18464 	static const GLchar* input_use = "    if ((TYPE(0) == gohanINDEX_GOHAN) &&\n"
   18465 									 "        (TYPE(1) == gotenINDEX_GOTEN) )\n"
   18466 									 "    {\n"
   18467 									 "        result += vec4(1, 0.5, 0.25, 0.125);\n"
   18468 									 "    }\n";
   18469 	static const GLchar* output_use = "    gohanINDEX_GOHAN = TYPE(0);\n"
   18470 									  "    gotenINDEX_GOTEN = TYPE(1);\n"
   18471 									  "    if (vec4(0) == result)\n"
   18472 									  "    {\n"
   18473 									  "        gohanINDEX_GOHAN = TYPE(1);\n"
   18474 									  "        gotenINDEX_GOTEN = TYPE(0);\n"
   18475 									  "    }\n";
   18476 	static const GLchar* fs = "#version 430 core\n"
   18477 							  "#extension GL_ARB_enhanced_layouts : require\n"
   18478 							  "\n"
   18479 							  "in  vec4 gs_fs;\n"
   18480 							  "out vec4 fs_out;\n"
   18481 							  "\n"
   18482 							  "void main()\n"
   18483 							  "{\n"
   18484 							  "    fs_out = gs_fs;\n"
   18485 							  "}\n"
   18486 							  "\n";
   18487 	static const GLchar* fs_tested = "#version 430 core\n"
   18488 									 "#extension GL_ARB_enhanced_layouts : require\n"
   18489 									 "\n"
   18490 									 "VAR_DEFINITION"
   18491 									 "\n"
   18492 									 "in  vec4 gs_fs;\n"
   18493 									 "out vec4 fs_out;\n"
   18494 									 "\n"
   18495 									 "void main()\n"
   18496 									 "{\n"
   18497 									 "    vec4 result = gs_fs;\n"
   18498 									 "\n"
   18499 									 "VARIABLE_USE"
   18500 									 "\n"
   18501 									 "    fs_out = result;\n"
   18502 									 "}\n"
   18503 									 "\n";
   18504 	static const GLchar* gs = "#version 430 core\n"
   18505 							  "#extension GL_ARB_enhanced_layouts : require\n"
   18506 							  "\n"
   18507 							  "layout(points)                           in;\n"
   18508 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   18509 							  "\n"
   18510 							  "in  vec4 tes_gs[];\n"
   18511 							  "out vec4 gs_fs;\n"
   18512 							  "\n"
   18513 							  "void main()\n"
   18514 							  "{\n"
   18515 							  "    gs_fs = tes_gs[0];\n"
   18516 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   18517 							  "    EmitVertex();\n"
   18518 							  "    gs_fs = tes_gs[0];\n"
   18519 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   18520 							  "    EmitVertex();\n"
   18521 							  "    gs_fs = tes_gs[0];\n"
   18522 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   18523 							  "    EmitVertex();\n"
   18524 							  "    gs_fs = tes_gs[0];\n"
   18525 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   18526 							  "    EmitVertex();\n"
   18527 							  "}\n"
   18528 							  "\n";
   18529 	static const GLchar* gs_tested = "#version 430 core\n"
   18530 									 "#extension GL_ARB_enhanced_layouts : require\n"
   18531 									 "\n"
   18532 									 "layout(points)                           in;\n"
   18533 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   18534 									 "\n"
   18535 									 "VAR_DEFINITION"
   18536 									 "\n"
   18537 									 "in  vec4 tes_gs[];\n"
   18538 									 "out vec4 gs_fs;\n"
   18539 									 "\n"
   18540 									 "void main()\n"
   18541 									 "{\n"
   18542 									 "    vec4 result = tes_gs[0];\n"
   18543 									 "\n"
   18544 									 "VARIABLE_USE"
   18545 									 "\n"
   18546 									 "    gs_fs = result;\n"
   18547 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   18548 									 "    EmitVertex();\n"
   18549 									 "    gs_fs = result;\n"
   18550 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   18551 									 "    EmitVertex();\n"
   18552 									 "    gs_fs = result;\n"
   18553 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   18554 									 "    EmitVertex();\n"
   18555 									 "    gs_fs = result;\n"
   18556 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   18557 									 "    EmitVertex();\n"
   18558 									 "}\n"
   18559 									 "\n";
   18560 	static const GLchar* tcs = "#version 430 core\n"
   18561 							   "#extension GL_ARB_enhanced_layouts : require\n"
   18562 							   "\n"
   18563 							   "layout(vertices = 1) out;\n"
   18564 							   "\n"
   18565 							   "in  vec4 vs_tcs[];\n"
   18566 							   "out vec4 tcs_tes[];\n"
   18567 							   "\n"
   18568 							   "void main()\n"
   18569 							   "{\n"
   18570 							   "\n"
   18571 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   18572 							   "\n"
   18573 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   18574 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   18575 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   18576 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   18577 							   "    gl_TessLevelInner[0] = 1.0;\n"
   18578 							   "    gl_TessLevelInner[1] = 1.0;\n"
   18579 							   "}\n"
   18580 							   "\n";
   18581 	static const GLchar* tcs_tested = "#version 430 core\n"
   18582 									  "#extension GL_ARB_enhanced_layouts : require\n"
   18583 									  "\n"
   18584 									  "layout(vertices = 1) out;\n"
   18585 									  "\n"
   18586 									  "VAR_DEFINITION"
   18587 									  "\n"
   18588 									  "in  vec4 vs_tcs[];\n"
   18589 									  "out vec4 tcs_tes[];\n"
   18590 									  "\n"
   18591 									  "void main()\n"
   18592 									  "{\n"
   18593 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   18594 									  "\n"
   18595 									  "VARIABLE_USE"
   18596 									  "\n"
   18597 									  "    tcs_tes[gl_InvocationID] = result;\n"
   18598 									  "\n"
   18599 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   18600 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   18601 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   18602 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   18603 									  "    gl_TessLevelInner[0] = 1.0;\n"
   18604 									  "    gl_TessLevelInner[1] = 1.0;\n"
   18605 									  "}\n"
   18606 									  "\n";
   18607 	static const GLchar* tes = "#version 430 core\n"
   18608 							   "#extension GL_ARB_enhanced_layouts : require\n"
   18609 							   "\n"
   18610 							   "layout(isolines, point_mode) in;\n"
   18611 							   "\n"
   18612 							   "in  vec4 tcs_tes[];\n"
   18613 							   "out vec4 tes_gs;\n"
   18614 							   "\n"
   18615 							   "void main()\n"
   18616 							   "{\n"
   18617 							   "    tes_gs = tcs_tes[0];\n"
   18618 							   "}\n"
   18619 							   "\n";
   18620 	static const GLchar* tes_tested = "#version 430 core\n"
   18621 									  "#extension GL_ARB_enhanced_layouts : require\n"
   18622 									  "\n"
   18623 									  "layout(isolines, point_mode) in;\n"
   18624 									  "\n"
   18625 									  "VAR_DEFINITION"
   18626 									  "\n"
   18627 									  "in  vec4 tcs_tes[];\n"
   18628 									  "out vec4 tes_gs;\n"
   18629 									  "\n"
   18630 									  "void main()\n"
   18631 									  "{\n"
   18632 									  "    vec4 result = tcs_tes[0];\n"
   18633 									  "\n"
   18634 									  "VARIABLE_USE"
   18635 									  "\n"
   18636 									  "    tes_gs += result;\n"
   18637 									  "}\n"
   18638 									  "\n";
   18639 	static const GLchar* vs = "#version 430 core\n"
   18640 							  "#extension GL_ARB_enhanced_layouts : require\n"
   18641 							  "\n"
   18642 							  "in  vec4 in_vs;\n"
   18643 							  "out vec4 vs_tcs;\n"
   18644 							  "\n"
   18645 							  "void main()\n"
   18646 							  "{\n"
   18647 							  "    vs_tcs = in_vs;\n"
   18648 							  "}\n"
   18649 							  "\n";
   18650 	static const GLchar* vs_tested = "#version 430 core\n"
   18651 									 "#extension GL_ARB_enhanced_layouts : require\n"
   18652 									 "\n"
   18653 									 "VAR_DEFINITION"
   18654 									 "\n"
   18655 									 "in  vec4 in_vs;\n"
   18656 									 "out vec4 vs_tcs;\n"
   18657 									 "\n"
   18658 									 "void main()\n"
   18659 									 "{\n"
   18660 									 "    vec4 result = in_vs;\n"
   18661 									 "\n"
   18662 									 "VARIABLE_USE"
   18663 									 "\n"
   18664 									 "    vs_tcs += result;\n"
   18665 									 "}\n"
   18666 									 "\n";
   18667 
   18668 	std::string source;
   18669 	testCase&   test_case = m_test_cases[test_case_index];
   18670 
   18671 	if (test_case.m_stage == stage)
   18672 	{
   18673 		const GLchar* array_gohan = "";
   18674 		const GLchar* array_goten = "";
   18675 		const GLchar* aux_gohan   = getAuxiliaryQualifier(test_case.m_aux_gohan);
   18676 		const GLchar* aux_goten   = getAuxiliaryQualifier(test_case.m_aux_goten);
   18677 		GLchar		  buffer_gohan[16];
   18678 		GLchar		  buffer_goten[16];
   18679 		const GLchar* direction   = "in ";
   18680 		const GLchar* index_gohan = "";
   18681 		const GLchar* index_goten = "";
   18682 		const GLchar* int_gohan   = test_case.m_int_gohan;
   18683 		const GLchar* int_goten   = test_case.m_int_goten;
   18684 		size_t		  position	= 0;
   18685 		size_t		  temp;
   18686 		const GLchar* type_gohan_name = test_case.m_type_gohan.GetGLSLTypeName();
   18687 		const GLchar* type_goten_name = test_case.m_type_goten.GetGLSLTypeName();
   18688 		const GLchar* var_use		  = input_use;
   18689 
   18690 		if (false == test_case.m_is_input)
   18691 		{
   18692 			direction = "out";
   18693 
   18694 			var_use = output_use;
   18695 		}
   18696 
   18697 		sprintf(buffer_gohan, "%d", test_case.m_component_gohan);
   18698 		sprintf(buffer_goten, "%d", test_case.m_component_goten);
   18699 
   18700 		switch (stage)
   18701 		{
   18702 		case Utils::Shader::FRAGMENT:
   18703 			source = fs_tested;
   18704 			break;
   18705 		case Utils::Shader::GEOMETRY:
   18706 			source		= gs_tested;
   18707 			array_gohan = "[]";
   18708 			index_gohan = "[0]";
   18709 			array_goten = "[]";
   18710 			index_goten = "[0]";
   18711 			break;
   18712 		case Utils::Shader::TESS_CTRL:
   18713 			source = tcs_tested;
   18714 			if (PATCH != test_case.m_aux_gohan)
   18715 			{
   18716 				array_gohan = "[]";
   18717 				index_gohan = "[gl_InvocationID]";
   18718 			}
   18719 			if (PATCH != test_case.m_aux_goten)
   18720 			{
   18721 				array_goten = "[]";
   18722 				index_goten = "[gl_InvocationID]";
   18723 			}
   18724 			break;
   18725 		case Utils::Shader::TESS_EVAL:
   18726 			source		= tes_tested;
   18727 			array_gohan = "[]";
   18728 			index_gohan = "[0]";
   18729 			array_goten = "[]";
   18730 			index_goten = "[0]";
   18731 			break;
   18732 		case Utils::Shader::VERTEX:
   18733 			source = vs_tested;
   18734 			break;
   18735 		default:
   18736 			TCU_FAIL("Invalid enum");
   18737 		}
   18738 
   18739 		temp = position;
   18740 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   18741 		position = temp;
   18742 		Utils::replaceToken("COMPONENT", position, buffer_gohan, source);
   18743 		Utils::replaceToken("AUX", position, aux_gohan, source);
   18744 		Utils::replaceToken("INTERPOLATION", position, int_gohan, source);
   18745 		Utils::replaceToken("DIRECTION", position, direction, source);
   18746 		Utils::replaceToken("TYPE", position, type_gohan_name, source);
   18747 		Utils::replaceToken("ARRAY", position, array_gohan, source);
   18748 		Utils::replaceToken("COMPONENT", position, buffer_goten, source);
   18749 		Utils::replaceToken("AUX", position, aux_goten, source);
   18750 		Utils::replaceToken("INTERPOLATION", position, int_goten, source);
   18751 		Utils::replaceToken("DIRECTION", position, direction, source);
   18752 		Utils::replaceToken("TYPE", position, type_goten_name, source);
   18753 		Utils::replaceToken("ARRAY", position, array_goten, source);
   18754 
   18755 		temp = position;
   18756 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   18757 		position = temp;
   18758 		if (true == test_case.m_is_input)
   18759 		{
   18760 			Utils::replaceToken("TYPE", position, type_gohan_name, source);
   18761 			Utils::replaceToken("TYPE", position, type_goten_name, source);
   18762 		}
   18763 		else
   18764 		{
   18765 			Utils::replaceToken("TYPE", position, type_gohan_name, source);
   18766 			Utils::replaceToken("TYPE", position, type_goten_name, source);
   18767 			Utils::replaceToken("TYPE", position, type_gohan_name, source);
   18768 			Utils::replaceToken("TYPE", position, type_goten_name, source);
   18769 		}
   18770 
   18771 		Utils::replaceAllTokens("INDEX_GOHAN", index_gohan, source);
   18772 		Utils::replaceAllTokens("INDEX_GOTEN", index_goten, source);
   18773 	}
   18774 	else
   18775 	{
   18776 		switch (stage)
   18777 		{
   18778 		case Utils::Shader::FRAGMENT:
   18779 			source = fs;
   18780 			break;
   18781 		case Utils::Shader::GEOMETRY:
   18782 			source = gs;
   18783 			break;
   18784 		case Utils::Shader::TESS_CTRL:
   18785 			source = tcs;
   18786 			break;
   18787 		case Utils::Shader::TESS_EVAL:
   18788 			source = tes;
   18789 			break;
   18790 		case Utils::Shader::VERTEX:
   18791 			source = vs;
   18792 			break;
   18793 		default:
   18794 			TCU_FAIL("Invalid enum");
   18795 		}
   18796 	}
   18797 
   18798 	return source;
   18799 }
   18800 
   18801 /** Get description of test case
   18802  *
   18803  * @param test_case_index Index of test case
   18804  *
   18805  * @return Test case description
   18806  **/
   18807 std::string VaryingLocationAliasingWithMixedAuxiliaryStorageTest::getTestCaseName(GLuint test_case_index)
   18808 {
   18809 	std::stringstream stream;
   18810 	testCase&		  test_case = m_test_cases[test_case_index];
   18811 
   18812 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage) << ", "
   18813 		   << getAuxiliaryQualifier(test_case.m_aux_gohan) << " " << test_case.m_type_gohan.GetGLSLTypeName() << " at "
   18814 		   << test_case.m_component_gohan << ", " << getAuxiliaryQualifier(test_case.m_aux_goten) << " "
   18815 		   << test_case.m_type_goten.GetGLSLTypeName() << " at " << test_case.m_component_goten << ". Direction: ";
   18816 
   18817 	if (true == test_case.m_is_input)
   18818 	{
   18819 		stream << "input";
   18820 	}
   18821 	else
   18822 	{
   18823 		stream << "output";
   18824 	}
   18825 
   18826 	return stream.str();
   18827 }
   18828 
   18829 /** Get number of test cases
   18830  *
   18831  * @return Number of test cases
   18832  **/
   18833 GLuint VaryingLocationAliasingWithMixedAuxiliaryStorageTest::getTestCaseNumber()
   18834 {
   18835 	return static_cast<GLuint>(m_test_cases.size());
   18836 }
   18837 
   18838 /** Selects if "compute" stage is relevant for test
   18839  *
   18840  * @param ignored
   18841  *
   18842  * @return false
   18843  **/
   18844 bool VaryingLocationAliasingWithMixedAuxiliaryStorageTest::isComputeRelevant(GLuint /* test_case_index */)
   18845 {
   18846 	return false;
   18847 }
   18848 
   18849 /** Prepare all test cases
   18850  *
   18851  **/
   18852 void VaryingLocationAliasingWithMixedAuxiliaryStorageTest::testInit()
   18853 {
   18854 	static const GLuint n_components_per_location = 4;
   18855 	const GLuint		n_types					  = getTypesNumber();
   18856 
   18857 	for (GLuint i = 0; i < n_types; ++i)
   18858 	{
   18859 		const Utils::Type& type_gohan		   = getType(i);
   18860 		const bool		   is_float_type_gohan = isFloatType(type_gohan);
   18861 
   18862 		/* Skip matrices */
   18863 		if (1 != type_gohan.m_n_columns)
   18864 		{
   18865 			continue;
   18866 		}
   18867 
   18868 		for (GLuint j = 0; j < n_types; ++j)
   18869 		{
   18870 			const Utils::Type& type_goten		   = getType(j);
   18871 			const bool		   is_flat_req_gohan   = (Utils::Type::Float == type_gohan.m_basic_type) ? false : true;
   18872 			const bool		   is_flat_req_goten   = (Utils::Type::Float == type_goten.m_basic_type) ? false : true;
   18873 			const bool		   is_float_type_goten = isFloatType(type_goten);
   18874 
   18875 			/* Skip matrices */
   18876 			if (1 != type_goten.m_n_columns)
   18877 			{
   18878 				continue;
   18879 			}
   18880 
   18881 			/* Skip invalid combinations */
   18882 			if (is_float_type_gohan != is_float_type_goten)
   18883 			{
   18884 				continue;
   18885 			}
   18886 
   18887 			const GLuint n_req_components_gohan = type_gohan.m_n_rows;
   18888 			const GLuint n_req_components_goten = type_goten.m_n_rows;
   18889 
   18890 			/* Skip pairs that cannot fit into one location */
   18891 			if (n_components_per_location < (n_req_components_gohan + n_req_components_goten))
   18892 			{
   18893 				continue;
   18894 			}
   18895 
   18896 			const GLuint gohan = 0;
   18897 			const GLuint goten = gohan + n_req_components_gohan;
   18898 
   18899 			const GLchar* fs_int_gohan = is_flat_req_gohan ? "flat" : "";
   18900 			const GLchar* fs_int_goten = is_flat_req_goten ? "flat" : "";
   18901 
   18902 			testCase test_case_tcs_np = { gohan,	  goten,	 NONE, PATCH, "", "", false, Utils::Shader::TESS_CTRL,
   18903 										  type_gohan, type_goten };
   18904 
   18905 			testCase test_case_tcs_pn = { gohan,	  goten,	 PATCH, NONE, "", "", false, Utils::Shader::TESS_CTRL,
   18906 										  type_gohan, type_goten };
   18907 
   18908 			testCase test_case_tes_np = { gohan,	  goten,	 NONE, PATCH, "", "", true, Utils::Shader::TESS_EVAL,
   18909 										  type_gohan, type_goten };
   18910 
   18911 			testCase test_case_tes_pn = { gohan,	  goten,	 PATCH, NONE, "", "", true, Utils::Shader::TESS_EVAL,
   18912 										  type_gohan, type_goten };
   18913 
   18914 			testCase test_case_fs_nc = { gohan,		   goten,		 NONE, CENTROID,
   18915 										 fs_int_gohan, fs_int_goten, true, Utils::Shader::FRAGMENT,
   18916 										 type_gohan,   type_goten };
   18917 
   18918 			testCase test_case_fs_cn = { gohan,		   goten,		 CENTROID, NONE,
   18919 										 fs_int_gohan, fs_int_goten, true,	 Utils::Shader::FRAGMENT,
   18920 										 type_gohan,   type_goten };
   18921 
   18922 			testCase test_case_fs_ns = { gohan,		   goten,		 NONE, SAMPLE,
   18923 										 fs_int_gohan, fs_int_goten, true, Utils::Shader::FRAGMENT,
   18924 										 type_gohan,   type_goten };
   18925 
   18926 			testCase test_case_fs_sn = { gohan,		   goten,		 SAMPLE, NONE,
   18927 										 fs_int_gohan, fs_int_goten, true,   Utils::Shader::FRAGMENT,
   18928 										 type_gohan,   type_goten };
   18929 
   18930 			testCase test_case_fs_cs = { gohan,		   goten,		 CENTROID, SAMPLE,
   18931 										 fs_int_gohan, fs_int_goten, true,	 Utils::Shader::FRAGMENT,
   18932 										 type_gohan,   type_goten };
   18933 
   18934 			testCase test_case_fs_sc = { gohan,		   goten,		 SAMPLE, CENTROID,
   18935 										 fs_int_gohan, fs_int_goten, true,   Utils::Shader::FRAGMENT,
   18936 										 type_gohan,   type_goten };
   18937 
   18938 			m_test_cases.push_back(test_case_tcs_np);
   18939 			m_test_cases.push_back(test_case_tcs_pn);
   18940 			m_test_cases.push_back(test_case_tes_np);
   18941 			m_test_cases.push_back(test_case_tes_pn);
   18942 			m_test_cases.push_back(test_case_fs_nc);
   18943 			m_test_cases.push_back(test_case_fs_cn);
   18944 			m_test_cases.push_back(test_case_fs_ns);
   18945 			m_test_cases.push_back(test_case_fs_sn);
   18946 			m_test_cases.push_back(test_case_fs_cs);
   18947 			m_test_cases.push_back(test_case_fs_sc);
   18948 		}
   18949 	}
   18950 }
   18951 
   18952 /** Get auxiliary storage qualifier
   18953  *
   18954  * @param aux Enumeration
   18955  *
   18956  * @return GLSL qualifier
   18957  **/
   18958 const GLchar* VaryingLocationAliasingWithMixedAuxiliaryStorageTest::getAuxiliaryQualifier(AUXILIARIES aux)
   18959 {
   18960 	const GLchar* result = 0;
   18961 
   18962 	switch (aux)
   18963 	{
   18964 	case NONE:
   18965 		result = "";
   18966 		break;
   18967 	case PATCH:
   18968 		result = "patch";
   18969 		break;
   18970 	case CENTROID:
   18971 		result = "centroid";
   18972 		break;
   18973 	case SAMPLE:
   18974 		result = "sample";
   18975 		break;
   18976 	default:
   18977 		TCU_FAIL("Invalid enum");
   18978 	}
   18979 
   18980 	return result;
   18981 }
   18982 
   18983 /** Check if given type is float
   18984  *
   18985  * @param type Type in question
   18986  *
   18987  * @return true if tpye is float, false otherwise
   18988  **/
   18989 bool VaryingLocationAliasingWithMixedAuxiliaryStorageTest::isFloatType(const Utils::Type& type)
   18990 {
   18991 	bool is_float = false;
   18992 
   18993 	if ((Utils::Type::Double == type.m_basic_type) || (Utils::Type::Float == type.m_basic_type))
   18994 	{
   18995 		is_float = true;
   18996 	}
   18997 
   18998 	return is_float;
   18999 }
   19000 
   19001 /* Constants used by VertexAttribLocationAPITest */
   19002 const GLuint VertexAttribLocationAPITest::m_goten_location = 6;
   19003 
   19004 /** Constructor
   19005  *
   19006  * @param context Test framework context
   19007  **/
   19008 VertexAttribLocationAPITest::VertexAttribLocationAPITest(deqp::Context& context)
   19009 	: TextureTestBase(context, "vertex_attrib_location_api",
   19010 					  "Test verifies that attribute locations API works as expected")
   19011 {
   19012 }
   19013 
   19014 /** Does BindAttribLocation for "goten" and relink program
   19015  *
   19016  * @param program           Program object
   19017  * @param program_interface Interface of program
   19018  **/
   19019 void VertexAttribLocationAPITest::prepareAttribLocation(Utils::Program&			 program,
   19020 														Utils::ProgramInterface& program_interface)
   19021 {
   19022 	const Functions& gl = m_context.getRenderContext().getFunctions();
   19023 
   19024 	gl.bindAttribLocation(program.m_id, m_goten_location, "goten");
   19025 	GLU_EXPECT_NO_ERROR(gl.getError(), "BindAttribLocation");
   19026 
   19027 	program.Link(gl, program.m_id);
   19028 
   19029 	/* We still need to get locations for gohan and chichi */
   19030 	TextureTestBase::prepareAttribLocation(program, program_interface);
   19031 }
   19032 
   19033 /** Get interface of program
   19034  *
   19035  * @param ignored
   19036  * @param program_interface   Interface of program
   19037  * @param ignored
   19038  **/
   19039 void VertexAttribLocationAPITest::getProgramInterface(GLuint /* test_case_index */,
   19040 													  Utils::ProgramInterface& program_interface,
   19041 													  Utils::VaryingPassthrough& /* varying_passthrough */)
   19042 {
   19043 	Utils::ShaderInterface& si		  = program_interface.GetShaderInterface(Utils::Shader::VERTEX);
   19044 	const Utils::Type&		type	  = Utils::Type::vec4;
   19045 	const GLuint			type_size = type.GetSize();
   19046 
   19047 	/* Offsets */
   19048 	const GLuint chichi_offset = 0;
   19049 	const GLuint goten_offset  = chichi_offset + type_size;
   19050 	const GLuint gohan_offset  = goten_offset + type_size;
   19051 	const GLuint goku_offset   = gohan_offset + type_size;
   19052 
   19053 	/* Locations */
   19054 	const GLuint goku_location  = 2;
   19055 	const GLuint goten_location = m_goten_location;
   19056 
   19057 	/* Generate data */
   19058 	m_goku_data   = type.GenerateDataPacked();
   19059 	m_gohan_data  = type.GenerateDataPacked();
   19060 	m_goten_data  = type.GenerateDataPacked();
   19061 	m_chichi_data = type.GenerateDataPacked();
   19062 
   19063 	/* Globals */
   19064 	si.m_globals = "const uint GOKU_LOCATION = 2;\n";
   19065 
   19066 	/* Attributes */
   19067 	si.Input("goku" /* name */, "layout (location = GOKU_LOCATION)" /* qualifiers */, 0 /* expected_componenet */,
   19068 			 goku_location /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   19069 			 0u /* n_array_elements */, 0u /* stride */, goku_offset /* offset */, (GLvoid*)&m_goku_data[0] /* data */,
   19070 			 m_goku_data.size() /* data_size */);
   19071 
   19072 	si.Input("gohan" /* name */, "" /* qualifiers */, 0 /* expected_componenet */,
   19073 			 Utils::Variable::m_automatic_location /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   19074 			 0u /* n_array_elements */, 0u /* stride */, gohan_offset /* offset */,
   19075 			 (GLvoid*)&m_gohan_data[0] /* data */, m_gohan_data.size() /* data_size */);
   19076 
   19077 	si.Input("goten" /* name */, "" /* qualifiers */, 0 /* expected_componenet */,
   19078 			 goten_location /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   19079 			 0u /* n_array_elements */, 0u /* stride */, goten_offset /* offset */,
   19080 			 (GLvoid*)&m_goten_data[0] /* data */, m_goten_data.size() /* data_size */);
   19081 
   19082 	si.Input("chichi" /* name */, "" /* qualifiers */, 0 /* expected_componenet */,
   19083 			 Utils::Variable::m_automatic_location /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   19084 			 0u /* n_array_elements */, 0u /* stride */, chichi_offset /* offset */,
   19085 			 (GLvoid*)&m_chichi_data[0] /* data */, m_chichi_data.size() /* data_size */);
   19086 }
   19087 
   19088 /** Selects if "compute" stage is relevant for test
   19089  *
   19090  * @param ignored
   19091  *
   19092  * @return false
   19093  **/
   19094 bool VertexAttribLocationAPITest::isComputeRelevant(GLuint /* test_case_index */)
   19095 {
   19096 	return false;
   19097 }
   19098 
   19099 /* Constants used by FragmentDataLocationAPITest */
   19100 const GLuint FragmentDataLocationAPITest::m_goten_location = 6;
   19101 
   19102 /** Constructor
   19103  *
   19104  * @param context Test framework context
   19105  **/
   19106 FragmentDataLocationAPITest::FragmentDataLocationAPITest(deqp::Context& context)
   19107 	: TextureTestBase(context, "fragment_data_location_api",
   19108 					  "Test verifies that fragment data locations API works as expected")
   19109 	, m_goku(context)
   19110 	, m_gohan(context)
   19111 	, m_goten(context)
   19112 	, m_chichi(context)
   19113 {
   19114 }
   19115 
   19116 /** Verifies contents of drawn images
   19117  *
   19118  * @param ignored
   19119  * @param ignored
   19120  *
   19121  * @return true if images are filled with expected values, false otherwise
   19122  **/
   19123 bool FragmentDataLocationAPITest::checkResults(glw::GLuint /* test_case_index */, Utils::Texture& /* color_0 */)
   19124 {
   19125 	static const GLuint size			= m_width * m_height;
   19126 	static const GLuint expected_goku   = 0xff000000;
   19127 	static const GLuint expected_gohan  = 0xff0000ff;
   19128 	static const GLuint expected_goten  = 0xff00ff00;
   19129 	static const GLuint expected_chichi = 0xffff0000;
   19130 
   19131 	std::vector<GLuint> data;
   19132 	data.resize(size);
   19133 
   19134 	m_goku.Get(GL_RGBA, GL_UNSIGNED_BYTE, &data[0]);
   19135 
   19136 	for (GLuint i = 0; i < size; ++i)
   19137 	{
   19138 		const GLuint color = data[i];
   19139 
   19140 		if (expected_goku != color)
   19141 		{
   19142 			m_context.getTestContext().getLog() << tcu::TestLog::Message << "RGBA8[" << i << "]:" << color
   19143 												<< tcu::TestLog::EndMessage;
   19144 			return false;
   19145 		}
   19146 	}
   19147 
   19148 	m_gohan.Get(GL_RGBA, GL_UNSIGNED_BYTE, &data[0]);
   19149 
   19150 	for (GLuint i = 0; i < size; ++i)
   19151 	{
   19152 		const GLuint color = data[i];
   19153 
   19154 		if (expected_gohan != color)
   19155 		{
   19156 			m_context.getTestContext().getLog() << tcu::TestLog::Message << "RGBA8[" << i << "]:" << color
   19157 												<< tcu::TestLog::EndMessage;
   19158 			return false;
   19159 		}
   19160 	}
   19161 
   19162 	m_goten.Get(GL_RGBA, GL_UNSIGNED_BYTE, &data[0]);
   19163 
   19164 	for (GLuint i = 0; i < size; ++i)
   19165 	{
   19166 		const GLuint color = data[i];
   19167 
   19168 		if (expected_goten != color)
   19169 		{
   19170 			m_context.getTestContext().getLog() << tcu::TestLog::Message << "RGBA8[" << i << "]:" << color
   19171 												<< tcu::TestLog::EndMessage;
   19172 			return false;
   19173 		}
   19174 	}
   19175 
   19176 	m_chichi.Get(GL_RGBA, GL_UNSIGNED_BYTE, &data[0]);
   19177 
   19178 	for (GLuint i = 0; i < size; ++i)
   19179 	{
   19180 		const GLuint color = data[i];
   19181 
   19182 		if (expected_chichi != color)
   19183 		{
   19184 			m_context.getTestContext().getLog() << tcu::TestLog::Message << "RGBA8[" << i << "]:" << color
   19185 												<< tcu::TestLog::EndMessage;
   19186 			return false;
   19187 		}
   19188 	}
   19189 
   19190 	return true;
   19191 }
   19192 
   19193 /** Prepare code snippet that will set out variables
   19194  *
   19195  * @param ignored
   19196  * @param ignored
   19197  * @param stage               Shader stage
   19198  *
   19199  * @return Code that pass in variables to next stage
   19200  **/
   19201 std::string FragmentDataLocationAPITest::getPassSnippet(GLuint /* test_case_index */,
   19202 														Utils::VaryingPassthrough& /* varying_passthrough */,
   19203 														Utils::Shader::STAGES stage)
   19204 {
   19205 	std::string result;
   19206 
   19207 	/* Skip for compute shader */
   19208 	if (Utils::Shader::FRAGMENT != stage)
   19209 	{
   19210 		result = "";
   19211 	}
   19212 	else
   19213 	{
   19214 		result = "chichi = vec4(0, 0, 1, 1);\n"
   19215 				 "    goku   = vec4(0, 0, 0, 1);\n"
   19216 				 "    goten  = vec4(0, 1, 0, 1);\n"
   19217 				 "    gohan  = vec4(1, 0, 0, 1);\n";
   19218 	}
   19219 
   19220 	return result;
   19221 }
   19222 
   19223 /** Get interface of program
   19224  *
   19225  * @param ignored
   19226  * @param program_interface Interface of program
   19227  * @param ignored
   19228  **/
   19229 void FragmentDataLocationAPITest::getProgramInterface(GLuint /* test_case_index */,
   19230 													  Utils::ProgramInterface& program_interface,
   19231 													  Utils::VaryingPassthrough& /* varying_passthrough */)
   19232 {
   19233 	Utils::ShaderInterface& si   = program_interface.GetShaderInterface(Utils::Shader::FRAGMENT);
   19234 	const Utils::Type&		type = Utils::Type::vec4;
   19235 
   19236 	/* Locations */
   19237 	m_goku_location = 2;
   19238 
   19239 	/* Globals */
   19240 	si.m_globals = "const uint GOKU_LOCATION = 2;\n";
   19241 
   19242 	/* Attributes */
   19243 	si.Output("goku" /* name */, "layout (location = GOKU_LOCATION)" /* qualifiers */, 0 /* expected_componenet */,
   19244 			  m_goku_location /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   19245 			  0u /* n_array_elements */, 0u /* stride */, 0u /* offset */, (GLvoid*)0 /* data */, 0u /* data_size */);
   19246 
   19247 	si.Output("gohan" /* name */, "" /* qualifiers */, 0 /* expected_componenet */,
   19248 			  Utils::Variable::m_automatic_location /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   19249 			  0u /* n_array_elements */, 0u /* stride */, 0u /* offset */, (GLvoid*)0 /* data */, 0u /* data_size */);
   19250 
   19251 	si.Output("goten" /* name */, "" /* qualifiers */, 0 /* expected_componenet */,
   19252 			  m_goten_location /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   19253 			  0u /* n_array_elements */, 0u /* stride */, 0u /* offset */, (GLvoid*)0 /* data */, 0u /* data_size */);
   19254 
   19255 	si.Output("chichi" /* name */, "" /* qualifiers */, 0 /* expected_componenet */,
   19256 			  Utils::Variable::m_automatic_location /* expected_location */, type /* type */, GL_FALSE /* normalized */,
   19257 			  0u /* n_array_elements */, 0u /* stride */, 0u /* offset */, (GLvoid*)0 /* data */, 0u /* data_size */);
   19258 }
   19259 
   19260 /** Selects if "compute" stage is relevant for test
   19261  *
   19262  * @param ignored
   19263  *
   19264  * @return false
   19265  **/
   19266 bool FragmentDataLocationAPITest::isComputeRelevant(GLuint /* test_case_index */)
   19267 {
   19268 	return false;
   19269 }
   19270 
   19271 /** Get locations for all outputs with automatic_location
   19272  *
   19273  * @param program           Program object
   19274  * @param program_interface Interface of program
   19275  **/
   19276 void FragmentDataLocationAPITest::prepareFragmentDataLoc(Utils::Program&		  program,
   19277 														 Utils::ProgramInterface& program_interface)
   19278 {
   19279 	/* Bind location of goten */
   19280 	const Functions& gl = m_context.getRenderContext().getFunctions();
   19281 
   19282 	gl.bindFragDataLocation(program.m_id, m_goten_location, "goten");
   19283 	GLU_EXPECT_NO_ERROR(gl.getError(), "BindFragDataLocation");
   19284 
   19285 	program.Link(gl, program.m_id);
   19286 
   19287 	/* Prepare locations for gohan and chichi */
   19288 	TextureTestBase::prepareFragmentDataLoc(program, program_interface);
   19289 
   19290 	/* Get all locations */
   19291 	Utils::ShaderInterface& si = program_interface.GetShaderInterface(Utils::Shader::FRAGMENT);
   19292 
   19293 	Utils::Variable::PtrVector& outputs = si.m_outputs;
   19294 
   19295 	for (Utils::Variable::PtrVector::iterator it = outputs.begin(); outputs.end() != it; ++it)
   19296 	{
   19297 		const Utils::Variable::Descriptor& desc = (*it)->m_descriptor;
   19298 
   19299 		if (0 == desc.m_name.compare("gohan"))
   19300 		{
   19301 			m_gohan_location = desc.m_expected_location;
   19302 		}
   19303 		else if (0 == desc.m_name.compare("chichi"))
   19304 		{
   19305 			m_chichi_location = desc.m_expected_location;
   19306 		}
   19307 
   19308 		/* Locations of goku and goten are fixed */
   19309 	}
   19310 }
   19311 
   19312 /** Prepare framebuffer with single texture as color attachment
   19313  *
   19314  * @param framebuffer     Framebuffer
   19315  * @param color_0_texture Texture that will used as color attachment
   19316  **/
   19317 void FragmentDataLocationAPITest::prepareFramebuffer(Utils::Framebuffer& framebuffer, Utils::Texture& color_0_texture)
   19318 {
   19319 	/* Let parent prepare its stuff */
   19320 	TextureTestBase::prepareFramebuffer(framebuffer, color_0_texture);
   19321 
   19322 	/* Prepare data */
   19323 	std::vector<GLuint> texture_data;
   19324 	texture_data.resize(m_width * m_height);
   19325 
   19326 	for (GLuint i = 0; i < texture_data.size(); ++i)
   19327 	{
   19328 		texture_data[i] = 0x20406080;
   19329 	}
   19330 
   19331 	/* Prepare textures */
   19332 	m_goku.Init(Utils::Texture::TEX_2D, m_width, m_height, 0, GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, &texture_data[0]);
   19333 
   19334 	m_gohan.Init(Utils::Texture::TEX_2D, m_width, m_height, 0, GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, &texture_data[0]);
   19335 
   19336 	m_goten.Init(Utils::Texture::TEX_2D, m_width, m_height, 0, GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, &texture_data[0]);
   19337 
   19338 	m_chichi.Init(Utils::Texture::TEX_2D, m_width, m_height, 0, GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, &texture_data[0]);
   19339 
   19340 	/* Attach textures to framebuffer */
   19341 	framebuffer.Bind();
   19342 	framebuffer.AttachTexture(GL_COLOR_ATTACHMENT0 + m_goku_location, m_goku.m_id, m_width, m_height);
   19343 	framebuffer.AttachTexture(GL_COLOR_ATTACHMENT0 + m_gohan_location, m_gohan.m_id, m_width, m_height);
   19344 	framebuffer.AttachTexture(GL_COLOR_ATTACHMENT0 + m_goten_location, m_goten.m_id, m_width, m_height);
   19345 	framebuffer.AttachTexture(GL_COLOR_ATTACHMENT0 + m_chichi_location, m_chichi.m_id, m_width, m_height);
   19346 
   19347 	/* Set up drawbuffers */
   19348 	const Functions& gl = m_context.getRenderContext().getFunctions();
   19349 	// The fragment shader can have more than 4 color outputs, but it only care about 4 (goku, gohan, goten, chichi).
   19350 	// We will first initialize all draw buffers to NONE and then set the real value for the 4 outputs we care about
   19351 	GLint maxDrawBuffers = 0;
   19352 	gl.getIntegerv(GL_MAX_DRAW_BUFFERS, &maxDrawBuffers);
   19353 
   19354 	std::vector<GLenum> buffers(maxDrawBuffers, GL_NONE);
   19355 	buffers[m_chichi_location] = GLenum(GL_COLOR_ATTACHMENT0 + m_chichi_location);
   19356 	buffers[m_goten_location]  = GLenum(GL_COLOR_ATTACHMENT0 + m_goten_location);
   19357 	buffers[m_goku_location]   = GLenum(GL_COLOR_ATTACHMENT0 + m_goku_location);
   19358 	buffers[m_gohan_location]  = GLenum(GL_COLOR_ATTACHMENT0 + m_gohan_location);
   19359 
   19360 	gl.drawBuffers(maxDrawBuffers, buffers.data());
   19361 	GLU_EXPECT_NO_ERROR(gl.getError(), "DrawBuffers");
   19362 }
   19363 
   19364 /** Constructor
   19365  *
   19366  * @param context Test framework context
   19367  **/
   19368 XFBInputTest::XFBInputTest(deqp::Context& context)
   19369 	: NegativeTestBase(context, "xfb_input",
   19370 					   "Test verifies that compiler reports error when xfb qualifiers are used with input")
   19371 {
   19372 }
   19373 
   19374 /** Source for given test case and stage
   19375  *
   19376  * @param test_case_index Index of test case
   19377  * @param stage           Shader stage
   19378  *
   19379  * @return Shader source
   19380  **/
   19381 std::string XFBInputTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   19382 {
   19383 	static const GLchar* buffer_var_definition = "layout (xfb_buffer = 2) in vec4 gohanARRAY;\n";
   19384 	static const GLchar* offset_var_definition = "layout (xfb_offset = 16) in vec4 gohanARRAY;\n";
   19385 	static const GLchar* stride_var_definition = "layout (xfb_stride = 32) in vec4 gohanARRAY;\n";
   19386 	static const GLchar* input_use			   = "    result += gohanINDEX;\n";
   19387 	static const GLchar* fs					   = "#version 430 core\n"
   19388 							  "#extension GL_ARB_enhanced_layouts : require\n"
   19389 							  "\n"
   19390 							  "in  vec4 gs_fs;\n"
   19391 							  "out vec4 fs_out;\n"
   19392 							  "\n"
   19393 							  "void main()\n"
   19394 							  "{\n"
   19395 							  "    fs_out = gs_fs;\n"
   19396 							  "}\n"
   19397 							  "\n";
   19398 	static const GLchar* fs_tested = "#version 430 core\n"
   19399 									 "#extension GL_ARB_enhanced_layouts : require\n"
   19400 									 "\n"
   19401 									 "VAR_DEFINITION"
   19402 									 "\n"
   19403 									 "in  vec4 gs_fs;\n"
   19404 									 "out vec4 fs_out;\n"
   19405 									 "\n"
   19406 									 "void main()\n"
   19407 									 "{\n"
   19408 									 "    vec4 result = gs_fs;\n"
   19409 									 "\n"
   19410 									 "VARIABLE_USE"
   19411 									 "\n"
   19412 									 "    fs_out = result;\n"
   19413 									 "}\n"
   19414 									 "\n";
   19415 	static const GLchar* gs = "#version 430 core\n"
   19416 							  "#extension GL_ARB_enhanced_layouts : require\n"
   19417 							  "\n"
   19418 							  "layout(points)                           in;\n"
   19419 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   19420 							  "\n"
   19421 							  "in  vec4 tes_gs[];\n"
   19422 							  "out vec4 gs_fs;\n"
   19423 							  "\n"
   19424 							  "void main()\n"
   19425 							  "{\n"
   19426 							  "    gs_fs = tes_gs[0];\n"
   19427 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   19428 							  "    EmitVertex();\n"
   19429 							  "    gs_fs = tes_gs[0];\n"
   19430 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   19431 							  "    EmitVertex();\n"
   19432 							  "    gs_fs = tes_gs[0];\n"
   19433 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   19434 							  "    EmitVertex();\n"
   19435 							  "    gs_fs = tes_gs[0];\n"
   19436 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   19437 							  "    EmitVertex();\n"
   19438 							  "}\n"
   19439 							  "\n";
   19440 	static const GLchar* gs_tested = "#version 430 core\n"
   19441 									 "#extension GL_ARB_enhanced_layouts : require\n"
   19442 									 "\n"
   19443 									 "layout(points)                           in;\n"
   19444 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   19445 									 "\n"
   19446 									 "VAR_DEFINITION"
   19447 									 "\n"
   19448 									 "in  vec4 tes_gs[];\n"
   19449 									 "out vec4 gs_fs;\n"
   19450 									 "\n"
   19451 									 "void main()\n"
   19452 									 "{\n"
   19453 									 "    vec4 result = tes_gs[0];\n"
   19454 									 "\n"
   19455 									 "VARIABLE_USE"
   19456 									 "\n"
   19457 									 "    gs_fs = result;\n"
   19458 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   19459 									 "    EmitVertex();\n"
   19460 									 "    gs_fs = result;\n"
   19461 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   19462 									 "    EmitVertex();\n"
   19463 									 "    gs_fs = result;\n"
   19464 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   19465 									 "    EmitVertex();\n"
   19466 									 "    gs_fs = result;\n"
   19467 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   19468 									 "    EmitVertex();\n"
   19469 									 "}\n"
   19470 									 "\n";
   19471 	static const GLchar* tcs = "#version 430 core\n"
   19472 							   "#extension GL_ARB_enhanced_layouts : require\n"
   19473 							   "\n"
   19474 							   "layout(vertices = 1) out;\n"
   19475 							   "\n"
   19476 							   "in  vec4 vs_tcs[];\n"
   19477 							   "out vec4 tcs_tes[];\n"
   19478 							   "\n"
   19479 							   "void main()\n"
   19480 							   "{\n"
   19481 							   "\n"
   19482 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   19483 							   "\n"
   19484 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   19485 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   19486 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   19487 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   19488 							   "    gl_TessLevelInner[0] = 1.0;\n"
   19489 							   "    gl_TessLevelInner[1] = 1.0;\n"
   19490 							   "}\n"
   19491 							   "\n";
   19492 	static const GLchar* tcs_tested = "#version 430 core\n"
   19493 									  "#extension GL_ARB_enhanced_layouts : require\n"
   19494 									  "\n"
   19495 									  "layout(vertices = 1) out;\n"
   19496 									  "\n"
   19497 									  "VAR_DEFINITION"
   19498 									  "\n"
   19499 									  "in  vec4 vs_tcs[];\n"
   19500 									  "out vec4 tcs_tes[];\n"
   19501 									  "\n"
   19502 									  "void main()\n"
   19503 									  "{\n"
   19504 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   19505 									  "\n"
   19506 									  "VARIABLE_USE"
   19507 									  "\n"
   19508 									  "    tcs_tes[gl_InvocationID] = result;\n"
   19509 									  "\n"
   19510 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   19511 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   19512 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   19513 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   19514 									  "    gl_TessLevelInner[0] = 1.0;\n"
   19515 									  "    gl_TessLevelInner[1] = 1.0;\n"
   19516 									  "}\n"
   19517 									  "\n";
   19518 	static const GLchar* tes = "#version 430 core\n"
   19519 							   "#extension GL_ARB_enhanced_layouts : require\n"
   19520 							   "\n"
   19521 							   "layout(isolines, point_mode) in;\n"
   19522 							   "\n"
   19523 							   "in  vec4 tcs_tes[];\n"
   19524 							   "out vec4 tes_gs;\n"
   19525 							   "\n"
   19526 							   "void main()\n"
   19527 							   "{\n"
   19528 							   "    tes_gs = tcs_tes[0];\n"
   19529 							   "}\n"
   19530 							   "\n";
   19531 	static const GLchar* tes_tested = "#version 430 core\n"
   19532 									  "#extension GL_ARB_enhanced_layouts : require\n"
   19533 									  "\n"
   19534 									  "layout(isolines, point_mode) in;\n"
   19535 									  "\n"
   19536 									  "VAR_DEFINITION"
   19537 									  "\n"
   19538 									  "in  vec4 tcs_tes[];\n"
   19539 									  "out vec4 tes_gs;\n"
   19540 									  "\n"
   19541 									  "void main()\n"
   19542 									  "{\n"
   19543 									  "    vec4 result = tcs_tes[0];\n"
   19544 									  "\n"
   19545 									  "VARIABLE_USE"
   19546 									  "\n"
   19547 									  "    tes_gs += result;\n"
   19548 									  "}\n"
   19549 									  "\n";
   19550 	static const GLchar* vs = "#version 430 core\n"
   19551 							  "#extension GL_ARB_enhanced_layouts : require\n"
   19552 							  "\n"
   19553 							  "in  vec4 in_vs;\n"
   19554 							  "out vec4 vs_tcs;\n"
   19555 							  "\n"
   19556 							  "void main()\n"
   19557 							  "{\n"
   19558 							  "    vs_tcs = in_vs;\n"
   19559 							  "}\n"
   19560 							  "\n";
   19561 	static const GLchar* vs_tested = "#version 430 core\n"
   19562 									 "#extension GL_ARB_enhanced_layouts : require\n"
   19563 									 "\n"
   19564 									 "VAR_DEFINITION"
   19565 									 "\n"
   19566 									 "in  vec4 in_vs;\n"
   19567 									 "out vec4 vs_tcs;\n"
   19568 									 "\n"
   19569 									 "void main()\n"
   19570 									 "{\n"
   19571 									 "    vec4 result = in_vs;\n"
   19572 									 "\n"
   19573 									 "VARIABLE_USE"
   19574 									 "\n"
   19575 									 "    vs_tcs += result;\n"
   19576 									 "}\n"
   19577 									 "\n";
   19578 
   19579 	std::string source;
   19580 	testCase&   test_case = m_test_cases[test_case_index];
   19581 
   19582 	if (test_case.m_stage == stage)
   19583 	{
   19584 		const GLchar* array	= "";
   19585 		const GLchar* index	= "";
   19586 		size_t		  position = 0;
   19587 		size_t		  temp;
   19588 		const GLchar* var_definition = 0;
   19589 		const GLchar* var_use		 = input_use;
   19590 
   19591 		switch (test_case.m_qualifier)
   19592 		{
   19593 		case BUFFER:
   19594 			var_definition = buffer_var_definition;
   19595 			break;
   19596 		case OFFSET:
   19597 			var_definition = offset_var_definition;
   19598 			break;
   19599 		case STRIDE:
   19600 			var_definition = stride_var_definition;
   19601 			break;
   19602 		default:
   19603 			TCU_FAIL("Invalid enum");
   19604 		}
   19605 
   19606 		switch (stage)
   19607 		{
   19608 		case Utils::Shader::FRAGMENT:
   19609 			source = fs_tested;
   19610 			break;
   19611 		case Utils::Shader::GEOMETRY:
   19612 			source = gs_tested;
   19613 			array  = "[]";
   19614 			index  = "[0]";
   19615 			break;
   19616 		case Utils::Shader::TESS_CTRL:
   19617 			source = tcs_tested;
   19618 			array  = "[]";
   19619 			index  = "[gl_InvocationID]";
   19620 			break;
   19621 		case Utils::Shader::TESS_EVAL:
   19622 			source = tes_tested;
   19623 			array  = "[]";
   19624 			index  = "[0]";
   19625 			break;
   19626 		case Utils::Shader::VERTEX:
   19627 			source = vs_tested;
   19628 			break;
   19629 		default:
   19630 			TCU_FAIL("Invalid enum");
   19631 		}
   19632 
   19633 		temp = position;
   19634 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   19635 		position = temp;
   19636 		Utils::replaceToken("ARRAY", position, array, source);
   19637 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   19638 
   19639 		Utils::replaceAllTokens("INDEX", index, source);
   19640 	}
   19641 	else
   19642 	{
   19643 		switch (stage)
   19644 		{
   19645 		case Utils::Shader::FRAGMENT:
   19646 			source = fs;
   19647 			break;
   19648 		case Utils::Shader::GEOMETRY:
   19649 			source = gs;
   19650 			break;
   19651 		case Utils::Shader::TESS_CTRL:
   19652 			source = tcs;
   19653 			break;
   19654 		case Utils::Shader::TESS_EVAL:
   19655 			source = tes;
   19656 			break;
   19657 		case Utils::Shader::VERTEX:
   19658 			source = vs;
   19659 			break;
   19660 		default:
   19661 			TCU_FAIL("Invalid enum");
   19662 		}
   19663 	}
   19664 
   19665 	return source;
   19666 }
   19667 
   19668 /** Get description of test case
   19669  *
   19670  * @param test_case_index Index of test case
   19671  *
   19672  * @return Test case description
   19673  **/
   19674 std::string XFBInputTest::getTestCaseName(GLuint test_case_index)
   19675 {
   19676 	std::stringstream stream;
   19677 	testCase&		  test_case = m_test_cases[test_case_index];
   19678 
   19679 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage) << ", qualifier: ";
   19680 
   19681 	switch (test_case.m_qualifier)
   19682 	{
   19683 	case BUFFER:
   19684 		stream << "xfb_buffer";
   19685 		break;
   19686 	case OFFSET:
   19687 		stream << "xfb_offset";
   19688 		break;
   19689 	case STRIDE:
   19690 		stream << "xfb_stride";
   19691 		break;
   19692 	default:
   19693 		TCU_FAIL("Invalid enum");
   19694 	}
   19695 
   19696 	return stream.str();
   19697 }
   19698 
   19699 /** Get number of test cases
   19700  *
   19701  * @return Number of test cases
   19702  **/
   19703 GLuint XFBInputTest::getTestCaseNumber()
   19704 {
   19705 	return static_cast<GLuint>(m_test_cases.size());
   19706 }
   19707 
   19708 /** Selects if "compute" stage is relevant for test
   19709  *
   19710  * @param ignored
   19711  *
   19712  * @return false
   19713  **/
   19714 bool XFBInputTest::isComputeRelevant(GLuint /* test_case_index */)
   19715 {
   19716 	return false;
   19717 }
   19718 
   19719 /** Prepare all test cases
   19720  *
   19721  **/
   19722 void XFBInputTest::testInit()
   19723 {
   19724 	for (GLuint qualifier = 0; qualifier < QUALIFIERS_MAX; ++qualifier)
   19725 	{
   19726 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   19727 		{
   19728 			if (Utils::Shader::COMPUTE == stage)
   19729 			{
   19730 				continue;
   19731 			}
   19732 
   19733 			testCase test_case = { (QUALIFIERS)qualifier, (Utils::Shader::STAGES)stage };
   19734 
   19735 			m_test_cases.push_back(test_case);
   19736 		}
   19737 	}
   19738 }
   19739 
   19740 /* Constants used by XFBAllStagesTest */
   19741 const GLuint XFBAllStagesTest::m_gs_index = 3;
   19742 
   19743 /** Constructor
   19744  *
   19745  * @param context Test context
   19746  **/
   19747 XFBAllStagesTest::XFBAllStagesTest(deqp::Context& context)
   19748 	: BufferTestBase(context, "xfb_all_stages",
   19749 					 "Test verifies that only last stage in vertex processing can output to transform feedback")
   19750 {
   19751 	/* Nothing to be done here */
   19752 }
   19753 
   19754 /** Get descriptors of buffers necessary for test
   19755  *
   19756  * @param ignored
   19757  * @param out_descriptors Descriptors of buffers used by test
   19758  **/
   19759 void XFBAllStagesTest::getBufferDescriptors(glw::GLuint /* test_case_index */,
   19760 											bufferDescriptor::Vector& out_descriptors)
   19761 {
   19762 	static const GLuint n_stages = 4;
   19763 	const Utils::Type&  vec4	 = Utils::Type::vec4;
   19764 
   19765 	/* Data */
   19766 	tcu::Vec4 sum;
   19767 
   19768 	/* Test uses single uniform and xfb per stage + uniform for fragment shader */
   19769 	out_descriptors.resize(n_stages * 2 + 1);
   19770 
   19771 	/* */
   19772 	for (GLuint i = 0; i < n_stages; ++i)
   19773 	{
   19774 		/* Get references */
   19775 		bufferDescriptor& uniform = out_descriptors[i + 0];
   19776 		bufferDescriptor& xfb	 = out_descriptors[i + n_stages];
   19777 
   19778 		/* Index */
   19779 		uniform.m_index = i;
   19780 		xfb.m_index		= i;
   19781 
   19782 		/* Target */
   19783 		uniform.m_target = Utils::Buffer::Uniform;
   19784 		xfb.m_target	 = Utils::Buffer::Transform_feedback;
   19785 
   19786 		/* Data */
   19787 		const tcu::Vec4 var(Utils::GetRandFloat(), Utils::GetRandFloat(), Utils::GetRandFloat(), Utils::GetRandFloat());
   19788 
   19789 		sum += var;
   19790 
   19791 		uniform.m_initial_data.resize(vec4.GetSize());
   19792 		memcpy(&uniform.m_initial_data[0], var.getPtr(), vec4.GetSize());
   19793 
   19794 		xfb.m_initial_data = vec4.GenerateDataPacked();
   19795 
   19796 		if (m_gs_index != i)
   19797 		{
   19798 			xfb.m_expected_data = xfb.m_initial_data;
   19799 		}
   19800 		else
   19801 		{
   19802 			xfb.m_expected_data.resize(vec4.GetSize());
   19803 			memcpy(&xfb.m_expected_data[0], sum.getPtr(), vec4.GetSize());
   19804 		}
   19805 	}
   19806 
   19807 	/* FS */
   19808 	{
   19809 		/* Get reference */
   19810 		bufferDescriptor& uniform = out_descriptors[n_stages * 2];
   19811 
   19812 		/* Index */
   19813 		uniform.m_index = n_stages;
   19814 
   19815 		/* Target */
   19816 		uniform.m_target = Utils::Buffer::Uniform;
   19817 
   19818 		/* Data */
   19819 		const tcu::Vec4 var(Utils::GetRandFloat(), Utils::GetRandFloat(), Utils::GetRandFloat(), Utils::GetRandFloat());
   19820 
   19821 		uniform.m_initial_data.resize(vec4.GetSize());
   19822 		memcpy(&uniform.m_initial_data[0], var.getPtr(), vec4.GetSize());
   19823 	}
   19824 }
   19825 
   19826 /** Get body of main function for given shader stage
   19827  *
   19828  * @param ignored
   19829  * @param stage            Shader stage
   19830  * @param out_assignments  Set to empty
   19831  * @param out_calculations Set to empty
   19832  **/
   19833 void XFBAllStagesTest::getShaderBody(glw::GLuint /* test_case_index */, Utils::Shader::STAGES stage,
   19834 									 std::string& out_assignments, std::string& out_calculations)
   19835 {
   19836 	out_calculations = "";
   19837 
   19838 	static const GLchar* vs  = "    vs_tcs  = uni_vs;\n";
   19839 	static const GLchar* tcs = "    tcs_tes[gl_InvocationID] = uni_tcs + vs_tcs[gl_InvocationID];\n";
   19840 	static const GLchar* tes = "    tes_gs  = uni_tes + tcs_tes[0];\n";
   19841 	static const GLchar* gs  = "    gs_fs   = uni_gs  + tes_gs[0];\n";
   19842 	static const GLchar* fs  = "    fs_out  = uni_fs  + gs_fs;\n";
   19843 
   19844 	const GLchar* assignments = 0;
   19845 	switch (stage)
   19846 	{
   19847 	case Utils::Shader::FRAGMENT:
   19848 		assignments = fs;
   19849 		break;
   19850 	case Utils::Shader::GEOMETRY:
   19851 		assignments = gs;
   19852 		break;
   19853 	case Utils::Shader::TESS_CTRL:
   19854 		assignments = tcs;
   19855 		break;
   19856 	case Utils::Shader::TESS_EVAL:
   19857 		assignments = tes;
   19858 		break;
   19859 	case Utils::Shader::VERTEX:
   19860 		assignments = vs;
   19861 		break;
   19862 	default:
   19863 		TCU_FAIL("Invalid enum");
   19864 	}
   19865 
   19866 	out_assignments = assignments;
   19867 }
   19868 
   19869 /** Get interface of shader
   19870  *
   19871  * @param ignored
   19872  * @param stage         Shader stage
   19873  * @param out_interface Set to ""
   19874  **/
   19875 void XFBAllStagesTest::getShaderInterface(glw::GLuint /* test_case_index */, Utils::Shader::STAGES stage,
   19876 										  std::string& out_interface)
   19877 {
   19878 	static const GLchar* vs = "layout(xfb_buffer = 0, xfb_offset = 0) out     vec4 vs_tcs;\n"
   19879 							  "layout(binding    = 0)                 uniform vs_block {\n"
   19880 							  "    vec4 uni_vs;\n"
   19881 							  "};\n";
   19882 	static const GLchar* tcs = "                                       in      vec4 vs_tcs[];\n"
   19883 							   "layout(xfb_buffer = 1, xfb_offset = 0) out     vec4 tcs_tes[1];\n"
   19884 							   "layout(binding    = 1)                 uniform tcs_block {\n"
   19885 							   "    vec4 uni_tcs;\n"
   19886 							   "};\n";
   19887 	static const GLchar* tes = "                                       in      vec4 tcs_tes[];\n"
   19888 							   "layout(xfb_buffer = 2, xfb_offset = 0) out     vec4 tes_gs;\n"
   19889 							   "layout(binding    = 2)                 uniform tes_block {\n"
   19890 							   "    vec4 uni_tes;\n"
   19891 							   "};\n";
   19892 	static const GLchar* gs = "                                       in      vec4 tes_gs[];\n"
   19893 							  "layout(xfb_buffer = 3, xfb_offset = 0) out     vec4 gs_fs;\n"
   19894 							  "layout(binding    = 3)                 uniform gs_block {\n"
   19895 							  "    vec4 uni_gs;\n"
   19896 							  "};\n";
   19897 	static const GLchar* fs = "                       in      vec4 gs_fs;\n"
   19898 							  "                       out     vec4 fs_out;\n"
   19899 							  "layout(binding    = 4) uniform fs_block {\n"
   19900 							  "    vec4 uni_fs;\n"
   19901 							  "};\n";
   19902 
   19903 	const GLchar* interface = 0;
   19904 	switch (stage)
   19905 	{
   19906 	case Utils::Shader::FRAGMENT:
   19907 		interface = fs;
   19908 		break;
   19909 	case Utils::Shader::GEOMETRY:
   19910 		interface = gs;
   19911 		break;
   19912 	case Utils::Shader::TESS_CTRL:
   19913 		interface = tcs;
   19914 		break;
   19915 	case Utils::Shader::TESS_EVAL:
   19916 		interface = tes;
   19917 		break;
   19918 	case Utils::Shader::VERTEX:
   19919 		interface = vs;
   19920 		break;
   19921 	default:
   19922 		TCU_FAIL("Invalid enum");
   19923 	}
   19924 
   19925 	out_interface = interface;
   19926 }
   19927 
   19928 /* Constants used by XFBStrideOfEmptyListTest */
   19929 const GLuint XFBStrideOfEmptyListTest::m_stride = 64;
   19930 
   19931 /** Constructor
   19932  *
   19933  * @param context Test context
   19934  **/
   19935 XFBStrideOfEmptyListTest::XFBStrideOfEmptyListTest(deqp::Context& context)
   19936 	: BufferTestBase(context, "xfb_stride_of_empty_list",
   19937 					 "Test verifies that xfb_stride qualifier is respected when no xfb_offset is specified")
   19938 {
   19939 	/* Nothing to be done here */
   19940 }
   19941 
   19942 /** Execute drawArrays for single vertex
   19943  *
   19944  * @param test_case_index Index of test case
   19945  *
   19946  * @return true if proper error is reported
   19947  **/
   19948 bool XFBStrideOfEmptyListTest::executeDrawCall(bool /* tesEnabled */, GLuint test_case_index)
   19949 {
   19950 	const Functions& gl		= m_context.getRenderContext().getFunctions();
   19951 	bool			 result = true;
   19952 
   19953 	/* Draw */
   19954 	gl.disable(GL_RASTERIZER_DISCARD);
   19955 	GLU_EXPECT_NO_ERROR(gl.getError(), "Disable");
   19956 
   19957 	gl.beginTransformFeedback(GL_POINTS);
   19958 	GLenum error = gl.getError();
   19959 	switch (test_case_index)
   19960 	{
   19961 	case VALID:
   19962 		if (GL_NO_ERROR != error)
   19963 		{
   19964 			gl.endTransformFeedback();
   19965 			GLU_EXPECT_NO_ERROR(error, "BeginTransformFeedback");
   19966 		}
   19967 
   19968 		gl.drawArrays(GL_PATCHES, 0 /* first */, 1 /* count */);
   19969 		error = gl.getError();
   19970 
   19971 		gl.endTransformFeedback();
   19972 		GLU_EXPECT_NO_ERROR(error, "DrawArrays");
   19973 		GLU_EXPECT_NO_ERROR(gl.getError(), "EndTransformFeedback");
   19974 
   19975 		break;
   19976 
   19977 	case FIRST_MISSING:
   19978 		if (GL_NO_ERROR == error)
   19979 		{
   19980 			gl.endTransformFeedback();
   19981 		}
   19982 
   19983 		if (GL_INVALID_OPERATION != error)
   19984 		{
   19985 			m_context.getTestContext().getLog()
   19986 				<< tcu::TestLog::Message << "XFB at index 0, that is written by GS, is missing. It was expected that "
   19987 											"INVALID_OPERATION will generated by BeginTransformFeedback. Got: "
   19988 				<< glu::getErrorStr(error) << tcu::TestLog::EndMessage;
   19989 
   19990 			result = false;
   19991 		}
   19992 
   19993 		break;
   19994 
   19995 	case SECOND_MISSING:
   19996 		if (GL_NO_ERROR == error)
   19997 		{
   19998 			gl.endTransformFeedback();
   19999 		}
   20000 
   20001 		if (GL_INVALID_OPERATION != error)
   20002 		{
   20003 			m_context.getTestContext().getLog()
   20004 				<< tcu::TestLog::Message << "XFB at index 1, that is declared as empty, is missing. It was expected "
   20005 											"that INVALID_OPERATION will generated by BeginTransformFeedback. Got: "
   20006 				<< glu::getErrorStr(error) << tcu::TestLog::EndMessage;
   20007 
   20008 			result = false;
   20009 		}
   20010 
   20011 		break;
   20012 	}
   20013 
   20014 	/* Done */
   20015 	return result;
   20016 }
   20017 
   20018 /** Get descriptors of buffers necessary for test
   20019  *
   20020  * @param test_case_index Index of test case
   20021  * @param out_descriptors Descriptors of buffers used by test
   20022  **/
   20023 void XFBStrideOfEmptyListTest::getBufferDescriptors(glw::GLuint				  test_case_index,
   20024 													bufferDescriptor::Vector& out_descriptors)
   20025 {
   20026 	switch (test_case_index)
   20027 	{
   20028 	case VALID:
   20029 	{
   20030 		/* Test needs single uniform and two xfbs */
   20031 		out_descriptors.resize(3);
   20032 
   20033 		/* Get references */
   20034 		bufferDescriptor& uniform = out_descriptors[0];
   20035 		bufferDescriptor& xfb_0   = out_descriptors[1];
   20036 		bufferDescriptor& xfb_1   = out_descriptors[2];
   20037 
   20038 		/* Index */
   20039 		uniform.m_index = 0;
   20040 		xfb_0.m_index   = 0;
   20041 		xfb_1.m_index   = 1;
   20042 
   20043 		/* Target */
   20044 		uniform.m_target = Utils::Buffer::Uniform;
   20045 		xfb_0.m_target   = Utils::Buffer::Transform_feedback;
   20046 		xfb_1.m_target   = Utils::Buffer::Transform_feedback;
   20047 
   20048 		/* Data */
   20049 		uniform.m_initial_data = Utils::Type::vec4.GenerateDataPacked();
   20050 
   20051 		xfb_0.m_initial_data  = Utils::Type::vec4.GenerateDataPacked();
   20052 		xfb_0.m_expected_data = uniform.m_initial_data;
   20053 
   20054 		/* Data, contents are the same as no modification is expected */
   20055 		xfb_1.m_initial_data.resize(m_stride);
   20056 		xfb_1.m_expected_data.resize(m_stride);
   20057 
   20058 		for (GLuint i = 0; i < m_stride; ++i)
   20059 		{
   20060 			xfb_1.m_initial_data[0]  = (glw::GLubyte)i;
   20061 			xfb_1.m_expected_data[0] = (glw::GLubyte)i;
   20062 		}
   20063 	}
   20064 
   20065 	break;
   20066 
   20067 	case FIRST_MISSING:
   20068 	{
   20069 		/* Test needs single uniform and two xfbs */
   20070 		out_descriptors.resize(2);
   20071 
   20072 		/* Get references */
   20073 		bufferDescriptor& uniform = out_descriptors[0];
   20074 		bufferDescriptor& xfb_1   = out_descriptors[1];
   20075 
   20076 		/* Index */
   20077 		uniform.m_index = 0;
   20078 		xfb_1.m_index   = 1;
   20079 
   20080 		/* Target */
   20081 		uniform.m_target = Utils::Buffer::Uniform;
   20082 		xfb_1.m_target   = Utils::Buffer::Transform_feedback;
   20083 
   20084 		/* Data */
   20085 		uniform.m_initial_data = Utils::Type::vec4.GenerateDataPacked();
   20086 
   20087 		/* Draw call will not be executed, contents does not matter */
   20088 		xfb_1.m_initial_data.resize(m_stride);
   20089 	}
   20090 
   20091 	break;
   20092 
   20093 	case SECOND_MISSING:
   20094 	{
   20095 		/* Test needs single uniform and two xfbs */
   20096 		out_descriptors.resize(2);
   20097 
   20098 		/* Get references */
   20099 		bufferDescriptor& uniform = out_descriptors[0];
   20100 		bufferDescriptor& xfb_0   = out_descriptors[1];
   20101 
   20102 		/* Index */
   20103 		uniform.m_index = 0;
   20104 		xfb_0.m_index   = 0;
   20105 
   20106 		/* Target */
   20107 		uniform.m_target = Utils::Buffer::Uniform;
   20108 		xfb_0.m_target   = Utils::Buffer::Transform_feedback;
   20109 
   20110 		/* Data */
   20111 		uniform.m_initial_data = Utils::Type::vec4.GenerateDataPacked();
   20112 
   20113 		/* Draw call will not be executed, contents does not matter */
   20114 		xfb_0.m_initial_data = Utils::Type::vec4.GenerateDataPacked();
   20115 	}
   20116 
   20117 	break;
   20118 	}
   20119 }
   20120 
   20121 /** Get body of main function for given shader stage
   20122  *
   20123  * @param ignored
   20124  * @param stage            Shader stage
   20125  * @param out_assignments  Set to empty
   20126  * @param out_calculations Set to empty
   20127  **/
   20128 void XFBStrideOfEmptyListTest::getShaderBody(GLuint /* test_case_index */, Utils::Shader::STAGES stage,
   20129 											 std::string& out_assignments, std::string& out_calculations)
   20130 {
   20131 	out_calculations = "";
   20132 
   20133 	static const GLchar* gs = "    gs_fs  = uni_gs;\n";
   20134 	static const GLchar* fs = "    fs_out = vec4(gs_fs);\n";
   20135 
   20136 	const GLchar* assignments = "";
   20137 	switch (stage)
   20138 	{
   20139 	case Utils::Shader::FRAGMENT:
   20140 		assignments = fs;
   20141 		break;
   20142 	case Utils::Shader::GEOMETRY:
   20143 		assignments = gs;
   20144 		break;
   20145 	default:
   20146 		break;
   20147 	}
   20148 
   20149 	out_assignments = assignments;
   20150 }
   20151 
   20152 /** Get interface of shader
   20153  *
   20154  * @param ignored
   20155  * @param stage            Shader stage
   20156  * @param out_interface    Set to ""
   20157  **/
   20158 void XFBStrideOfEmptyListTest::getShaderInterface(GLuint /* test_case_index */, Utils::Shader::STAGES stage,
   20159 												  std::string& out_interface)
   20160 {
   20161 	static const GLchar* gs = "layout (xfb_buffer = 0, xfb_offset = 0)  out     vec4 gs_fs;\n"
   20162 							  "layout (xfb_buffer = 1, xfb_stride = 64) out;\n"
   20163 							  "\n"
   20164 							  "layout (binding    = 0)                  uniform gs_block {\n"
   20165 							  "    vec4 uni_gs;\n"
   20166 							  "};\n";
   20167 	static const GLchar* fs = "in  vec4 gs_fs;\n"
   20168 							  "out vec4 fs_out;\n";
   20169 
   20170 	switch (stage)
   20171 	{
   20172 	case Utils::Shader::FRAGMENT:
   20173 		out_interface = fs;
   20174 		break;
   20175 	case Utils::Shader::GEOMETRY:
   20176 		out_interface = gs;
   20177 		break;
   20178 	default:
   20179 		out_interface = "";
   20180 		return;
   20181 	}
   20182 }
   20183 
   20184 /** Returns buffer details in human readable form.
   20185  *
   20186  * @param test_case_index Index of test case
   20187  *
   20188  * @return Case description
   20189  **/
   20190 std::string XFBStrideOfEmptyListTest::getTestCaseName(GLuint test_case_index)
   20191 {
   20192 	std::string result;
   20193 
   20194 	switch (test_case_index)
   20195 	{
   20196 	case VALID:
   20197 		result = "Valid case";
   20198 		break;
   20199 	case FIRST_MISSING:
   20200 		result = "Missing xfb at index 0";
   20201 		break;
   20202 	case SECOND_MISSING:
   20203 		result = "Missing xfb at index 1";
   20204 		break;
   20205 	default:
   20206 		TCU_FAIL("Invalid enum");
   20207 	}
   20208 
   20209 	return result;
   20210 }
   20211 
   20212 /** Get number of test cases
   20213  *
   20214  * @return 3
   20215  **/
   20216 GLuint XFBStrideOfEmptyListTest::getTestCaseNumber()
   20217 {
   20218 	return 3;
   20219 }
   20220 
   20221 /* Constants used by XFBStrideOfEmptyListTest */
   20222 const GLuint XFBStrideOfEmptyListAndAPITest::m_stride = 64;
   20223 
   20224 /** Constructor
   20225  *
   20226  * @param context Test context
   20227  **/
   20228 XFBStrideOfEmptyListAndAPITest::XFBStrideOfEmptyListAndAPITest(deqp::Context& context)
   20229 	: BufferTestBase(context, "xfb_stride_of_empty_list_and_api",
   20230 					 "Test verifies that xfb_stride qualifier is not overriden by API")
   20231 {
   20232 	/* Nothing to be done here */
   20233 }
   20234 
   20235 /** Execute drawArrays for single vertex
   20236  *
   20237  * @param test_case_index Index of test case
   20238  *
   20239  * @return true if proper error is reported
   20240  **/
   20241 bool XFBStrideOfEmptyListAndAPITest::executeDrawCall(bool /* tesEnabled */, GLuint test_case_index)
   20242 {
   20243 	const Functions& gl		= m_context.getRenderContext().getFunctions();
   20244 	bool			 result = true;
   20245 
   20246 	/* Draw */
   20247 	gl.disable(GL_RASTERIZER_DISCARD);
   20248 	GLU_EXPECT_NO_ERROR(gl.getError(), "Disable");
   20249 
   20250 	gl.beginTransformFeedback(GL_POINTS);
   20251 	GLenum error = gl.getError();
   20252 	switch (test_case_index)
   20253 	{
   20254 	case VALID:
   20255 		if (GL_NO_ERROR != error)
   20256 		{
   20257 			gl.endTransformFeedback();
   20258 			GLU_EXPECT_NO_ERROR(error, "BeginTransformFeedback");
   20259 		}
   20260 
   20261 		gl.drawArrays(GL_PATCHES, 0 /* first */, 1 /* count */);
   20262 		error = gl.getError();
   20263 
   20264 		gl.endTransformFeedback();
   20265 		GLU_EXPECT_NO_ERROR(error, "DrawArrays");
   20266 		GLU_EXPECT_NO_ERROR(gl.getError(), "EndTransformFeedback");
   20267 
   20268 		break;
   20269 
   20270 	case FIRST_MISSING:
   20271 		if (GL_NO_ERROR == error)
   20272 		{
   20273 			gl.endTransformFeedback();
   20274 		}
   20275 
   20276 		if (GL_INVALID_OPERATION != error)
   20277 		{
   20278 			m_context.getTestContext().getLog()
   20279 				<< tcu::TestLog::Message << "XFB at index 0, that is declared as empty, is missing. It was expected "
   20280 											"that INVALID_OPERATION will generated by BeginTransformFeedback. Got: "
   20281 				<< glu::getErrorStr(error) << tcu::TestLog::EndMessage;
   20282 
   20283 			result = false;
   20284 		}
   20285 
   20286 		break;
   20287 
   20288 	case SECOND_MISSING:
   20289 		if (GL_NO_ERROR == error)
   20290 		{
   20291 			gl.endTransformFeedback();
   20292 		}
   20293 
   20294 		if (GL_INVALID_OPERATION != error)
   20295 		{
   20296 			m_context.getTestContext().getLog()
   20297 				<< tcu::TestLog::Message << "XFB at index 1, that is written by GS, is missing. It was expected that "
   20298 											"INVALID_OPERATION will generated by BeginTransformFeedback. Got: "
   20299 				<< glu::getErrorStr(error) << tcu::TestLog::EndMessage;
   20300 
   20301 			result = false;
   20302 		}
   20303 
   20304 		break;
   20305 	}
   20306 
   20307 	/* Done */
   20308 	return result;
   20309 }
   20310 
   20311 /** Get descriptors of buffers necessary for test
   20312  *
   20313  * @param test_case_index Index of test case
   20314  * @param out_descriptors Descriptors of buffers used by test
   20315  **/
   20316 void XFBStrideOfEmptyListAndAPITest::getBufferDescriptors(glw::GLuint				test_case_index,
   20317 														  bufferDescriptor::Vector& out_descriptors)
   20318 {
   20319 	switch (test_case_index)
   20320 	{
   20321 	case VALID:
   20322 	{
   20323 		/* Test needs single uniform and two xfbs */
   20324 		out_descriptors.resize(3);
   20325 
   20326 		/* Get references */
   20327 		bufferDescriptor& uniform = out_descriptors[0];
   20328 		bufferDescriptor& xfb_0   = out_descriptors[1];
   20329 		bufferDescriptor& xfb_1   = out_descriptors[2];
   20330 
   20331 		/* Index */
   20332 		uniform.m_index = 0;
   20333 		xfb_0.m_index   = 0;
   20334 		xfb_1.m_index   = 1;
   20335 
   20336 		/* Target */
   20337 		uniform.m_target = Utils::Buffer::Uniform;
   20338 		xfb_0.m_target   = Utils::Buffer::Transform_feedback;
   20339 		xfb_1.m_target   = Utils::Buffer::Transform_feedback;
   20340 
   20341 		/* Data */
   20342 		uniform.m_initial_data = Utils::Type::vec4.GenerateDataPacked();
   20343 
   20344 		/* Data, contents are the same as no modification is expected */
   20345 		xfb_0.m_initial_data.resize(m_stride);
   20346 		xfb_0.m_expected_data.resize(m_stride);
   20347 
   20348 		for (GLuint i = 0; i < m_stride; ++i)
   20349 		{
   20350 			xfb_0.m_initial_data[0]  = (glw::GLubyte)i;
   20351 			xfb_0.m_expected_data[0] = (glw::GLubyte)i;
   20352 		}
   20353 
   20354 		xfb_1.m_initial_data  = Utils::Type::vec4.GenerateDataPacked();
   20355 		xfb_1.m_expected_data = uniform.m_initial_data;
   20356 	}
   20357 
   20358 	break;
   20359 
   20360 	case FIRST_MISSING:
   20361 	{
   20362 		/* Test needs single uniform and two xfbs */
   20363 		out_descriptors.resize(2);
   20364 
   20365 		/* Get references */
   20366 		bufferDescriptor& uniform = out_descriptors[0];
   20367 		bufferDescriptor& xfb_1   = out_descriptors[1];
   20368 
   20369 		/* Index */
   20370 		uniform.m_index = 0;
   20371 		xfb_1.m_index   = 1;
   20372 
   20373 		/* Target */
   20374 		uniform.m_target = Utils::Buffer::Uniform;
   20375 		xfb_1.m_target   = Utils::Buffer::Transform_feedback;
   20376 
   20377 		/* Data */
   20378 		uniform.m_initial_data = Utils::Type::vec4.GenerateDataPacked();
   20379 
   20380 		/* Draw call will not be executed, contents does not matter */
   20381 		xfb_1.m_initial_data = Utils::Type::vec4.GenerateDataPacked();
   20382 	}
   20383 
   20384 	break;
   20385 
   20386 	case SECOND_MISSING:
   20387 	{
   20388 		/* Test needs single uniform and two xfbs */
   20389 		out_descriptors.resize(2);
   20390 
   20391 		/* Get references */
   20392 		bufferDescriptor& uniform = out_descriptors[0];
   20393 		bufferDescriptor& xfb_0   = out_descriptors[1];
   20394 
   20395 		/* Index */
   20396 		uniform.m_index = 0;
   20397 		xfb_0.m_index   = 0;
   20398 
   20399 		/* Target */
   20400 		uniform.m_target = Utils::Buffer::Uniform;
   20401 		xfb_0.m_target   = Utils::Buffer::Transform_feedback;
   20402 
   20403 		/* Data */
   20404 		uniform.m_initial_data = Utils::Type::vec4.GenerateDataPacked();
   20405 
   20406 		/* Draw call will not be executed, contents does not matter */
   20407 		xfb_0.m_initial_data.resize(m_stride);
   20408 	}
   20409 
   20410 	break;
   20411 	}
   20412 }
   20413 
   20414 /** Get list of names of varyings that will be registered with TransformFeedbackVaryings
   20415  *
   20416  * @param ignored
   20417  * @param captured_varyings Vector of varying names to be captured
   20418  **/
   20419 void XFBStrideOfEmptyListAndAPITest::getCapturedVaryings(glw::GLuint /* test_case_index */,
   20420 														 Utils::Program::NameVector& captured_varyings)
   20421 {
   20422 	captured_varyings.push_back("gs_fs");
   20423 }
   20424 
   20425 /** Get body of main function for given shader stage
   20426  *
   20427  * @param ignored
   20428  * @param stage            Shader stage
   20429  * @param out_assignments  Set to empty
   20430  * @param out_calculations Set to empty
   20431  **/
   20432 void XFBStrideOfEmptyListAndAPITest::getShaderBody(GLuint /* test_case_index */, Utils::Shader::STAGES stage,
   20433 												   std::string& out_assignments, std::string& out_calculations)
   20434 {
   20435 	out_calculations = "";
   20436 
   20437 	static const GLchar* gs = "    gs_fs  = uni_gs;\n";
   20438 	static const GLchar* fs = "    fs_out = vec4(gs_fs);\n";
   20439 
   20440 	const GLchar* assignments = "";
   20441 	switch (stage)
   20442 	{
   20443 	case Utils::Shader::FRAGMENT:
   20444 		assignments = fs;
   20445 		break;
   20446 	case Utils::Shader::GEOMETRY:
   20447 		assignments = gs;
   20448 		break;
   20449 	default:
   20450 		break;
   20451 	}
   20452 
   20453 	out_assignments = assignments;
   20454 }
   20455 
   20456 /** Get interface of shader
   20457  *
   20458  * @param ignored
   20459  * @param stage            Shader stage
   20460  * @param out_interface    Set to ""
   20461  **/
   20462 void XFBStrideOfEmptyListAndAPITest::getShaderInterface(GLuint /* test_case_index */, Utils::Shader::STAGES stage,
   20463 														std::string& out_interface)
   20464 {
   20465 	static const GLchar* gs = "layout (xfb_buffer = 0, xfb_stride = 64) out;\n"
   20466 							  "layout (xfb_buffer = 1, xfb_offset = 0)  out vec4 gs_fs;\n"
   20467 							  "\n"
   20468 							  "layout(binding    = 0) uniform gs_block {\n"
   20469 							  "    vec4 uni_gs;\n"
   20470 							  "};\n";
   20471 	static const GLchar* fs = "in  vec4 gs_fs;\n"
   20472 							  "out vec4 fs_out;\n";
   20473 
   20474 	switch (stage)
   20475 	{
   20476 	case Utils::Shader::FRAGMENT:
   20477 		out_interface = fs;
   20478 		break;
   20479 	case Utils::Shader::GEOMETRY:
   20480 		out_interface = gs;
   20481 		break;
   20482 	default:
   20483 		out_interface = "";
   20484 		return;
   20485 	}
   20486 }
   20487 
   20488 /** Returns buffer details in human readable form.
   20489  *
   20490  * @param test_case_index Index of test case
   20491  *
   20492  * @return Case description
   20493  **/
   20494 std::string XFBStrideOfEmptyListAndAPITest::getTestCaseName(GLuint test_case_index)
   20495 {
   20496 	std::string result;
   20497 
   20498 	switch (test_case_index)
   20499 	{
   20500 	case VALID:
   20501 		result = "Valid case";
   20502 		break;
   20503 	case FIRST_MISSING:
   20504 		result = "Missing xfb at index 0";
   20505 		break;
   20506 	case SECOND_MISSING:
   20507 		result = "Missing xfb at index 1";
   20508 		break;
   20509 	default:
   20510 		TCU_FAIL("Invalid enum");
   20511 	}
   20512 
   20513 	return result;
   20514 }
   20515 
   20516 /** Get number of test cases
   20517  *
   20518  * @return 2
   20519  **/
   20520 GLuint XFBStrideOfEmptyListAndAPITest::getTestCaseNumber()
   20521 {
   20522 	return 3;
   20523 }
   20524 
   20525 /** Constructor
   20526  *
   20527  * @param context Test framework context
   20528  **/
   20529 XFBTooSmallStrideTest::XFBTooSmallStrideTest(deqp::Context& context)
   20530 	: NegativeTestBase(context, "xfb_too_small_stride",
   20531 					   "Test verifies that compiler reports error when xfb_stride sets not enough space")
   20532 {
   20533 }
   20534 
   20535 /** Source for given test case and stage
   20536  *
   20537  * @param test_case_index Index of test case
   20538  * @param stage           Shader stage
   20539  *
   20540  * @return Shader source
   20541  **/
   20542 std::string XFBTooSmallStrideTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   20543 {
   20544 	static const GLchar* array_var_definition = "layout (xfb_buffer = 0, xfb_stride = 32) out;\n"
   20545 												"\n"
   20546 												"layout (xfb_offset = 16) out vec4 gohanARRAY[4];\n";
   20547 	static const GLchar* block_var_definition = "layout (xfb_buffer = 0, xfb_stride = 32) out;\n"
   20548 												"\n"
   20549 												"layout (xfb_offset = 0) out Goku {\n"
   20550 												"    vec4 gohan;\n"
   20551 												"    vec4 goten;\n"
   20552 												"    vec4 chichi;\n"
   20553 												"} gokuARRAY;\n";
   20554 	static const GLchar* offset_var_definition = "layout (xfb_buffer = 0, xfb_stride = 40) out;\n"
   20555 												 "\n"
   20556 												 "layout (xfb_offset = 32) out vec4 gohanARRAY;\n";
   20557 	// The test considers gohan overflows the buffer 0, but according to spec, it is valid to declare the variable with qualifier "layout (xfb_offset = 16, xfb_stride = 32) out vec4 gohan;"
   20558 	// To make the shader failed to compile, change xfb_stride to a value that is smaller than 32
   20559 	static const GLchar* stride_var_definition = "layout (xfb_buffer = 0, xfb_stride = 28) out;\n"
   20560 												 "\n"
   20561 												 "layout (xfb_offset = 16, xfb_stride = 28) out vec4 gohanARRAY;\n";
   20562 	static const GLchar* array_use = "    gohanINDEX[0] = result / 2;\n"
   20563 									 "    gohanINDEX[1] = result / 4;\n"
   20564 									 "    gohanINDEX[2] = result / 6;\n"
   20565 									 "    gohanINDEX[3] = result / 8;\n";
   20566 	static const GLchar* block_use = "    gokuINDEX.gohan  = result / 2;\n"
   20567 									 "    gokuINDEX.goten  = result / 4;\n"
   20568 									 "    gokuINDEX.chichi = result / 6;\n";
   20569 	static const GLchar* output_use = "gohanINDEX = result / 4;\n";
   20570 	static const GLchar* fs			= "#version 430 core\n"
   20571 							  "#extension GL_ARB_enhanced_layouts : require\n"
   20572 							  "\n"
   20573 							  "in  vec4 gs_fs;\n"
   20574 							  "out vec4 fs_out;\n"
   20575 							  "\n"
   20576 							  "void main()\n"
   20577 							  "{\n"
   20578 							  "    fs_out = gs_fs;\n"
   20579 							  "}\n"
   20580 							  "\n";
   20581 	static const GLchar* gs_tested = "#version 430 core\n"
   20582 									 "#extension GL_ARB_enhanced_layouts : require\n"
   20583 									 "\n"
   20584 									 "layout(points)                           in;\n"
   20585 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   20586 									 "\n"
   20587 									 "VAR_DEFINITION"
   20588 									 "\n"
   20589 									 "in  vec4 tes_gs[];\n"
   20590 									 "out vec4 gs_fs;\n"
   20591 									 "\n"
   20592 									 "void main()\n"
   20593 									 "{\n"
   20594 									 "    vec4 result = tes_gs[0];\n"
   20595 									 "\n"
   20596 									 "VARIABLE_USE"
   20597 									 "\n"
   20598 									 "    gs_fs = result;\n"
   20599 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   20600 									 "    EmitVertex();\n"
   20601 									 "    gs_fs = result;\n"
   20602 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   20603 									 "    EmitVertex();\n"
   20604 									 "    gs_fs = result;\n"
   20605 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   20606 									 "    EmitVertex();\n"
   20607 									 "    gs_fs = result;\n"
   20608 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   20609 									 "    EmitVertex();\n"
   20610 									 "}\n"
   20611 									 "\n";
   20612 	static const GLchar* tcs = "#version 430 core\n"
   20613 							   "#extension GL_ARB_enhanced_layouts : require\n"
   20614 							   "\n"
   20615 							   "layout(vertices = 1) out;\n"
   20616 							   "\n"
   20617 							   "in  vec4 vs_tcs[];\n"
   20618 							   "out vec4 tcs_tes[];\n"
   20619 							   "\n"
   20620 							   "void main()\n"
   20621 							   "{\n"
   20622 							   "\n"
   20623 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   20624 							   "\n"
   20625 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   20626 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   20627 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   20628 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   20629 							   "    gl_TessLevelInner[0] = 1.0;\n"
   20630 							   "    gl_TessLevelInner[1] = 1.0;\n"
   20631 							   "}\n"
   20632 							   "\n";
   20633 	static const GLchar* tcs_tested = "#version 430 core\n"
   20634 									  "#extension GL_ARB_enhanced_layouts : require\n"
   20635 									  "\n"
   20636 									  "layout(vertices = 1) out;\n"
   20637 									  "\n"
   20638 									  "VAR_DEFINITION"
   20639 									  "\n"
   20640 									  "in  vec4 vs_tcs[];\n"
   20641 									  "out vec4 tcs_tes[];\n"
   20642 									  "\n"
   20643 									  "void main()\n"
   20644 									  "{\n"
   20645 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   20646 									  "\n"
   20647 									  "VARIABLE_USE"
   20648 									  "\n"
   20649 									  "    tcs_tes[gl_InvocationID] = result;\n"
   20650 									  "\n"
   20651 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   20652 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   20653 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   20654 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   20655 									  "    gl_TessLevelInner[0] = 1.0;\n"
   20656 									  "    gl_TessLevelInner[1] = 1.0;\n"
   20657 									  "}\n"
   20658 									  "\n";
   20659 	static const GLchar* tes_tested = "#version 430 core\n"
   20660 									  "#extension GL_ARB_enhanced_layouts : require\n"
   20661 									  "\n"
   20662 									  "layout(isolines, point_mode) in;\n"
   20663 									  "\n"
   20664 									  "VAR_DEFINITION"
   20665 									  "\n"
   20666 									  "in  vec4 tcs_tes[];\n"
   20667 									  "out vec4 tes_gs;\n"
   20668 									  "\n"
   20669 									  "void main()\n"
   20670 									  "{\n"
   20671 									  "    vec4 result = tcs_tes[0];\n"
   20672 									  "\n"
   20673 									  "VARIABLE_USE"
   20674 									  "\n"
   20675 									  "    tes_gs += result;\n"
   20676 									  "}\n"
   20677 									  "\n";
   20678 	static const GLchar* vs = "#version 430 core\n"
   20679 							  "#extension GL_ARB_enhanced_layouts : require\n"
   20680 							  "\n"
   20681 							  "in  vec4 in_vs;\n"
   20682 							  "out vec4 vs_tcs;\n"
   20683 							  "\n"
   20684 							  "void main()\n"
   20685 							  "{\n"
   20686 							  "    vs_tcs = in_vs;\n"
   20687 							  "}\n"
   20688 							  "\n";
   20689 	static const GLchar* vs_tested = "#version 430 core\n"
   20690 									 "#extension GL_ARB_enhanced_layouts : require\n"
   20691 									 "\n"
   20692 									 "VAR_DEFINITION"
   20693 									 "\n"
   20694 									 "in  vec4 in_vs;\n"
   20695 									 "out vec4 vs_tcs;\n"
   20696 									 "\n"
   20697 									 "void main()\n"
   20698 									 "{\n"
   20699 									 "    vec4 result = in_vs;\n"
   20700 									 "\n"
   20701 									 "VARIABLE_USE"
   20702 									 "\n"
   20703 									 "    vs_tcs += result;\n"
   20704 									 "}\n"
   20705 									 "\n";
   20706 
   20707 	std::string source;
   20708 	testCase&   test_case = m_test_cases[test_case_index];
   20709 
   20710 	if (test_case.m_stage == stage)
   20711 	{
   20712 		const GLchar* array	= "";
   20713 		const GLchar* index	= "";
   20714 		size_t		  position = 0;
   20715 		size_t		  temp;
   20716 		const GLchar* var_definition = 0;
   20717 		const GLchar* var_use		 = 0;
   20718 
   20719 		switch (test_case.m_case)
   20720 		{
   20721 		case OFFSET:
   20722 			var_definition = offset_var_definition;
   20723 			var_use		   = output_use;
   20724 			break;
   20725 		case STRIDE:
   20726 			var_definition = stride_var_definition;
   20727 			var_use		   = output_use;
   20728 			break;
   20729 		case BLOCK:
   20730 			var_definition = block_var_definition;
   20731 			var_use		   = block_use;
   20732 			break;
   20733 		case ARRAY:
   20734 			var_definition = array_var_definition;
   20735 			var_use		   = array_use;
   20736 			break;
   20737 		default:
   20738 			TCU_FAIL("Invalid enum");
   20739 		}
   20740 
   20741 		switch (stage)
   20742 		{
   20743 		case Utils::Shader::GEOMETRY:
   20744 			source = gs_tested;
   20745 			array  = "[]";
   20746 			index  = "[0]";
   20747 			break;
   20748 		case Utils::Shader::TESS_CTRL:
   20749 			source = tcs_tested;
   20750 			array  = "[]";
   20751 			index  = "[gl_InvocationID]";
   20752 			break;
   20753 		case Utils::Shader::TESS_EVAL:
   20754 			source = tes_tested;
   20755 			array  = "[]";
   20756 			index  = "[0]";
   20757 			break;
   20758 		case Utils::Shader::VERTEX:
   20759 			source = vs_tested;
   20760 			break;
   20761 		default:
   20762 			TCU_FAIL("Invalid enum");
   20763 		}
   20764 
   20765 		temp = position;
   20766 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   20767 		position = temp;
   20768 		Utils::replaceToken("ARRAY", position, array, source);
   20769 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   20770 
   20771 		Utils::replaceAllTokens("INDEX", index, source);
   20772 	}
   20773 	else
   20774 	{
   20775 		switch (test_case.m_stage)
   20776 		{
   20777 		case Utils::Shader::GEOMETRY:
   20778 			switch (stage)
   20779 			{
   20780 			case Utils::Shader::FRAGMENT:
   20781 				source = fs;
   20782 				break;
   20783 			case Utils::Shader::VERTEX:
   20784 				source = vs;
   20785 				break;
   20786 			default:
   20787 				source = "";
   20788 			}
   20789 			break;
   20790 		case Utils::Shader::TESS_CTRL:
   20791 			switch (stage)
   20792 			{
   20793 			case Utils::Shader::FRAGMENT:
   20794 				source = fs;
   20795 				break;
   20796 			case Utils::Shader::VERTEX:
   20797 				source = vs;
   20798 				break;
   20799 			default:
   20800 				source = "";
   20801 			}
   20802 			break;
   20803 		case Utils::Shader::TESS_EVAL:
   20804 			switch (stage)
   20805 			{
   20806 			case Utils::Shader::FRAGMENT:
   20807 				source = fs;
   20808 				break;
   20809 			case Utils::Shader::TESS_CTRL:
   20810 				source = tcs;
   20811 				break;
   20812 			case Utils::Shader::VERTEX:
   20813 				source = vs;
   20814 				break;
   20815 			default:
   20816 				source = "";
   20817 			}
   20818 			break;
   20819 		case Utils::Shader::VERTEX:
   20820 			switch (stage)
   20821 			{
   20822 			case Utils::Shader::FRAGMENT:
   20823 				source = fs;
   20824 				break;
   20825 			default:
   20826 				source = "";
   20827 			}
   20828 			break;
   20829 		default:
   20830 			TCU_FAIL("Invalid enum");
   20831 			break;
   20832 		}
   20833 	}
   20834 
   20835 	return source;
   20836 }
   20837 
   20838 /** Get description of test case
   20839  *
   20840  * @param test_case_index Index of test case
   20841  *
   20842  * @return Test case description
   20843  **/
   20844 std::string XFBTooSmallStrideTest::getTestCaseName(GLuint test_case_index)
   20845 {
   20846 	std::stringstream stream;
   20847 	testCase&		  test_case = m_test_cases[test_case_index];
   20848 
   20849 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage) << ", case: ";
   20850 
   20851 	switch (test_case.m_case)
   20852 	{
   20853 	case OFFSET:
   20854 		stream << "buffer stride: 40, vec4 offset: 32";
   20855 		break;
   20856 	case STRIDE:
   20857 		stream << "buffer stride: 32, vec4 off 16 stride: 32";
   20858 		break;
   20859 	case BLOCK:
   20860 		stream << "buffer stride: 32, block 3xvec4 offset 0";
   20861 		break;
   20862 	case ARRAY:
   20863 		stream << "buffer stride: 32, vec4[4] offset 16";
   20864 		break;
   20865 	default:
   20866 		TCU_FAIL("Invalid enum");
   20867 	}
   20868 
   20869 	return stream.str();
   20870 }
   20871 
   20872 /** Get number of test cases
   20873  *
   20874  * @return Number of test cases
   20875  **/
   20876 GLuint XFBTooSmallStrideTest::getTestCaseNumber()
   20877 {
   20878 	return static_cast<GLuint>(m_test_cases.size());
   20879 }
   20880 
   20881 /** Selects if "compute" stage is relevant for test
   20882  *
   20883  * @param ignored
   20884  *
   20885  * @return false
   20886  **/
   20887 bool XFBTooSmallStrideTest::isComputeRelevant(GLuint /* test_case_index */)
   20888 {
   20889 	return false;
   20890 }
   20891 
   20892 /** Prepare all test cases
   20893  *
   20894  **/
   20895 void XFBTooSmallStrideTest::testInit()
   20896 {
   20897 	for (GLuint c = 0; c < CASE_MAX; ++c)
   20898 	{
   20899 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   20900 		{
   20901 			/*
   20902 			 It is invalid to define transform feedback output in TCS, according to spec:
   20903 			 The data captured in transform feedback mode depends on the active programs on each of the shader stages.
   20904 			 If a program is active for the geometry shader stage, transform feedback captures the vertices of each
   20905 			 primitive emitted by the geometry shader. Otherwise, if a program is active for the tessellation evaluation
   20906 			 shader stage, transform feedback captures each primitive produced by the tessellation primitive generator,
   20907 			 whose vertices are processed by the tessellation evaluation shader. Otherwise, transform feedback captures
   20908 			 each primitive processed by the vertex shader.
   20909 			 */
   20910 			if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::TESS_CTRL == stage) ||
   20911 				(Utils::Shader::FRAGMENT == stage))
   20912 			{
   20913 				continue;
   20914 			}
   20915 
   20916 			testCase test_case = { (CASES)c, (Utils::Shader::STAGES)stage };
   20917 
   20918 			m_test_cases.push_back(test_case);
   20919 		}
   20920 	}
   20921 }
   20922 
   20923 /** Constructor
   20924  *
   20925  * @param context Test framework context
   20926  **/
   20927 XFBVariableStrideTest::XFBVariableStrideTest(deqp::Context& context)
   20928 	: NegativeTestBase(context, "xfb_variable_stride", "Test verifies that stride qualifier is respected")
   20929 {
   20930 }
   20931 
   20932 /** Source for given test case and stage
   20933  *
   20934  * @param test_case_index Index of test case
   20935  * @param stage           Shader stage
   20936  *
   20937  * @return Shader source
   20938  **/
   20939 std::string XFBVariableStrideTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   20940 {
   20941 	static const GLchar* invalid_var_definition =
   20942 		"const uint type_size = SIZE;\n"
   20943 		"\n"
   20944 		"layout (xfb_offset = 0, xfb_stride = 2 * type_size) out TYPE gokuARRAY;\n"
   20945 		"layout (xfb_offset = type_size)                     out TYPE vegetaARRAY;\n";
   20946 	static const GLchar* valid_var_definition =
   20947 		"const uint type_size = SIZE;\n"
   20948 		"\n"
   20949 		"layout (xfb_offset = 0, xfb_stride = 2 * type_size) out TYPE gokuARRAY;\n";
   20950 	static const GLchar* invalid_use = "    gokuINDEX   = TYPE(1);\n"
   20951 									   "    vegetaINDEX = TYPE(0);\n"
   20952 									   "    if (vec4(0) == result)\n"
   20953 									   "    {\n"
   20954 									   "        gokuINDEX   = TYPE(0);\n"
   20955 									   "        vegetaINDEX = TYPE(1);\n"
   20956 									   "    }\n";
   20957 	static const GLchar* valid_use = "    gokuINDEX   = TYPE(1);\n"
   20958 									 "    if (vec4(0) == result)\n"
   20959 									 "    {\n"
   20960 									 "        gokuINDEX   = TYPE(0);\n"
   20961 									 "    }\n";
   20962 	static const GLchar* fs = "#version 430 core\n"
   20963 							  "#extension GL_ARB_enhanced_layouts : require\n"
   20964 							  "\n"
   20965 							  "in  vec4 any_fs;\n"
   20966 							  "out vec4 fs_out;\n"
   20967 							  "\n"
   20968 							  "void main()\n"
   20969 							  "{\n"
   20970 							  "    fs_out = any_fs;\n"
   20971 							  "}\n"
   20972 							  "\n";
   20973 	static const GLchar* gs_tested = "#version 430 core\n"
   20974 									 "#extension GL_ARB_enhanced_layouts : require\n"
   20975 									 "\n"
   20976 									 "layout(points)                           in;\n"
   20977 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   20978 									 "\n"
   20979 									 "VAR_DEFINITION"
   20980 									 "\n"
   20981 									 "in  vec4 vs_any[];\n"
   20982 									 "out vec4 any_fs;\n"
   20983 									 "\n"
   20984 									 "void main()\n"
   20985 									 "{\n"
   20986 									 "    vec4 result = vs_any[0];\n"
   20987 									 "\n"
   20988 									 "VARIABLE_USE"
   20989 									 "\n"
   20990 									 "    any_fs = result;\n"
   20991 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   20992 									 "    EmitVertex();\n"
   20993 									 "    any_fs = result;\n"
   20994 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   20995 									 "    EmitVertex();\n"
   20996 									 "    any_fs = result;\n"
   20997 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   20998 									 "    EmitVertex();\n"
   20999 									 "    any_fs = result;\n"
   21000 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   21001 									 "    EmitVertex();\n"
   21002 									 "}\n"
   21003 									 "\n";
   21004 	static const GLchar* tcs = "#version 430 core\n"
   21005 							   "#extension GL_ARB_enhanced_layouts : require\n"
   21006 							   "\n"
   21007 							   "layout(vertices = 1) out;\n"
   21008 							   "\n"
   21009 							   "in  vec4 vs_any[];\n"
   21010 							   "out vec4 tcs_tes[];\n"
   21011 							   "\n"
   21012 							   "void main()\n"
   21013 							   "{\n"
   21014 							   "\n"
   21015 							   "    tcs_tes[gl_InvocationID] = vs_any[gl_InvocationID];\n"
   21016 							   "\n"
   21017 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   21018 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   21019 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   21020 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   21021 							   "    gl_TessLevelInner[0] = 1.0;\n"
   21022 							   "    gl_TessLevelInner[1] = 1.0;\n"
   21023 							   "}\n"
   21024 							   "\n";
   21025 	static const GLchar* tcs_tested = "#version 430 core\n"
   21026 									  "#extension GL_ARB_enhanced_layouts : require\n"
   21027 									  "\n"
   21028 									  "layout(vertices = 1) out;\n"
   21029 									  "\n"
   21030 									  "VAR_DEFINITION"
   21031 									  "\n"
   21032 									  "in  vec4 vs_any[];\n"
   21033 									  "out vec4 any_fs[];\n"
   21034 									  "\n"
   21035 									  "void main()\n"
   21036 									  "{\n"
   21037 									  "    vec4 result = vs_any[gl_InvocationID];\n"
   21038 									  "\n"
   21039 									  "VARIABLE_USE"
   21040 									  "\n"
   21041 									  "    any_fs[gl_InvocationID] = result;\n"
   21042 									  "\n"
   21043 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   21044 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   21045 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   21046 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   21047 									  "    gl_TessLevelInner[0] = 1.0;\n"
   21048 									  "    gl_TessLevelInner[1] = 1.0;\n"
   21049 									  "}\n"
   21050 									  "\n";
   21051 	static const GLchar* tes_tested = "#version 430 core\n"
   21052 									  "#extension GL_ARB_enhanced_layouts : require\n"
   21053 									  "\n"
   21054 									  "layout(isolines, point_mode) in;\n"
   21055 									  "\n"
   21056 									  "VAR_DEFINITION"
   21057 									  "\n"
   21058 									  "in  vec4 tcs_tes[];\n"
   21059 									  "out vec4 any_fs;\n"
   21060 									  "\n"
   21061 									  "void main()\n"
   21062 									  "{\n"
   21063 									  "    vec4 result = tcs_tes[0];\n"
   21064 									  "\n"
   21065 									  "VARIABLE_USE"
   21066 									  "\n"
   21067 									  "    any_fs = result;\n"
   21068 									  "}\n"
   21069 									  "\n";
   21070 	static const GLchar* vs = "#version 430 core\n"
   21071 							  "#extension GL_ARB_enhanced_layouts : require\n"
   21072 							  "\n"
   21073 							  "in  vec4 in_vs;\n"
   21074 							  "out vec4 vs_any;\n"
   21075 							  "\n"
   21076 							  "void main()\n"
   21077 							  "{\n"
   21078 							  "    vs_any = in_vs;\n"
   21079 							  "}\n"
   21080 							  "\n";
   21081 	static const GLchar* vs_tested = "#version 430 core\n"
   21082 									 "#extension GL_ARB_enhanced_layouts : require\n"
   21083 									 "\n"
   21084 									 "VAR_DEFINITION"
   21085 									 "\n"
   21086 									 "in  vec4 in_vs;\n"
   21087 									 "out vec4 any_fs;\n"
   21088 									 "\n"
   21089 									 "void main()\n"
   21090 									 "{\n"
   21091 									 "    vec4 result = in_vs;\n"
   21092 									 "\n"
   21093 									 "VARIABLE_USE"
   21094 									 "\n"
   21095 									 "    any_fs = result;\n"
   21096 									 "}\n"
   21097 									 "\n";
   21098 
   21099 	std::string source;
   21100 	testCase&   test_case = m_test_cases[test_case_index];
   21101 
   21102 	if (test_case.m_stage == stage)
   21103 	{
   21104 		const GLchar* array = "";
   21105 		GLchar		  buffer[16];
   21106 		const GLchar* index	= "";
   21107 		size_t		  position = 0;
   21108 		size_t		  temp;
   21109 		const GLchar* type_name		 = test_case.m_type.GetGLSLTypeName();
   21110 		const GLchar* var_definition = 0;
   21111 		const GLchar* var_use		 = 0;
   21112 
   21113 		sprintf(buffer, "%d", test_case.m_type.GetSize());
   21114 
   21115 		switch (test_case.m_case)
   21116 		{
   21117 		case VALID:
   21118 			var_definition = valid_var_definition;
   21119 			var_use		   = valid_use;
   21120 			break;
   21121 		case INVALID:
   21122 			var_definition = invalid_var_definition;
   21123 			var_use		   = invalid_use;
   21124 			break;
   21125 		default:
   21126 			TCU_FAIL("Invalid enum");
   21127 		}
   21128 
   21129 		switch (stage)
   21130 		{
   21131 		case Utils::Shader::GEOMETRY:
   21132 			source = gs_tested;
   21133 			array  = "[1]";
   21134 			index  = "[0]";
   21135 			break;
   21136 		case Utils::Shader::TESS_CTRL:
   21137 			source = tcs_tested;
   21138 			array  = "[1]";
   21139 			index  = "[gl_InvocationID]";
   21140 			break;
   21141 		case Utils::Shader::TESS_EVAL:
   21142 			source = tes_tested;
   21143 			array  = "[1]";
   21144 			index  = "[0]";
   21145 			break;
   21146 		case Utils::Shader::VERTEX:
   21147 			source = vs_tested;
   21148 			break;
   21149 		default:
   21150 			TCU_FAIL("Invalid enum");
   21151 		}
   21152 
   21153 		temp = position;
   21154 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   21155 		position = temp;
   21156 		Utils::replaceToken("SIZE", position, buffer, source);
   21157 		Utils::replaceToken("ARRAY", position, array, source);
   21158 		if (INVALID == test_case.m_case)
   21159 		{
   21160 			Utils::replaceToken("ARRAY", position, array, source);
   21161 		}
   21162 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   21163 
   21164 		Utils::replaceAllTokens("TYPE", type_name, source);
   21165 		Utils::replaceAllTokens("INDEX", index, source);
   21166 	}
   21167 	else
   21168 	{
   21169 		switch (test_case.m_stage)
   21170 		{
   21171 		case Utils::Shader::GEOMETRY:
   21172 			switch (stage)
   21173 			{
   21174 			case Utils::Shader::FRAGMENT:
   21175 				source = fs;
   21176 				break;
   21177 			case Utils::Shader::VERTEX:
   21178 				source = vs;
   21179 				break;
   21180 			default:
   21181 				source = "";
   21182 			}
   21183 			break;
   21184 		case Utils::Shader::TESS_CTRL:
   21185 			switch (stage)
   21186 			{
   21187 			case Utils::Shader::FRAGMENT:
   21188 				source = fs;
   21189 				break;
   21190 			case Utils::Shader::VERTEX:
   21191 				source = vs;
   21192 				break;
   21193 			default:
   21194 				source = "";
   21195 			}
   21196 			break;
   21197 		case Utils::Shader::TESS_EVAL:
   21198 			switch (stage)
   21199 			{
   21200 			case Utils::Shader::FRAGMENT:
   21201 				source = fs;
   21202 				break;
   21203 			case Utils::Shader::TESS_CTRL:
   21204 				source = tcs;
   21205 				break;
   21206 			case Utils::Shader::VERTEX:
   21207 				source = vs;
   21208 				break;
   21209 			default:
   21210 				source = "";
   21211 			}
   21212 			break;
   21213 		case Utils::Shader::VERTEX:
   21214 			switch (stage)
   21215 			{
   21216 			case Utils::Shader::FRAGMENT:
   21217 				source = fs;
   21218 				break;
   21219 			default:
   21220 				source = "";
   21221 			}
   21222 			break;
   21223 		default:
   21224 			TCU_FAIL("Invalid enum");
   21225 			break;
   21226 		}
   21227 	}
   21228 
   21229 	return source;
   21230 }
   21231 
   21232 /** Get description of test case
   21233  *
   21234  * @param test_case_index Index of test case
   21235  *
   21236  * @return Test case description
   21237  **/
   21238 std::string XFBVariableStrideTest::getTestCaseName(GLuint test_case_index)
   21239 {
   21240 	std::stringstream stream;
   21241 	testCase&		  test_case = m_test_cases[test_case_index];
   21242 
   21243 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage)
   21244 		   << ", type: " << test_case.m_type.GetGLSLTypeName() << ", case: ";
   21245 
   21246 	switch (test_case.m_case)
   21247 	{
   21248 	case VALID:
   21249 		stream << "valid";
   21250 		break;
   21251 	case INVALID:
   21252 		stream << "invalid";
   21253 		break;
   21254 	default:
   21255 		TCU_FAIL("Invalid enum");
   21256 	}
   21257 
   21258 	return stream.str();
   21259 }
   21260 
   21261 /** Get number of test cases
   21262  *
   21263  * @return Number of test cases
   21264  **/
   21265 GLuint XFBVariableStrideTest::getTestCaseNumber()
   21266 {
   21267 	return static_cast<GLuint>(m_test_cases.size());
   21268 }
   21269 
   21270 /** Selects if "compute" stage is relevant for test
   21271  *
   21272  * @param ignored
   21273  *
   21274  * @return false
   21275  **/
   21276 bool XFBVariableStrideTest::isComputeRelevant(GLuint /* test_case_index */)
   21277 {
   21278 	return false;
   21279 }
   21280 
   21281 /** Selects if compilation failure is expected result
   21282  *
   21283  * @param test_case_index Index of test case
   21284  *
   21285  * @return true
   21286  **/
   21287 bool XFBVariableStrideTest::isFailureExpected(GLuint test_case_index)
   21288 {
   21289 	testCase& test_case = m_test_cases[test_case_index];
   21290 
   21291 	return (INVALID == test_case.m_case);
   21292 }
   21293 
   21294 /** Prepare all test cases
   21295  *
   21296  **/
   21297 void XFBVariableStrideTest::testInit()
   21298 {
   21299 	const GLuint n_types = getTypesNumber();
   21300 
   21301 	for (GLuint i = 0; i < n_types; ++i)
   21302 	{
   21303 		const Utils::Type& type = getType(i);
   21304 
   21305 		/*
   21306 		 Some of the cases are declared as following are considered as invalid,
   21307 		 but accoring to spec, the following declaration is valid: shaders in the
   21308 		 transform feedback capturing mode have an initial global default of layout(xfb_buffer=0) out,
   21309 		 so for the first variable's declaration, the xfb_stride = 16 is applied on buffer 0,  for the
   21310 		 second variable, its buffer is also inherited from global buffer 0, and its offset does not overflows
   21311 		 the stride.
   21312 
   21313 		 The xfb_stride is the memory width of given buffer, not for variable even though xfb_stride
   21314 		 is declared on the variable. It seems that the writter of this case misunderstand the concept of
   21315 		 xfb_stride, because spec describes that xfb_stride can be declared multiple times for the same buffer,
   21316 		 it is a compile or link-time error to have different values specified for the stride for the same buffer.
   21317 
   21318 		 int type_size = 8;
   21319 		 layout (xfb_offset = 0, xfb_stride = 2 * type_size) out double goku;
   21320 		 layout (xfb_offset = type_size)                     out double vegeta;
   21321 		 */
   21322 		// all the shaders are valid, so remove the following loop(it contains CASE_MAX is enum of valid and invalid)
   21323 		// for (GLuint c = 0; c < CASE_MAX; ++c)
   21324 		{
   21325 			for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   21326 			{
   21327 				if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::TESS_CTRL == stage) ||
   21328 					(Utils::Shader::FRAGMENT == stage))
   21329 				{
   21330 					continue;
   21331 				}
   21332 
   21333 				testCase test_case = { (CASES)VALID, (Utils::Shader::STAGES)stage, type };
   21334 
   21335 				m_test_cases.push_back(test_case);
   21336 			}
   21337 		}
   21338 	}
   21339 }
   21340 
   21341 /** Constructor
   21342  *
   21343  * @param context Test framework context
   21344  **/
   21345 XFBBlockStrideTest::XFBBlockStrideTest(deqp::Context& context)
   21346 	: TestBase(context, "xfb_block_stride", "Test verifies that stride qualifier is respected for blocks")
   21347 {
   21348 }
   21349 
   21350 /** Source for given test case and stage
   21351  *
   21352  * @param test_case_index Index of test case
   21353  * @param stage           Shader stage
   21354  *
   21355  * @return Shader source
   21356  **/
   21357 std::string XFBBlockStrideTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   21358 {
   21359 	static const GLchar* var_definition = "layout (xfb_offset = 0, xfb_stride = 128) out Goku {\n"
   21360 										  "    vec4 gohan;\n"
   21361 										  "    vec4 goten;\n"
   21362 										  "    vec4 chichi;\n"
   21363 										  "} gokuARRAY;\n";
   21364 	static const GLchar* var_use = "    gokuINDEX.gohan  = vec4(1, 0, 0, 0);\n"
   21365 								   "    gokuINDEX.goten  = vec4(0, 0, 1, 0);\n"
   21366 								   "    gokuINDEX.chichi = vec4(0, 1, 0, 0);\n"
   21367 								   "    if (vec4(0) == result)\n"
   21368 								   "    {\n"
   21369 								   "        gokuINDEX.gohan  = vec4(0, 1, 1, 1);\n"
   21370 								   "        gokuINDEX.goten  = vec4(1, 1, 0, 1);\n"
   21371 								   "        gokuINDEX.chichi = vec4(1, 0, 1, 1);\n"
   21372 								   "    }\n";
   21373 	static const GLchar* gs_tested =
   21374 		"#version 430 core\n"
   21375 		"#extension GL_ARB_enhanced_layouts : require\n"
   21376 		"\n"
   21377 		"layout(points)                           in;\n"
   21378 		"layout(triangle_strip, max_vertices = 4) out;\n"
   21379 		"\n"
   21380 		"VAR_DEFINITION"
   21381 		"\n"
   21382 		"out gl_PerVertex \n"
   21383 		"{ \n"
   21384 		"   vec4  gl_Position; \n" // gl_Position must be redeclared in separable program mode
   21385 		"}; \n"
   21386 		"in  vec4 tes_gs[];\n"
   21387 		"out vec4 gs_fs;\n"
   21388 		"\n"
   21389 		"void main()\n"
   21390 		"{\n"
   21391 		"    vec4 result = tes_gs[0];\n"
   21392 		"\n"
   21393 		"VARIABLE_USE"
   21394 		"\n"
   21395 		"    gs_fs = result;\n"
   21396 		"    gl_Position  = vec4(-1, -1, 0, 1);\n"
   21397 		"    EmitVertex();\n"
   21398 		"    gs_fs = result;\n"
   21399 		"    gl_Position  = vec4(-1, 1, 0, 1);\n"
   21400 		"    EmitVertex();\n"
   21401 		"    gs_fs = result;\n"
   21402 		"    gl_Position  = vec4(1, -1, 0, 1);\n"
   21403 		"    EmitVertex();\n"
   21404 		"    gs_fs = result;\n"
   21405 		"    gl_Position  = vec4(1, 1, 0, 1);\n"
   21406 		"    EmitVertex();\n"
   21407 		"}\n"
   21408 		"\n";
   21409 	static const GLchar* tcs = "#version 430 core\n"
   21410 							   "#extension GL_ARB_enhanced_layouts : require\n"
   21411 							   "\n"
   21412 							   "layout(vertices = 1) out;\n"
   21413 							   "\n"
   21414 							   "in  vec4 vs_tcs[];\n"
   21415 							   "out vec4 tcs_tes[];\n"
   21416 							   "\n"
   21417 							   "void main()\n"
   21418 							   "{\n"
   21419 							   "\n"
   21420 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   21421 							   "\n"
   21422 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   21423 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   21424 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   21425 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   21426 							   "    gl_TessLevelInner[0] = 1.0;\n"
   21427 							   "    gl_TessLevelInner[1] = 1.0;\n"
   21428 							   "}\n"
   21429 							   "\n";
   21430 #if 0
   21431 	static const GLchar* tcs_tested =
   21432 		"#version 430 core\n"
   21433 		"#extension GL_ARB_enhanced_layouts : require\n"
   21434 		"\n"
   21435 		"layout(vertices = 1) out;\n"
   21436 		"\n"
   21437 		"VAR_DEFINITION"
   21438 		"\n"
   21439 		"in  vec4 vs_tcs[];\n"
   21440 		"out vec4 tcs_tes[];\n"
   21441 		"\n"
   21442 		"void main()\n"
   21443 		"{\n"
   21444 		"    vec4 result = vs_tcs[gl_InvocationID];\n"
   21445 		"\n"
   21446 		"VARIABLE_USE"
   21447 		"\n"
   21448 		"    tcs_tes[gl_InvocationID] = result;\n"
   21449 		"\n"
   21450 		"    gl_TessLevelOuter[0] = 1.0;\n"
   21451 		"    gl_TessLevelOuter[1] = 1.0;\n"
   21452 		"    gl_TessLevelOuter[2] = 1.0;\n"
   21453 		"    gl_TessLevelOuter[3] = 1.0;\n"
   21454 		"    gl_TessLevelInner[0] = 1.0;\n"
   21455 		"    gl_TessLevelInner[1] = 1.0;\n"
   21456 		"}\n"
   21457 		"\n";
   21458 #endif
   21459 	static const GLchar* tes_tested = "#version 430 core\n"
   21460 									  "#extension GL_ARB_enhanced_layouts : require\n"
   21461 									  "\n"
   21462 									  "layout(isolines, point_mode) in;\n"
   21463 									  "\n"
   21464 									  "VAR_DEFINITION"
   21465 									  "\n"
   21466 									  "in  vec4 tcs_tes[];\n"
   21467 									  "out vec4 tes_gs;\n"
   21468 									  "\n"
   21469 									  "void main()\n"
   21470 									  "{\n"
   21471 									  "    vec4 result = tcs_tes[0];\n"
   21472 									  "\n"
   21473 									  "VARIABLE_USE"
   21474 									  "\n"
   21475 									  "    tes_gs += result;\n"
   21476 									  "}\n"
   21477 									  "\n";
   21478 	static const GLchar* vs = "#version 430 core\n"
   21479 							  "#extension GL_ARB_enhanced_layouts : require\n"
   21480 							  "\n"
   21481 							  "in  vec4 in_vs;\n"
   21482 							  "out vec4 vs_tcs;\n"
   21483 							  "\n"
   21484 							  "void main()\n"
   21485 							  "{\n"
   21486 							  "    vs_tcs = in_vs;\n"
   21487 							  "}\n"
   21488 							  "\n";
   21489 	static const GLchar* vs_tested = "#version 430 core\n"
   21490 									 "#extension GL_ARB_enhanced_layouts : require\n"
   21491 									 "\n"
   21492 									 "VAR_DEFINITION"
   21493 									 "\n"
   21494 									 "in  vec4 in_vs;\n"
   21495 									 "out vec4 vs_tcs;\n"
   21496 									 "\n"
   21497 									 "void main()\n"
   21498 									 "{\n"
   21499 									 "    vec4 result = in_vs;\n"
   21500 									 "\n"
   21501 									 "VARIABLE_USE"
   21502 									 "\n"
   21503 									 "    vs_tcs += result;\n"
   21504 									 "}\n"
   21505 									 "\n";
   21506 
   21507 	std::string			  source;
   21508 	Utils::Shader::STAGES test_case = m_test_cases[test_case_index];
   21509 
   21510 	if (test_case == stage)
   21511 	{
   21512 		const GLchar* array	= "";
   21513 		const GLchar* index	= "";
   21514 		size_t		  position = 0;
   21515 		size_t		  temp;
   21516 		// It is a compile time error to apply xfb_offset to the declaration of an unsized array(GLSL4.5 spec: Page73)
   21517 		// change array = "[]" to "[1]"
   21518 		switch (stage)
   21519 		{
   21520 		case Utils::Shader::GEOMETRY:
   21521 			source = gs_tested;
   21522 			array  = "[1]";
   21523 			index  = "[0]";
   21524 			break;
   21525 /*
   21526 			 It is invalid to define transform feedback output in HS
   21527 			 */
   21528 #if 0
   21529 			case Utils::Shader::TESS_CTRL:
   21530 			source = tcs_tested;
   21531 			array = "[]";
   21532 			index = "[gl_InvocationID]";
   21533 			break;
   21534 #endif
   21535 		case Utils::Shader::TESS_EVAL:
   21536 			source = tes_tested;
   21537 			array  = "[1]";
   21538 			index  = "[0]";
   21539 			break;
   21540 		case Utils::Shader::VERTEX:
   21541 			source = vs_tested;
   21542 			break;
   21543 		default:
   21544 			TCU_FAIL("Invalid enum");
   21545 		}
   21546 
   21547 		temp = position;
   21548 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   21549 		position = temp;
   21550 		Utils::replaceToken("ARRAY", position, array, source);
   21551 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   21552 
   21553 		Utils::replaceAllTokens("INDEX", index, source);
   21554 	}
   21555 	else
   21556 	{
   21557 		switch (test_case)
   21558 		{
   21559 		case Utils::Shader::GEOMETRY:
   21560 			switch (stage)
   21561 			{
   21562 			case Utils::Shader::VERTEX:
   21563 				source = vs;
   21564 				break;
   21565 			default:
   21566 				source = "";
   21567 			}
   21568 			break;
   21569 		case Utils::Shader::TESS_CTRL:
   21570 			switch (stage)
   21571 			{
   21572 			case Utils::Shader::VERTEX:
   21573 				source = vs;
   21574 				break;
   21575 			default:
   21576 				source = "";
   21577 			}
   21578 			break;
   21579 		case Utils::Shader::TESS_EVAL:
   21580 			switch (stage)
   21581 			{
   21582 			case Utils::Shader::TESS_CTRL:
   21583 				source = tcs;
   21584 				break;
   21585 			case Utils::Shader::VERTEX:
   21586 				source = vs;
   21587 				break;
   21588 			default:
   21589 				source = "";
   21590 			}
   21591 			break;
   21592 		case Utils::Shader::VERTEX:
   21593 			source = "";
   21594 			break;
   21595 		default:
   21596 			TCU_FAIL("Invalid enum");
   21597 			break;
   21598 		}
   21599 	}
   21600 
   21601 	return source;
   21602 }
   21603 
   21604 /** Get description of test case
   21605  *
   21606  * @param test_case_index Index of test case
   21607  *
   21608  * @return Test case description
   21609  **/
   21610 std::string XFBBlockStrideTest::getTestCaseName(GLuint test_case_index)
   21611 {
   21612 	std::stringstream stream;
   21613 
   21614 	stream << "Stage: " << Utils::Shader::GetStageName(m_test_cases[test_case_index]);
   21615 
   21616 	return stream.str();
   21617 }
   21618 
   21619 /** Get number of test cases
   21620  *
   21621  * @return Number of test cases
   21622  **/
   21623 GLuint XFBBlockStrideTest::getTestCaseNumber()
   21624 {
   21625 	return static_cast<GLuint>(m_test_cases.size());
   21626 }
   21627 
   21628 /** Inspects program for xfb stride
   21629  *
   21630  * @param program Program to query
   21631  *
   21632  * @return true if query results match expected values, false otherwise
   21633  **/
   21634 bool XFBBlockStrideTest::inspectProgram(Utils::Program& program)
   21635 {
   21636 	GLint stride = 0;
   21637 
   21638 	program.GetResource(GL_TRANSFORM_FEEDBACK_BUFFER, 0 /* index */, GL_TRANSFORM_FEEDBACK_BUFFER_STRIDE,
   21639 						1 /* buf_size */, &stride);
   21640 
   21641 	return (128 == stride);
   21642 }
   21643 
   21644 /** Runs test case
   21645  *
   21646  * @param test_case_index Id of test case
   21647  *
   21648  * @return true if test case pass, false otherwise
   21649  **/
   21650 bool XFBBlockStrideTest::testCase(GLuint test_case_index)
   21651 {
   21652 	const std::string& gs_source = getShaderSource(test_case_index, Utils::Shader::GEOMETRY);
   21653 	Utils::Program	 program(m_context);
   21654 	const std::string& tcs_source		= getShaderSource(test_case_index, Utils::Shader::TESS_CTRL);
   21655 	const std::string& tes_source		= getShaderSource(test_case_index, Utils::Shader::TESS_EVAL);
   21656 	bool			   test_case_result = true;
   21657 	const std::string& vs_source		= getShaderSource(test_case_index, Utils::Shader::VERTEX);
   21658 
   21659 	program.Init("" /* cs */, "", gs_source, tcs_source, tes_source, vs_source, true /* separable */);
   21660 
   21661 	test_case_result = inspectProgram(program);
   21662 
   21663 	return test_case_result;
   21664 }
   21665 
   21666 /** Prepare all test cases
   21667  *
   21668  **/
   21669 void XFBBlockStrideTest::testInit()
   21670 {
   21671 	for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   21672 	{
   21673 		if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::TESS_CTRL == stage) ||
   21674 			(Utils::Shader::FRAGMENT == stage))
   21675 		{
   21676 			continue;
   21677 		}
   21678 
   21679 		m_test_cases.push_back((Utils::Shader::STAGES)stage);
   21680 	}
   21681 }
   21682 
   21683 /** Constructor
   21684  *
   21685  * @param context Test context
   21686  **/
   21687 XFBBlockMemberStrideTest::XFBBlockMemberStrideTest(deqp::Context& context)
   21688 	: BufferTestBase(context, "xfb_block_member_stride",
   21689 					 "Test verifies that xfb_stride qualifier is respected for block member")
   21690 {
   21691 	/* Nothing to be done here */
   21692 }
   21693 
   21694 /** Get descriptors of buffers necessary for test
   21695  *
   21696  * @param ignored
   21697  * @param out_descriptors Descriptors of buffers used by test
   21698  **/
   21699 void XFBBlockMemberStrideTest::getBufferDescriptors(glw::GLuint /* test_case_index */,
   21700 													bufferDescriptor::Vector& out_descriptors)
   21701 {
   21702 	const Utils::Type& vec4 = Utils::Type::vec4;
   21703 
   21704 	/* Test needs single uniform and xfb */
   21705 	out_descriptors.resize(2);
   21706 
   21707 	/* Get references */
   21708 	bufferDescriptor& uniform = out_descriptors[0];
   21709 	bufferDescriptor& xfb	 = out_descriptors[1];
   21710 
   21711 	/* Index */
   21712 	uniform.m_index = 0;
   21713 	xfb.m_index		= 0;
   21714 
   21715 	/* Target */
   21716 	uniform.m_target = Utils::Buffer::Uniform;
   21717 	xfb.m_target	 = Utils::Buffer::Transform_feedback;
   21718 
   21719 	/* Data */
   21720 	static const GLuint			vec4_size   = 16;
   21721 	const std::vector<GLubyte>& gohan_data  = vec4.GenerateDataPacked();
   21722 	const std::vector<GLubyte>& goten_data  = vec4.GenerateDataPacked();
   21723 	const std::vector<GLubyte>& chichi_data = vec4.GenerateDataPacked();
   21724 
   21725 	/* Uniform data */
   21726 	uniform.m_initial_data.resize(3 * vec4_size);
   21727 	memcpy(&uniform.m_initial_data[0] + 0, &gohan_data[0], vec4_size);
   21728 	memcpy(&uniform.m_initial_data[0] + vec4_size, &goten_data[0], vec4_size);
   21729 	memcpy(&uniform.m_initial_data[0] + 2 * vec4_size, &chichi_data[0], vec4_size);
   21730 
   21731 	/* XFB data */
   21732 	xfb.m_initial_data.resize(4 * vec4_size);
   21733 	xfb.m_expected_data.resize(4 * vec4_size);
   21734 
   21735 	for (GLuint i = 0; i < 4 * vec4_size; ++i)
   21736 	{
   21737 		xfb.m_initial_data[i]  = (glw::GLubyte)i;
   21738 		xfb.m_expected_data[i] = (glw::GLubyte)i;
   21739 	}
   21740 
   21741 	// the xfb_offset of "chichi" should be 32
   21742 	memcpy(&xfb.m_expected_data[0] + 0, &gohan_data[0], vec4_size);
   21743 	memcpy(&xfb.m_expected_data[0] + vec4_size, &goten_data[0], vec4_size);
   21744 	memcpy(&xfb.m_expected_data[0] + 2 * vec4_size, &chichi_data[0], vec4_size);
   21745 }
   21746 
   21747 /** Get body of main function for given shader stage
   21748  *
   21749  * @param ignored
   21750  * @param stage            Shader stage
   21751  * @param out_assignments  Set to empty
   21752  * @param out_calculations Set to empty
   21753  **/
   21754 void XFBBlockMemberStrideTest::getShaderBody(GLuint /* test_case_index */, Utils::Shader::STAGES stage,
   21755 											 std::string& out_assignments, std::string& out_calculations)
   21756 {
   21757 	out_calculations = "";
   21758 
   21759 	static const GLchar* gs = "    gohan  = uni_gohan;\n"
   21760 							  "    goten  = uni_goten;\n"
   21761 							  "    chichi = uni_chichi;\n";
   21762 	static const GLchar* fs = "    fs_out = gohan + goten + chichi;\n";
   21763 
   21764 	const GLchar* assignments = "";
   21765 	switch (stage)
   21766 	{
   21767 	case Utils::Shader::FRAGMENT:
   21768 		assignments = fs;
   21769 		break;
   21770 	case Utils::Shader::GEOMETRY:
   21771 		assignments = gs;
   21772 		break;
   21773 	default:
   21774 		break;
   21775 	}
   21776 
   21777 	out_assignments = assignments;
   21778 }
   21779 
   21780 /** Get interface of shader
   21781  *
   21782  * @param ignored
   21783  * @param stage            Shader stage
   21784  * @param out_interface    Set to ""
   21785  **/
   21786 void XFBBlockMemberStrideTest::getShaderInterface(GLuint /* test_case_index */, Utils::Shader::STAGES stage,
   21787 												  std::string& out_interface)
   21788 {
   21789 	static const GLchar* gs = "layout (xfb_buffer = 0, xfb_offset = 0) out Goku {\n"
   21790 							  "                             vec4 gohan;\n"
   21791 							  "    layout (xfb_stride = 48) vec4 goten;\n"
   21792 							  "                             vec4 chichi;\n"
   21793 							  "};\n"
   21794 							  "layout(binding = 0) uniform gs_block {\n"
   21795 							  "    vec4 uni_gohan;\n"
   21796 							  "    vec4 uni_goten;\n"
   21797 							  "    vec4 uni_chichi;\n"
   21798 							  "};\n";
   21799 	static const GLchar* fs = "in Goku {\n"
   21800 							  "    vec4 gohan;\n"
   21801 							  "    vec4 goten;\n"
   21802 							  "    vec4 chichi;\n"
   21803 							  "};\n"
   21804 							  "out vec4 fs_out;\n";
   21805 
   21806 	switch (stage)
   21807 	{
   21808 	case Utils::Shader::FRAGMENT:
   21809 		out_interface = fs;
   21810 		break;
   21811 	case Utils::Shader::GEOMETRY:
   21812 		out_interface = gs;
   21813 		break;
   21814 	default:
   21815 		out_interface = "";
   21816 		return;
   21817 	}
   21818 }
   21819 
   21820 /** Inspects program to check if all resources are as expected
   21821  *
   21822  * @param ignored
   21823  * @param program    Program instance
   21824  * @param out_stream Error message
   21825  *
   21826  * @return true if everything is ok, false otherwise
   21827  **/
   21828 bool XFBBlockMemberStrideTest::inspectProgram(GLuint /* test_case_index*/, Utils::Program& program,
   21829 											  std::stringstream& out_stream)
   21830 {
   21831 	const GLuint gohan_id  = program.GetResourceIndex("gohan", GL_TRANSFORM_FEEDBACK_VARYING);
   21832 	const GLuint goten_id  = program.GetResourceIndex("goten", GL_TRANSFORM_FEEDBACK_VARYING);
   21833 	const GLuint chichi_id = program.GetResourceIndex("chichi", GL_TRANSFORM_FEEDBACK_VARYING);
   21834 
   21835 	GLint gohan_offset  = 0;
   21836 	GLint goten_offset  = 0;
   21837 	GLint chichi_offset = 0;
   21838 
   21839 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, gohan_id, GL_OFFSET, 1, &gohan_offset);
   21840 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, goten_id, GL_OFFSET, 1, &goten_offset);
   21841 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, chichi_id, GL_OFFSET, 1, &chichi_offset);
   21842 
   21843 	// the xfb_offset of "chichi" should be 32
   21844 	if ((0 != gohan_offset) || (16 != goten_offset) || (32 != chichi_offset))
   21845 	{
   21846 		out_stream << "Got wrong offset: [" << gohan_offset << ", " << goten_offset << ", " << chichi_offset
   21847 				   << "] expected: [0, 16, 32]";
   21848 		return false;
   21849 	}
   21850 
   21851 	return true;
   21852 }
   21853 
   21854 /** Constructor
   21855  *
   21856  * @param context Test framework context
   21857  **/
   21858 XFBDuplicatedStrideTest::XFBDuplicatedStrideTest(deqp::Context& context)
   21859 	: NegativeTestBase(context, "xfb_duplicated_stride",
   21860 					   "Test verifies that compiler reports error when conflicting stride qualifiers are used")
   21861 {
   21862 }
   21863 
   21864 /** Source for given test case and stage
   21865  *
   21866  * @param test_case_index Index of test case
   21867  * @param stage           Shader stage
   21868  *
   21869  * @return Shader source
   21870  **/
   21871 std::string XFBDuplicatedStrideTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   21872 {
   21873 	static const GLchar* invalid_var_definition = "const uint valid_stride = 64;\n"
   21874 												  "const uint conflicting_stride = 128;\n"
   21875 												  "\n"
   21876 												  "layout (xfb_buffer = 0, xfb_stride = valid_stride)       out;\n"
   21877 												  "layout (xfb_buffer = 0, xfb_stride = conflicting_stride) out;\n";
   21878 	static const GLchar* valid_var_definition = "const uint valid_stride = 64;\n"
   21879 												"\n"
   21880 												"layout (xfb_buffer = 0, xfb_stride = valid_stride) out;\n"
   21881 												"layout (xfb_buffer = 0, xfb_stride = valid_stride) out;\n";
   21882 	static const GLchar* fs = "#version 430 core\n"
   21883 							  "#extension GL_ARB_enhanced_layouts : require\n"
   21884 							  "\n"
   21885 							  "in  vec4 any_fs;\n"
   21886 							  "out vec4 fs_out;\n"
   21887 							  "\n"
   21888 							  "void main()\n"
   21889 							  "{\n"
   21890 							  "    fs_out = any_fs;\n"
   21891 							  "}\n"
   21892 							  "\n";
   21893 	static const GLchar* gs_tested = "#version 430 core\n"
   21894 									 "#extension GL_ARB_enhanced_layouts : require\n"
   21895 									 "\n"
   21896 									 "layout(points)                           in;\n"
   21897 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   21898 									 "\n"
   21899 									 "VAR_DEFINITION"
   21900 									 "\n"
   21901 									 "in  vec4 vs_any[];\n"
   21902 									 "out vec4 any_fs;\n"
   21903 									 "\n"
   21904 									 "void main()\n"
   21905 									 "{\n"
   21906 									 "    vec4 result = vs_any[0];\n"
   21907 									 "\n"
   21908 									 "VARIABLE_USE"
   21909 									 "\n"
   21910 									 "    any_fs = result;\n"
   21911 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   21912 									 "    EmitVertex();\n"
   21913 									 "    any_fs = result;\n"
   21914 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   21915 									 "    EmitVertex();\n"
   21916 									 "    any_fs = result;\n"
   21917 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   21918 									 "    EmitVertex();\n"
   21919 									 "    any_fs = result;\n"
   21920 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   21921 									 "    EmitVertex();\n"
   21922 									 "}\n"
   21923 									 "\n";
   21924 	static const GLchar* tcs = "#version 430 core\n"
   21925 							   "#extension GL_ARB_enhanced_layouts : require\n"
   21926 							   "\n"
   21927 							   "layout(vertices = 1) out;\n"
   21928 							   "\n"
   21929 							   "in  vec4 vs_any[];\n"
   21930 							   "out vec4 tcs_tes[];\n"
   21931 							   "\n"
   21932 							   "void main()\n"
   21933 							   "{\n"
   21934 							   "\n"
   21935 							   "    tcs_tes[gl_InvocationID] = vs_any[gl_InvocationID];\n"
   21936 							   "\n"
   21937 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   21938 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   21939 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   21940 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   21941 							   "    gl_TessLevelInner[0] = 1.0;\n"
   21942 							   "    gl_TessLevelInner[1] = 1.0;\n"
   21943 							   "}\n"
   21944 							   "\n";
   21945 	static const GLchar* tcs_tested = "#version 430 core\n"
   21946 									  "#extension GL_ARB_enhanced_layouts : require\n"
   21947 									  "\n"
   21948 									  "layout(vertices = 1) out;\n"
   21949 									  "\n"
   21950 									  "VAR_DEFINITION"
   21951 									  "\n"
   21952 									  "in  vec4 vs_any[];\n"
   21953 									  "out vec4 any_fs[];\n"
   21954 									  "\n"
   21955 									  "void main()\n"
   21956 									  "{\n"
   21957 									  "    vec4 result = vs_any[gl_InvocationID];\n"
   21958 									  "\n"
   21959 									  "VARIABLE_USE"
   21960 									  "\n"
   21961 									  "    any_fs[gl_InvocationID] = result;\n"
   21962 									  "\n"
   21963 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   21964 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   21965 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   21966 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   21967 									  "    gl_TessLevelInner[0] = 1.0;\n"
   21968 									  "    gl_TessLevelInner[1] = 1.0;\n"
   21969 									  "}\n"
   21970 									  "\n";
   21971 	static const GLchar* tes_tested = "#version 430 core\n"
   21972 									  "#extension GL_ARB_enhanced_layouts : require\n"
   21973 									  "\n"
   21974 									  "layout(isolines, point_mode) in;\n"
   21975 									  "\n"
   21976 									  "VAR_DEFINITION"
   21977 									  "\n"
   21978 									  "in  vec4 tcs_tes[];\n"
   21979 									  "out vec4 any_fs;\n"
   21980 									  "\n"
   21981 									  "void main()\n"
   21982 									  "{\n"
   21983 									  "    vec4 result = tcs_tes[0];\n"
   21984 									  "\n"
   21985 									  "VARIABLE_USE"
   21986 									  "\n"
   21987 									  "    any_fs = result;\n"
   21988 									  "}\n"
   21989 									  "\n";
   21990 	static const GLchar* vs = "#version 430 core\n"
   21991 							  "#extension GL_ARB_enhanced_layouts : require\n"
   21992 							  "\n"
   21993 							  "in  vec4 in_vs;\n"
   21994 							  "out vec4 vs_any;\n"
   21995 							  "\n"
   21996 							  "void main()\n"
   21997 							  "{\n"
   21998 							  "    vs_any = in_vs;\n"
   21999 							  "}\n"
   22000 							  "\n";
   22001 	static const GLchar* vs_tested = "#version 430 core\n"
   22002 									 "#extension GL_ARB_enhanced_layouts : require\n"
   22003 									 "\n"
   22004 									 "VAR_DEFINITION"
   22005 									 "\n"
   22006 									 "in  vec4 in_vs;\n"
   22007 									 "out vec4 any_fs;\n"
   22008 									 "\n"
   22009 									 "void main()\n"
   22010 									 "{\n"
   22011 									 "    vec4 result = in_vs;\n"
   22012 									 "\n"
   22013 									 "VARIABLE_USE"
   22014 									 "\n"
   22015 									 "    any_fs += result;\n"
   22016 									 "}\n"
   22017 									 "\n";
   22018 
   22019 	std::string source;
   22020 	testCase&   test_case = m_test_cases[test_case_index];
   22021 
   22022 	if (test_case.m_stage == stage)
   22023 	{
   22024 		size_t		  position		 = 0;
   22025 		const GLchar* var_definition = 0;
   22026 		const GLchar* var_use		 = "";
   22027 
   22028 		switch (test_case.m_case)
   22029 		{
   22030 		case VALID:
   22031 			var_definition = valid_var_definition;
   22032 			break;
   22033 		case INVALID:
   22034 			var_definition = invalid_var_definition;
   22035 			break;
   22036 		default:
   22037 			TCU_FAIL("Invalid enum");
   22038 		}
   22039 
   22040 		switch (stage)
   22041 		{
   22042 		case Utils::Shader::GEOMETRY:
   22043 			source = gs_tested;
   22044 			break;
   22045 		case Utils::Shader::TESS_CTRL:
   22046 			source = tcs_tested;
   22047 			break;
   22048 		case Utils::Shader::TESS_EVAL:
   22049 			source = tes_tested;
   22050 			break;
   22051 		case Utils::Shader::VERTEX:
   22052 			source = vs_tested;
   22053 			break;
   22054 		default:
   22055 			TCU_FAIL("Invalid enum");
   22056 		}
   22057 
   22058 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   22059 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   22060 	}
   22061 	else
   22062 	{
   22063 		switch (test_case.m_stage)
   22064 		{
   22065 		case Utils::Shader::GEOMETRY:
   22066 			switch (stage)
   22067 			{
   22068 			case Utils::Shader::FRAGMENT:
   22069 				source = fs;
   22070 				break;
   22071 			case Utils::Shader::VERTEX:
   22072 				source = vs;
   22073 				break;
   22074 			default:
   22075 				source = "";
   22076 			}
   22077 			break;
   22078 		case Utils::Shader::TESS_CTRL:
   22079 			switch (stage)
   22080 			{
   22081 			case Utils::Shader::FRAGMENT:
   22082 				source = fs;
   22083 				break;
   22084 			case Utils::Shader::VERTEX:
   22085 				source = vs;
   22086 				break;
   22087 			default:
   22088 				source = "";
   22089 			}
   22090 			break;
   22091 		case Utils::Shader::TESS_EVAL:
   22092 			switch (stage)
   22093 			{
   22094 			case Utils::Shader::FRAGMENT:
   22095 				source = fs;
   22096 				break;
   22097 			case Utils::Shader::TESS_CTRL:
   22098 				source = tcs;
   22099 				break;
   22100 			case Utils::Shader::VERTEX:
   22101 				source = vs;
   22102 				break;
   22103 			default:
   22104 				source = "";
   22105 			}
   22106 			break;
   22107 		case Utils::Shader::VERTEX:
   22108 			switch (stage)
   22109 			{
   22110 			case Utils::Shader::FRAGMENT:
   22111 				source = fs;
   22112 				break;
   22113 			default:
   22114 				source = "";
   22115 			}
   22116 			break;
   22117 		default:
   22118 			TCU_FAIL("Invalid enum");
   22119 			break;
   22120 		}
   22121 	}
   22122 
   22123 	return source;
   22124 }
   22125 
   22126 /** Get description of test case
   22127  *
   22128  * @param test_case_index Index of test case
   22129  *
   22130  * @return Test case description
   22131  **/
   22132 std::string XFBDuplicatedStrideTest::getTestCaseName(GLuint test_case_index)
   22133 {
   22134 	std::stringstream stream;
   22135 	testCase&		  test_case = m_test_cases[test_case_index];
   22136 
   22137 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage) << ", case: ";
   22138 
   22139 	switch (test_case.m_case)
   22140 	{
   22141 	case VALID:
   22142 		stream << "valid";
   22143 		break;
   22144 	case INVALID:
   22145 		stream << "invalid";
   22146 		break;
   22147 	default:
   22148 		TCU_FAIL("Invalid enum");
   22149 	}
   22150 
   22151 	return stream.str();
   22152 }
   22153 
   22154 /** Get number of test cases
   22155  *
   22156  * @return Number of test cases
   22157  **/
   22158 GLuint XFBDuplicatedStrideTest::getTestCaseNumber()
   22159 {
   22160 	return static_cast<GLuint>(m_test_cases.size());
   22161 }
   22162 
   22163 /** Selects if "compute" stage is relevant for test
   22164  *
   22165  * @param ignored
   22166  *
   22167  * @return false
   22168  **/
   22169 bool XFBDuplicatedStrideTest::isComputeRelevant(GLuint /* test_case_index */)
   22170 {
   22171 	return false;
   22172 }
   22173 
   22174 /** Selects if compilation failure is expected result
   22175  *
   22176  * @param test_case_index Index of test case
   22177  *
   22178  * @return true
   22179  **/
   22180 bool XFBDuplicatedStrideTest::isFailureExpected(GLuint test_case_index)
   22181 {
   22182 	testCase& test_case = m_test_cases[test_case_index];
   22183 
   22184 	return (INVALID == test_case.m_case);
   22185 }
   22186 
   22187 /** Prepare all test cases
   22188  *
   22189  **/
   22190 void XFBDuplicatedStrideTest::testInit()
   22191 {
   22192 	for (GLuint c = 0; c < CASE_MAX; ++c)
   22193 	{
   22194 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   22195 		{
   22196 			if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::TESS_CTRL == stage) ||
   22197 				(Utils::Shader::FRAGMENT == stage))
   22198 			{
   22199 				continue;
   22200 			}
   22201 
   22202 			testCase test_case = { (CASES)c, (Utils::Shader::STAGES)stage };
   22203 
   22204 			m_test_cases.push_back(test_case);
   22205 		}
   22206 	}
   22207 }
   22208 
   22209 /** Constructor
   22210  *
   22211  * @param context Test framework context
   22212  **/
   22213 XFBGetProgramResourceAPITest::XFBGetProgramResourceAPITest(deqp::Context& context)
   22214 	: TestBase(context, "xfb_get_program_resource_api",
   22215 			   "Test verifies that get program resource reports correct results for XFB")
   22216 {
   22217 }
   22218 
   22219 /** Source for given test case and stage
   22220  *
   22221  * @param test_case_index Index of test case
   22222  * @param stage           Shader stage
   22223  *
   22224  * @return Shader source
   22225  **/
   22226 std::string XFBGetProgramResourceAPITest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   22227 {
   22228 	static const GLchar* api_var_definition = "out TYPE b0_v1ARRAY;\n"
   22229 											  "out TYPE b1_v1ARRAY;\n"
   22230 											  "out TYPE b0_v3ARRAY;\n"
   22231 											  "out TYPE b0_v0ARRAY;\n";
   22232 	static const GLchar* xfb_var_definition =
   22233 		"const uint type_size = SIZE;\n"
   22234 		"\n"
   22235 		"layout (xfb_buffer = 1, xfb_stride = 4 * type_size) out;\n"
   22236 		"\n"
   22237 		"layout (xfb_buffer = 0, xfb_offset = 1 * type_size) out TYPE b0_v1ARRAY;\n"
   22238 		"layout (xfb_buffer = 1, xfb_offset = 1 * type_size) out TYPE b1_v1ARRAY;\n"
   22239 		"layout (xfb_buffer = 0, xfb_offset = 3 * type_size) out TYPE b0_v3ARRAY;\n"
   22240 		"layout (xfb_buffer = 0, xfb_offset = 0 * type_size) out TYPE b0_v0ARRAY;\n";
   22241 	static const GLchar* var_use = "    b0_v1INDEX = TYPE(0);\n"
   22242 								   "    b1_v1INDEX = TYPE(1);\n"
   22243 								   "    b0_v3INDEX = TYPE(0);\n"
   22244 								   "    b0_v0INDEX = TYPE(1);\n"
   22245 								   "    if (vec4(0) == result)\n"
   22246 								   "    {\n"
   22247 								   "        b0_v1INDEX = TYPE(1);\n"
   22248 								   "        b1_v1INDEX = TYPE(0);\n"
   22249 								   "        b0_v3INDEX = TYPE(1);\n"
   22250 								   "        b0_v0INDEX = TYPE(0);\n"
   22251 								   "    }\n";
   22252 	static const GLchar* gs_tested =
   22253 		"#version 430 core\n"
   22254 		"#extension GL_ARB_enhanced_layouts : require\n"
   22255 		"\n"
   22256 		"layout(points)                           in;\n"
   22257 		"layout(triangle_strip, max_vertices = 4) out;\n"
   22258 		"\n"
   22259 		"VAR_DEFINITION"
   22260 		"\n"
   22261 		"out gl_PerVertex \n"
   22262 		"{ \n"
   22263 		"   vec4  gl_Position; \n" // gl_Position must be redeclared in separable program mode
   22264 		"}; \n"
   22265 		"in  vec4 tes_gs[];\n"
   22266 		"out vec4 gs_fs;\n"
   22267 		"\n"
   22268 		"void main()\n"
   22269 		"{\n"
   22270 		"    vec4 result = tes_gs[0];\n"
   22271 		"\n"
   22272 		"VARIABLE_USE"
   22273 		"\n"
   22274 		"    gs_fs = result;\n"
   22275 		"    gl_Position  = vec4(-1, -1, 0, 1);\n"
   22276 		"    EmitVertex();\n"
   22277 		"    gs_fs = result;\n"
   22278 		"    gl_Position  = vec4(-1, 1, 0, 1);\n"
   22279 		"    EmitVertex();\n"
   22280 		"    gs_fs = result;\n"
   22281 		"    gl_Position  = vec4(1, -1, 0, 1);\n"
   22282 		"    EmitVertex();\n"
   22283 		"    gs_fs = result;\n"
   22284 		"    gl_Position  = vec4(1, 1, 0, 1);\n"
   22285 		"    EmitVertex();\n"
   22286 		"}\n"
   22287 		"\n";
   22288 #if 0
   22289 	static const GLchar* tcs_tested =
   22290 		"#version 430 core\n"
   22291 		"#extension GL_ARB_enhanced_layouts : require\n"
   22292 		"\n"
   22293 		"layout(vertices = 1) out;\n"
   22294 		"\n"
   22295 		"VAR_DEFINITION"
   22296 		"\n"
   22297 		"in  vec4 vs_tcs[];\n"
   22298 		"out vec4 tcs_tes[];\n"
   22299 		"\n"
   22300 		"void main()\n"
   22301 		"{\n"
   22302 		"    vec4 result = vs_tcs[gl_InvocationID];\n"
   22303 		"\n"
   22304 		"VARIABLE_USE"
   22305 		"\n"
   22306 		"    tcs_tes[gl_InvocationID] = result;\n"
   22307 		"\n"
   22308 		"    gl_TessLevelOuter[0] = 1.0;\n"
   22309 		"    gl_TessLevelOuter[1] = 1.0;\n"
   22310 		"    gl_TessLevelOuter[2] = 1.0;\n"
   22311 		"    gl_TessLevelOuter[3] = 1.0;\n"
   22312 		"    gl_TessLevelInner[0] = 1.0;\n"
   22313 		"    gl_TessLevelInner[1] = 1.0;\n"
   22314 		"}\n"
   22315 		"\n";
   22316 #endif
   22317 	static const GLchar* tes_tested = "#version 430 core\n"
   22318 									  "#extension GL_ARB_enhanced_layouts : require\n"
   22319 									  "\n"
   22320 									  "layout(isolines, point_mode) in;\n"
   22321 									  "\n"
   22322 									  "VAR_DEFINITION"
   22323 									  "\n"
   22324 									  "in  vec4 tcs_tes[];\n"
   22325 									  "out vec4 tes_gs;\n"
   22326 									  "\n"
   22327 									  "void main()\n"
   22328 									  "{\n"
   22329 									  "    vec4 result = tcs_tes[0];\n"
   22330 									  "\n"
   22331 									  "VARIABLE_USE"
   22332 									  "\n"
   22333 									  "    tes_gs = result;\n"
   22334 									  "}\n"
   22335 									  "\n";
   22336 	static const GLchar* vs_tested = "#version 430 core\n"
   22337 									 "#extension GL_ARB_enhanced_layouts : require\n"
   22338 									 "\n"
   22339 									 "VAR_DEFINITION"
   22340 									 "\n"
   22341 									 "in  vec4 in_vs;\n"
   22342 									 "out vec4 vs_tcs;\n"
   22343 									 "\n"
   22344 									 "void main()\n"
   22345 									 "{\n"
   22346 									 "    vec4 result = in_vs;\n"
   22347 									 "\n"
   22348 									 "VARIABLE_USE"
   22349 									 "\n"
   22350 									 "    vs_tcs = result;\n"
   22351 									 "}\n"
   22352 									 "\n";
   22353 
   22354 	std::string		 source;
   22355 	const test_Case& test_case = m_test_cases[test_case_index];
   22356 
   22357 	if (test_case.m_stage == stage)
   22358 	{
   22359 		const GLchar* array = "";
   22360 		GLchar		  buffer[16];
   22361 		const GLchar* index	= "";
   22362 		size_t		  position = 0;
   22363 		size_t		  temp;
   22364 		const GLchar* type_name		 = test_case.m_type.GetGLSLTypeName();
   22365 		const GLchar* var_definition = 0;
   22366 
   22367 		sprintf(buffer, "%d", test_case.m_type.GetSize());
   22368 
   22369 		if (XFB == test_case.m_case)
   22370 		{
   22371 			var_definition = xfb_var_definition;
   22372 		}
   22373 		else
   22374 		{
   22375 			var_definition = api_var_definition;
   22376 		}
   22377 
   22378 		// It is a compile time error to apply xfb_offset to the declaration of an unsized array(GLSL4.5 spec: Page73)
   22379 		// change array = "[]" to "[1]"
   22380 		switch (stage)
   22381 		{
   22382 		case Utils::Shader::GEOMETRY:
   22383 			source = gs_tested;
   22384 			array  = "[1]";
   22385 			index  = "[0]";
   22386 			break;
   22387 // It is invalid to output transform feedback varyings in tessellation control shader
   22388 #if 0
   22389 		case Utils::Shader::TESS_CTRL:
   22390 			source = tcs_tested;
   22391 			array = "[]";
   22392 			index = "[gl_InvocationID]";
   22393 			break;
   22394 #endif
   22395 		case Utils::Shader::TESS_EVAL:
   22396 			source = tes_tested;
   22397 			array  = "[1]";
   22398 			index  = "[0]";
   22399 			break;
   22400 		case Utils::Shader::VERTEX:
   22401 			source = vs_tested;
   22402 			break;
   22403 		default:
   22404 			TCU_FAIL("Invalid enum");
   22405 		}
   22406 
   22407 		temp = position;
   22408 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   22409 		if (XFB == test_case.m_case)
   22410 		{
   22411 			position = temp;
   22412 			Utils::replaceToken("SIZE", position, buffer, source);
   22413 		}
   22414 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   22415 
   22416 		Utils::replaceAllTokens("ARRAY", array, source);
   22417 		Utils::replaceAllTokens("INDEX", index, source);
   22418 		Utils::replaceAllTokens("TYPE", type_name, source);
   22419 	}
   22420 	else
   22421 	{
   22422 		source = "";
   22423 	}
   22424 
   22425 	return source;
   22426 }
   22427 
   22428 /** Get description of test case
   22429  *
   22430  * @param test_case_index Index of test case
   22431  *
   22432  * @return Test case description
   22433  **/
   22434 std::string XFBGetProgramResourceAPITest::getTestCaseName(GLuint test_case_index)
   22435 {
   22436 	std::stringstream stream;
   22437 	const test_Case&  test_case = m_test_cases[test_case_index];
   22438 
   22439 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage)
   22440 		   << ", type: " << test_case.m_type.GetGLSLTypeName() << ", case: ";
   22441 
   22442 	switch (test_case.m_case)
   22443 	{
   22444 	case INTERLEAVED:
   22445 		stream << "interleaved";
   22446 		break;
   22447 	case SEPARATED:
   22448 		stream << "separated";
   22449 		break;
   22450 	case XFB:
   22451 		stream << "xfb";
   22452 		break;
   22453 	default:
   22454 		TCU_FAIL("Invalid enum");
   22455 	}
   22456 
   22457 	return stream.str();
   22458 }
   22459 
   22460 /** Get number of test cases
   22461  *
   22462  * @return Number of test cases
   22463  **/
   22464 GLuint XFBGetProgramResourceAPITest::getTestCaseNumber()
   22465 {
   22466 	return static_cast<GLuint>(m_test_cases.size());
   22467 }
   22468 
   22469 /** Inspects program for offset, buffer index, buffer stride and type
   22470  *
   22471  * @param test_case_index Index of test case
   22472  * @param program         Program to query
   22473  *
   22474  * @return true if query results match expected values, false otherwise
   22475  **/
   22476 bool XFBGetProgramResourceAPITest::inspectProgram(glw::GLuint test_case_index, Utils::Program& program)
   22477 {
   22478 	GLint			 b0_stride	= 0;
   22479 	GLint			 b1_stride	= 0;
   22480 	GLint			 b0_v0_buf	= 0;
   22481 	GLint			 b0_v0_offset = 0;
   22482 	GLint			 b0_v0_type   = 0;
   22483 	GLint			 b0_v1_buf	= 0;
   22484 	GLint			 b0_v1_offset = 0;
   22485 	GLint			 b0_v1_type   = 0;
   22486 	GLint			 b0_v3_buf	= 0;
   22487 	GLint			 b0_v3_offset = 0;
   22488 	GLint			 b0_v3_type   = 0;
   22489 	GLint			 b1_v1_buf	= 0;
   22490 	GLint			 b1_v1_offset = 0;
   22491 	GLint			 b1_v1_type   = 0;
   22492 	const test_Case& test_case	= m_test_cases[test_case_index];
   22493 	const GLenum	 type_enum	= test_case.m_type.GetTypeGLenum();
   22494 	const GLint		 type_size	= test_case.m_type.GetSize();
   22495 
   22496 	GLuint b0_v0_index = program.GetResourceIndex("b0_v0", GL_TRANSFORM_FEEDBACK_VARYING);
   22497 	GLuint b0_v1_index = program.GetResourceIndex("b0_v1", GL_TRANSFORM_FEEDBACK_VARYING);
   22498 	GLuint b0_v3_index = program.GetResourceIndex("b0_v3", GL_TRANSFORM_FEEDBACK_VARYING);
   22499 	GLuint b1_v1_index = program.GetResourceIndex("b1_v1", GL_TRANSFORM_FEEDBACK_VARYING);
   22500 
   22501 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b0_v0_index, GL_OFFSET, 1 /* buf_size */, &b0_v0_offset);
   22502 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b0_v1_index, GL_OFFSET, 1 /* buf_size */, &b0_v1_offset);
   22503 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b0_v3_index, GL_OFFSET, 1 /* buf_size */, &b0_v3_offset);
   22504 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b1_v1_index, GL_OFFSET, 1 /* buf_size */, &b1_v1_offset);
   22505 
   22506 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b0_v0_index, GL_TYPE, 1 /* buf_size */, &b0_v0_type);
   22507 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b0_v1_index, GL_TYPE, 1 /* buf_size */, &b0_v1_type);
   22508 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b0_v3_index, GL_TYPE, 1 /* buf_size */, &b0_v3_type);
   22509 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b1_v1_index, GL_TYPE, 1 /* buf_size */, &b1_v1_type);
   22510 
   22511 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b0_v0_index, GL_TRANSFORM_FEEDBACK_BUFFER_INDEX,
   22512 						1 /* buf_size */, &b0_v0_buf);
   22513 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b0_v1_index, GL_TRANSFORM_FEEDBACK_BUFFER_INDEX,
   22514 						1 /* buf_size */, &b0_v1_buf);
   22515 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b0_v3_index, GL_TRANSFORM_FEEDBACK_BUFFER_INDEX,
   22516 						1 /* buf_size */, &b0_v3_buf);
   22517 	program.GetResource(GL_TRANSFORM_FEEDBACK_VARYING, b1_v1_index, GL_TRANSFORM_FEEDBACK_BUFFER_INDEX,
   22518 						1 /* buf_size */, &b1_v1_buf);
   22519 
   22520 	program.GetResource(GL_TRANSFORM_FEEDBACK_BUFFER, b0_v0_buf, GL_TRANSFORM_FEEDBACK_BUFFER_STRIDE, 1 /* buf_size */,
   22521 						&b0_stride);
   22522 	program.GetResource(GL_TRANSFORM_FEEDBACK_BUFFER, b1_v1_buf, GL_TRANSFORM_FEEDBACK_BUFFER_STRIDE, 1 /* buf_size */,
   22523 						&b1_stride);
   22524 
   22525 	if (SEPARATED != test_case.m_case)
   22526 	{
   22527 		return (((GLint)(4 * type_size) == b0_stride) && ((GLint)(4 * type_size) == b1_stride) &&
   22528 				((GLint)(0) == b0_v0_buf) && ((GLint)(0 * type_size) == b0_v0_offset) &&
   22529 				((GLint)(type_enum) == b0_v0_type) && ((GLint)(0) == b0_v1_buf) &&
   22530 				((GLint)(1 * type_size) == b0_v1_offset) && ((GLint)(type_enum) == b0_v1_type) &&
   22531 				((GLint)(0) == b0_v3_buf) && ((GLint)(3 * type_size) == b0_v3_offset) &&
   22532 				((GLint)(type_enum) == b0_v3_type) && ((GLint)(1) == b1_v1_buf) &&
   22533 				((GLint)(1 * type_size) == b1_v1_offset) && ((GLint)(type_enum) == b1_v1_type));
   22534 	}
   22535 	else
   22536 	{
   22537 		return (((GLint)(1 * type_size) == b0_stride) && ((GLint)(1 * type_size) == b1_stride) &&
   22538 				((GLint)(0) == b0_v0_buf) && ((GLint)(0) == b0_v0_offset) && ((GLint)(type_enum) == b0_v0_type) &&
   22539 				((GLint)(1) == b0_v1_buf) && ((GLint)(0) == b0_v1_offset) && ((GLint)(type_enum) == b0_v1_type) &&
   22540 				((GLint)(2) == b0_v3_buf) && ((GLint)(0) == b0_v3_offset) && ((GLint)(type_enum) == b0_v3_type) &&
   22541 				((GLint)(3) == b1_v1_buf) && ((GLint)(0) == b1_v1_offset) && ((GLint)(type_enum) == b1_v1_type));
   22542 	}
   22543 }
   22544 
   22545 /** Insert gl_SkipComponents
   22546  *
   22547  * @param num_components How many gl_SkipComponents1 need to be inserted
   22548  * @param varyings The transform feedback varyings string vector
   22549  *
   22550  **/
   22551 void XFBGetProgramResourceAPITest::insertSkipComponents(int num_components, Utils::Program::NameVector& varyings)
   22552 {
   22553 	int num_component_4 = num_components / 4;
   22554 	int num_component_1 = num_components % 4;
   22555 	for (int i = 0; i < num_component_4; i++)
   22556 	{
   22557 		varyings.push_back("gl_SkipComponents4");
   22558 	}
   22559 	switch (num_component_1)
   22560 	{
   22561 	case 1:
   22562 		varyings.push_back("gl_SkipComponents1");
   22563 		break;
   22564 	case 2:
   22565 		varyings.push_back("gl_SkipComponents2");
   22566 		break;
   22567 	case 3:
   22568 		varyings.push_back("gl_SkipComponents3");
   22569 		break;
   22570 	default:
   22571 		break;
   22572 	}
   22573 }
   22574 
   22575 /** Runs test case
   22576  *
   22577  * @param test_case_index Id of test case
   22578  *
   22579  * @return true if test case pass, false otherwise
   22580  **/
   22581 bool XFBGetProgramResourceAPITest::testCase(GLuint test_case_index)
   22582 {
   22583 	const std::string& gs_source = getShaderSource(test_case_index, Utils::Shader::GEOMETRY);
   22584 	Utils::Program	 program(m_context);
   22585 	const std::string& tcs_source		= getShaderSource(test_case_index, Utils::Shader::TESS_CTRL);
   22586 	const std::string& tes_source		= getShaderSource(test_case_index, Utils::Shader::TESS_EVAL);
   22587 	const test_Case&   test_case		= m_test_cases[test_case_index];
   22588 	bool			   test_case_result = true;
   22589 	const std::string& vs_source		= getShaderSource(test_case_index, Utils::Shader::VERTEX);
   22590 
   22591 	// According to spec: gl_SkipComponents1 ~ gl_SkipComponents4 is treated as specifying a one- to four-component floating point output variables with undefined values.
   22592 	// No data will be recorded for such strings, but the offset assigned to the next variable in varyings and the stride of the assigned bingding point will be affected.
   22593 
   22594 	if (INTERLEAVED == test_case.m_case)
   22595 	{
   22596 		/*
   22597 		 layout (xfb_buffer = 0, xfb_offset = 1 * type_size) out type b0_v1;
   22598 		 layout (xfb_buffer = 1, xfb_offset = 1 * type_size) out type b1_v1;
   22599 		 layout (xfb_buffer = 0, xfb_offset = 3 * type_size) out type b0_v3;
   22600 		 layout (xfb_buffer = 0, xfb_offset = 0 * type_size) out type b0_v0;
   22601 
   22602 		 Note: the type can be float, double, mat2, mat3x2, dmat2, dmat3x2..., so to make the each variable of "captured_varyings" has the same xfb_offset with the above shaders,
   22603 		 we need to calculate how many "gl_SkipComponents" need to be inserted.
   22604 		 */
   22605 		Utils::Program::NameVector captured_varyings;
   22606 		captured_varyings.push_back("b0_v0");
   22607 		captured_varyings.push_back("b0_v1");
   22608 		// Compute how many gl_SkipComponents to be inserted
   22609 		int numComponents = test_case.m_type.GetSize() / 4;
   22610 		insertSkipComponents(numComponents, captured_varyings);
   22611 		captured_varyings.push_back("b0_v3");
   22612 		captured_varyings.push_back("gl_NextBuffer");
   22613 		insertSkipComponents(numComponents, captured_varyings);
   22614 		captured_varyings.push_back("b1_v1");
   22615 		insertSkipComponents(numComponents * 2, captured_varyings);
   22616 
   22617 		program.Init("" /* cs */, "", gs_source, tcs_source, tes_source, vs_source, captured_varyings, true,
   22618 					 true /* separable */);
   22619 	}
   22620 	else if (SEPARATED == test_case.m_case)
   22621 	{
   22622 		Utils::Program::NameVector captured_varyings;
   22623 
   22624 		captured_varyings.push_back("b0_v0");
   22625 		captured_varyings.push_back("b0_v1");
   22626 		captured_varyings.push_back("b0_v3");
   22627 		captured_varyings.push_back("b1_v1");
   22628 
   22629 		program.Init("" /* cs */, "", gs_source, tcs_source, tes_source, vs_source, captured_varyings, false,
   22630 					 true /* separable */);
   22631 	}
   22632 	else
   22633 	{
   22634 
   22635 		program.Init("" /* cs */, "", gs_source, tcs_source, tes_source, vs_source, true /* separable */);
   22636 	}
   22637 
   22638 	test_case_result = inspectProgram(test_case_index, program);
   22639 
   22640 	return test_case_result;
   22641 }
   22642 
   22643 /** Prepare all test cases
   22644  *
   22645  **/
   22646 void XFBGetProgramResourceAPITest::testInit()
   22647 {
   22648 	const Functions& gl		 = m_context.getRenderContext().getFunctions();
   22649 	const GLuint	 n_types = getTypesNumber();
   22650 	GLint			 max_xfb_int;
   22651 	GLint			 max_xfb_sep;
   22652 
   22653 	gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS, &max_xfb_int);
   22654 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   22655 
   22656 	gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS, &max_xfb_sep);
   22657 	GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   22658 
   22659 	GLint max_varyings;
   22660 	gl.getIntegerv(GL_MAX_VARYING_COMPONENTS, &max_varyings);
   22661 
   22662 	for (GLuint i = 0; i < n_types; ++i)
   22663 	{
   22664 		// When i == 7, the type is dmat4, i == 9 the type is dmat4x3, the number of output components exceeds the maximum value that AMD's driver supported,
   22665 		// the MAX_VARYING_COMPONENTS is 32 in our driver, but when the variable type is dmat4 or dmat4x3, the number of output component is 33, to make the
   22666 		// shader valid, we can either skip the dmat4, dmat4x3 or query the implementation-dependent value MAX_VARYING_COMPONENTS before generating the shader
   22667 		// to guarantee the number of varying not exceeded.
   22668 		/*
   22669 		 layout (xfb_buffer = 1, xfb_stride = 4 * type_size) out;
   22670 		 layout (xfb_buffer = 0, xfb_offset = 1 * type_size) out type b0_v1;
   22671 		 layout (xfb_buffer = 1, xfb_offset = 1 * type_size) out type b1_v1;
   22672 		 layout (xfb_buffer = 0, xfb_offset = 3 * type_size) out type b0_v3;
   22673 		 layout (xfb_buffer = 0, xfb_offset = 0 * type_size) out type b0_v0;
   22674 		 in  vec4 in_vs;
   22675 		 out vec4 vs_tcs;
   22676 		 */
   22677 		if (i == 7 || i == 9)
   22678 			continue;
   22679 		const Utils::Type& type = getType(i);
   22680 		if (4 * type.GetNumComponents() + 4 > (GLuint)max_varyings)
   22681 		{
   22682 			continue;
   22683 		}
   22684 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   22685 		{
   22686 			/*
   22687 			 It is invalid to define transform feedback output in HS
   22688 			 */
   22689 			if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::TESS_CTRL == stage) ||
   22690 				(Utils::Shader::FRAGMENT == stage))
   22691 			{
   22692 				continue;
   22693 			}
   22694 
   22695 			test_Case test_case_int = { INTERLEAVED, (Utils::Shader::STAGES)stage, type };
   22696 			test_Case test_case_sep = { SEPARATED, (Utils::Shader::STAGES)stage, type };
   22697 			test_Case test_case_xfb = { XFB, (Utils::Shader::STAGES)stage, type };
   22698 
   22699 			if ((int)type.GetSize() <= max_xfb_int)
   22700 			{
   22701 				m_test_cases.push_back(test_case_xfb);
   22702 				m_test_cases.push_back(test_case_int);
   22703 			}
   22704 
   22705 			if ((int)type.GetSize() <= max_xfb_sep)
   22706 			{
   22707 				m_test_cases.push_back(test_case_sep);
   22708 			}
   22709 		}
   22710 	}
   22711 }
   22712 
   22713 /** Constructor
   22714  *
   22715  * @param context Test context
   22716  **/
   22717 XFBOverrideQualifiersWithAPITest::XFBOverrideQualifiersWithAPITest(deqp::Context& context)
   22718 	: BufferTestBase(context, "xfb_override_qualifiers_with_api",
   22719 					 "Test verifies that xfb_offset qualifier is not overriden with API")
   22720 {
   22721 	/* Nothing to be done here */
   22722 }
   22723 
   22724 /** Get descriptors of buffers necessary for test
   22725  *
   22726  * @param test_case_index Index of test case
   22727  * @param out_descriptors Descriptors of buffers used by test
   22728  **/
   22729 void XFBOverrideQualifiersWithAPITest::getBufferDescriptors(glw::GLuint				  test_case_index,
   22730 															bufferDescriptor::Vector& out_descriptors)
   22731 {
   22732 	const Utils::Type& type = getType(test_case_index);
   22733 
   22734 	/* Test needs single uniform and xfb */
   22735 	out_descriptors.resize(2);
   22736 
   22737 	/* Get references */
   22738 	bufferDescriptor& uniform = out_descriptors[0];
   22739 	bufferDescriptor& xfb	 = out_descriptors[1];
   22740 
   22741 	/* Index */
   22742 	uniform.m_index = 0;
   22743 	xfb.m_index		= 0;
   22744 
   22745 	/* Target */
   22746 	uniform.m_target = Utils::Buffer::Uniform;
   22747 	xfb.m_target	 = Utils::Buffer::Transform_feedback;
   22748 
   22749 	/* Data */
   22750 	const GLuint				gen_start   = Utils::s_rand;
   22751 	const std::vector<GLubyte>& vegeta_data = type.GenerateData();
   22752 	const std::vector<GLubyte>& trunks_data = type.GenerateData();
   22753 	const std::vector<GLubyte>& goku_data   = type.GenerateData();
   22754 
   22755 	Utils::s_rand								= gen_start;
   22756 	const std::vector<GLubyte>& vegeta_data_pck = type.GenerateDataPacked();
   22757 	type.GenerateDataPacked(); // generate the data for trunks
   22758 	const std::vector<GLubyte>& goku_data_pck = type.GenerateDataPacked();
   22759 
   22760 	const GLuint type_size	 = static_cast<GLuint>(vegeta_data.size());
   22761 	const GLuint type_size_pck = static_cast<GLuint>(vegeta_data_pck.size());
   22762 
   22763 	/* Uniform data */
   22764 	uniform.m_initial_data.resize(3 * type_size);
   22765 	memcpy(&uniform.m_initial_data[0] + 0, &vegeta_data[0], type_size);
   22766 	memcpy(&uniform.m_initial_data[0] + type_size, &trunks_data[0], type_size);
   22767 	memcpy(&uniform.m_initial_data[0] + 2 * type_size, &goku_data[0], type_size);
   22768 
   22769 	/* XFB data */
   22770 	xfb.m_initial_data.resize(3 * type_size_pck);
   22771 	xfb.m_expected_data.resize(3 * type_size_pck);
   22772 
   22773 	for (GLuint i = 0; i < 3 * type_size_pck; ++i)
   22774 	{
   22775 		xfb.m_initial_data[i]  = (glw::GLubyte)i;
   22776 		xfb.m_expected_data[i] = (glw::GLubyte)i;
   22777 	}
   22778 
   22779 	memcpy(&xfb.m_expected_data[0] + 0, &goku_data_pck[0], type_size_pck);
   22780 	memcpy(&xfb.m_expected_data[0] + 2 * type_size_pck, &vegeta_data_pck[0], type_size_pck);
   22781 }
   22782 
   22783 /** Get list of names of varyings that will be registered with TransformFeedbackVaryings
   22784  *
   22785  * @param ignored
   22786  * @param captured_varyings List of names
   22787  **/
   22788 void XFBOverrideQualifiersWithAPITest::getCapturedVaryings(glw::GLuint /* test_case_index */,
   22789 														   Utils::Program::NameVector& captured_varyings)
   22790 {
   22791 	captured_varyings.resize(1);
   22792 
   22793 	captured_varyings[0] = "trunks";
   22794 }
   22795 
   22796 /** Get body of main function for given shader stage
   22797  *
   22798  * @param test_case_index  Index of test case
   22799  * @param stage            Shader stage
   22800  * @param out_assignments  Set to empty
   22801  * @param out_calculations Set to empty
   22802  **/
   22803 void XFBOverrideQualifiersWithAPITest::getShaderBody(GLuint test_case_index, Utils::Shader::STAGES stage,
   22804 													 std::string& out_assignments, std::string& out_calculations)
   22805 {
   22806 	out_calculations = "";
   22807 
   22808 	static const GLchar* gs = "    vegeta = uni_vegeta;\n"
   22809 							  "    trunks = uni_trunks;\n"
   22810 							  "    goku   = uni_goku;\n";
   22811 	static const GLchar* fs = "    fs_out = vec4(0);\n"
   22812 							  "    if (TYPE(1) == goku + trunks + vegeta)\n"
   22813 							  "    {\n"
   22814 							  "        fs_out = vec4(1);\n"
   22815 							  "    }\n";
   22816 
   22817 	const GLchar* assignments = "";
   22818 	switch (stage)
   22819 	{
   22820 	case Utils::Shader::FRAGMENT:
   22821 		assignments = fs;
   22822 		break;
   22823 	case Utils::Shader::GEOMETRY:
   22824 		assignments = gs;
   22825 		break;
   22826 	default:
   22827 		break;
   22828 	}
   22829 
   22830 	out_assignments = assignments;
   22831 
   22832 	if (Utils::Shader::FRAGMENT == stage)
   22833 	{
   22834 		const Utils::Type& type = getType(test_case_index);
   22835 
   22836 		Utils::replaceAllTokens("TYPE", type.GetGLSLTypeName(), out_assignments);
   22837 	}
   22838 }
   22839 
   22840 /** Get interface of shader
   22841  *
   22842  * @param test_case_index  Index of test case
   22843  * @param stage            Shader stage
   22844  * @param out_interface    Set to ""
   22845  **/
   22846 void XFBOverrideQualifiersWithAPITest::getShaderInterface(GLuint test_case_index, Utils::Shader::STAGES stage,
   22847 														  std::string& out_interface)
   22848 {
   22849 	static const GLchar* gs = "const uint sizeof_type = SIZE;\n"
   22850 							  "\n"
   22851 							  "layout (xfb_offset = 2 * sizeof_type) flat out TYPE vegeta;\n"
   22852 							  "                                      flat out TYPE trunks;\n"
   22853 							  "layout (xfb_offset = 0)               flat out TYPE goku;\n"
   22854 							  "\n"
   22855 							  /*
   22856 		 There is no packing qualifier for uniform block gs_block, according to spec, it should be "shared" by default,
   22857 		 the definition equals to "layout(binding=0, shared)", if the block is declared as shared, each block member will
   22858 		 not be packed, and each block member's layout in memory is implementation dependent, so we can't use the API
   22859 		 glBufferData() to update the UBO directly, we need to query each block member's offset first, then upload the
   22860 		 data to the corresponding offset, otherwise we can't get the correct data from UBO; to make the test passed,
   22861 		 we need to add the qualifier std140,  and change the declaration as layout(binding=0, std140), which can make
   22862 		 sure all the block members are packed and the application can upload the data by glBufferData() directly.
   22863 		 */
   22864 							  "layout(binding = 0, std140) uniform gs_block {\n"
   22865 							  "    TYPE uni_vegeta;\n"
   22866 							  "    TYPE uni_trunks;\n"
   22867 							  "    TYPE uni_goku;\n"
   22868 							  "};\n";
   22869 	static const GLchar* fs = "flat in TYPE vegeta;\n"
   22870 							  "flat in TYPE trunks;\n"
   22871 							  "flat in TYPE goku;\n"
   22872 							  "\n"
   22873 							  "out vec4 fs_out;\n";
   22874 
   22875 	const Utils::Type& type = getType(test_case_index);
   22876 
   22877 	switch (stage)
   22878 	{
   22879 	case Utils::Shader::FRAGMENT:
   22880 		out_interface = fs;
   22881 		break;
   22882 	case Utils::Shader::GEOMETRY:
   22883 		out_interface = gs;
   22884 		break;
   22885 	default:
   22886 		out_interface = "";
   22887 		return;
   22888 	}
   22889 
   22890 	if (Utils::Shader::GEOMETRY == stage)
   22891 	{
   22892 		GLchar		 buffer[16];
   22893 		size_t		 position  = 0;
   22894 		const GLuint type_size = type.GetSize();
   22895 
   22896 		sprintf(buffer, "%d", type_size);
   22897 
   22898 		Utils::replaceToken("SIZE", position, buffer, out_interface);
   22899 	}
   22900 
   22901 	Utils::replaceAllTokens("TYPE", type.GetGLSLTypeName(), out_interface);
   22902 }
   22903 
   22904 /** Get type name
   22905  *
   22906  * @param test_case_index Index of test case
   22907  *
   22908  * @return Name of type test in test_case_index
   22909  **/
   22910 std::string XFBOverrideQualifiersWithAPITest::getTestCaseName(glw::GLuint test_case_index)
   22911 {
   22912 	return getTypeName(test_case_index);
   22913 }
   22914 
   22915 /** Returns number of types to test
   22916  *
   22917  * @return Number of types, 34
   22918  **/
   22919 glw::GLuint XFBOverrideQualifiersWithAPITest::getTestCaseNumber()
   22920 {
   22921 	return getTypesNumber();
   22922 }
   22923 
   22924 /** Inspects program to check if all resources are as expected
   22925  *
   22926  * @param test_case_index Index of test case
   22927  * @param program         Program instance
   22928  * @param out_stream      Error message
   22929  *
   22930  * @return true if everything is ok, false otherwise
   22931  **/
   22932 bool XFBOverrideQualifiersWithAPITest::inspectProgram(GLuint test_case_index, Utils::Program& program,
   22933 													  std::stringstream& out_stream)
   22934 {
   22935 	GLint			   stride	= 0;
   22936 	const Utils::Type& type		 = getType(test_case_index);
   22937 	const GLuint	   type_size = type.GetSize(false);
   22938 
   22939 	program.GetResource(GL_TRANSFORM_FEEDBACK_BUFFER, 0 /* index */, GL_TRANSFORM_FEEDBACK_BUFFER_STRIDE,
   22940 						1 /* buf_size */, &stride);
   22941 
   22942 	if ((GLint)(3 * type_size) != stride)
   22943 	{
   22944 		out_stream << "Stride is: " << stride << " expected: " << (3 * type_size);
   22945 
   22946 		return false;
   22947 	}
   22948 
   22949 	return true;
   22950 }
   22951 
   22952 /** Constructor
   22953  *
   22954  * @param context Test context
   22955  **/
   22956 XFBVertexStreamsTest::XFBVertexStreamsTest(deqp::Context& context)
   22957 	: BufferTestBase(context, "xfb_vertex_streams",
   22958 					 "Test verifies that xfb qualifier works with multiple output streams")
   22959 {
   22960 	/* Nothing to be done here */
   22961 }
   22962 
   22963 /** Get descriptors of buffers necessary for test
   22964  *
   22965  * @param ignored
   22966  * @param out_descriptors Descriptors of buffers used by test
   22967  **/
   22968 void XFBVertexStreamsTest::getBufferDescriptors(glw::GLuint /* test_case_index */,
   22969 												bufferDescriptor::Vector& out_descriptors)
   22970 {
   22971 	const Utils::Type& type = Utils::Type::vec4;
   22972 
   22973 	/* Test needs single uniform and three xfbs */
   22974 	out_descriptors.resize(4);
   22975 
   22976 	/* Get references */
   22977 	bufferDescriptor& uniform = out_descriptors[0];
   22978 	bufferDescriptor& xfb_1   = out_descriptors[1];
   22979 	bufferDescriptor& xfb_2   = out_descriptors[2];
   22980 	bufferDescriptor& xfb_3   = out_descriptors[3];
   22981 
   22982 	/* Index */
   22983 	uniform.m_index = 0;
   22984 	xfb_1.m_index   = 1;
   22985 	xfb_2.m_index   = 2;
   22986 	xfb_3.m_index   = 3;
   22987 
   22988 	/* Target */
   22989 	uniform.m_target = Utils::Buffer::Uniform;
   22990 	xfb_1.m_target   = Utils::Buffer::Transform_feedback;
   22991 	xfb_2.m_target   = Utils::Buffer::Transform_feedback;
   22992 	xfb_3.m_target   = Utils::Buffer::Transform_feedback;
   22993 
   22994 	/* Data */
   22995 	const std::vector<GLubyte>& goku_data   = type.GenerateData();
   22996 	const std::vector<GLubyte>& gohan_data  = type.GenerateData();
   22997 	const std::vector<GLubyte>& goten_data  = type.GenerateData();
   22998 	const std::vector<GLubyte>& picolo_data = type.GenerateData();
   22999 	const std::vector<GLubyte>& vegeta_data = type.GenerateData();
   23000 	const std::vector<GLubyte>& bulma_data  = type.GenerateData();
   23001 
   23002 	const GLuint type_size = static_cast<GLuint>(vegeta_data.size());
   23003 
   23004 	/* Uniform data */
   23005 	uniform.m_initial_data.resize(6 * type_size);
   23006 	memcpy(&uniform.m_initial_data[0] + 0, &goku_data[0], type_size);
   23007 	memcpy(&uniform.m_initial_data[0] + type_size, &gohan_data[0], type_size);
   23008 	memcpy(&uniform.m_initial_data[0] + 2 * type_size, &goten_data[0], type_size);
   23009 	memcpy(&uniform.m_initial_data[0] + 3 * type_size, &picolo_data[0], type_size);
   23010 	memcpy(&uniform.m_initial_data[0] + 4 * type_size, &vegeta_data[0], type_size);
   23011 	memcpy(&uniform.m_initial_data[0] + 5 * type_size, &bulma_data[0], type_size);
   23012 
   23013 	/* XFB data */
   23014 	static const GLuint xfb_stride = 64;
   23015 	xfb_1.m_initial_data.resize(xfb_stride);
   23016 	xfb_1.m_expected_data.resize(xfb_stride);
   23017 	xfb_2.m_initial_data.resize(xfb_stride);
   23018 	xfb_2.m_expected_data.resize(xfb_stride);
   23019 	xfb_3.m_initial_data.resize(xfb_stride);
   23020 	xfb_3.m_expected_data.resize(xfb_stride);
   23021 
   23022 	for (GLuint i = 0; i < xfb_stride; ++i)
   23023 	{
   23024 		xfb_1.m_initial_data[i]  = (glw::GLubyte)i;
   23025 		xfb_1.m_expected_data[i] = (glw::GLubyte)i;
   23026 		xfb_2.m_initial_data[i]  = (glw::GLubyte)i;
   23027 		xfb_2.m_expected_data[i] = (glw::GLubyte)i;
   23028 		xfb_3.m_initial_data[i]  = (glw::GLubyte)i;
   23029 		xfb_3.m_expected_data[i] = (glw::GLubyte)i;
   23030 	}
   23031 
   23032 	memcpy(&xfb_1.m_expected_data[0] + 48, &goku_data[0], type_size);
   23033 	memcpy(&xfb_1.m_expected_data[0] + 32, &gohan_data[0], type_size);
   23034 	memcpy(&xfb_1.m_expected_data[0] + 16, &goten_data[0], type_size);
   23035 	memcpy(&xfb_3.m_expected_data[0] + 48, &picolo_data[0], type_size);
   23036 	memcpy(&xfb_3.m_expected_data[0] + 32, &vegeta_data[0], type_size);
   23037 	memcpy(&xfb_2.m_expected_data[0] + 32, &bulma_data[0], type_size);
   23038 }
   23039 
   23040 /** Get body of main function for given shader stage
   23041  *
   23042  * @param ignored
   23043  * @param stage            Shader stage
   23044  * @param out_assignments  Set to empty
   23045  * @param out_calculations Set to empty
   23046  **/
   23047 void XFBVertexStreamsTest::getShaderBody(GLuint /* test_case_index */, Utils::Shader::STAGES stage,
   23048 										 std::string& out_assignments, std::string& out_calculations)
   23049 {
   23050 	out_calculations = "";
   23051 
   23052 	// the shader declares the output variables with different "stream" qualifier, to make the data can export to
   23053 	// each stream, we must call the function EmitStreamVertex() and EndStreamPrimitive() to make each vertex emitted
   23054 	// by the GS is assigned to specific stream.
   23055 	static const GLchar* gs = "    goku   = uni_goku;\n"
   23056 							  "    gohan  = uni_gohan;\n"
   23057 							  "    goten  = uni_goten;\n"
   23058 							  "    EmitStreamVertex(0);\n"
   23059 							  "    EndStreamPrimitive(0);\n"
   23060 							  "    picolo = uni_picolo;\n"
   23061 							  "    vegeta = uni_vegeta;\n"
   23062 							  "    EmitStreamVertex(1);\n"
   23063 							  "    EndStreamPrimitive(1);\n"
   23064 							  "    bulma  = uni_bulma;\n"
   23065 							  "    EmitStreamVertex(2);\n"
   23066 							  "    EndStreamPrimitive(2);\n";
   23067 
   23068 	static const GLchar* fs = "    fs_out = gohan + goku + goten;\n";
   23069 
   23070 	const GLchar* assignments = "";
   23071 	switch (stage)
   23072 	{
   23073 	case Utils::Shader::FRAGMENT:
   23074 		assignments = fs;
   23075 		break;
   23076 	case Utils::Shader::GEOMETRY:
   23077 		assignments = gs;
   23078 		break;
   23079 	default:
   23080 		break;
   23081 	}
   23082 
   23083 	out_assignments = assignments;
   23084 }
   23085 
   23086 /** Get interface of shader
   23087  *
   23088  * @param ignored
   23089  * @param stage            Shader stage
   23090  * @param out_interface    Set to ""
   23091  **/
   23092 void XFBVertexStreamsTest::getShaderInterface(GLuint /* test_case_index */, Utils::Shader::STAGES stage,
   23093 											  std::string& out_interface)
   23094 {
   23095 	static const GLchar* gs = "layout (xfb_buffer = 1, xfb_stride = 64) out;\n"
   23096 							  "layout (xfb_buffer = 2, xfb_stride = 64) out;\n"
   23097 							  "layout (xfb_buffer = 3, xfb_stride = 64) out;\n"
   23098 							  "\n"
   23099 							  "layout (stream = 0, xfb_buffer = 1, xfb_offset = 48) out vec4 goku;\n"
   23100 							  "layout (stream = 0, xfb_buffer = 1, xfb_offset = 32) out vec4 gohan;\n"
   23101 							  "layout (stream = 0, xfb_buffer = 1, xfb_offset = 16) out vec4 goten;\n"
   23102 							  "layout (stream = 1, xfb_buffer = 3, xfb_offset = 48) out vec4 picolo;\n"
   23103 							  "layout (stream = 1, xfb_buffer = 3, xfb_offset = 32) out vec4 vegeta;\n"
   23104 							  "layout (stream = 2, xfb_buffer = 2, xfb_offset = 32) out vec4 bulma;\n"
   23105 							  "\n"
   23106 							  "layout(binding = 0) uniform gs_block {\n"
   23107 							  "    vec4 uni_goku;\n"
   23108 							  "    vec4 uni_gohan;\n"
   23109 							  "    vec4 uni_goten;\n"
   23110 							  "    vec4 uni_picolo;\n"
   23111 							  "    vec4 uni_vegeta;\n"
   23112 							  "    vec4 uni_bulma;\n"
   23113 							  "};\n";
   23114 	/*
   23115 	 Fixed incorrect usage of in/out qualifier, the following variable should be input symbols for fragment shader
   23116 	 */
   23117 	static const GLchar* fs = "in vec4 goku;\n"
   23118 							  "in vec4 gohan;\n"
   23119 							  "in vec4 goten;\n"
   23120 							  "\n"
   23121 							  "out vec4 fs_out;\n";
   23122 
   23123 	switch (stage)
   23124 	{
   23125 	case Utils::Shader::FRAGMENT:
   23126 		out_interface = fs;
   23127 		break;
   23128 	case Utils::Shader::GEOMETRY:
   23129 		out_interface = gs;
   23130 		break;
   23131 	default:
   23132 		out_interface = "";
   23133 		return;
   23134 	}
   23135 }
   23136 
   23137 /** Constructor
   23138  *
   23139  * @param context Test framework context
   23140  **/
   23141 XFBMultipleVertexStreamsTest::XFBMultipleVertexStreamsTest(deqp::Context& context)
   23142 	: NegativeTestBase(
   23143 		  context, "xfb_multiple_vertex_streams",
   23144 		  "Test verifies that compiler reports error when multiple streams are captured with same xfb_buffer")
   23145 {
   23146 }
   23147 
   23148 /** Source for given test case and stage
   23149  *
   23150  * @param ignored
   23151  * @param stage           Shader stage
   23152  *
   23153  * @return Shader source
   23154  **/
   23155 std::string XFBMultipleVertexStreamsTest::getShaderSource(GLuint /* test_case_index */, Utils::Shader::STAGES stage)
   23156 {
   23157 	static const GLchar* var_definition = "const uint valid_stride = 64;\n"
   23158 										  "\n"
   23159 										  "layout (xfb_buffer = 1, xfb_stride = valid_stride) out;\n"
   23160 										  "layout (xfb_buffer = 3, xfb_stride = valid_stride) out;\n"
   23161 										  "\n"
   23162 										  "\n"
   23163 										  "layout (stream = 0, xfb_buffer = 1, xfb_offset = 48) out vec4 goku;\n"
   23164 										  "layout (stream = 1, xfb_buffer = 1, xfb_offset = 32) out vec4 gohan;\n"
   23165 										  "layout (stream = 2, xfb_buffer = 1, xfb_offset = 16) out vec4 goten;\n";
   23166 	static const GLchar* var_use = "    goku  = result / 2;\n"
   23167 								   "    gohan = result / 4;\n"
   23168 								   "    goten = result / 6;\n";
   23169 	static const GLchar* fs = "#version 430 core\n"
   23170 							  "#extension GL_ARB_enhanced_layouts : require\n"
   23171 							  "\n"
   23172 							  "in  vec4 gs_fs;\n"
   23173 							  "in  vec4 goku;\n"
   23174 							  "out vec4 fs_out;\n"
   23175 							  "\n"
   23176 							  "void main()\n"
   23177 							  "{\n"
   23178 							  "    fs_out = gs_fs + goku;\n"
   23179 							  "}\n"
   23180 							  "\n";
   23181 	static const GLchar* gs = "#version 430 core\n"
   23182 							  "#extension GL_ARB_enhanced_layouts : require\n"
   23183 							  "\n"
   23184 							  "layout(points)                           in;\n"
   23185 							  "layout(triangle_strip, max_vertices = 4) out;\n"
   23186 							  "\n"
   23187 							  "VAR_DEFINITION"
   23188 							  "\n"
   23189 							  "in  vec4 tes_gs[];\n"
   23190 							  "out vec4 gs_fs;\n"
   23191 							  "\n"
   23192 							  "void main()\n"
   23193 							  "{\n"
   23194 							  "    vec4 result = tes_gs[0];\n"
   23195 							  "\n"
   23196 							  "VARIABLE_USE"
   23197 							  "\n"
   23198 							  "    gs_fs = result;\n"
   23199 							  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   23200 							  "    EmitVertex();\n"
   23201 							  "    gs_fs = result;\n"
   23202 							  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   23203 							  "    EmitVertex();\n"
   23204 							  "    gs_fs = result;\n"
   23205 							  "    gl_Position  = vec4(1, -1, 0, 1);\n"
   23206 							  "    EmitVertex();\n"
   23207 							  "    gs_fs = result;\n"
   23208 							  "    gl_Position  = vec4(1, 1, 0, 1);\n"
   23209 							  "    EmitVertex();\n"
   23210 							  "}\n"
   23211 							  "\n";
   23212 	static const GLchar* vs = "#version 430 core\n"
   23213 							  "#extension GL_ARB_enhanced_layouts : require\n"
   23214 							  "\n"
   23215 							  "in  vec4 in_vs;\n"
   23216 							  "out vec4 vs_tcs;\n"
   23217 							  "\n"
   23218 							  "void main()\n"
   23219 							  "{\n"
   23220 							  "    vs_tcs = in_vs;\n"
   23221 							  "}\n"
   23222 							  "\n";
   23223 
   23224 	std::string source;
   23225 
   23226 	if (Utils::Shader::GEOMETRY == stage)
   23227 	{
   23228 		size_t position = 0;
   23229 
   23230 		source = gs;
   23231 
   23232 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   23233 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   23234 	}
   23235 	else
   23236 	{
   23237 		switch (stage)
   23238 		{
   23239 		case Utils::Shader::FRAGMENT:
   23240 			source = fs;
   23241 			break;
   23242 		case Utils::Shader::VERTEX:
   23243 			source = vs;
   23244 			break;
   23245 		default:
   23246 			source = "";
   23247 		}
   23248 	}
   23249 
   23250 	return source;
   23251 }
   23252 
   23253 /** Selects if "compute" stage is relevant for test
   23254  *
   23255  * @param ignored
   23256  *
   23257  * @return false
   23258  **/
   23259 bool XFBMultipleVertexStreamsTest::isComputeRelevant(GLuint /* test_case_index */)
   23260 {
   23261 	return false;
   23262 }
   23263 
   23264 /** Constructor
   23265  *
   23266  * @param context Test framework context
   23267  **/
   23268 XFBExceedBufferLimitTest::XFBExceedBufferLimitTest(deqp::Context& context)
   23269 	: NegativeTestBase(context, "xfb_exceed_buffer_limit",
   23270 					   "Test verifies that compiler reports error when xfb_buffer qualifier exceeds limit")
   23271 {
   23272 }
   23273 
   23274 /** Source for given test case and stage
   23275  *
   23276  * @param test_case_index Index of test case
   23277  * @param stage           Shader stage
   23278  *
   23279  * @return Shader source
   23280  **/
   23281 std::string XFBExceedBufferLimitTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   23282 {
   23283 	static const GLchar* block_var_definition = "const uint buffer_index = BUFFER;\n"
   23284 												"\n"
   23285 												"layout (xfb_buffer = buffer_index, xfb_offset = 0) out Goku {\n"
   23286 												"    vec4 member;\n"
   23287 												"} gokuARRAY;\n";
   23288 	static const GLchar* global_var_definition = "const uint buffer_index = BUFFER;\n"
   23289 												 "\n"
   23290 												 "layout (xfb_buffer = buffer_index) out;\n";
   23291 	static const GLchar* vector_var_definition = "const uint buffer_index = BUFFER;\n"
   23292 												 "\n"
   23293 												 "layout (xfb_buffer = buffer_index) out vec4 gokuARRAY;\n";
   23294 	static const GLchar* block_use  = "    gokuINDEX.member = result / 2;\n";
   23295 	static const GLchar* global_use = "";
   23296 	static const GLchar* vector_use = "    gokuINDEX = result / 2;\n";
   23297 	static const GLchar* fs			= "#version 430 core\n"
   23298 							  "#extension GL_ARB_enhanced_layouts : require\n"
   23299 							  "\n"
   23300 							  "in  vec4 gs_fs;\n"
   23301 							  "out vec4 fs_out;\n"
   23302 							  "\n"
   23303 							  "void main()\n"
   23304 							  "{\n"
   23305 							  "    fs_out = gs_fs;\n"
   23306 							  "}\n"
   23307 							  "\n";
   23308 	static const GLchar* gs_tested = "#version 430 core\n"
   23309 									 "#extension GL_ARB_enhanced_layouts : require\n"
   23310 									 "\n"
   23311 									 "layout(points)                           in;\n"
   23312 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   23313 									 "\n"
   23314 									 "VAR_DEFINITION"
   23315 									 "\n"
   23316 									 "in  vec4 tes_gs[];\n"
   23317 									 "out vec4 gs_fs;\n"
   23318 									 "\n"
   23319 									 "void main()\n"
   23320 									 "{\n"
   23321 									 "    vec4 result = tes_gs[0];\n"
   23322 									 "\n"
   23323 									 "VARIABLE_USE"
   23324 									 "\n"
   23325 									 "    gs_fs = result;\n"
   23326 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   23327 									 "    EmitVertex();\n"
   23328 									 "    gs_fs = result;\n"
   23329 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   23330 									 "    EmitVertex();\n"
   23331 									 "    gs_fs = result;\n"
   23332 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   23333 									 "    EmitVertex();\n"
   23334 									 "    gs_fs = result;\n"
   23335 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   23336 									 "    EmitVertex();\n"
   23337 									 "}\n"
   23338 									 "\n";
   23339 	static const GLchar* tcs = "#version 430 core\n"
   23340 							   "#extension GL_ARB_enhanced_layouts : require\n"
   23341 							   "\n"
   23342 							   "layout(vertices = 1) out;\n"
   23343 							   "\n"
   23344 							   "in  vec4 vs_tcs[];\n"
   23345 							   "out vec4 tcs_tes[];\n"
   23346 							   "\n"
   23347 							   "void main()\n"
   23348 							   "{\n"
   23349 							   "\n"
   23350 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   23351 							   "\n"
   23352 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   23353 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   23354 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   23355 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   23356 							   "    gl_TessLevelInner[0] = 1.0;\n"
   23357 							   "    gl_TessLevelInner[1] = 1.0;\n"
   23358 							   "}\n"
   23359 							   "\n";
   23360 	static const GLchar* tcs_tested = "#version 430 core\n"
   23361 									  "#extension GL_ARB_enhanced_layouts : require\n"
   23362 									  "\n"
   23363 									  "layout(vertices = 1) out;\n"
   23364 									  "\n"
   23365 									  "VAR_DEFINITION"
   23366 									  "\n"
   23367 									  "in  vec4 vs_tcs[];\n"
   23368 									  "out vec4 tcs_tes[];\n"
   23369 									  "\n"
   23370 									  "void main()\n"
   23371 									  "{\n"
   23372 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   23373 									  "\n"
   23374 									  "VARIABLE_USE"
   23375 									  "\n"
   23376 									  "    tcs_tes[gl_InvocationID] = result;\n"
   23377 									  "\n"
   23378 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   23379 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   23380 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   23381 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   23382 									  "    gl_TessLevelInner[0] = 1.0;\n"
   23383 									  "    gl_TessLevelInner[1] = 1.0;\n"
   23384 									  "}\n"
   23385 									  "\n";
   23386 	static const GLchar* tes_tested = "#version 430 core\n"
   23387 									  "#extension GL_ARB_enhanced_layouts : require\n"
   23388 									  "\n"
   23389 									  "layout(isolines, point_mode) in;\n"
   23390 									  "\n"
   23391 									  "VAR_DEFINITION"
   23392 									  "\n"
   23393 									  "in  vec4 tcs_tes[];\n"
   23394 									  "out vec4 tes_gs;\n"
   23395 									  "\n"
   23396 									  "void main()\n"
   23397 									  "{\n"
   23398 									  "    vec4 result = tcs_tes[0];\n"
   23399 									  "\n"
   23400 									  "VARIABLE_USE"
   23401 									  "\n"
   23402 									  "    tes_gs += result;\n"
   23403 									  "}\n"
   23404 									  "\n";
   23405 	static const GLchar* vs = "#version 430 core\n"
   23406 							  "#extension GL_ARB_enhanced_layouts : require\n"
   23407 							  "\n"
   23408 							  "in  vec4 in_vs;\n"
   23409 							  "out vec4 vs_tcs;\n"
   23410 							  "\n"
   23411 							  "void main()\n"
   23412 							  "{\n"
   23413 							  "    vs_tcs = in_vs;\n"
   23414 							  "}\n"
   23415 							  "\n";
   23416 	static const GLchar* vs_tested = "#version 430 core\n"
   23417 									 "#extension GL_ARB_enhanced_layouts : require\n"
   23418 									 "\n"
   23419 									 "VAR_DEFINITION"
   23420 									 "\n"
   23421 									 "in  vec4 in_vs;\n"
   23422 									 "out vec4 vs_tcs;\n"
   23423 									 "\n"
   23424 									 "void main()\n"
   23425 									 "{\n"
   23426 									 "    vec4 result = in_vs;\n"
   23427 									 "\n"
   23428 									 "VARIABLE_USE"
   23429 									 "\n"
   23430 									 "    vs_tcs = result;\n"
   23431 									 "}\n"
   23432 									 "\n";
   23433 
   23434 	std::string source;
   23435 	testCase&   test_case = m_test_cases[test_case_index];
   23436 
   23437 	if (test_case.m_stage == stage)
   23438 	{
   23439 		const GLchar*	array = "";
   23440 		GLchar			 buffer[16];
   23441 		const Functions& gl		   = m_context.getRenderContext().getFunctions();
   23442 		const GLchar*	index	 = "";
   23443 		GLint			 max_n_xfb = 0;
   23444 		size_t			 position  = 0;
   23445 		size_t			 temp;
   23446 		const GLchar*	var_definition = 0;
   23447 		const GLchar*	var_use		= 0;
   23448 
   23449 		gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_BUFFERS, &max_n_xfb);
   23450 		GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   23451 
   23452 		sprintf(buffer, "%d", max_n_xfb);
   23453 
   23454 		switch (test_case.m_case)
   23455 		{
   23456 		case BLOCK:
   23457 			var_definition = block_var_definition;
   23458 			var_use		   = block_use;
   23459 			break;
   23460 		case GLOBAL:
   23461 			var_definition = global_var_definition;
   23462 			var_use		   = global_use;
   23463 			break;
   23464 		case VECTOR:
   23465 			var_definition = vector_var_definition;
   23466 			var_use		   = vector_use;
   23467 			break;
   23468 		default:
   23469 			TCU_FAIL("Invalid enum");
   23470 		}
   23471 
   23472 		switch (stage)
   23473 		{
   23474 		case Utils::Shader::GEOMETRY:
   23475 			source = gs_tested;
   23476 			array  = "[]";
   23477 			index  = "[0]";
   23478 			break;
   23479 		case Utils::Shader::TESS_CTRL:
   23480 			source = tcs_tested;
   23481 			array  = "[]";
   23482 			index  = "[gl_InvocationID]";
   23483 			break;
   23484 		case Utils::Shader::TESS_EVAL:
   23485 			source = tes_tested;
   23486 			array  = "[]";
   23487 			index  = "[0]";
   23488 			break;
   23489 		case Utils::Shader::VERTEX:
   23490 			source = vs_tested;
   23491 			break;
   23492 		default:
   23493 			TCU_FAIL("Invalid enum");
   23494 		}
   23495 
   23496 		temp = position;
   23497 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   23498 		position = temp;
   23499 		Utils::replaceToken("BUFFER", position, buffer, source);
   23500 		if (GLOBAL != test_case.m_case)
   23501 		{
   23502 			Utils::replaceToken("ARRAY", position, array, source);
   23503 		}
   23504 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   23505 
   23506 		Utils::replaceAllTokens("INDEX", index, source);
   23507 	}
   23508 	else
   23509 	{
   23510 		switch (test_case.m_stage)
   23511 		{
   23512 		case Utils::Shader::GEOMETRY:
   23513 			switch (stage)
   23514 			{
   23515 			case Utils::Shader::FRAGMENT:
   23516 				source = fs;
   23517 				break;
   23518 			case Utils::Shader::VERTEX:
   23519 				source = vs;
   23520 				break;
   23521 			default:
   23522 				source = "";
   23523 			}
   23524 			break;
   23525 		case Utils::Shader::TESS_CTRL:
   23526 			switch (stage)
   23527 			{
   23528 			case Utils::Shader::FRAGMENT:
   23529 				source = fs;
   23530 				break;
   23531 			case Utils::Shader::VERTEX:
   23532 				source = vs;
   23533 				break;
   23534 			default:
   23535 				source = "";
   23536 			}
   23537 			break;
   23538 		case Utils::Shader::TESS_EVAL:
   23539 			switch (stage)
   23540 			{
   23541 			case Utils::Shader::FRAGMENT:
   23542 				source = fs;
   23543 				break;
   23544 			case Utils::Shader::TESS_CTRL:
   23545 				source = tcs;
   23546 				break;
   23547 			case Utils::Shader::VERTEX:
   23548 				source = vs;
   23549 				break;
   23550 			default:
   23551 				source = "";
   23552 			}
   23553 			break;
   23554 		case Utils::Shader::VERTEX:
   23555 			switch (stage)
   23556 			{
   23557 			case Utils::Shader::FRAGMENT:
   23558 				source = fs;
   23559 				break;
   23560 			default:
   23561 				source = "";
   23562 			}
   23563 			break;
   23564 		default:
   23565 			TCU_FAIL("Invalid enum");
   23566 			break;
   23567 		}
   23568 	}
   23569 
   23570 	return source;
   23571 }
   23572 
   23573 /** Get description of test case
   23574  *
   23575  * @param test_case_index Index of test case
   23576  *
   23577  * @return Test case description
   23578  **/
   23579 std::string XFBExceedBufferLimitTest::getTestCaseName(GLuint test_case_index)
   23580 {
   23581 	std::stringstream stream;
   23582 	testCase&		  test_case = m_test_cases[test_case_index];
   23583 
   23584 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage) << ", case: ";
   23585 
   23586 	switch (test_case.m_case)
   23587 	{
   23588 	case BLOCK:
   23589 		stream << "BLOCK";
   23590 		break;
   23591 	case GLOBAL:
   23592 		stream << "GLOBAL";
   23593 		break;
   23594 	case VECTOR:
   23595 		stream << "VECTOR";
   23596 		break;
   23597 	default:
   23598 		TCU_FAIL("Invalid enum");
   23599 	}
   23600 
   23601 	return stream.str();
   23602 }
   23603 
   23604 /** Get number of test cases
   23605  *
   23606  * @return Number of test cases
   23607  **/
   23608 GLuint XFBExceedBufferLimitTest::getTestCaseNumber()
   23609 {
   23610 	return static_cast<GLuint>(m_test_cases.size());
   23611 }
   23612 
   23613 /** Selects if "compute" stage is relevant for test
   23614  *
   23615  * @param ignored
   23616  *
   23617  * @return false
   23618  **/
   23619 bool XFBExceedBufferLimitTest::isComputeRelevant(GLuint /* test_case_index */)
   23620 {
   23621 	return false;
   23622 }
   23623 
   23624 /** Prepare all test cases
   23625  *
   23626  **/
   23627 void XFBExceedBufferLimitTest::testInit()
   23628 {
   23629 	for (GLuint c = 0; c < CASE_MAX; ++c)
   23630 	{
   23631 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   23632 		{
   23633 			if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::TESS_CTRL == stage) ||
   23634 				(Utils::Shader::FRAGMENT == stage))
   23635 			{
   23636 				continue;
   23637 			}
   23638 
   23639 			testCase test_case = { (CASES)c, (Utils::Shader::STAGES)stage };
   23640 
   23641 			m_test_cases.push_back(test_case);
   23642 		}
   23643 	}
   23644 }
   23645 
   23646 /** Constructor
   23647  *
   23648  * @param context Test framework context
   23649  **/
   23650 XFBExceedOffsetLimitTest::XFBExceedOffsetLimitTest(deqp::Context& context)
   23651 	: NegativeTestBase(context, "xfb_exceed_offset_limit",
   23652 					   "Test verifies that compiler reports error when xfb_offset qualifier exceeds limit")
   23653 {
   23654 }
   23655 
   23656 /** Source for given test case and stage
   23657  *
   23658  * @param test_case_index Index of test case
   23659  * @param stage           Shader stage
   23660  *
   23661  * @return Shader source
   23662  **/
   23663 std::string XFBExceedOffsetLimitTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   23664 {
   23665 	static const GLchar* block_var_definition = "const uint max_size = SIZE;\n"
   23666 												"\n"
   23667 												"layout (xfb_buffer = 0, xfb_offset = max_size + 16) out Goku {\n"
   23668 												"    vec4 member;\n"
   23669 												"} gokuARRAY;\n";
   23670 	static const GLchar* global_var_definition = "const uint max_size = SIZE;\n"
   23671 												 "\n"
   23672 												 "layout (xfb_buffer = 0, xfb_stride = max_size + 16) out;\n";
   23673 	static const GLchar* vector_var_definition =
   23674 		"const uint max_size = SIZE;\n"
   23675 		"\n"
   23676 		"layout (xfb_buffer = 0, xfb_offset = max_size + 16) out vec4 gokuARRAY;\n";
   23677 	static const GLchar* block_use  = "    gokuINDEX.member = result / 2;\n";
   23678 	static const GLchar* global_use = "";
   23679 	static const GLchar* vector_use = "    gokuINDEX = result / 2;\n";
   23680 	static const GLchar* fs			= "#version 430 core\n"
   23681 							  "#extension GL_ARB_enhanced_layouts : require\n"
   23682 							  "\n"
   23683 							  "in  vec4 gs_fs;\n"
   23684 							  "out vec4 fs_out;\n"
   23685 							  "\n"
   23686 							  "void main()\n"
   23687 							  "{\n"
   23688 							  "    fs_out = gs_fs;\n"
   23689 							  "}\n"
   23690 							  "\n";
   23691 	static const GLchar* gs_tested = "#version 430 core\n"
   23692 									 "#extension GL_ARB_enhanced_layouts : require\n"
   23693 									 "\n"
   23694 									 "layout(points)                           in;\n"
   23695 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   23696 									 "\n"
   23697 									 "VAR_DEFINITION"
   23698 									 "\n"
   23699 									 "in  vec4 tes_gs[];\n"
   23700 									 "out vec4 gs_fs;\n"
   23701 									 "\n"
   23702 									 "void main()\n"
   23703 									 "{\n"
   23704 									 "    vec4 result = tes_gs[0];\n"
   23705 									 "\n"
   23706 									 "VARIABLE_USE"
   23707 									 "\n"
   23708 									 "    gs_fs = result;\n"
   23709 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   23710 									 "    EmitVertex();\n"
   23711 									 "    gs_fs = result;\n"
   23712 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   23713 									 "    EmitVertex();\n"
   23714 									 "    gs_fs = result;\n"
   23715 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   23716 									 "    EmitVertex();\n"
   23717 									 "    gs_fs = result;\n"
   23718 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   23719 									 "    EmitVertex();\n"
   23720 									 "}\n"
   23721 									 "\n";
   23722 	static const GLchar* tcs = "#version 430 core\n"
   23723 							   "#extension GL_ARB_enhanced_layouts : require\n"
   23724 							   "\n"
   23725 							   "layout(vertices = 1) out;\n"
   23726 							   "\n"
   23727 							   "in  vec4 vs_tcs[];\n"
   23728 							   "out vec4 tcs_tes[];\n"
   23729 							   "\n"
   23730 							   "void main()\n"
   23731 							   "{\n"
   23732 							   "\n"
   23733 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   23734 							   "\n"
   23735 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   23736 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   23737 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   23738 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   23739 							   "    gl_TessLevelInner[0] = 1.0;\n"
   23740 							   "    gl_TessLevelInner[1] = 1.0;\n"
   23741 							   "}\n"
   23742 							   "\n";
   23743 	static const GLchar* tcs_tested = "#version 430 core\n"
   23744 									  "#extension GL_ARB_enhanced_layouts : require\n"
   23745 									  "\n"
   23746 									  "layout(vertices = 1) out;\n"
   23747 									  "\n"
   23748 									  "VAR_DEFINITION"
   23749 									  "\n"
   23750 									  "in  vec4 vs_tcs[];\n"
   23751 									  "out vec4 tcs_tes[];\n"
   23752 									  "\n"
   23753 									  "void main()\n"
   23754 									  "{\n"
   23755 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   23756 									  "\n"
   23757 									  "VARIABLE_USE"
   23758 									  "\n"
   23759 									  "    tcs_tes[gl_InvocationID] = result;\n"
   23760 									  "\n"
   23761 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   23762 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   23763 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   23764 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   23765 									  "    gl_TessLevelInner[0] = 1.0;\n"
   23766 									  "    gl_TessLevelInner[1] = 1.0;\n"
   23767 									  "}\n"
   23768 									  "\n";
   23769 	static const GLchar* tes_tested = "#version 430 core\n"
   23770 									  "#extension GL_ARB_enhanced_layouts : require\n"
   23771 									  "\n"
   23772 									  "layout(isolines, point_mode) in;\n"
   23773 									  "\n"
   23774 									  "VAR_DEFINITION"
   23775 									  "\n"
   23776 									  "in  vec4 tcs_tes[];\n"
   23777 									  "out vec4 tes_gs;\n"
   23778 									  "\n"
   23779 									  "void main()\n"
   23780 									  "{\n"
   23781 									  "    vec4 result = tcs_tes[0];\n"
   23782 									  "\n"
   23783 									  "VARIABLE_USE"
   23784 									  "\n"
   23785 									  "    tes_gs += result;\n"
   23786 									  "}\n"
   23787 									  "\n";
   23788 	static const GLchar* vs = "#version 430 core\n"
   23789 							  "#extension GL_ARB_enhanced_layouts : require\n"
   23790 							  "\n"
   23791 							  "in  vec4 in_vs;\n"
   23792 							  "out vec4 vs_tcs;\n"
   23793 							  "\n"
   23794 							  "void main()\n"
   23795 							  "{\n"
   23796 							  "    vs_tcs = in_vs;\n"
   23797 							  "}\n"
   23798 							  "\n";
   23799 	static const GLchar* vs_tested = "#version 430 core\n"
   23800 									 "#extension GL_ARB_enhanced_layouts : require\n"
   23801 									 "\n"
   23802 									 "VAR_DEFINITION"
   23803 									 "\n"
   23804 									 "in  vec4 in_vs;\n"
   23805 									 "out vec4 vs_tcs;\n"
   23806 									 "\n"
   23807 									 "void main()\n"
   23808 									 "{\n"
   23809 									 "    vec4 result = in_vs;\n"
   23810 									 "\n"
   23811 									 "VARIABLE_USE"
   23812 									 "\n"
   23813 									 "    vs_tcs = result;\n"
   23814 									 "}\n"
   23815 									 "\n";
   23816 
   23817 	std::string source;
   23818 	testCase&   test_case = m_test_cases[test_case_index];
   23819 
   23820 	if (test_case.m_stage == stage)
   23821 	{
   23822 		const GLchar*	array = "";
   23823 		GLchar			 buffer[16];
   23824 		const Functions& gl				 = m_context.getRenderContext().getFunctions();
   23825 		const GLchar*	index			 = "";
   23826 		GLint			 max_n_xfb_comp  = 0;
   23827 		GLint			 max_n_xfb_bytes = 0;
   23828 		size_t			 position		 = 0;
   23829 		size_t			 temp;
   23830 		const GLchar*	var_definition = 0;
   23831 		const GLchar*	var_use		= 0;
   23832 
   23833 		gl.getIntegerv(GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS, &max_n_xfb_comp);
   23834 		GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
   23835 
   23836 		max_n_xfb_bytes = max_n_xfb_comp * 4;
   23837 
   23838 		sprintf(buffer, "%d", max_n_xfb_bytes);
   23839 
   23840 		switch (test_case.m_case)
   23841 		{
   23842 		case BLOCK:
   23843 			var_definition = block_var_definition;
   23844 			var_use		   = block_use;
   23845 			break;
   23846 		case GLOBAL:
   23847 			var_definition = global_var_definition;
   23848 			var_use		   = global_use;
   23849 			break;
   23850 		case VECTOR:
   23851 			var_definition = vector_var_definition;
   23852 			var_use		   = vector_use;
   23853 			break;
   23854 		default:
   23855 			TCU_FAIL("Invalid enum");
   23856 		}
   23857 		// It is a compile time error to apply xfb_offset to the declaration of an unsized array(GLSL4.5 spec: Page73)
   23858 		// change array = "[]" to "[1]"
   23859 		switch (stage)
   23860 		{
   23861 		case Utils::Shader::GEOMETRY:
   23862 			source = gs_tested;
   23863 			array  = "[1]";
   23864 			index  = "[0]";
   23865 			break;
   23866 		case Utils::Shader::TESS_CTRL:
   23867 			source = tcs_tested;
   23868 			array  = "[1]";
   23869 			index  = "[gl_InvocationID]";
   23870 			break;
   23871 		case Utils::Shader::TESS_EVAL:
   23872 			source = tes_tested;
   23873 			array  = "[1]";
   23874 			index  = "[0]";
   23875 			break;
   23876 		case Utils::Shader::VERTEX:
   23877 			source = vs_tested;
   23878 			break;
   23879 		default:
   23880 			TCU_FAIL("Invalid enum");
   23881 		}
   23882 
   23883 		temp = position;
   23884 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   23885 		position = temp;
   23886 		Utils::replaceToken("SIZE", position, buffer, source);
   23887 		if (GLOBAL != test_case.m_case)
   23888 		{
   23889 			Utils::replaceToken("ARRAY", position, array, source);
   23890 		}
   23891 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   23892 
   23893 		Utils::replaceAllTokens("INDEX", index, source);
   23894 	}
   23895 	else
   23896 	{
   23897 		switch (test_case.m_stage)
   23898 		{
   23899 		case Utils::Shader::GEOMETRY:
   23900 			switch (stage)
   23901 			{
   23902 			case Utils::Shader::FRAGMENT:
   23903 				source = fs;
   23904 				break;
   23905 			case Utils::Shader::VERTEX:
   23906 				source = vs;
   23907 				break;
   23908 			default:
   23909 				source = "";
   23910 			}
   23911 			break;
   23912 		case Utils::Shader::TESS_CTRL:
   23913 			switch (stage)
   23914 			{
   23915 			case Utils::Shader::FRAGMENT:
   23916 				source = fs;
   23917 				break;
   23918 			case Utils::Shader::VERTEX:
   23919 				source = vs;
   23920 				break;
   23921 			default:
   23922 				source = "";
   23923 			}
   23924 			break;
   23925 		case Utils::Shader::TESS_EVAL:
   23926 			switch (stage)
   23927 			{
   23928 			case Utils::Shader::FRAGMENT:
   23929 				source = fs;
   23930 				break;
   23931 			case Utils::Shader::TESS_CTRL:
   23932 				source = tcs;
   23933 				break;
   23934 			case Utils::Shader::VERTEX:
   23935 				source = vs;
   23936 				break;
   23937 			default:
   23938 				source = "";
   23939 			}
   23940 			break;
   23941 		case Utils::Shader::VERTEX:
   23942 			switch (stage)
   23943 			{
   23944 			case Utils::Shader::FRAGMENT:
   23945 				source = fs;
   23946 				break;
   23947 			default:
   23948 				source = "";
   23949 			}
   23950 			break;
   23951 		default:
   23952 			TCU_FAIL("Invalid enum");
   23953 			break;
   23954 		}
   23955 	}
   23956 
   23957 	return source;
   23958 }
   23959 
   23960 /** Get description of test case
   23961  *
   23962  * @param test_case_index Index of test case
   23963  *
   23964  * @return Test case description
   23965  **/
   23966 std::string XFBExceedOffsetLimitTest::getTestCaseName(GLuint test_case_index)
   23967 {
   23968 	std::stringstream stream;
   23969 	testCase&		  test_case = m_test_cases[test_case_index];
   23970 
   23971 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage) << ", case: ";
   23972 
   23973 	switch (test_case.m_case)
   23974 	{
   23975 	case BLOCK:
   23976 		stream << "BLOCK";
   23977 		break;
   23978 	case GLOBAL:
   23979 		stream << "GLOBAL";
   23980 		break;
   23981 	case VECTOR:
   23982 		stream << "VECTOR";
   23983 		break;
   23984 	default:
   23985 		TCU_FAIL("Invalid enum");
   23986 	}
   23987 
   23988 	return stream.str();
   23989 }
   23990 
   23991 /** Get number of test cases
   23992  *
   23993  * @return Number of test cases
   23994  **/
   23995 GLuint XFBExceedOffsetLimitTest::getTestCaseNumber()
   23996 {
   23997 	return static_cast<GLuint>(m_test_cases.size());
   23998 }
   23999 
   24000 /** Selects if "compute" stage is relevant for test
   24001  *
   24002  * @param ignored
   24003  *
   24004  * @return false
   24005  **/
   24006 bool XFBExceedOffsetLimitTest::isComputeRelevant(GLuint /* test_case_index */)
   24007 {
   24008 	return false;
   24009 }
   24010 
   24011 /** Prepare all test cases
   24012  *
   24013  **/
   24014 void XFBExceedOffsetLimitTest::testInit()
   24015 {
   24016 	for (GLuint c = 0; c < CASE_MAX; ++c)
   24017 	{
   24018 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   24019 		{
   24020 			if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::TESS_CTRL == stage) ||
   24021 				(Utils::Shader::FRAGMENT == stage))
   24022 			{
   24023 				continue;
   24024 			}
   24025 
   24026 			testCase test_case = { (CASES)c, (Utils::Shader::STAGES)stage };
   24027 
   24028 			m_test_cases.push_back(test_case);
   24029 		}
   24030 	}
   24031 }
   24032 
   24033 /** Constructor
   24034  *
   24035  * @param context Test context
   24036  **/
   24037 XFBGlobalBufferTest::XFBGlobalBufferTest(deqp::Context& context)
   24038 	: BufferTestBase(context, "xfb_global_buffer", "Test verifies that global xfb_buffer qualifier is respected")
   24039 {
   24040 	/* Nothing to be done here */
   24041 }
   24042 
   24043 /** Get descriptors of buffers necessary for test
   24044  *
   24045  * @param test_case_index Index of test case
   24046  * @param out_descriptors Descriptors of buffers used by test
   24047  **/
   24048 void XFBGlobalBufferTest::getBufferDescriptors(glw::GLuint test_case_index, bufferDescriptor::Vector& out_descriptors)
   24049 {
   24050 	// the function "getType(test_case_index)" can't return correct data type, so change code as following:
   24051 	const Utils::Type& type = m_test_cases[test_case_index].m_type;
   24052 
   24053 	/* Test needs single uniform and two xfbs */
   24054 	out_descriptors.resize(3);
   24055 
   24056 	/* Get references */
   24057 	bufferDescriptor& uniform = out_descriptors[0];
   24058 	bufferDescriptor& xfb_1   = out_descriptors[1];
   24059 	bufferDescriptor& xfb_3   = out_descriptors[2];
   24060 
   24061 	/* Index */
   24062 	uniform.m_index = 0;
   24063 	xfb_1.m_index   = 1;
   24064 	xfb_3.m_index   = 3;
   24065 
   24066 	/* Target */
   24067 	uniform.m_target = Utils::Buffer::Uniform;
   24068 	xfb_1.m_target   = Utils::Buffer::Transform_feedback;
   24069 	xfb_3.m_target   = Utils::Buffer::Transform_feedback;
   24070 
   24071 	/* Data */
   24072 	const GLuint				gen_start   = Utils::s_rand;
   24073 	const std::vector<GLubyte>& chichi_data = type.GenerateData();
   24074 	const std::vector<GLubyte>& bulma_data  = type.GenerateData();
   24075 	const std::vector<GLubyte>& trunks_data = type.GenerateData();
   24076 	const std::vector<GLubyte>& bra_data	= type.GenerateData();
   24077 	const std::vector<GLubyte>& gohan_data  = type.GenerateData();
   24078 	const std::vector<GLubyte>& goten_data  = type.GenerateData();
   24079 
   24080 	Utils::s_rand								= gen_start;
   24081 	const std::vector<GLubyte>& chichi_data_pck = type.GenerateDataPacked();
   24082 	const std::vector<GLubyte>& bulma_data_pck  = type.GenerateDataPacked();
   24083 	const std::vector<GLubyte>& trunks_data_pck = type.GenerateDataPacked();
   24084 	const std::vector<GLubyte>& bra_data_pck	= type.GenerateDataPacked();
   24085 	const std::vector<GLubyte>& gohan_data_pck  = type.GenerateDataPacked();
   24086 	const std::vector<GLubyte>& goten_data_pck  = type.GenerateDataPacked();
   24087 
   24088 	const GLuint type_size	 = static_cast<GLuint>(chichi_data.size());
   24089 	const GLuint type_size_pck = static_cast<GLuint>(chichi_data_pck.size());
   24090 
   24091 	/* Uniform data */
   24092 	uniform.m_initial_data.resize(6 * type_size);
   24093 	memcpy(&uniform.m_initial_data[0] + 0, &chichi_data[0], type_size);
   24094 	memcpy(&uniform.m_initial_data[0] + type_size, &bulma_data[0], type_size);
   24095 	memcpy(&uniform.m_initial_data[0] + 2 * type_size, &trunks_data[0], type_size);
   24096 	memcpy(&uniform.m_initial_data[0] + 3 * type_size, &bra_data[0], type_size);
   24097 	memcpy(&uniform.m_initial_data[0] + 4 * type_size, &gohan_data[0], type_size);
   24098 	memcpy(&uniform.m_initial_data[0] + 5 * type_size, &goten_data[0], type_size);
   24099 
   24100 	/* XFB data */
   24101 	xfb_1.m_initial_data.resize(3 * type_size_pck);
   24102 	xfb_1.m_expected_data.resize(3 * type_size_pck);
   24103 	xfb_3.m_initial_data.resize(3 * type_size_pck);
   24104 	xfb_3.m_expected_data.resize(3 * type_size_pck);
   24105 
   24106 	for (GLuint i = 0; i < 3 * type_size_pck; ++i)
   24107 	{
   24108 		xfb_1.m_initial_data[i]  = (glw::GLubyte)i;
   24109 		xfb_1.m_expected_data[i] = (glw::GLubyte)i;
   24110 		xfb_3.m_initial_data[i]  = (glw::GLubyte)i;
   24111 		xfb_3.m_expected_data[i] = (glw::GLubyte)i;
   24112 	}
   24113 
   24114 	memcpy(&xfb_3.m_expected_data[0] + 2 * type_size_pck, &chichi_data_pck[0], type_size_pck);
   24115 	memcpy(&xfb_1.m_expected_data[0] + 0 * type_size_pck, &bulma_data_pck[0], type_size_pck);
   24116 	memcpy(&xfb_1.m_expected_data[0] + 1 * type_size_pck, &trunks_data_pck[0], type_size_pck);
   24117 	memcpy(&xfb_1.m_expected_data[0] + 2 * type_size_pck, &bra_data_pck[0], type_size_pck);
   24118 	memcpy(&xfb_3.m_expected_data[0] + 0 * type_size_pck, &gohan_data_pck[0], type_size_pck);
   24119 	memcpy(&xfb_3.m_expected_data[0] + 1 * type_size_pck, &goten_data_pck[0], type_size_pck);
   24120 }
   24121 
   24122 /** Source for given test case and stage
   24123  *
   24124  * @param test_case_index Index of test case
   24125  * @param stage           Shader stage
   24126  *
   24127  * @return Shader source
   24128  **/
   24129 std::string XFBGlobalBufferTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   24130 {
   24131 	static const GLchar* fs =
   24132 		"#version 430 core\n"
   24133 		"#extension GL_ARB_enhanced_layouts : require\n"
   24134 		"\n"
   24135 		"flat in TYPE chichi;\n"
   24136 		"flat in TYPE bulma;\n"
   24137 		"in Vegeta {\n"
   24138 		"    flat TYPE trunk;\n"
   24139 		"    flat TYPE bra;\n"
   24140 		"} vegeta;\n"
   24141 		"in Goku {\n"
   24142 		"    flat TYPE gohan;\n"
   24143 		"    flat TYPE goten;\n"
   24144 		"} goku;\n"
   24145 		"\n"
   24146 		"out vec4 fs_out;\n"
   24147 		"\n"
   24148 		"void main()\n"
   24149 		"{\n"
   24150 		"    fs_out = vec4(1);\n"
   24151 		"    if (TYPE(1) != chichi + bulma + vegeta.trunk + vegeta.bra + goku.gohan + goku.goten)\n"
   24152 		"    {\n"
   24153 		"        fs_out = vec4(0);\n"
   24154 		"    }\n"
   24155 		"}\n"
   24156 		"\n";
   24157 
   24158 	static const GLchar* gs = "#version 430 core\n"
   24159 							  "#extension GL_ARB_enhanced_layouts : require\n"
   24160 							  "\n"
   24161 							  "layout(points)                   in;\n"
   24162 							  "layout(points, max_vertices = 1) out;\n"
   24163 							  "\n"
   24164 							  "INTERFACE"
   24165 							  "\n"
   24166 							  "void main()\n"
   24167 							  "{\n"
   24168 							  "ASSIGNMENTS"
   24169 							  "    EmitVertex();\n"
   24170 							  "}\n"
   24171 							  "\n";
   24172 
   24173 	static const GLchar* tcs = "#version 430 core\n"
   24174 							   "#extension GL_ARB_enhanced_layouts : require\n"
   24175 							   "\n"
   24176 							   "layout(vertices = 1) out;\n"
   24177 							   "\n"
   24178 							   "\n"
   24179 							   "void main()\n"
   24180 							   "{\n"
   24181 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   24182 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   24183 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   24184 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   24185 							   "    gl_TessLevelInner[0] = 1.0;\n"
   24186 							   "    gl_TessLevelInner[1] = 1.0;\n"
   24187 							   "}\n"
   24188 							   "\n";
   24189 
   24190 	static const GLchar* tes = "#version 430 core\n"
   24191 							   "#extension GL_ARB_enhanced_layouts : require\n"
   24192 							   "\n"
   24193 							   "layout(isolines, point_mode) in;\n"
   24194 							   "\n"
   24195 							   "INTERFACE"
   24196 							   "\n"
   24197 							   "void main()\n"
   24198 							   "{\n"
   24199 							   "ASSIGNMENTS"
   24200 							   "}\n"
   24201 							   "\n";
   24202 
   24203 	static const GLchar* vs = "#version 430 core\n"
   24204 							  "#extension GL_ARB_enhanced_layouts : require\n"
   24205 							  "\n"
   24206 							  "void main()\n"
   24207 							  "{\n"
   24208 							  "}\n"
   24209 							  "\n";
   24210 
   24211 	static const GLchar* vs_tested = "#version 430 core\n"
   24212 									 "#extension GL_ARB_enhanced_layouts : require\n"
   24213 									 "\n"
   24214 									 "INTERFACE"
   24215 									 "\n"
   24216 									 "void main()\n"
   24217 									 "{\n"
   24218 									 "ASSIGNMENTS"
   24219 									 "}\n"
   24220 									 "\n";
   24221 
   24222 	std::string		 source;
   24223 	const _testCase& test_case = m_test_cases[test_case_index];
   24224 	const GLchar*	type_name = test_case.m_type.GetGLSLTypeName();
   24225 
   24226 	if (test_case.m_stage == stage)
   24227 	{
   24228 		std::string assignments = "    chichi       = uni_chichi;\n"
   24229 								  "    bulma        = uni_bulma;\n"
   24230 								  "    vegeta.trunk = uni_trunk;\n"
   24231 								  "    vegeta.bra   = uni_bra;\n"
   24232 								  "    goku.gohan   = uni_gohan;\n"
   24233 								  "    goku.goten   = uni_goten;\n";
   24234 
   24235 		std::string interface = "layout (xfb_buffer = 3) out;\n"
   24236 								"\n"
   24237 								"const uint type_size = SIZE;\n"
   24238 								"\n"
   24239 								"layout (                xfb_offset = 2 * type_size) flat out TYPE chichi;\n"
   24240 								"layout (xfb_buffer = 1, xfb_offset = 0)             flat out TYPE bulma;\n"
   24241 								"layout (xfb_buffer = 1, xfb_offset = 1 * type_size) out Vegeta {\n"
   24242 								"    flat TYPE trunk;\n"
   24243 								"    flat TYPE bra;\n"
   24244 								"} vegeta;\n"
   24245 								"layout (                xfb_offset = 0)             out Goku {\n"
   24246 								"    flat TYPE gohan;\n"
   24247 								"    flat TYPE goten;\n"
   24248 								"} goku;\n"
   24249 								"\n"
   24250 								// Uniform block must be declared with std140, otherwise each block member is not packed
   24251 								"layout(binding = 0, std140) uniform block {\n"
   24252 								"    TYPE uni_chichi;\n"
   24253 								"    TYPE uni_bulma;\n"
   24254 								"    TYPE uni_trunk;\n"
   24255 								"    TYPE uni_bra;\n"
   24256 								"    TYPE uni_gohan;\n"
   24257 								"    TYPE uni_goten;\n"
   24258 								"};\n";
   24259 
   24260 		/* Prepare interface string */
   24261 		{
   24262 			GLchar		 buffer[16];
   24263 			size_t		 position  = 0;
   24264 			const GLuint type_size = test_case.m_type.GetSize();
   24265 
   24266 			sprintf(buffer, "%d", type_size);
   24267 
   24268 			Utils::replaceToken("SIZE", position, buffer, interface);
   24269 			Utils::replaceAllTokens("TYPE", type_name, interface);
   24270 		}
   24271 
   24272 		switch (stage)
   24273 		{
   24274 		case Utils::Shader::GEOMETRY:
   24275 			source = gs;
   24276 			break;
   24277 		case Utils::Shader::TESS_EVAL:
   24278 			source = tes;
   24279 			break;
   24280 		case Utils::Shader::VERTEX:
   24281 			source = vs_tested;
   24282 			break;
   24283 		default:
   24284 			TCU_FAIL("Invalid enum");
   24285 		}
   24286 
   24287 		/* Replace tokens */
   24288 		{
   24289 			size_t position = 0;
   24290 
   24291 			Utils::replaceToken("INTERFACE", position, interface.c_str(), source);
   24292 			Utils::replaceToken("ASSIGNMENTS", position, assignments.c_str(), source);
   24293 		}
   24294 	}
   24295 	else
   24296 	{
   24297 		switch (test_case.m_stage)
   24298 		{
   24299 		case Utils::Shader::GEOMETRY:
   24300 			switch (stage)
   24301 			{
   24302 			case Utils::Shader::FRAGMENT:
   24303 				source = fs;
   24304 				Utils::replaceAllTokens("TYPE", type_name, source);
   24305 				break;
   24306 			case Utils::Shader::VERTEX:
   24307 				source = vs;
   24308 				break;
   24309 			default:
   24310 				source = "";
   24311 			}
   24312 			break;
   24313 		case Utils::Shader::TESS_EVAL:
   24314 			switch (stage)
   24315 			{
   24316 			case Utils::Shader::FRAGMENT:
   24317 				source = fs;
   24318 				Utils::replaceAllTokens("TYPE", type_name, source);
   24319 				break;
   24320 			case Utils::Shader::TESS_CTRL:
   24321 				source = tcs;
   24322 				break;
   24323 			case Utils::Shader::VERTEX:
   24324 				source = vs;
   24325 				break;
   24326 			default:
   24327 				source = "";
   24328 			}
   24329 			break;
   24330 		case Utils::Shader::VERTEX:
   24331 			switch (stage)
   24332 			{
   24333 			case Utils::Shader::FRAGMENT:
   24334 				source = fs;
   24335 				Utils::replaceAllTokens("TYPE", type_name, source);
   24336 				break;
   24337 			default:
   24338 				source = "";
   24339 			}
   24340 			break;
   24341 		default:
   24342 			TCU_FAIL("Invalid enum");
   24343 			break;
   24344 		}
   24345 	}
   24346 
   24347 	return source;
   24348 }
   24349 
   24350 /** Get name of test case
   24351  *
   24352  * @param test_case_index Index of test case
   24353  *
   24354  * @return Name of case
   24355  **/
   24356 std::string XFBGlobalBufferTest::getTestCaseName(GLuint test_case_index)
   24357 {
   24358 	std::string		 name;
   24359 	const _testCase& test_case = m_test_cases[test_case_index];
   24360 
   24361 	name = "Tested stage: ";
   24362 	name.append(Utils::Shader::GetStageName(test_case.m_stage));
   24363 	name.append(". Tested type: ");
   24364 	name.append(test_case.m_type.GetGLSLTypeName());
   24365 
   24366 	return name;
   24367 }
   24368 
   24369 /** Get number of cases
   24370  *
   24371  * @return Number of test cases
   24372  **/
   24373 GLuint XFBGlobalBufferTest::getTestCaseNumber()
   24374 {
   24375 	return static_cast<GLuint>(m_test_cases.size());
   24376 }
   24377 
   24378 /** Prepare set of test cases
   24379  *
   24380  **/
   24381 void XFBGlobalBufferTest::testInit()
   24382 {
   24383 	GLuint n_types = getTypesNumber();
   24384 
   24385 	for (GLuint i = 0; i < n_types; ++i)
   24386 	{
   24387 		const Utils::Type& type = getType(i);
   24388 		/*
   24389 		 When the tfx varying is the following type, the number of output exceeds the gl_MaxVaryingComponents, which will
   24390 		 cause a link time error.
   24391 		 */
   24392 		if (strcmp(type.GetGLSLTypeName(), "dmat3") == 0 || strcmp(type.GetGLSLTypeName(), "dmat4") == 0 ||
   24393 			strcmp(type.GetGLSLTypeName(), "dmat3x4") == 0 || strcmp(type.GetGLSLTypeName(), "dmat4x3") == 0)
   24394 		{
   24395 			continue;
   24396 		}
   24397 		const _testCase test_cases[] = { { Utils::Shader::VERTEX, type },
   24398 										 { Utils::Shader::GEOMETRY, type },
   24399 										 { Utils::Shader::TESS_EVAL, type } };
   24400 
   24401 		m_test_cases.push_back(test_cases[0]);
   24402 		m_test_cases.push_back(test_cases[1]);
   24403 		m_test_cases.push_back(test_cases[2]);
   24404 	}
   24405 }
   24406 
   24407 /** Constructor
   24408  *
   24409  * @param context Test context
   24410  **/
   24411 XFBStrideTest::XFBStrideTest(deqp::Context& context)
   24412 	: BufferTestBase(context, "xfb_stride", "Test verifies that correct stride is used for all types")
   24413 {
   24414 	/* Nothing to be done here */
   24415 }
   24416 
   24417 /** Execute drawArrays for single vertex
   24418  *
   24419  * @param test_case_index
   24420  *
   24421  * @return true
   24422  **/
   24423 bool XFBStrideTest::executeDrawCall(bool /* tesEnabled */, GLuint test_case_index)
   24424 {
   24425 	const Functions& gl				= m_context.getRenderContext().getFunctions();
   24426 	GLenum			 primitive_type = GL_PATCHES;
   24427 	const testCase&  test_case		= m_test_cases[test_case_index];
   24428 
   24429 	if (Utils::Shader::VERTEX == test_case.m_stage)
   24430 	{
   24431 		primitive_type = GL_POINTS;
   24432 	}
   24433 
   24434 	gl.disable(GL_RASTERIZER_DISCARD);
   24435 	GLU_EXPECT_NO_ERROR(gl.getError(), "Disable");
   24436 
   24437 	gl.beginTransformFeedback(GL_POINTS);
   24438 	GLU_EXPECT_NO_ERROR(gl.getError(), "BeginTransformFeedback");
   24439 
   24440 	gl.drawArrays(primitive_type, 0 /* first */, 2 /* count */);
   24441 	GLU_EXPECT_NO_ERROR(gl.getError(), "DrawArrays");
   24442 
   24443 	gl.endTransformFeedback();
   24444 	GLU_EXPECT_NO_ERROR(gl.getError(), "EndTransformFeedback");
   24445 
   24446 	return true;
   24447 }
   24448 
   24449 /** Get descriptors of buffers necessary for test
   24450  *
   24451  * @param test_case_index Index of test case
   24452  * @param out_descriptors Descriptors of buffers used by test
   24453  **/
   24454 void XFBStrideTest::getBufferDescriptors(GLuint test_case_index, bufferDescriptor::Vector& out_descriptors)
   24455 {
   24456 	const testCase&	test_case = m_test_cases[test_case_index];
   24457 	const Utils::Type& type		 = test_case.m_type;
   24458 
   24459 	/* Test needs single uniform and xfb */
   24460 	out_descriptors.resize(2);
   24461 
   24462 	/* Get references */
   24463 	bufferDescriptor& uniform = out_descriptors[0];
   24464 	bufferDescriptor& xfb	 = out_descriptors[1];
   24465 
   24466 	/* Index */
   24467 	uniform.m_index = 0;
   24468 	xfb.m_index		= 0;
   24469 
   24470 	/* Target */
   24471 	uniform.m_target = Utils::Buffer::Uniform;
   24472 	xfb.m_target	 = Utils::Buffer::Transform_feedback;
   24473 
   24474 	/* Data */
   24475 	const GLuint				rand_start   = Utils::s_rand;
   24476 	const std::vector<GLubyte>& uniform_data = type.GenerateData();
   24477 
   24478 	Utils::s_rand						 = rand_start;
   24479 	const std::vector<GLubyte>& xfb_data = type.GenerateDataPacked();
   24480 
   24481 	const GLuint uni_type_size = static_cast<GLuint>(uniform_data.size());
   24482 	const GLuint xfb_type_size = static_cast<GLuint>(xfb_data.size());
   24483 	/*
   24484 	 Note: If xfb varying output from vertex shader, the variable "goku" will only output once to transform feedback buffer,
   24485 	 if xfb varying output from TES or GS, because the input primitive type in TES is defined as "layout(isolines, point_mode) in;",
   24486 	 the primitive type is line which make the variable "goku" will output twice to transform feedback buffer, so for vertex shader
   24487 	 only one valid data should be initialized in xfb.m_expected_data
   24488 	 */
   24489 	const GLuint xfb_data_size = (test_case.m_stage == Utils::Shader::VERTEX) ? xfb_type_size : xfb_type_size * 2;
   24490 	/* Uniform data */
   24491 	uniform.m_initial_data.resize(uni_type_size);
   24492 	memcpy(&uniform.m_initial_data[0] + 0 * uni_type_size, &uniform_data[0], uni_type_size);
   24493 
   24494 	/* XFB data */
   24495 	xfb.m_initial_data.resize(xfb_data_size);
   24496 	xfb.m_expected_data.resize(xfb_data_size);
   24497 
   24498 	for (GLuint i = 0; i < xfb_data_size; ++i)
   24499 	{
   24500 		xfb.m_initial_data[i]  = (glw::GLubyte)i;
   24501 		xfb.m_expected_data[i] = (glw::GLubyte)i;
   24502 	}
   24503 
   24504 	if (test_case.m_stage == Utils::Shader::VERTEX)
   24505 	{
   24506 		memcpy(&xfb.m_expected_data[0] + 0 * xfb_type_size, &xfb_data[0], xfb_type_size);
   24507 	}
   24508 	else
   24509 	{
   24510 		memcpy(&xfb.m_expected_data[0] + 0 * xfb_type_size, &xfb_data[0], xfb_type_size);
   24511 		memcpy(&xfb.m_expected_data[0] + 1 * xfb_type_size, &xfb_data[0], xfb_type_size);
   24512 	}
   24513 }
   24514 
   24515 /** Get body of main function for given shader stage
   24516  *
   24517  * @param test_case_index  Index of test case
   24518  * @param stage            Shader stage
   24519  * @param out_assignments  Set to empty
   24520  * @param out_calculations Set to empty
   24521  **/
   24522 void XFBStrideTest::getShaderBody(GLuint test_case_index, Utils::Shader::STAGES stage, std::string& out_assignments,
   24523 								  std::string& out_calculations)
   24524 {
   24525 	const testCase& test_case = m_test_cases[test_case_index];
   24526 
   24527 	out_calculations = "";
   24528 
   24529 	static const GLchar* vs_tes_gs = "    goku = uni_goku;\n";
   24530 	static const GLchar* fs		   = "    fs_out = vec4(1, 0.25, 0.5, 0.75);\n"
   24531 							  "    if (TYPE(0) == goku)\n"
   24532 							  "    {\n"
   24533 							  "         fs_out = vec4(1, 0.75, 0.5, 0.5);\n"
   24534 							  "    }\n";
   24535 
   24536 	const GLchar* assignments = "";
   24537 
   24538 	if (test_case.m_stage == stage)
   24539 	{
   24540 		switch (stage)
   24541 		{
   24542 		case Utils::Shader::GEOMETRY:
   24543 			assignments = vs_tes_gs;
   24544 			break;
   24545 		case Utils::Shader::TESS_EVAL:
   24546 			assignments = vs_tes_gs;
   24547 			break;
   24548 		case Utils::Shader::VERTEX:
   24549 			assignments = vs_tes_gs;
   24550 			break;
   24551 		default:
   24552 			TCU_FAIL("Invalid enum");
   24553 		}
   24554 	}
   24555 	else
   24556 	{
   24557 		switch (stage)
   24558 		{
   24559 		case Utils::Shader::FRAGMENT:
   24560 			assignments = fs;
   24561 			break;
   24562 		case Utils::Shader::GEOMETRY:
   24563 		case Utils::Shader::TESS_CTRL:
   24564 		case Utils::Shader::TESS_EVAL:
   24565 		case Utils::Shader::VERTEX:
   24566 			break;
   24567 		default:
   24568 			TCU_FAIL("Invalid enum");
   24569 		}
   24570 	}
   24571 
   24572 	out_assignments = assignments;
   24573 
   24574 	if (Utils::Shader::FRAGMENT == stage)
   24575 	{
   24576 		Utils::replaceAllTokens("TYPE", test_case.m_type.GetGLSLTypeName(), out_assignments);
   24577 	}
   24578 }
   24579 
   24580 /** Get interface of shader
   24581  *
   24582  * @param test_case_index  Index of test case
   24583  * @param stage            Shader stage
   24584  * @param out_interface    Set to ""
   24585  **/
   24586 void XFBStrideTest::getShaderInterface(GLuint test_case_index, Utils::Shader::STAGES stage, std::string& out_interface)
   24587 {
   24588 	static const GLchar* vs_tes_gs = "layout (xfb_offset = 0) FLAT out TYPE goku;\n"
   24589 									 "\n"
   24590 									 "layout(std140, binding = 0) uniform Goku {\n"
   24591 									 "    TYPE uni_goku;\n"
   24592 									 "};\n";
   24593 	static const GLchar* fs = "FLAT in TYPE goku;\n"
   24594 							  "\n"
   24595 							  "out vec4 fs_out;\n";
   24596 
   24597 	const testCase& test_case = m_test_cases[test_case_index];
   24598 	const GLchar*   interface = "";
   24599 	const GLchar*   flat	  = "";
   24600 
   24601 	if (test_case.m_stage == stage)
   24602 	{
   24603 		switch (stage)
   24604 		{
   24605 		case Utils::Shader::GEOMETRY:
   24606 			interface = vs_tes_gs;
   24607 			break;
   24608 		case Utils::Shader::TESS_EVAL:
   24609 			interface = vs_tes_gs;
   24610 			break;
   24611 		case Utils::Shader::VERTEX:
   24612 			interface = vs_tes_gs;
   24613 			break;
   24614 		default:
   24615 			TCU_FAIL("Invalid enum");
   24616 		}
   24617 	}
   24618 	else
   24619 	{
   24620 		switch (stage)
   24621 		{
   24622 		case Utils::Shader::FRAGMENT:
   24623 			interface = fs;
   24624 			break;
   24625 		case Utils::Shader::GEOMETRY:
   24626 		case Utils::Shader::TESS_CTRL:
   24627 		case Utils::Shader::TESS_EVAL:
   24628 		case Utils::Shader::VERTEX:
   24629 			break;
   24630 		default:
   24631 			TCU_FAIL("Invalid enum");
   24632 		}
   24633 	}
   24634 
   24635 	out_interface = interface;
   24636 
   24637 	if (Utils::Type::Float != test_case.m_type.m_basic_type)
   24638 	{
   24639 		flat = "flat";
   24640 	}
   24641 
   24642 	Utils::replaceAllTokens("FLAT", flat, out_interface);
   24643 	Utils::replaceAllTokens("TYPE", test_case.m_type.GetGLSLTypeName(), out_interface);
   24644 }
   24645 
   24646 /** Get source code of shader
   24647  *
   24648  * @param test_case_index Index of test case
   24649  * @param stage           Shader stage
   24650  *
   24651  * @return Source
   24652  **/
   24653 std::string XFBStrideTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   24654 {
   24655 	std::string		source;
   24656 	const testCase& test_case = m_test_cases[test_case_index];
   24657 
   24658 	switch (test_case.m_stage)
   24659 	{
   24660 	case Utils::Shader::VERTEX:
   24661 		switch (stage)
   24662 		{
   24663 		case Utils::Shader::FRAGMENT:
   24664 		case Utils::Shader::VERTEX:
   24665 			source = BufferTestBase::getShaderSource(test_case_index, stage);
   24666 			break;
   24667 		default:
   24668 			break;
   24669 		}
   24670 		break;
   24671 
   24672 	case Utils::Shader::TESS_EVAL:
   24673 		switch (stage)
   24674 		{
   24675 		case Utils::Shader::FRAGMENT:
   24676 		case Utils::Shader::TESS_CTRL:
   24677 		case Utils::Shader::TESS_EVAL:
   24678 		case Utils::Shader::VERTEX:
   24679 			source = BufferTestBase::getShaderSource(test_case_index, stage);
   24680 			break;
   24681 		default:
   24682 			break;
   24683 		}
   24684 		break;
   24685 
   24686 	case Utils::Shader::GEOMETRY:
   24687 		source = BufferTestBase::getShaderSource(test_case_index, stage);
   24688 		break;
   24689 
   24690 	default:
   24691 		TCU_FAIL("Invalid enum");
   24692 		break;
   24693 	}
   24694 
   24695 	/* */
   24696 	return source;
   24697 }
   24698 
   24699 /** Get name of test case
   24700  *
   24701  * @param test_case_index Index of test case
   24702  *
   24703  * @return Name of tested stage
   24704  **/
   24705 std::string XFBStrideTest::getTestCaseName(glw::GLuint test_case_index)
   24706 {
   24707 	std::stringstream stream;
   24708 	const testCase&   test_case = m_test_cases[test_case_index];
   24709 
   24710 	stream << "Type: " << test_case.m_type.GetGLSLTypeName()
   24711 		   << ", stage: " << Utils::Shader::GetStageName(test_case.m_stage);
   24712 
   24713 	return stream.str();
   24714 }
   24715 
   24716 /** Returns number of test cases
   24717  *
   24718  * @return TEST_MAX
   24719  **/
   24720 glw::GLuint XFBStrideTest::getTestCaseNumber()
   24721 {
   24722 	return static_cast<GLuint>(m_test_cases.size());
   24723 }
   24724 
   24725 /** Prepare all test cases
   24726  *
   24727  **/
   24728 void XFBStrideTest::testInit()
   24729 {
   24730 	const GLuint n_types = getTypesNumber();
   24731 
   24732 	for (GLuint i = 0; i < n_types; ++i)
   24733 	{
   24734 		const Utils::Type& type = getType(i);
   24735 
   24736 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   24737 		{
   24738 			if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::FRAGMENT == stage) ||
   24739 				(Utils::Shader::TESS_CTRL == stage))
   24740 			{
   24741 				continue;
   24742 			}
   24743 
   24744 			testCase test_case = { (Utils::Shader::STAGES)stage, type };
   24745 
   24746 			m_test_cases.push_back(test_case);
   24747 		}
   24748 	}
   24749 }
   24750 
   24751 /** Constructor
   24752  *
   24753  * @param context Test framework context
   24754  **/
   24755 XFBBlockMemberBufferTest::XFBBlockMemberBufferTest(deqp::Context& context)
   24756 	: NegativeTestBase(
   24757 		  context, "xfb_block_member_buffer",
   24758 		  "Test verifies that compiler reports error when block member has different xfb_buffer qualifier than buffer")
   24759 {
   24760 }
   24761 
   24762 /** Source for given test case and stage
   24763  *
   24764  * @param test_case_index Index of test case
   24765  * @param stage           Shader stage
   24766  *
   24767  * @return Shader source
   24768  **/
   24769 std::string XFBBlockMemberBufferTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   24770 {
   24771 	static const GLchar* var_definition = "layout (xfb_offset = 0) out Goku {\n"
   24772 										  "                            vec4 gohan;\n"
   24773 										  "    layout (xfb_buffer = 1) vec4 goten;\n"
   24774 										  "} gokuARRAY;\n";
   24775 	static const GLchar* var_use = "    gokuINDEX.gohan = result / 2;\n"
   24776 								   "    gokuINDEX.goten = result / 4;\n";
   24777 	static const GLchar* fs = "#version 430 core\n"
   24778 							  "#extension GL_ARB_enhanced_layouts : require\n"
   24779 							  "\n"
   24780 							  "in  vec4 gs_fs;\n"
   24781 							  "out vec4 fs_out;\n"
   24782 							  "\n"
   24783 							  "void main()\n"
   24784 							  "{\n"
   24785 							  "    fs_out = gs_fs;\n"
   24786 							  "}\n"
   24787 							  "\n";
   24788 	static const GLchar* gs_tested = "#version 430 core\n"
   24789 									 "#extension GL_ARB_enhanced_layouts : require\n"
   24790 									 "\n"
   24791 									 "layout(points)                           in;\n"
   24792 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   24793 									 "\n"
   24794 									 "VAR_DEFINITION"
   24795 									 "\n"
   24796 									 "in  vec4 tes_gs[];\n"
   24797 									 "out vec4 gs_fs;\n"
   24798 									 "\n"
   24799 									 "void main()\n"
   24800 									 "{\n"
   24801 									 "    vec4 result = tes_gs[0];\n"
   24802 									 "\n"
   24803 									 "VARIABLE_USE"
   24804 									 "\n"
   24805 									 "    gs_fs = result;\n"
   24806 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   24807 									 "    EmitVertex();\n"
   24808 									 "    gs_fs = result;\n"
   24809 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   24810 									 "    EmitVertex();\n"
   24811 									 "    gs_fs = result;\n"
   24812 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   24813 									 "    EmitVertex();\n"
   24814 									 "    gs_fs = result;\n"
   24815 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   24816 									 "    EmitVertex();\n"
   24817 									 "}\n"
   24818 									 "\n";
   24819 	static const GLchar* tcs = "#version 430 core\n"
   24820 							   "#extension GL_ARB_enhanced_layouts : require\n"
   24821 							   "\n"
   24822 							   "layout(vertices = 1) out;\n"
   24823 							   "\n"
   24824 							   "in  vec4 vs_tcs[];\n"
   24825 							   "out vec4 tcs_tes[];\n"
   24826 							   "\n"
   24827 							   "void main()\n"
   24828 							   "{\n"
   24829 							   "\n"
   24830 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   24831 							   "\n"
   24832 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   24833 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   24834 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   24835 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   24836 							   "    gl_TessLevelInner[0] = 1.0;\n"
   24837 							   "    gl_TessLevelInner[1] = 1.0;\n"
   24838 							   "}\n"
   24839 							   "\n";
   24840 	static const GLchar* tcs_tested = "#version 430 core\n"
   24841 									  "#extension GL_ARB_enhanced_layouts : require\n"
   24842 									  "\n"
   24843 									  "layout(vertices = 1) out;\n"
   24844 									  "\n"
   24845 									  "VAR_DEFINITION"
   24846 									  "\n"
   24847 									  "in  vec4 vs_tcs[];\n"
   24848 									  "out vec4 tcs_tes[];\n"
   24849 									  "\n"
   24850 									  "void main()\n"
   24851 									  "{\n"
   24852 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   24853 									  "\n"
   24854 									  "VARIABLE_USE"
   24855 									  "\n"
   24856 									  "    tcs_tes[gl_InvocationID] = result;\n"
   24857 									  "\n"
   24858 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   24859 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   24860 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   24861 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   24862 									  "    gl_TessLevelInner[0] = 1.0;\n"
   24863 									  "    gl_TessLevelInner[1] = 1.0;\n"
   24864 									  "}\n"
   24865 									  "\n";
   24866 	static const GLchar* tes_tested = "#version 430 core\n"
   24867 									  "#extension GL_ARB_enhanced_layouts : require\n"
   24868 									  "\n"
   24869 									  "layout(isolines, point_mode) in;\n"
   24870 									  "\n"
   24871 									  "VAR_DEFINITION"
   24872 									  "\n"
   24873 									  "in  vec4 tcs_tes[];\n"
   24874 									  "out vec4 tes_gs;\n"
   24875 									  "\n"
   24876 									  "void main()\n"
   24877 									  "{\n"
   24878 									  "    vec4 result = tcs_tes[0];\n"
   24879 									  "\n"
   24880 									  "VARIABLE_USE"
   24881 									  "\n"
   24882 									  "    tes_gs += result;\n"
   24883 									  "}\n"
   24884 									  "\n";
   24885 	static const GLchar* vs = "#version 430 core\n"
   24886 							  "#extension GL_ARB_enhanced_layouts : require\n"
   24887 							  "\n"
   24888 							  "in  vec4 in_vs;\n"
   24889 							  "out vec4 vs_tcs;\n"
   24890 							  "\n"
   24891 							  "void main()\n"
   24892 							  "{\n"
   24893 							  "    vs_tcs = in_vs;\n"
   24894 							  "}\n"
   24895 							  "\n";
   24896 	static const GLchar* vs_tested = "#version 430 core\n"
   24897 									 "#extension GL_ARB_enhanced_layouts : require\n"
   24898 									 "\n"
   24899 									 "VAR_DEFINITION"
   24900 									 "\n"
   24901 									 "in  vec4 in_vs;\n"
   24902 									 "out vec4 vs_tcs;\n"
   24903 									 "\n"
   24904 									 "void main()\n"
   24905 									 "{\n"
   24906 									 "    vec4 result = in_vs;\n"
   24907 									 "\n"
   24908 									 "VARIABLE_USE"
   24909 									 "\n"
   24910 									 "    vs_tcs = result;\n"
   24911 									 "}\n"
   24912 									 "\n";
   24913 
   24914 	std::string source;
   24915 	testCase&   test_case = m_test_cases[test_case_index];
   24916 
   24917 	if (test_case.m_stage == stage)
   24918 	{
   24919 		const GLchar* array	= "";
   24920 		const GLchar* index	= "";
   24921 		size_t		  position = 0;
   24922 
   24923 		switch (stage)
   24924 		{
   24925 		case Utils::Shader::GEOMETRY:
   24926 			source = gs_tested;
   24927 			array  = "[]";
   24928 			index  = "[0]";
   24929 			break;
   24930 		case Utils::Shader::TESS_CTRL:
   24931 			source = tcs_tested;
   24932 			array  = "[]";
   24933 			index  = "[gl_InvocationID]";
   24934 			break;
   24935 		case Utils::Shader::TESS_EVAL:
   24936 			source = tes_tested;
   24937 			array  = "[]";
   24938 			index  = "[0]";
   24939 			break;
   24940 		case Utils::Shader::VERTEX:
   24941 			source = vs_tested;
   24942 			break;
   24943 		default:
   24944 			TCU_FAIL("Invalid enum");
   24945 		}
   24946 
   24947 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   24948 		position = 0;
   24949 		Utils::replaceToken("ARRAY", position, array, source);
   24950 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   24951 
   24952 		Utils::replaceAllTokens("INDEX", index, source);
   24953 	}
   24954 	else
   24955 	{
   24956 		switch (test_case.m_stage)
   24957 		{
   24958 		case Utils::Shader::GEOMETRY:
   24959 			switch (stage)
   24960 			{
   24961 			case Utils::Shader::FRAGMENT:
   24962 				source = fs;
   24963 				break;
   24964 			case Utils::Shader::VERTEX:
   24965 				source = vs;
   24966 				break;
   24967 			default:
   24968 				source = "";
   24969 			}
   24970 			break;
   24971 		case Utils::Shader::TESS_CTRL:
   24972 			switch (stage)
   24973 			{
   24974 			case Utils::Shader::FRAGMENT:
   24975 				source = fs;
   24976 				break;
   24977 			case Utils::Shader::VERTEX:
   24978 				source = vs;
   24979 				break;
   24980 			default:
   24981 				source = "";
   24982 			}
   24983 			break;
   24984 		case Utils::Shader::TESS_EVAL:
   24985 			switch (stage)
   24986 			{
   24987 			case Utils::Shader::FRAGMENT:
   24988 				source = fs;
   24989 				break;
   24990 			case Utils::Shader::TESS_CTRL:
   24991 				source = tcs;
   24992 				break;
   24993 			case Utils::Shader::VERTEX:
   24994 				source = vs;
   24995 				break;
   24996 			default:
   24997 				source = "";
   24998 			}
   24999 			break;
   25000 		case Utils::Shader::VERTEX:
   25001 			switch (stage)
   25002 			{
   25003 			case Utils::Shader::FRAGMENT:
   25004 				source = fs;
   25005 				break;
   25006 			default:
   25007 				source = "";
   25008 			}
   25009 			break;
   25010 		default:
   25011 			TCU_FAIL("Invalid enum");
   25012 			break;
   25013 		}
   25014 	}
   25015 
   25016 	return source;
   25017 }
   25018 
   25019 /** Get description of test case
   25020  *
   25021  * @param test_case_index Index of test case
   25022  *
   25023  * @return Test case description
   25024  **/
   25025 std::string XFBBlockMemberBufferTest::getTestCaseName(GLuint test_case_index)
   25026 {
   25027 	std::stringstream stream;
   25028 	testCase&		  test_case = m_test_cases[test_case_index];
   25029 
   25030 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage);
   25031 
   25032 	return stream.str();
   25033 }
   25034 
   25035 /** Get number of test cases
   25036  *
   25037  * @return Number of test cases
   25038  **/
   25039 GLuint XFBBlockMemberBufferTest::getTestCaseNumber()
   25040 {
   25041 	return static_cast<GLuint>(m_test_cases.size());
   25042 }
   25043 
   25044 /** Selects if "compute" stage is relevant for test
   25045  *
   25046  * @param ignored
   25047  *
   25048  * @return false
   25049  **/
   25050 bool XFBBlockMemberBufferTest::isComputeRelevant(GLuint /* test_case_index */)
   25051 {
   25052 	return false;
   25053 }
   25054 
   25055 /** Prepare all test cases
   25056  *
   25057  **/
   25058 void XFBBlockMemberBufferTest::testInit()
   25059 {
   25060 	for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   25061 	{
   25062 		if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::TESS_CTRL == stage) ||
   25063 			(Utils::Shader::FRAGMENT == stage))
   25064 		{
   25065 			continue;
   25066 		}
   25067 
   25068 		testCase test_case = { (Utils::Shader::STAGES)stage };
   25069 
   25070 		m_test_cases.push_back(test_case);
   25071 	}
   25072 }
   25073 
   25074 /** Constructor
   25075  *
   25076  * @param context Test framework context
   25077  **/
   25078 XFBOutputOverlappingTest::XFBOutputOverlappingTest(deqp::Context& context)
   25079 	: NegativeTestBase(context, "xfb_output_overlapping",
   25080 					   "Test verifies that compiler reports error when two xfb qualified outputs overlap")
   25081 {
   25082 }
   25083 
   25084 /** Source for given test case and stage
   25085  *
   25086  * @param test_case_index Index of test case
   25087  * @param stage           Shader stage
   25088  *
   25089  * @return Shader source
   25090  **/
   25091 std::string XFBOutputOverlappingTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   25092 {
   25093 	static const GLchar* var_definition = "layout (xfb_offset = OFFSET) out TYPE gohanARRAY;\n"
   25094 										  "layout (xfb_offset = OFFSET) out TYPE gotenARRAY;\n";
   25095 	static const GLchar* var_use = "    gohanINDEX = TYPE(0);\n"
   25096 								   "    gotenINDEX = TYPE(1);\n"
   25097 								   "    if (vec4(0) == result)\n"
   25098 								   "    {\n"
   25099 								   "        gohanINDEX = TYPE(1);\n"
   25100 								   "        gotenINDEX = TYPE(0);\n"
   25101 								   "    }\n";
   25102 	static const GLchar* fs = "#version 430 core\n"
   25103 							  "#extension GL_ARB_enhanced_layouts : require\n"
   25104 							  "\n"
   25105 							  "in  vec4 gs_fs;\n"
   25106 							  "out vec4 fs_out;\n"
   25107 							  "\n"
   25108 							  "void main()\n"
   25109 							  "{\n"
   25110 							  "    fs_out = gs_fs;\n"
   25111 							  "}\n"
   25112 							  "\n";
   25113 	static const GLchar* gs_tested = "#version 430 core\n"
   25114 									 "#extension GL_ARB_enhanced_layouts : require\n"
   25115 									 "\n"
   25116 									 "layout(points)                           in;\n"
   25117 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   25118 									 "\n"
   25119 									 "VAR_DEFINITION"
   25120 									 "\n"
   25121 									 "in  vec4 tes_gs[];\n"
   25122 									 "out vec4 gs_fs;\n"
   25123 									 "\n"
   25124 									 "void main()\n"
   25125 									 "{\n"
   25126 									 "    vec4 result = tes_gs[0];\n"
   25127 									 "\n"
   25128 									 "VARIABLE_USE"
   25129 									 "\n"
   25130 									 "    gs_fs = result;\n"
   25131 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   25132 									 "    EmitVertex();\n"
   25133 									 "    gs_fs = result;\n"
   25134 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   25135 									 "    EmitVertex();\n"
   25136 									 "    gs_fs = result;\n"
   25137 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   25138 									 "    EmitVertex();\n"
   25139 									 "    gs_fs = result;\n"
   25140 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   25141 									 "    EmitVertex();\n"
   25142 									 "}\n"
   25143 									 "\n";
   25144 	static const GLchar* tcs = "#version 430 core\n"
   25145 							   "#extension GL_ARB_enhanced_layouts : require\n"
   25146 							   "\n"
   25147 							   "layout(vertices = 1) out;\n"
   25148 							   "\n"
   25149 							   "in  vec4 vs_tcs[];\n"
   25150 							   "out vec4 tcs_tes[];\n"
   25151 							   "\n"
   25152 							   "void main()\n"
   25153 							   "{\n"
   25154 							   "\n"
   25155 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   25156 							   "\n"
   25157 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   25158 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   25159 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   25160 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   25161 							   "    gl_TessLevelInner[0] = 1.0;\n"
   25162 							   "    gl_TessLevelInner[1] = 1.0;\n"
   25163 							   "}\n"
   25164 							   "\n";
   25165 	static const GLchar* tcs_tested = "#version 430 core\n"
   25166 									  "#extension GL_ARB_enhanced_layouts : require\n"
   25167 									  "\n"
   25168 									  "layout(vertices = 1) out;\n"
   25169 									  "\n"
   25170 									  "VAR_DEFINITION"
   25171 									  "\n"
   25172 									  "in  vec4 vs_tcs[];\n"
   25173 									  "out vec4 tcs_tes[];\n"
   25174 									  "\n"
   25175 									  "void main()\n"
   25176 									  "{\n"
   25177 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   25178 									  "\n"
   25179 									  "VARIABLE_USE"
   25180 									  "\n"
   25181 									  "    tcs_tes[gl_InvocationID] = result;\n"
   25182 									  "\n"
   25183 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   25184 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   25185 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   25186 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   25187 									  "    gl_TessLevelInner[0] = 1.0;\n"
   25188 									  "    gl_TessLevelInner[1] = 1.0;\n"
   25189 									  "}\n"
   25190 									  "\n";
   25191 	static const GLchar* tes_tested = "#version 430 core\n"
   25192 									  "#extension GL_ARB_enhanced_layouts : require\n"
   25193 									  "\n"
   25194 									  "layout(isolines, point_mode) in;\n"
   25195 									  "\n"
   25196 									  "VAR_DEFINITION"
   25197 									  "\n"
   25198 									  "in  vec4 tcs_tes[];\n"
   25199 									  "out vec4 tes_gs;\n"
   25200 									  "\n"
   25201 									  "void main()\n"
   25202 									  "{\n"
   25203 									  "    vec4 result = tcs_tes[0];\n"
   25204 									  "\n"
   25205 									  "VARIABLE_USE"
   25206 									  "\n"
   25207 									  "    tes_gs += result;\n"
   25208 									  "}\n"
   25209 									  "\n";
   25210 	static const GLchar* vs = "#version 430 core\n"
   25211 							  "#extension GL_ARB_enhanced_layouts : require\n"
   25212 							  "\n"
   25213 							  "in  vec4 in_vs;\n"
   25214 							  "out vec4 vs_tcs;\n"
   25215 							  "\n"
   25216 							  "void main()\n"
   25217 							  "{\n"
   25218 							  "    vs_tcs = in_vs;\n"
   25219 							  "}\n"
   25220 							  "\n";
   25221 	static const GLchar* vs_tested = "#version 430 core\n"
   25222 									 "#extension GL_ARB_enhanced_layouts : require\n"
   25223 									 "\n"
   25224 									 "VAR_DEFINITION"
   25225 									 "\n"
   25226 									 "in  vec4 in_vs;\n"
   25227 									 "out vec4 vs_tcs;\n"
   25228 									 "\n"
   25229 									 "void main()\n"
   25230 									 "{\n"
   25231 									 "    vec4 result = in_vs;\n"
   25232 									 "\n"
   25233 									 "VARIABLE_USE"
   25234 									 "\n"
   25235 									 "    vs_tcs = result;\n"
   25236 									 "}\n"
   25237 									 "\n";
   25238 
   25239 	std::string source;
   25240 	testCase&   test_case = m_test_cases[test_case_index];
   25241 
   25242 	if (test_case.m_stage == stage)
   25243 	{
   25244 		const GLchar* array = "";
   25245 		GLchar		  buffer_gohan[16];
   25246 		GLchar		  buffer_goten[16];
   25247 		const GLchar* index			 = "";
   25248 		size_t		  position		 = 0;
   25249 		size_t		  position_start = 0;
   25250 		const GLchar* type_name		 = test_case.m_type.GetGLSLTypeName();
   25251 
   25252 		sprintf(buffer_gohan, "%d", test_case.m_offset_gohan);
   25253 		sprintf(buffer_goten, "%d", test_case.m_offset_goten);
   25254 
   25255 		switch (stage)
   25256 		{
   25257 		case Utils::Shader::GEOMETRY:
   25258 			source = gs_tested;
   25259 			array  = "[]";
   25260 			index  = "[0]";
   25261 			break;
   25262 		case Utils::Shader::TESS_CTRL:
   25263 			source = tcs_tested;
   25264 			array  = "[]";
   25265 			index  = "[gl_InvocationID]";
   25266 			break;
   25267 		case Utils::Shader::TESS_EVAL:
   25268 			source = tes_tested;
   25269 			array  = "[]";
   25270 			index  = "[0]";
   25271 			break;
   25272 		case Utils::Shader::VERTEX:
   25273 			source = vs_tested;
   25274 			break;
   25275 		default:
   25276 			TCU_FAIL("Invalid enum");
   25277 		}
   25278 
   25279 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   25280 		position = 0;
   25281 		Utils::replaceToken("OFFSET", position, buffer_gohan, source);
   25282 		Utils::replaceToken("TYPE", position, type_name, source);
   25283 		Utils::replaceToken("ARRAY", position, array, source);
   25284 		Utils::replaceToken("OFFSET", position, buffer_goten, source);
   25285 		Utils::replaceToken("TYPE", position, type_name, source);
   25286 		Utils::replaceToken("ARRAY", position, array, source);
   25287 		position_start = position;
   25288 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   25289 		position = position_start;
   25290 		Utils::replaceToken("INDEX", position, index, source);
   25291 		Utils::replaceToken("TYPE", position, type_name, source);
   25292 		Utils::replaceToken("INDEX", position, index, source);
   25293 		Utils::replaceToken("TYPE", position, type_name, source);
   25294 		Utils::replaceToken("INDEX", position, index, source);
   25295 		Utils::replaceToken("TYPE", position, type_name, source);
   25296 		Utils::replaceToken("INDEX", position, index, source);
   25297 		Utils::replaceToken("TYPE", position, type_name, source);
   25298 	}
   25299 	else
   25300 	{
   25301 		switch (test_case.m_stage)
   25302 		{
   25303 		case Utils::Shader::GEOMETRY:
   25304 			switch (stage)
   25305 			{
   25306 			case Utils::Shader::FRAGMENT:
   25307 				source = fs;
   25308 				break;
   25309 			case Utils::Shader::VERTEX:
   25310 				source = vs;
   25311 				break;
   25312 			default:
   25313 				source = "";
   25314 			}
   25315 			break;
   25316 		case Utils::Shader::TESS_CTRL:
   25317 			switch (stage)
   25318 			{
   25319 			case Utils::Shader::FRAGMENT:
   25320 				source = fs;
   25321 				break;
   25322 			case Utils::Shader::VERTEX:
   25323 				source = vs;
   25324 				break;
   25325 			default:
   25326 				source = "";
   25327 			}
   25328 			break;
   25329 		case Utils::Shader::TESS_EVAL:
   25330 			switch (stage)
   25331 			{
   25332 			case Utils::Shader::FRAGMENT:
   25333 				source = fs;
   25334 				break;
   25335 			case Utils::Shader::TESS_CTRL:
   25336 				source = tcs;
   25337 				break;
   25338 			case Utils::Shader::VERTEX:
   25339 				source = vs;
   25340 				break;
   25341 			default:
   25342 				source = "";
   25343 			}
   25344 			break;
   25345 		case Utils::Shader::VERTEX:
   25346 			switch (stage)
   25347 			{
   25348 			case Utils::Shader::FRAGMENT:
   25349 				source = fs;
   25350 				break;
   25351 			default:
   25352 				source = "";
   25353 			}
   25354 			break;
   25355 		default:
   25356 			TCU_FAIL("Invalid enum");
   25357 			break;
   25358 		}
   25359 	}
   25360 
   25361 	return source;
   25362 }
   25363 
   25364 /** Get description of test case
   25365  *
   25366  * @param test_case_index Index of test case
   25367  *
   25368  * @return Test case description
   25369  **/
   25370 std::string XFBOutputOverlappingTest::getTestCaseName(GLuint test_case_index)
   25371 {
   25372 	std::stringstream stream;
   25373 	testCase&		  test_case = m_test_cases[test_case_index];
   25374 
   25375 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage)
   25376 		   << ", type: " << test_case.m_type.GetGLSLTypeName() << ", offsets: " << test_case.m_offset_gohan << " & "
   25377 		   << test_case.m_offset_goten;
   25378 
   25379 	return stream.str();
   25380 }
   25381 
   25382 /** Get number of test cases
   25383  *
   25384  * @return Number of test cases
   25385  **/
   25386 GLuint XFBOutputOverlappingTest::getTestCaseNumber()
   25387 {
   25388 	return static_cast<GLuint>(m_test_cases.size());
   25389 }
   25390 
   25391 /** Selects if "compute" stage is relevant for test
   25392  *
   25393  * @param ignored
   25394  *
   25395  * @return false
   25396  **/
   25397 bool XFBOutputOverlappingTest::isComputeRelevant(GLuint /* test_case_index */)
   25398 {
   25399 	return false;
   25400 }
   25401 
   25402 /** Prepare all test cases
   25403  *
   25404  **/
   25405 void XFBOutputOverlappingTest::testInit()
   25406 {
   25407 	const GLuint n_types = getTypesNumber();
   25408 
   25409 	for (GLuint i = 0; i < n_types; ++i)
   25410 	{
   25411 		const Utils::Type& type			  = getType(i);
   25412 		const GLuint	   base_alingment = Utils::Type::GetTypeSize(type.m_basic_type);
   25413 
   25414 		/* Skip scalars, not applicable as:
   25415 		 *
   25416 		 *     The offset must be a multiple of the size of the first component of the first
   25417 		 *     qualified variable or block member, or a compile-time error results.
   25418 		 */
   25419 		if ((1 == type.m_n_columns) && (1 == type.m_n_rows))
   25420 		{
   25421 			continue;
   25422 		}
   25423 
   25424 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   25425 		{
   25426 			if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::TESS_CTRL == stage) ||
   25427 				(Utils::Shader::FRAGMENT == stage))
   25428 			{
   25429 				continue;
   25430 			}
   25431 
   25432 			testCase test_case = { 0 /* gohan offset */, base_alingment /* goten_offset */,
   25433 								   (Utils::Shader::STAGES)stage, type };
   25434 
   25435 			m_test_cases.push_back(test_case);
   25436 		}
   25437 	}
   25438 }
   25439 
   25440 /** Constructor
   25441  *
   25442  * @param context Test framework context
   25443  **/
   25444 XFBInvalidOffsetAlignmentTest::XFBInvalidOffsetAlignmentTest(deqp::Context& context)
   25445 	: NegativeTestBase(context, "xfb_invalid_offset_alignment",
   25446 					   "Test verifies that compiler reports error when xfb_offset has invalid alignment")
   25447 {
   25448 }
   25449 
   25450 /** Source for given test case and stage
   25451  *
   25452  * @param test_case_index Index of test case
   25453  * @param stage           Shader stage
   25454  *
   25455  * @return Shader source
   25456  **/
   25457 std::string XFBInvalidOffsetAlignmentTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   25458 {
   25459 	static const GLchar* var_definition = "layout (xfb_offset = OFFSET) out TYPE gohanARRAY;\n";
   25460 	static const GLchar* var_use		= "    gohanINDEX = TYPE(0);\n"
   25461 								   "    if (vec4(0) == result)\n"
   25462 								   "    {\n"
   25463 								   "        gohanINDEX = TYPE(1);\n"
   25464 								   "    }\n";
   25465 	static const GLchar* fs = "#version 430 core\n"
   25466 							  "#extension GL_ARB_enhanced_layouts : require\n"
   25467 							  "\n"
   25468 							  "in  vec4 gs_fs;\n"
   25469 							  "out vec4 fs_out;\n"
   25470 							  "\n"
   25471 							  "void main()\n"
   25472 							  "{\n"
   25473 							  "    fs_out = gs_fs;\n"
   25474 							  "}\n"
   25475 							  "\n";
   25476 	static const GLchar* gs_tested = "#version 430 core\n"
   25477 									 "#extension GL_ARB_enhanced_layouts : require\n"
   25478 									 "\n"
   25479 									 "layout(points)                           in;\n"
   25480 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   25481 									 "\n"
   25482 									 "VAR_DEFINITION"
   25483 									 "\n"
   25484 									 "in  vec4 tes_gs[];\n"
   25485 									 "out vec4 gs_fs;\n"
   25486 									 "\n"
   25487 									 "void main()\n"
   25488 									 "{\n"
   25489 									 "    vec4 result = tes_gs[0];\n"
   25490 									 "\n"
   25491 									 "VARIABLE_USE"
   25492 									 "\n"
   25493 									 "    gs_fs = result;\n"
   25494 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   25495 									 "    EmitVertex();\n"
   25496 									 "    gs_fs = result;\n"
   25497 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   25498 									 "    EmitVertex();\n"
   25499 									 "    gs_fs = result;\n"
   25500 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   25501 									 "    EmitVertex();\n"
   25502 									 "    gs_fs = result;\n"
   25503 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   25504 									 "    EmitVertex();\n"
   25505 									 "}\n"
   25506 									 "\n";
   25507 	static const GLchar* tcs = "#version 430 core\n"
   25508 							   "#extension GL_ARB_enhanced_layouts : require\n"
   25509 							   "\n"
   25510 							   "layout(vertices = 1) out;\n"
   25511 							   "\n"
   25512 							   "in  vec4 vs_tcs[];\n"
   25513 							   "out vec4 tcs_tes[];\n"
   25514 							   "\n"
   25515 							   "void main()\n"
   25516 							   "{\n"
   25517 							   "\n"
   25518 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   25519 							   "\n"
   25520 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   25521 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   25522 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   25523 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   25524 							   "    gl_TessLevelInner[0] = 1.0;\n"
   25525 							   "    gl_TessLevelInner[1] = 1.0;\n"
   25526 							   "}\n"
   25527 							   "\n";
   25528 	static const GLchar* tcs_tested = "#version 430 core\n"
   25529 									  "#extension GL_ARB_enhanced_layouts : require\n"
   25530 									  "\n"
   25531 									  "layout(vertices = 1) out;\n"
   25532 									  "\n"
   25533 									  "VAR_DEFINITION"
   25534 									  "\n"
   25535 									  "in  vec4 vs_tcs[];\n"
   25536 									  "out vec4 tcs_tes[];\n"
   25537 									  "\n"
   25538 									  "void main()\n"
   25539 									  "{\n"
   25540 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   25541 									  "\n"
   25542 									  "VARIABLE_USE"
   25543 									  "\n"
   25544 									  "    tcs_tes[gl_InvocationID] = result;\n"
   25545 									  "\n"
   25546 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   25547 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   25548 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   25549 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   25550 									  "    gl_TessLevelInner[0] = 1.0;\n"
   25551 									  "    gl_TessLevelInner[1] = 1.0;\n"
   25552 									  "}\n"
   25553 									  "\n";
   25554 	static const GLchar* tes_tested = "#version 430 core\n"
   25555 									  "#extension GL_ARB_enhanced_layouts : require\n"
   25556 									  "\n"
   25557 									  "layout(isolines, point_mode) in;\n"
   25558 									  "\n"
   25559 									  "VAR_DEFINITION"
   25560 									  "\n"
   25561 									  "in  vec4 tcs_tes[];\n"
   25562 									  "out vec4 tes_gs;\n"
   25563 									  "\n"
   25564 									  "void main()\n"
   25565 									  "{\n"
   25566 									  "    vec4 result = tcs_tes[0];\n"
   25567 									  "\n"
   25568 									  "VARIABLE_USE"
   25569 									  "\n"
   25570 									  "    tes_gs += result;\n"
   25571 									  "}\n"
   25572 									  "\n";
   25573 	static const GLchar* vs = "#version 430 core\n"
   25574 							  "#extension GL_ARB_enhanced_layouts : require\n"
   25575 							  "\n"
   25576 							  "in  vec4 in_vs;\n"
   25577 							  "out vec4 vs_tcs;\n"
   25578 							  "\n"
   25579 							  "void main()\n"
   25580 							  "{\n"
   25581 							  "    vs_tcs = in_vs;\n"
   25582 							  "}\n"
   25583 							  "\n";
   25584 	static const GLchar* vs_tested = "#version 430 core\n"
   25585 									 "#extension GL_ARB_enhanced_layouts : require\n"
   25586 									 "\n"
   25587 									 "VAR_DEFINITION"
   25588 									 "\n"
   25589 									 "in  vec4 in_vs;\n"
   25590 									 "out vec4 vs_tcs;\n"
   25591 									 "\n"
   25592 									 "void main()\n"
   25593 									 "{\n"
   25594 									 "    vec4 result = in_vs;\n"
   25595 									 "\n"
   25596 									 "VARIABLE_USE"
   25597 									 "\n"
   25598 									 "    vs_tcs = result;\n"
   25599 									 "}\n"
   25600 									 "\n";
   25601 
   25602 	std::string source;
   25603 	testCase&   test_case = m_test_cases[test_case_index];
   25604 
   25605 	if (test_case.m_stage == stage)
   25606 	{
   25607 		const GLchar* array = "";
   25608 		GLchar		  buffer[16];
   25609 		const GLchar* index			 = "";
   25610 		size_t		  position		 = 0;
   25611 		size_t		  position_start = 0;
   25612 		const GLchar* type_name		 = test_case.m_type.GetGLSLTypeName();
   25613 
   25614 		sprintf(buffer, "%d", test_case.m_offset);
   25615 
   25616 		switch (stage)
   25617 		{
   25618 		case Utils::Shader::GEOMETRY:
   25619 			source = gs_tested;
   25620 			array  = "[]";
   25621 			index  = "[0]";
   25622 			break;
   25623 		case Utils::Shader::TESS_CTRL:
   25624 			source = tcs_tested;
   25625 			array  = "[]";
   25626 			index  = "[gl_InvocationID]";
   25627 			break;
   25628 		case Utils::Shader::TESS_EVAL:
   25629 			source = tes_tested;
   25630 			array  = "[]";
   25631 			index  = "[0]";
   25632 			break;
   25633 		case Utils::Shader::VERTEX:
   25634 			source = vs_tested;
   25635 			break;
   25636 		default:
   25637 			TCU_FAIL("Invalid enum");
   25638 		}
   25639 
   25640 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   25641 		position = 0;
   25642 		Utils::replaceToken("OFFSET", position, buffer, source);
   25643 		Utils::replaceToken("TYPE", position, type_name, source);
   25644 		Utils::replaceToken("ARRAY", position, array, source);
   25645 		position_start = position;
   25646 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   25647 		position = position_start;
   25648 		Utils::replaceToken("INDEX", position, index, source);
   25649 		Utils::replaceToken("TYPE", position, type_name, source);
   25650 		Utils::replaceToken("INDEX", position, index, source);
   25651 		Utils::replaceToken("TYPE", position, type_name, source);
   25652 	}
   25653 	else
   25654 	{
   25655 		switch (test_case.m_stage)
   25656 		{
   25657 		case Utils::Shader::GEOMETRY:
   25658 			switch (stage)
   25659 			{
   25660 			case Utils::Shader::FRAGMENT:
   25661 				source = fs;
   25662 				break;
   25663 			case Utils::Shader::VERTEX:
   25664 				source = vs;
   25665 				break;
   25666 			default:
   25667 				source = "";
   25668 			}
   25669 			break;
   25670 		case Utils::Shader::TESS_CTRL:
   25671 			switch (stage)
   25672 			{
   25673 			case Utils::Shader::FRAGMENT:
   25674 				source = fs;
   25675 				break;
   25676 			case Utils::Shader::VERTEX:
   25677 				source = vs;
   25678 				break;
   25679 			default:
   25680 				source = "";
   25681 			}
   25682 			break;
   25683 		case Utils::Shader::TESS_EVAL:
   25684 			switch (stage)
   25685 			{
   25686 			case Utils::Shader::FRAGMENT:
   25687 				source = fs;
   25688 				break;
   25689 			case Utils::Shader::TESS_CTRL:
   25690 				source = tcs;
   25691 				break;
   25692 			case Utils::Shader::VERTEX:
   25693 				source = vs;
   25694 				break;
   25695 			default:
   25696 				source = "";
   25697 			}
   25698 			break;
   25699 		case Utils::Shader::VERTEX:
   25700 			switch (stage)
   25701 			{
   25702 			case Utils::Shader::FRAGMENT:
   25703 				source = fs;
   25704 				break;
   25705 			default:
   25706 				source = "";
   25707 			}
   25708 			break;
   25709 		default:
   25710 			TCU_FAIL("Invalid enum");
   25711 			break;
   25712 		}
   25713 	}
   25714 
   25715 	return source;
   25716 }
   25717 
   25718 /** Get description of test case
   25719  *
   25720  * @param test_case_index Index of test case
   25721  *
   25722  * @return Test case description
   25723  **/
   25724 std::string XFBInvalidOffsetAlignmentTest::getTestCaseName(GLuint test_case_index)
   25725 {
   25726 	std::stringstream stream;
   25727 	testCase&		  test_case = m_test_cases[test_case_index];
   25728 
   25729 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage)
   25730 		   << ", type: " << test_case.m_type.GetGLSLTypeName() << ", offset: " << test_case.m_offset;
   25731 
   25732 	return stream.str();
   25733 }
   25734 
   25735 /** Get number of test cases
   25736  *
   25737  * @return Number of test cases
   25738  **/
   25739 GLuint XFBInvalidOffsetAlignmentTest::getTestCaseNumber()
   25740 {
   25741 	return static_cast<GLuint>(m_test_cases.size());
   25742 }
   25743 
   25744 /** Selects if "compute" stage is relevant for test
   25745  *
   25746  * @param ignored
   25747  *
   25748  * @return false
   25749  **/
   25750 bool XFBInvalidOffsetAlignmentTest::isComputeRelevant(GLuint /* test_case_index */)
   25751 {
   25752 	return false;
   25753 }
   25754 
   25755 /** Prepare all test cases
   25756  *
   25757  **/
   25758 void XFBInvalidOffsetAlignmentTest::testInit()
   25759 {
   25760 	const GLuint n_types = getTypesNumber();
   25761 
   25762 	for (GLuint i = 0; i < n_types; ++i)
   25763 	{
   25764 		const Utils::Type& type			  = getType(i);
   25765 		const GLuint	   base_alingment = Utils::Type::GetTypeSize(type.m_basic_type);
   25766 
   25767 		for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   25768 		{
   25769 			if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::TESS_CTRL == stage) ||
   25770 				(Utils::Shader::FRAGMENT == stage))
   25771 			{
   25772 				continue;
   25773 			}
   25774 
   25775 			for (GLuint offset = base_alingment + 1; offset < 2 * base_alingment; ++offset)
   25776 			{
   25777 				testCase test_case = { offset, (Utils::Shader::STAGES)stage, type };
   25778 
   25779 				m_test_cases.push_back(test_case);
   25780 			}
   25781 		}
   25782 	}
   25783 }
   25784 
   25785 /** Constructor
   25786  *
   25787  * @param context Test context
   25788  **/
   25789 XFBCaptureInactiveOutputVariableTest::XFBCaptureInactiveOutputVariableTest(deqp::Context& context)
   25790 	: BufferTestBase(context, "xfb_capture_inactive_output_variable",
   25791 					 "Test verifies that inactive variables are captured")
   25792 {
   25793 	/* Nothing to be done here */
   25794 }
   25795 
   25796 /** Execute drawArrays for single vertex
   25797  *
   25798  * @param test_case_index
   25799  *
   25800  * @return true
   25801  **/
   25802 bool XFBCaptureInactiveOutputVariableTest::executeDrawCall(bool /* tesEnabled */, GLuint test_case_index)
   25803 {
   25804 	const Functions& gl				= m_context.getRenderContext().getFunctions();
   25805 	GLenum			 primitive_type = GL_PATCHES;
   25806 
   25807 	if (TEST_VS == test_case_index)
   25808 	{
   25809 		primitive_type = GL_POINTS;
   25810 	}
   25811 
   25812 	gl.disable(GL_RASTERIZER_DISCARD);
   25813 	GLU_EXPECT_NO_ERROR(gl.getError(), "Disable");
   25814 
   25815 	gl.beginTransformFeedback(GL_POINTS);
   25816 	GLU_EXPECT_NO_ERROR(gl.getError(), "BeginTransformFeedback");
   25817 
   25818 	gl.drawArrays(primitive_type, 0 /* first */, 1 /* count */);
   25819 	GLU_EXPECT_NO_ERROR(gl.getError(), "DrawArrays");
   25820 
   25821 	gl.endTransformFeedback();
   25822 	GLU_EXPECT_NO_ERROR(gl.getError(), "EndTransformFeedback");
   25823 
   25824 	return true;
   25825 }
   25826 
   25827 /** Get descriptors of buffers necessary for test
   25828  *
   25829  * @param ignored
   25830  * @param out_descriptors Descriptors of buffers used by test
   25831  **/
   25832 void XFBCaptureInactiveOutputVariableTest::getBufferDescriptors(glw::GLuint /* test_case_index */,
   25833 																bufferDescriptor::Vector& out_descriptors)
   25834 {
   25835 	const Utils::Type& type = Utils::Type::vec4;
   25836 
   25837 	/* Test needs single uniform and xfb */
   25838 	out_descriptors.resize(2);
   25839 
   25840 	/* Get references */
   25841 	bufferDescriptor& uniform = out_descriptors[0];
   25842 	bufferDescriptor& xfb	 = out_descriptors[1];
   25843 
   25844 	/* Index */
   25845 	uniform.m_index = 0;
   25846 	xfb.m_index		= 0;
   25847 
   25848 	/* Target */
   25849 	uniform.m_target = Utils::Buffer::Uniform;
   25850 	xfb.m_target	 = Utils::Buffer::Transform_feedback;
   25851 
   25852 	/* Data */
   25853 	const std::vector<GLubyte>& gohan_data = type.GenerateData();
   25854 	const std::vector<GLubyte>& goten_data = type.GenerateData();
   25855 
   25856 	const GLuint type_size = static_cast<GLuint>(gohan_data.size());
   25857 
   25858 	/* Uniform data */
   25859 	uniform.m_initial_data.resize(2 * type_size);
   25860 	memcpy(&uniform.m_initial_data[0] + 0, &gohan_data[0], type_size);
   25861 	memcpy(&uniform.m_initial_data[0] + type_size, &goten_data[0], type_size);
   25862 
   25863 	/* XFB data */
   25864 	xfb.m_initial_data.resize(3 * type_size);
   25865 	xfb.m_expected_data.resize(3 * type_size);
   25866 
   25867 	for (GLuint i = 0; i < 3 * type_size; ++i)
   25868 	{
   25869 		xfb.m_initial_data[i]  = (glw::GLubyte)i;
   25870 		xfb.m_expected_data[i] = (glw::GLubyte)i;
   25871 	}
   25872 
   25873 	memcpy(&xfb.m_expected_data[0] + 2 * type_size, &gohan_data[0], type_size);
   25874 	memcpy(&xfb.m_expected_data[0] + 0 * type_size, &goten_data[0], type_size);
   25875 }
   25876 
   25877 /** Get body of main function for given shader stage
   25878  *
   25879  * @param test_case_index  Index of test case
   25880  * @param stage            Shader stage
   25881  * @param out_assignments  Set to empty
   25882  * @param out_calculations Set to empty
   25883  **/
   25884 void XFBCaptureInactiveOutputVariableTest::getShaderBody(GLuint test_case_index, Utils::Shader::STAGES stage,
   25885 														 std::string& out_assignments, std::string& out_calculations)
   25886 {
   25887 	out_calculations = "";
   25888 
   25889 	static const GLchar* vs_tes_gs = "    goten = uni_goten;\n"
   25890 									 "    gohan = uni_gohan;\n";
   25891 	static const GLchar* fs = "    fs_out = goku + gohan + goten;\n";
   25892 
   25893 	const GLchar* assignments = "";
   25894 
   25895 	switch (stage)
   25896 	{
   25897 	case Utils::Shader::FRAGMENT:
   25898 		assignments = fs;
   25899 		break;
   25900 
   25901 	case Utils::Shader::GEOMETRY:
   25902 		if (TEST_GS == test_case_index)
   25903 		{
   25904 			assignments = vs_tes_gs;
   25905 		}
   25906 		break;
   25907 
   25908 	case Utils::Shader::TESS_CTRL:
   25909 		break;
   25910 
   25911 	case Utils::Shader::TESS_EVAL:
   25912 		if (TEST_TES == test_case_index)
   25913 		{
   25914 			assignments = vs_tes_gs;
   25915 		}
   25916 		break;
   25917 
   25918 	case Utils::Shader::VERTEX:
   25919 		if (TEST_VS == test_case_index)
   25920 		{
   25921 			assignments = vs_tes_gs;
   25922 		}
   25923 		break;
   25924 
   25925 	default:
   25926 		TCU_FAIL("Invalid enum");
   25927 	}
   25928 
   25929 	out_assignments = assignments;
   25930 }
   25931 
   25932 /** Get interface of shader
   25933  *
   25934  * @param test_case_index  Index of test case
   25935  * @param stage            Shader stage
   25936  * @param out_interface    Set to ""
   25937  **/
   25938 void XFBCaptureInactiveOutputVariableTest::getShaderInterface(GLuint test_case_index, Utils::Shader::STAGES stage,
   25939 															  std::string& out_interface)
   25940 {
   25941 	static const GLchar* vs_tes_gs = "const uint sizeof_type = 16;\n"
   25942 									 "\n"
   25943 									 "layout (xfb_offset = 1 * sizeof_type) out vec4 goku;\n"
   25944 									 "layout (xfb_offset = 2 * sizeof_type) out vec4 gohan;\n"
   25945 									 "layout (xfb_offset = 0 * sizeof_type) out vec4 goten;\n"
   25946 									 "\n"
   25947 									 "layout(binding = 0) uniform block {\n"
   25948 									 "    vec4 uni_gohan;\n"
   25949 									 "    vec4 uni_goten;\n"
   25950 									 "};\n";
   25951 	static const GLchar* fs = "in vec4 goku;\n"
   25952 							  "in vec4 gohan;\n"
   25953 							  "in vec4 goten;\n"
   25954 							  "out vec4 fs_out;\n";
   25955 
   25956 	const GLchar* interface = "";
   25957 
   25958 	switch (stage)
   25959 	{
   25960 	case Utils::Shader::FRAGMENT:
   25961 		interface = fs;
   25962 		break;
   25963 
   25964 	case Utils::Shader::GEOMETRY:
   25965 		if (TEST_GS == test_case_index)
   25966 		{
   25967 			interface = vs_tes_gs;
   25968 		}
   25969 		break;
   25970 
   25971 	case Utils::Shader::TESS_CTRL:
   25972 		break;
   25973 
   25974 	case Utils::Shader::TESS_EVAL:
   25975 		if (TEST_TES == test_case_index)
   25976 		{
   25977 			interface = vs_tes_gs;
   25978 		}
   25979 		break;
   25980 
   25981 	case Utils::Shader::VERTEX:
   25982 		if (TEST_VS == test_case_index)
   25983 		{
   25984 			interface = vs_tes_gs;
   25985 		}
   25986 		break;
   25987 
   25988 	default:
   25989 		TCU_FAIL("Invalid enum");
   25990 	}
   25991 
   25992 	out_interface = interface;
   25993 }
   25994 
   25995 /** Get source code of shader
   25996  *
   25997  * @param test_case_index Index of test case
   25998  * @param stage           Shader stage
   25999  *
   26000  * @return Source
   26001  **/
   26002 std::string XFBCaptureInactiveOutputVariableTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   26003 {
   26004 	std::string source;
   26005 
   26006 	switch (test_case_index)
   26007 	{
   26008 	case TEST_VS:
   26009 		switch (stage)
   26010 		{
   26011 		case Utils::Shader::FRAGMENT:
   26012 		case Utils::Shader::VERTEX:
   26013 			source = BufferTestBase::getShaderSource(test_case_index, stage);
   26014 			break;
   26015 		default:
   26016 			break;
   26017 		}
   26018 		break;
   26019 
   26020 	case TEST_TES:
   26021 		switch (stage)
   26022 		{
   26023 		case Utils::Shader::FRAGMENT:
   26024 		case Utils::Shader::TESS_CTRL:
   26025 		case Utils::Shader::TESS_EVAL:
   26026 		case Utils::Shader::VERTEX:
   26027 			source = BufferTestBase::getShaderSource(test_case_index, stage);
   26028 			break;
   26029 		default:
   26030 			break;
   26031 		}
   26032 		break;
   26033 
   26034 	case TEST_GS:
   26035 		source = BufferTestBase::getShaderSource(test_case_index, stage);
   26036 		break;
   26037 
   26038 	default:
   26039 		TCU_FAIL("Invalid enum");
   26040 		break;
   26041 	}
   26042 
   26043 	/* */
   26044 	return source;
   26045 }
   26046 
   26047 /** Get name of test case
   26048  *
   26049  * @param test_case_index Index of test case
   26050  *
   26051  * @return Name of tested stage
   26052  **/
   26053 std::string XFBCaptureInactiveOutputVariableTest::getTestCaseName(glw::GLuint test_case_index)
   26054 {
   26055 	const GLchar* name = 0;
   26056 
   26057 	switch (test_case_index)
   26058 	{
   26059 	case TEST_VS:
   26060 		name = "vertex";
   26061 		break;
   26062 	case TEST_TES:
   26063 		name = "tessellation evaluation";
   26064 		break;
   26065 	case TEST_GS:
   26066 		name = "geometry";
   26067 		break;
   26068 	default:
   26069 		TCU_FAIL("Invalid enum");
   26070 	}
   26071 
   26072 	return name;
   26073 }
   26074 
   26075 /** Returns number of test cases
   26076  *
   26077  * @return TEST_MAX
   26078  **/
   26079 glw::GLuint XFBCaptureInactiveOutputVariableTest::getTestCaseNumber()
   26080 {
   26081 	return TEST_MAX;
   26082 }
   26083 
   26084 /** Inspects program to check if all resources are as expected
   26085  *
   26086  * @param ignored
   26087  * @param program         Program instance
   26088  * @param out_stream      Error message
   26089  *
   26090  * @return true if everything is ok, false otherwise
   26091  **/
   26092 bool XFBCaptureInactiveOutputVariableTest::inspectProgram(GLuint /* test_case_index */, Utils::Program& program,
   26093 														  std::stringstream& out_stream)
   26094 {
   26095 	GLint			   stride	= 0;
   26096 	const Utils::Type& type		 = Utils::Type::vec4;
   26097 	const GLuint	   type_size = type.GetSize();
   26098 
   26099 	program.GetResource(GL_TRANSFORM_FEEDBACK_BUFFER, 0 /* index */, GL_TRANSFORM_FEEDBACK_BUFFER_STRIDE,
   26100 						1 /* buf_size */, &stride);
   26101 
   26102 	if ((GLint)(3 * type_size) != stride)
   26103 	{
   26104 		out_stream << "Stride is: " << stride << " expected: " << (3 * type_size);
   26105 
   26106 		return false;
   26107 	}
   26108 
   26109 	return true;
   26110 }
   26111 
   26112 /** Verify contents of buffers
   26113  *
   26114  * @param buffers Collection of buffers to be verified
   26115  *
   26116  * @return true if everything is as expected, false otherwise
   26117  **/
   26118 bool XFBCaptureInactiveOutputVariableTest::verifyBuffers(bufferCollection& buffers)
   26119 {
   26120 	bool result = true;
   26121 
   26122 	bufferCollection::pair& pair	   = buffers.m_vector[1] /* xfb */;
   26123 	Utils::Buffer*			buffer	 = pair.m_buffer;
   26124 	bufferDescriptor*		descriptor = pair.m_descriptor;
   26125 
   26126 	/* Get pointer to contents of buffer */
   26127 	buffer->Bind();
   26128 	GLubyte* buffer_data = (GLubyte*)buffer->Map(Utils::Buffer::ReadOnly);
   26129 
   26130 	/* Get pointer to expected data */
   26131 	GLubyte* expected_data = (GLubyte*)&descriptor->m_expected_data[0];
   26132 
   26133 	/* Compare */
   26134 	static const GLuint vec4_size = 16;
   26135 
   26136 	int res_gohan = memcmp(buffer_data + 2 * vec4_size, expected_data + 2 * vec4_size, vec4_size);
   26137 	int res_goten = memcmp(buffer_data + 0 * vec4_size, expected_data + 0 * vec4_size, vec4_size);
   26138 
   26139 	if ((0 != res_gohan) || (0 != res_goten))
   26140 	{
   26141 		m_context.getTestContext().getLog()
   26142 			<< tcu::TestLog::Message << "Invalid result. Buffer: " << Utils::Buffer::GetBufferName(descriptor->m_target)
   26143 			<< ". Index: " << descriptor->m_index << tcu::TestLog::EndMessage;
   26144 
   26145 		result = false;
   26146 	}
   26147 
   26148 	/* Release buffer mapping */
   26149 	buffer->UnMap();
   26150 
   26151 	return result;
   26152 }
   26153 
   26154 /** Constructor
   26155  *
   26156  * @param context Test context
   26157  **/
   26158 XFBCaptureInactiveOutputComponentTest::XFBCaptureInactiveOutputComponentTest(deqp::Context& context)
   26159 	: BufferTestBase(context, "xfb_capture_inactive_output_component",
   26160 					 "Test verifies that inactive components are not modified")
   26161 {
   26162 	/* Nothing to be done here */
   26163 }
   26164 
   26165 /** Execute drawArrays for single vertex
   26166  *
   26167  * @param test_case_index
   26168  *
   26169  * @return true
   26170  **/
   26171 bool XFBCaptureInactiveOutputComponentTest::executeDrawCall(bool /* tesEnabled */, GLuint test_case_index)
   26172 {
   26173 	const Functions& gl				= m_context.getRenderContext().getFunctions();
   26174 	GLenum			 primitive_type = GL_PATCHES;
   26175 
   26176 	if (TEST_VS == test_case_index)
   26177 	{
   26178 		primitive_type = GL_POINTS;
   26179 	}
   26180 
   26181 	gl.disable(GL_RASTERIZER_DISCARD);
   26182 	GLU_EXPECT_NO_ERROR(gl.getError(), "Disable");
   26183 
   26184 	gl.beginTransformFeedback(GL_POINTS);
   26185 	GLU_EXPECT_NO_ERROR(gl.getError(), "BeginTransformFeedback");
   26186 
   26187 	gl.drawArrays(primitive_type, 0 /* first */, 1 /* count */);
   26188 	GLU_EXPECT_NO_ERROR(gl.getError(), "DrawArrays");
   26189 
   26190 	gl.endTransformFeedback();
   26191 	GLU_EXPECT_NO_ERROR(gl.getError(), "EndTransformFeedback");
   26192 
   26193 	return true;
   26194 }
   26195 
   26196 /** Get descriptors of buffers necessary for test
   26197  *
   26198  * @param ignored
   26199  * @param out_descriptors Descriptors of buffers used by test
   26200  **/
   26201 void XFBCaptureInactiveOutputComponentTest::getBufferDescriptors(glw::GLuint /* test_case_index */,
   26202 																 bufferDescriptor::Vector& out_descriptors)
   26203 {
   26204 	const Utils::Type& type = Utils::Type::vec4;
   26205 
   26206 	/* Test needs single uniform and xfb */
   26207 	out_descriptors.resize(2);
   26208 
   26209 	/* Get references */
   26210 	bufferDescriptor& uniform = out_descriptors[0];
   26211 	bufferDescriptor& xfb	 = out_descriptors[1];
   26212 
   26213 	/* Index */
   26214 	uniform.m_index = 0;
   26215 	xfb.m_index		= 0;
   26216 
   26217 	/* Target */
   26218 	uniform.m_target = Utils::Buffer::Uniform;
   26219 	xfb.m_target	 = Utils::Buffer::Transform_feedback;
   26220 
   26221 	/* Data */
   26222 	const std::vector<GLubyte>& goku_data   = type.GenerateData();
   26223 	const std::vector<GLubyte>& gohan_data  = type.GenerateData();
   26224 	const std::vector<GLubyte>& goten_data  = type.GenerateData();
   26225 	const std::vector<GLubyte>& chichi_data = type.GenerateData();
   26226 	const std::vector<GLubyte>& vegeta_data = type.GenerateData();
   26227 	const std::vector<GLubyte>& trunks_data = type.GenerateData();
   26228 	const std::vector<GLubyte>& bra_data	= type.GenerateData();
   26229 	const std::vector<GLubyte>& bulma_data  = type.GenerateData();
   26230 
   26231 	const GLuint comp_size = Utils::Type::GetTypeSize(type.m_basic_type);
   26232 	const GLuint type_size = static_cast<GLuint>(gohan_data.size());
   26233 
   26234 	/* Uniform data */
   26235 	uniform.m_initial_data.resize(8 * type_size);
   26236 	memcpy(&uniform.m_initial_data[0] + 0 * type_size, &goku_data[0], type_size);
   26237 	memcpy(&uniform.m_initial_data[0] + 1 * type_size, &gohan_data[0], type_size);
   26238 	memcpy(&uniform.m_initial_data[0] + 2 * type_size, &goten_data[0], type_size);
   26239 	memcpy(&uniform.m_initial_data[0] + 3 * type_size, &chichi_data[0], type_size);
   26240 	memcpy(&uniform.m_initial_data[0] + 4 * type_size, &vegeta_data[0], type_size);
   26241 	memcpy(&uniform.m_initial_data[0] + 5 * type_size, &trunks_data[0], type_size);
   26242 	memcpy(&uniform.m_initial_data[0] + 6 * type_size, &bra_data[0], type_size);
   26243 	memcpy(&uniform.m_initial_data[0] + 7 * type_size, &bulma_data[0], type_size);
   26244 
   26245 	/* XFB data */
   26246 	xfb.m_initial_data.resize(8 * type_size);
   26247 	xfb.m_expected_data.resize(8 * type_size);
   26248 
   26249 	for (GLuint i = 0; i < 8 * type_size; ++i)
   26250 	{
   26251 		xfb.m_initial_data[i]  = (glw::GLubyte)i;
   26252 		xfb.m_expected_data[i] = (glw::GLubyte)i;
   26253 	}
   26254 
   26255 	/* goku - x, z - 32 */
   26256 	memcpy(&xfb.m_expected_data[0] + 2 * type_size + 0 * comp_size, &goku_data[0] + 0 * comp_size, comp_size);
   26257 	memcpy(&xfb.m_expected_data[0] + 2 * type_size + 2 * comp_size, &goku_data[0] + 2 * comp_size, comp_size);
   26258 
   26259 	/* gohan - y, w - 0 */
   26260 	memcpy(&xfb.m_expected_data[0] + 0 * type_size + 1 * comp_size, &gohan_data[0] + 1 * comp_size, comp_size);
   26261 	memcpy(&xfb.m_expected_data[0] + 0 * type_size + 3 * comp_size, &gohan_data[0] + 3 * comp_size, comp_size);
   26262 
   26263 	/* goten - x, y - 16 */
   26264 	memcpy(&xfb.m_expected_data[0] + 1 * type_size + 0 * comp_size, &goten_data[0] + 0 * comp_size, comp_size);
   26265 	memcpy(&xfb.m_expected_data[0] + 1 * type_size + 1 * comp_size, &goten_data[0] + 1 * comp_size, comp_size);
   26266 
   26267 	/* chichi - z, w - 48 */
   26268 	memcpy(&xfb.m_expected_data[0] + 3 * type_size + 2 * comp_size, &chichi_data[0] + 2 * comp_size, comp_size);
   26269 	memcpy(&xfb.m_expected_data[0] + 3 * type_size + 3 * comp_size, &chichi_data[0] + 3 * comp_size, comp_size);
   26270 
   26271 	/* vegeta - x - 112 */
   26272 	memcpy(&xfb.m_expected_data[0] + 7 * type_size + 0 * comp_size, &vegeta_data[0] + 0 * comp_size, comp_size);
   26273 
   26274 	/* trunks - y - 96 */
   26275 	memcpy(&xfb.m_expected_data[0] + 6 * type_size + 1 * comp_size, &trunks_data[0] + 1 * comp_size, comp_size);
   26276 
   26277 	/* bra - z - 80 */
   26278 	memcpy(&xfb.m_expected_data[0] + 5 * type_size + 2 * comp_size, &bra_data[0] + 2 * comp_size, comp_size);
   26279 
   26280 	/* bulma - w - 64 */
   26281 	memcpy(&xfb.m_expected_data[0] + 4 * type_size + 3 * comp_size, &bulma_data[0] + 3 * comp_size, comp_size);
   26282 }
   26283 
   26284 /** Get body of main function for given shader stage
   26285  *
   26286  * @param test_case_index  Index of test case
   26287  * @param stage            Shader stage
   26288  * @param out_assignments  Set to empty
   26289  * @param out_calculations Set to empty
   26290  **/
   26291 void XFBCaptureInactiveOutputComponentTest::getShaderBody(GLuint test_case_index, Utils::Shader::STAGES stage,
   26292 														  std::string& out_assignments, std::string& out_calculations)
   26293 {
   26294 	out_calculations = "";
   26295 
   26296 	static const GLchar* vs_tes_gs = "    goku.x    = uni_goku.x   ;\n"
   26297 									 "    goku.z    = uni_goku.z   ;\n"
   26298 									 "    gohan.y   = uni_gohan.y  ;\n"
   26299 									 "    gohan.w   = uni_gohan.w  ;\n"
   26300 									 "    goten.x   = uni_goten.x  ;\n"
   26301 									 "    goten.y   = uni_goten.y  ;\n"
   26302 									 "    chichi.z  = uni_chichi.z ;\n"
   26303 									 "    chichi.w  = uni_chichi.w ;\n"
   26304 									 "    vegeta.x  = uni_vegeta.x ;\n"
   26305 									 "    trunks.y  = uni_trunks.y ;\n"
   26306 									 "    bra.z     = uni_bra.z    ;\n"
   26307 									 "    bulma.w   = uni_bulma.w  ;\n";
   26308 	static const GLchar* fs = "    fs_out = goku + gohan + goten + chichi + vegeta + trunks + bra + bulma;\n";
   26309 
   26310 	const GLchar* assignments = "";
   26311 
   26312 	switch (stage)
   26313 	{
   26314 	case Utils::Shader::FRAGMENT:
   26315 		assignments = fs;
   26316 		break;
   26317 
   26318 	case Utils::Shader::GEOMETRY:
   26319 		if (TEST_GS == test_case_index)
   26320 		{
   26321 			assignments = vs_tes_gs;
   26322 		}
   26323 		break;
   26324 
   26325 	case Utils::Shader::TESS_CTRL:
   26326 		break;
   26327 
   26328 	case Utils::Shader::TESS_EVAL:
   26329 		if (TEST_TES == test_case_index)
   26330 		{
   26331 			assignments = vs_tes_gs;
   26332 		}
   26333 		break;
   26334 
   26335 	case Utils::Shader::VERTEX:
   26336 		if (TEST_VS == test_case_index)
   26337 		{
   26338 			assignments = vs_tes_gs;
   26339 		}
   26340 		break;
   26341 
   26342 	default:
   26343 		TCU_FAIL("Invalid enum");
   26344 	}
   26345 
   26346 	out_assignments = assignments;
   26347 }
   26348 
   26349 /** Get interface of shader
   26350  *
   26351  * @param test_case_index  Index of test case
   26352  * @param stage            Shader stage
   26353  * @param out_interface    Set to ""
   26354  **/
   26355 void XFBCaptureInactiveOutputComponentTest::getShaderInterface(GLuint test_case_index, Utils::Shader::STAGES stage,
   26356 															   std::string& out_interface)
   26357 {
   26358 	static const GLchar* vs_tes_gs = "const uint sizeof_type = 16;\n"
   26359 									 "\n"
   26360 									 "layout (xfb_offset = 2 * sizeof_type) out vec4 goku;\n"
   26361 									 "layout (xfb_offset = 0 * sizeof_type) out vec4 gohan;\n"
   26362 									 "layout (xfb_offset = 1 * sizeof_type) out vec4 goten;\n"
   26363 									 "layout (xfb_offset = 3 * sizeof_type) out vec4 chichi;\n"
   26364 									 "layout (xfb_offset = 7 * sizeof_type) out vec4 vegeta;\n"
   26365 									 "layout (xfb_offset = 6 * sizeof_type) out vec4 trunks;\n"
   26366 									 "layout (xfb_offset = 5 * sizeof_type) out vec4 bra;\n"
   26367 									 "layout (xfb_offset = 4 * sizeof_type) out vec4 bulma;\n"
   26368 									 "\n"
   26369 									 "layout(binding = 0) uniform block {\n"
   26370 									 "    vec4 uni_goku;\n"
   26371 									 "    vec4 uni_gohan;\n"
   26372 									 "    vec4 uni_goten;\n"
   26373 									 "    vec4 uni_chichi;\n"
   26374 									 "    vec4 uni_vegeta;\n"
   26375 									 "    vec4 uni_trunks;\n"
   26376 									 "    vec4 uni_bra;\n"
   26377 									 "    vec4 uni_bulma;\n"
   26378 									 "};\n";
   26379 	static const GLchar* fs = "in vec4 vegeta;\n"
   26380 							  "in vec4 trunks;\n"
   26381 							  "in vec4 bra;\n"
   26382 							  "in vec4 bulma;\n"
   26383 							  "in vec4 goku;\n"
   26384 							  "in vec4 gohan;\n"
   26385 							  "in vec4 goten;\n"
   26386 							  "in vec4 chichi;\n"
   26387 							  "\n"
   26388 							  "out vec4 fs_out;\n";
   26389 
   26390 	const GLchar* interface = "";
   26391 
   26392 	switch (stage)
   26393 	{
   26394 	case Utils::Shader::FRAGMENT:
   26395 		interface = fs;
   26396 		break;
   26397 
   26398 	case Utils::Shader::GEOMETRY:
   26399 		if (TEST_GS == test_case_index)
   26400 		{
   26401 			interface = vs_tes_gs;
   26402 		}
   26403 		break;
   26404 
   26405 	case Utils::Shader::TESS_CTRL:
   26406 		break;
   26407 
   26408 	case Utils::Shader::TESS_EVAL:
   26409 		if (TEST_TES == test_case_index)
   26410 		{
   26411 			interface = vs_tes_gs;
   26412 		}
   26413 		break;
   26414 
   26415 	case Utils::Shader::VERTEX:
   26416 		if (TEST_VS == test_case_index)
   26417 		{
   26418 			interface = vs_tes_gs;
   26419 		}
   26420 		break;
   26421 
   26422 	default:
   26423 		TCU_FAIL("Invalid enum");
   26424 	}
   26425 
   26426 	out_interface = interface;
   26427 }
   26428 
   26429 /** Get source code of shader
   26430  *
   26431  * @param test_case_index Index of test case
   26432  * @param stage           Shader stage
   26433  *
   26434  * @return Source
   26435  **/
   26436 std::string XFBCaptureInactiveOutputComponentTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   26437 {
   26438 	std::string source;
   26439 
   26440 	switch (test_case_index)
   26441 	{
   26442 	case TEST_VS:
   26443 		switch (stage)
   26444 		{
   26445 		case Utils::Shader::FRAGMENT:
   26446 		case Utils::Shader::VERTEX:
   26447 			source = BufferTestBase::getShaderSource(test_case_index, stage);
   26448 			break;
   26449 		default:
   26450 			break;
   26451 		}
   26452 		break;
   26453 
   26454 	case TEST_TES:
   26455 		switch (stage)
   26456 		{
   26457 		case Utils::Shader::FRAGMENT:
   26458 		case Utils::Shader::TESS_CTRL:
   26459 		case Utils::Shader::TESS_EVAL:
   26460 		case Utils::Shader::VERTEX:
   26461 			source = BufferTestBase::getShaderSource(test_case_index, stage);
   26462 			break;
   26463 		default:
   26464 			break;
   26465 		}
   26466 		break;
   26467 
   26468 	case TEST_GS:
   26469 		source = BufferTestBase::getShaderSource(test_case_index, stage);
   26470 		break;
   26471 
   26472 	default:
   26473 		TCU_FAIL("Invalid enum");
   26474 		break;
   26475 	}
   26476 
   26477 	/* */
   26478 	return source;
   26479 }
   26480 
   26481 /** Get name of test case
   26482  *
   26483  * @param test_case_index Index of test case
   26484  *
   26485  * @return Name of tested stage
   26486  **/
   26487 std::string XFBCaptureInactiveOutputComponentTest::getTestCaseName(glw::GLuint test_case_index)
   26488 {
   26489 	const GLchar* name = 0;
   26490 
   26491 	switch (test_case_index)
   26492 	{
   26493 	case TEST_VS:
   26494 		name = "vertex";
   26495 		break;
   26496 	case TEST_TES:
   26497 		name = "tessellation evaluation";
   26498 		break;
   26499 	case TEST_GS:
   26500 		name = "geometry";
   26501 		break;
   26502 	default:
   26503 		TCU_FAIL("Invalid enum");
   26504 	}
   26505 
   26506 	return name;
   26507 }
   26508 
   26509 /** Returns number of test cases
   26510  *
   26511  * @return TEST_MAX
   26512  **/
   26513 glw::GLuint XFBCaptureInactiveOutputComponentTest::getTestCaseNumber()
   26514 {
   26515 	return TEST_MAX;
   26516 }
   26517 
   26518 /** Verify contents of buffers
   26519  *
   26520  * @param buffers Collection of buffers to be verified
   26521  *
   26522  * @return true if everything is as expected, false otherwise
   26523  **/
   26524 bool XFBCaptureInactiveOutputComponentTest::verifyBuffers(bufferCollection& buffers)
   26525 {
   26526 	bool result = true;
   26527 
   26528 	bufferCollection::pair& pair	   = buffers.m_vector[1] /* xfb */;
   26529 	Utils::Buffer*			buffer	 = pair.m_buffer;
   26530 	bufferDescriptor*		descriptor = pair.m_descriptor;
   26531 
   26532 	/* Get pointer to contents of buffer */
   26533 	buffer->Bind();
   26534 	GLubyte* buffer_data = (GLubyte*)buffer->Map(Utils::Buffer::ReadOnly);
   26535 
   26536 	/* Get pointer to expected data */
   26537 	GLubyte* expected_data = (GLubyte*)&descriptor->m_expected_data[0];
   26538 
   26539 	/* Compare */
   26540 	static const GLuint comp_size = 4;
   26541 	static const GLuint vec4_size = 16;
   26542 
   26543 	int res_goku_x =
   26544 		memcmp(buffer_data + 2 * vec4_size + 0 * comp_size, expected_data + 2 * vec4_size + 0 * comp_size, comp_size);
   26545 	int res_goku_z =
   26546 		memcmp(buffer_data + 2 * vec4_size + 2 * comp_size, expected_data + 2 * vec4_size + 2 * comp_size, comp_size);
   26547 
   26548 	int res_gohan_y =
   26549 		memcmp(buffer_data + 0 * vec4_size + 1 * comp_size, expected_data + 0 * vec4_size + 1 * comp_size, comp_size);
   26550 	int res_gohan_w =
   26551 		memcmp(buffer_data + 0 * vec4_size + 3 * comp_size, expected_data + 0 * vec4_size + 3 * comp_size, comp_size);
   26552 
   26553 	int res_goten_x =
   26554 		memcmp(buffer_data + 1 * vec4_size + 0 * comp_size, expected_data + 1 * vec4_size + 0 * comp_size, comp_size);
   26555 	int res_goten_y =
   26556 		memcmp(buffer_data + 1 * vec4_size + 1 * comp_size, expected_data + 1 * vec4_size + 1 * comp_size, comp_size);
   26557 
   26558 	int res_chichi_z =
   26559 		memcmp(buffer_data + 3 * vec4_size + 2 * comp_size, expected_data + 3 * vec4_size + 2 * comp_size, comp_size);
   26560 	int res_chichi_w =
   26561 		memcmp(buffer_data + 3 * vec4_size + 3 * comp_size, expected_data + 3 * vec4_size + 3 * comp_size, comp_size);
   26562 
   26563 	int res_vegeta_x =
   26564 		memcmp(buffer_data + 7 * vec4_size + 0 * comp_size, expected_data + 7 * vec4_size + 0 * comp_size, comp_size);
   26565 
   26566 	int res_trunks_y =
   26567 		memcmp(buffer_data + 6 * vec4_size + 1 * comp_size, expected_data + 6 * vec4_size + 1 * comp_size, comp_size);
   26568 
   26569 	int res_bra_z =
   26570 		memcmp(buffer_data + 5 * vec4_size + 2 * comp_size, expected_data + 5 * vec4_size + 2 * comp_size, comp_size);
   26571 
   26572 	int res_bulma_w =
   26573 		memcmp(buffer_data + 4 * vec4_size + 3 * comp_size, expected_data + 4 * vec4_size + 3 * comp_size, comp_size);
   26574 
   26575 	if ((0 != res_goku_x) || (0 != res_goku_z) || (0 != res_gohan_y) || (0 != res_gohan_w) || (0 != res_goten_x) ||
   26576 		(0 != res_goten_y) || (0 != res_chichi_z) || (0 != res_chichi_w) || (0 != res_vegeta_x) ||
   26577 		(0 != res_trunks_y) || (0 != res_bra_z) || (0 != res_bulma_w))
   26578 	{
   26579 		m_context.getTestContext().getLog()
   26580 			<< tcu::TestLog::Message << "Invalid result. Buffer: " << Utils::Buffer::GetBufferName(descriptor->m_target)
   26581 			<< ". Index: " << descriptor->m_index << tcu::TestLog::EndMessage;
   26582 
   26583 		result = false;
   26584 	}
   26585 
   26586 	/* Release buffer mapping */
   26587 	buffer->UnMap();
   26588 
   26589 	return result;
   26590 }
   26591 
   26592 /** Constructor
   26593  *
   26594  * @param context Test context
   26595  **/
   26596 XFBCaptureInactiveOutputBlockMemberTest::XFBCaptureInactiveOutputBlockMemberTest(deqp::Context& context)
   26597 	: BufferTestBase(context, "xfb_capture_inactive_output_block_member",
   26598 					 "Test verifies that inactive block members are captured")
   26599 {
   26600 	/* Nothing to be done here */
   26601 }
   26602 
   26603 /** Execute drawArrays for single vertex
   26604  *
   26605  * @param test_case_index
   26606  *
   26607  * @return true
   26608  **/
   26609 bool XFBCaptureInactiveOutputBlockMemberTest::executeDrawCall(bool /* tesEnabled */, GLuint test_case_index)
   26610 {
   26611 	const Functions& gl				= m_context.getRenderContext().getFunctions();
   26612 	GLenum			 primitive_type = GL_PATCHES;
   26613 
   26614 	if (TEST_VS == test_case_index)
   26615 	{
   26616 		primitive_type = GL_POINTS;
   26617 	}
   26618 
   26619 	gl.disable(GL_RASTERIZER_DISCARD);
   26620 	GLU_EXPECT_NO_ERROR(gl.getError(), "Disable");
   26621 
   26622 	gl.beginTransformFeedback(GL_POINTS);
   26623 	GLU_EXPECT_NO_ERROR(gl.getError(), "BeginTransformFeedback");
   26624 
   26625 	gl.drawArrays(primitive_type, 0 /* first */, 1 /* count */);
   26626 	GLU_EXPECT_NO_ERROR(gl.getError(), "DrawArrays");
   26627 
   26628 	gl.endTransformFeedback();
   26629 	GLU_EXPECT_NO_ERROR(gl.getError(), "EndTransformFeedback");
   26630 
   26631 	return true;
   26632 }
   26633 
   26634 /** Get descriptors of buffers necessary for test
   26635  *
   26636  * @param ignored
   26637  * @param out_descriptors Descriptors of buffers used by test
   26638  **/
   26639 void XFBCaptureInactiveOutputBlockMemberTest::getBufferDescriptors(glw::GLuint /* test_case_index */,
   26640 																   bufferDescriptor::Vector& out_descriptors)
   26641 {
   26642 	const Utils::Type& type = Utils::Type::vec4;
   26643 
   26644 	/* Test needs single uniform and xfb */
   26645 	out_descriptors.resize(2);
   26646 
   26647 	/* Get references */
   26648 	bufferDescriptor& uniform = out_descriptors[0];
   26649 	bufferDescriptor& xfb	 = out_descriptors[1];
   26650 
   26651 	/* Index */
   26652 	uniform.m_index = 0;
   26653 	xfb.m_index		= 0;
   26654 
   26655 	/* Target */
   26656 	uniform.m_target = Utils::Buffer::Uniform;
   26657 	xfb.m_target	 = Utils::Buffer::Transform_feedback;
   26658 
   26659 	/* Data */
   26660 	const std::vector<GLubyte>& gohan_data  = type.GenerateData();
   26661 	const std::vector<GLubyte>& chichi_data = type.GenerateData();
   26662 
   26663 	const GLuint type_size = static_cast<GLuint>(gohan_data.size());
   26664 
   26665 	/* Uniform data */
   26666 	uniform.m_initial_data.resize(2 * type_size);
   26667 	memcpy(&uniform.m_initial_data[0] + 0, &gohan_data[0], type_size);
   26668 	memcpy(&uniform.m_initial_data[0] + type_size, &chichi_data[0], type_size);
   26669 
   26670 	/* XFB data */
   26671 	xfb.m_initial_data.resize(4 * type_size);
   26672 	xfb.m_expected_data.resize(4 * type_size);
   26673 
   26674 	for (GLuint i = 0; i < 4 * type_size; ++i)
   26675 	{
   26676 		xfb.m_initial_data[i]  = (glw::GLubyte)i;
   26677 		xfb.m_expected_data[i] = (glw::GLubyte)i;
   26678 	}
   26679 
   26680 	memcpy(&xfb.m_expected_data[0] + 1 * type_size, &gohan_data[0], type_size);
   26681 	memcpy(&xfb.m_expected_data[0] + 3 * type_size, &chichi_data[0], type_size);
   26682 }
   26683 
   26684 /** Get body of main function for given shader stage
   26685  *
   26686  * @param test_case_index  Index of test case
   26687  * @param stage            Shader stage
   26688  * @param out_assignments  Set to empty
   26689  * @param out_calculations Set to empty
   26690  **/
   26691 void XFBCaptureInactiveOutputBlockMemberTest::getShaderBody(GLuint test_case_index, Utils::Shader::STAGES stage,
   26692 															std::string& out_assignments, std::string& out_calculations)
   26693 {
   26694 	out_calculations = "";
   26695 
   26696 	static const GLchar* vs_tes_gs = "    chichi = uni_chichi;\n"
   26697 									 "    gohan  = uni_gohan;\n";
   26698 	static const GLchar* fs = "    fs_out = goten + gohan + chichi;\n";
   26699 
   26700 	const GLchar* assignments = "";
   26701 
   26702 	switch (stage)
   26703 	{
   26704 	case Utils::Shader::FRAGMENT:
   26705 		assignments = fs;
   26706 		break;
   26707 
   26708 	case Utils::Shader::GEOMETRY:
   26709 		if (TEST_GS == test_case_index)
   26710 		{
   26711 			assignments = vs_tes_gs;
   26712 		}
   26713 		break;
   26714 
   26715 	case Utils::Shader::TESS_CTRL:
   26716 		break;
   26717 
   26718 	case Utils::Shader::TESS_EVAL:
   26719 		if (TEST_TES == test_case_index)
   26720 		{
   26721 			assignments = vs_tes_gs;
   26722 		}
   26723 		break;
   26724 
   26725 	case Utils::Shader::VERTEX:
   26726 		if (TEST_VS == test_case_index)
   26727 		{
   26728 			assignments = vs_tes_gs;
   26729 		}
   26730 		break;
   26731 
   26732 	default:
   26733 		TCU_FAIL("Invalid enum");
   26734 	}
   26735 
   26736 	out_assignments = assignments;
   26737 }
   26738 
   26739 /** Get interface of shader
   26740  *
   26741  * @param test_case_index  Index of test case
   26742  * @param stage            Shader stage
   26743  * @param out_interface    Set to ""
   26744  **/
   26745 void XFBCaptureInactiveOutputBlockMemberTest::getShaderInterface(GLuint test_case_index, Utils::Shader::STAGES stage,
   26746 																 std::string& out_interface)
   26747 {
   26748 	static const GLchar* vs_tes_gs = "const uint sizeof_type = 16;\n"
   26749 									 "\n"
   26750 									 "layout (xfb_offset = 1 * sizeof_type) out Goku {\n"
   26751 									 "    vec4 gohan;\n"
   26752 									 "    vec4 goten;\n"
   26753 									 "    vec4 chichi;\n"
   26754 									 "};\n"
   26755 									 "\n"
   26756 									 "layout(binding = 0) uniform block {\n"
   26757 									 "    vec4 uni_gohan;\n"
   26758 									 "    vec4 uni_chichi;\n"
   26759 									 "};\n";
   26760 	static const GLchar* fs = "in Goku {\n"
   26761 							  "    vec4 gohan;\n"
   26762 							  "    vec4 goten;\n"
   26763 							  "    vec4 chichi;\n"
   26764 							  "};\n"
   26765 							  "out vec4 fs_out;\n";
   26766 
   26767 	const GLchar* interface = "";
   26768 
   26769 	switch (stage)
   26770 	{
   26771 	case Utils::Shader::FRAGMENT:
   26772 		interface = fs;
   26773 		break;
   26774 
   26775 	case Utils::Shader::GEOMETRY:
   26776 		if (TEST_GS == test_case_index)
   26777 		{
   26778 			interface = vs_tes_gs;
   26779 		}
   26780 		break;
   26781 
   26782 	case Utils::Shader::TESS_CTRL:
   26783 		break;
   26784 
   26785 	case Utils::Shader::TESS_EVAL:
   26786 		if (TEST_TES == test_case_index)
   26787 		{
   26788 			interface = vs_tes_gs;
   26789 		}
   26790 		break;
   26791 
   26792 	case Utils::Shader::VERTEX:
   26793 		if (TEST_VS == test_case_index)
   26794 		{
   26795 			interface = vs_tes_gs;
   26796 		}
   26797 		break;
   26798 
   26799 	default:
   26800 		TCU_FAIL("Invalid enum");
   26801 	}
   26802 
   26803 	out_interface = interface;
   26804 }
   26805 
   26806 /** Get source code of shader
   26807  *
   26808  * @param test_case_index Index of test case
   26809  * @param stage           Shader stage
   26810  *
   26811  * @return Source
   26812  **/
   26813 std::string XFBCaptureInactiveOutputBlockMemberTest::getShaderSource(GLuint				   test_case_index,
   26814 																	 Utils::Shader::STAGES stage)
   26815 {
   26816 	std::string source;
   26817 
   26818 	switch (test_case_index)
   26819 	{
   26820 	case TEST_VS:
   26821 		switch (stage)
   26822 		{
   26823 		case Utils::Shader::FRAGMENT:
   26824 		case Utils::Shader::VERTEX:
   26825 			source = BufferTestBase::getShaderSource(test_case_index, stage);
   26826 			break;
   26827 		default:
   26828 			break;
   26829 		}
   26830 		break;
   26831 
   26832 	case TEST_TES:
   26833 		switch (stage)
   26834 		{
   26835 		case Utils::Shader::FRAGMENT:
   26836 		case Utils::Shader::TESS_CTRL:
   26837 		case Utils::Shader::TESS_EVAL:
   26838 		case Utils::Shader::VERTEX:
   26839 			source = BufferTestBase::getShaderSource(test_case_index, stage);
   26840 			break;
   26841 		default:
   26842 			break;
   26843 		}
   26844 		break;
   26845 
   26846 	case TEST_GS:
   26847 		source = BufferTestBase::getShaderSource(test_case_index, stage);
   26848 		break;
   26849 
   26850 	default:
   26851 		TCU_FAIL("Invalid enum");
   26852 		break;
   26853 	}
   26854 
   26855 	/* */
   26856 	return source;
   26857 }
   26858 
   26859 /** Get name of test case
   26860  *
   26861  * @param test_case_index Index of test case
   26862  *
   26863  * @return Name of tested stage
   26864  **/
   26865 std::string XFBCaptureInactiveOutputBlockMemberTest::getTestCaseName(glw::GLuint test_case_index)
   26866 {
   26867 	const GLchar* name = 0;
   26868 
   26869 	switch (test_case_index)
   26870 	{
   26871 	case TEST_VS:
   26872 		name = "vertex";
   26873 		break;
   26874 	case TEST_TES:
   26875 		name = "tessellation evaluation";
   26876 		break;
   26877 	case TEST_GS:
   26878 		name = "geometry";
   26879 		break;
   26880 	default:
   26881 		TCU_FAIL("Invalid enum");
   26882 	}
   26883 
   26884 	return name;
   26885 }
   26886 
   26887 /** Returns number of test cases
   26888  *
   26889  * @return TEST_MAX
   26890  **/
   26891 glw::GLuint XFBCaptureInactiveOutputBlockMemberTest::getTestCaseNumber()
   26892 {
   26893 	return TEST_MAX;
   26894 }
   26895 
   26896 /** Verify contents of buffers
   26897  *
   26898  * @param buffers Collection of buffers to be verified
   26899  *
   26900  * @return true if everything is as expected, false otherwise
   26901  **/
   26902 bool XFBCaptureInactiveOutputBlockMemberTest::verifyBuffers(bufferCollection& buffers)
   26903 {
   26904 	bool result = true;
   26905 
   26906 	bufferCollection::pair& pair	   = buffers.m_vector[1] /* xfb */;
   26907 	Utils::Buffer*			buffer	 = pair.m_buffer;
   26908 	bufferDescriptor*		descriptor = pair.m_descriptor;
   26909 
   26910 	/* Get pointer to contents of buffer */
   26911 	buffer->Bind();
   26912 	GLubyte* buffer_data = (GLubyte*)buffer->Map(Utils::Buffer::ReadOnly);
   26913 
   26914 	/* Get pointer to expected data */
   26915 	GLubyte* expected_data = (GLubyte*)&descriptor->m_expected_data[0];
   26916 
   26917 	/* Compare */
   26918 	static const GLuint vec4_size = 16;
   26919 
   26920 	int res_before = memcmp(buffer_data, expected_data, vec4_size);
   26921 	int res_gohan  = memcmp(buffer_data + 1 * vec4_size, expected_data + 1 * vec4_size, vec4_size);
   26922 	int res_chichi = memcmp(buffer_data + 3 * vec4_size, expected_data + 3 * vec4_size, vec4_size);
   26923 
   26924 	if ((0 != res_before) || (0 != res_gohan) || (0 != res_chichi))
   26925 	{
   26926 		m_context.getTestContext().getLog()
   26927 			<< tcu::TestLog::Message << "Invalid result. Buffer: " << Utils::Buffer::GetBufferName(descriptor->m_target)
   26928 			<< ". Index: " << descriptor->m_index << tcu::TestLog::EndMessage;
   26929 
   26930 		result = false;
   26931 	}
   26932 
   26933 	/* Release buffer mapping */
   26934 	buffer->UnMap();
   26935 
   26936 	return result;
   26937 }
   26938 
   26939 /** Constructor
   26940  *
   26941  * @param context Test context
   26942  **/
   26943 XFBCaptureStructTest::XFBCaptureStructTest(deqp::Context& context)
   26944 	: BufferTestBase(context, "xfb_capture_struct", "Test verifies that inactive structure members are captured")
   26945 {
   26946 	/* Nothing to be done here */
   26947 }
   26948 
   26949 /** Execute drawArrays for single vertex
   26950  *
   26951  * @param test_case_index
   26952  *
   26953  * @return true
   26954  **/
   26955 bool XFBCaptureStructTest::executeDrawCall(bool /* tesEnabled */, GLuint test_case_index)
   26956 {
   26957 	const Functions& gl				= m_context.getRenderContext().getFunctions();
   26958 	GLenum			 primitive_type = GL_PATCHES;
   26959 
   26960 	if (TEST_VS == test_case_index)
   26961 	{
   26962 		primitive_type = GL_POINTS;
   26963 	}
   26964 
   26965 	gl.disable(GL_RASTERIZER_DISCARD);
   26966 	GLU_EXPECT_NO_ERROR(gl.getError(), "Disable");
   26967 
   26968 	gl.beginTransformFeedback(GL_POINTS);
   26969 	GLU_EXPECT_NO_ERROR(gl.getError(), "BeginTransformFeedback");
   26970 
   26971 	gl.drawArrays(primitive_type, 0 /* first */, 1 /* count */);
   26972 	GLU_EXPECT_NO_ERROR(gl.getError(), "DrawArrays");
   26973 
   26974 	gl.endTransformFeedback();
   26975 	GLU_EXPECT_NO_ERROR(gl.getError(), "EndTransformFeedback");
   26976 
   26977 	return true;
   26978 }
   26979 
   26980 /** Get descriptors of buffers necessary for test
   26981  *
   26982  * @param ignored
   26983  * @param out_descriptors Descriptors of buffers used by test
   26984  **/
   26985 void XFBCaptureStructTest::getBufferDescriptors(glw::GLuint /* test_case_index */,
   26986 												bufferDescriptor::Vector& out_descriptors)
   26987 {
   26988 	const Utils::Type& type = Utils::Type::vec4;
   26989 
   26990 	/* Test needs single uniform and xfb */
   26991 	out_descriptors.resize(2);
   26992 
   26993 	/* Get references */
   26994 	bufferDescriptor& uniform = out_descriptors[0];
   26995 	bufferDescriptor& xfb	 = out_descriptors[1];
   26996 
   26997 	/* Index */
   26998 	uniform.m_index = 0;
   26999 	xfb.m_index		= 0;
   27000 
   27001 	/* Target */
   27002 	uniform.m_target = Utils::Buffer::Uniform;
   27003 	xfb.m_target	 = Utils::Buffer::Transform_feedback;
   27004 
   27005 	/* Data */
   27006 	const std::vector<GLubyte>& gohan_data  = type.GenerateData();
   27007 	const std::vector<GLubyte>& chichi_data = type.GenerateData();
   27008 
   27009 	const GLuint type_size = static_cast<GLuint>(gohan_data.size());
   27010 
   27011 	/* Uniform data */
   27012 	uniform.m_initial_data.resize(2 * type_size);
   27013 	memcpy(&uniform.m_initial_data[0] + 0, &gohan_data[0], type_size);
   27014 	memcpy(&uniform.m_initial_data[0] + type_size, &chichi_data[0], type_size);
   27015 
   27016 	/* XFB data */
   27017 	xfb.m_initial_data.resize(4 * type_size);
   27018 	xfb.m_expected_data.resize(4 * type_size);
   27019 
   27020 	for (GLuint i = 0; i < 4 * type_size; ++i)
   27021 	{
   27022 		xfb.m_initial_data[i]  = (glw::GLubyte)i;
   27023 		xfb.m_expected_data[i] = (glw::GLubyte)i;
   27024 	}
   27025 
   27026 	memcpy(&xfb.m_expected_data[0] + 1 * type_size, &gohan_data[0], type_size);
   27027 	memcpy(&xfb.m_expected_data[0] + 3 * type_size, &chichi_data[0], type_size);
   27028 }
   27029 
   27030 /** Get body of main function for given shader stage
   27031  *
   27032  * @param test_case_index  Index of test case
   27033  * @param stage            Shader stage
   27034  * @param out_assignments  Set to empty
   27035  * @param out_calculations Set to empty
   27036  **/
   27037 void XFBCaptureStructTest::getShaderBody(GLuint test_case_index, Utils::Shader::STAGES stage,
   27038 										 std::string& out_assignments, std::string& out_calculations)
   27039 {
   27040 	out_calculations = "";
   27041 
   27042 	static const GLchar* vs_tes_gs = "    goku.chichi = uni_chichi;\n"
   27043 									 "    goku.gohan  = uni_gohan;\n";
   27044 	static const GLchar* fs = "    fs_out = goku.goten + goku.gohan + goku.chichi;\n";
   27045 
   27046 	const GLchar* assignments = "";
   27047 
   27048 	switch (stage)
   27049 	{
   27050 	case Utils::Shader::FRAGMENT:
   27051 		assignments = fs;
   27052 		break;
   27053 
   27054 	case Utils::Shader::GEOMETRY:
   27055 		if (TEST_GS == test_case_index)
   27056 		{
   27057 			assignments = vs_tes_gs;
   27058 		}
   27059 		break;
   27060 
   27061 	case Utils::Shader::TESS_CTRL:
   27062 		break;
   27063 
   27064 	case Utils::Shader::TESS_EVAL:
   27065 		if (TEST_TES == test_case_index)
   27066 		{
   27067 			assignments = vs_tes_gs;
   27068 		}
   27069 		break;
   27070 
   27071 	case Utils::Shader::VERTEX:
   27072 		if (TEST_VS == test_case_index)
   27073 		{
   27074 			assignments = vs_tes_gs;
   27075 		}
   27076 		break;
   27077 
   27078 	default:
   27079 		TCU_FAIL("Invalid enum");
   27080 	}
   27081 
   27082 	out_assignments = assignments;
   27083 }
   27084 
   27085 /** Get interface of shader
   27086  *
   27087  * @param test_case_index  Index of test case
   27088  * @param stage            Shader stage
   27089  * @param out_interface    Set to ""
   27090  **/
   27091 void XFBCaptureStructTest::getShaderInterface(GLuint test_case_index, Utils::Shader::STAGES stage,
   27092 											  std::string& out_interface)
   27093 {
   27094 	static const GLchar* vs_tes_gs = "const uint sizeof_type = 16;\n"
   27095 									 "\n"
   27096 									 "struct Goku {\n"
   27097 									 "    vec4 gohan;\n"
   27098 									 "    vec4 goten;\n"
   27099 									 "    vec4 chichi;\n"
   27100 									 "};\n"
   27101 									 "\n"
   27102 									 "layout (xfb_offset = sizeof_type) out Goku goku;\n"
   27103 									 "\n"
   27104 									 "layout(binding = 0, std140) uniform block {\n"
   27105 									 "    vec4 uni_gohan;\n"
   27106 									 "    vec4 uni_chichi;\n"
   27107 									 "};\n";
   27108 	static const GLchar* fs = "struct Goku {\n"
   27109 							  "    vec4 gohan;\n"
   27110 							  "    vec4 goten;\n"
   27111 							  "    vec4 chichi;\n"
   27112 							  "};\n"
   27113 							  "\n"
   27114 							  "in Goku goku;\n"
   27115 							  "\n"
   27116 							  "out vec4 fs_out;\n";
   27117 
   27118 	const GLchar* interface = "";
   27119 
   27120 	switch (stage)
   27121 	{
   27122 	case Utils::Shader::FRAGMENT:
   27123 		interface = fs;
   27124 		break;
   27125 
   27126 	case Utils::Shader::GEOMETRY:
   27127 		if (TEST_GS == test_case_index)
   27128 		{
   27129 			interface = vs_tes_gs;
   27130 		}
   27131 		break;
   27132 
   27133 	case Utils::Shader::TESS_CTRL:
   27134 		break;
   27135 
   27136 	case Utils::Shader::TESS_EVAL:
   27137 		if (TEST_TES == test_case_index)
   27138 		{
   27139 			interface = vs_tes_gs;
   27140 		}
   27141 		break;
   27142 
   27143 	case Utils::Shader::VERTEX:
   27144 		if (TEST_VS == test_case_index)
   27145 		{
   27146 			interface = vs_tes_gs;
   27147 		}
   27148 		break;
   27149 
   27150 	default:
   27151 		TCU_FAIL("Invalid enum");
   27152 	}
   27153 
   27154 	out_interface = interface;
   27155 }
   27156 
   27157 /** Get source code of shader
   27158  *
   27159  * @param test_case_index Index of test case
   27160  * @param stage           Shader stage
   27161  *
   27162  * @return Source
   27163  **/
   27164 std::string XFBCaptureStructTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   27165 {
   27166 	std::string source;
   27167 
   27168 	switch (test_case_index)
   27169 	{
   27170 	case TEST_VS:
   27171 		switch (stage)
   27172 		{
   27173 		case Utils::Shader::FRAGMENT:
   27174 		case Utils::Shader::VERTEX:
   27175 			source = BufferTestBase::getShaderSource(test_case_index, stage);
   27176 			break;
   27177 		default:
   27178 			break;
   27179 		}
   27180 		break;
   27181 
   27182 	case TEST_TES:
   27183 		switch (stage)
   27184 		{
   27185 		case Utils::Shader::FRAGMENT:
   27186 		case Utils::Shader::TESS_CTRL:
   27187 		case Utils::Shader::TESS_EVAL:
   27188 		case Utils::Shader::VERTEX:
   27189 			source = BufferTestBase::getShaderSource(test_case_index, stage);
   27190 			break;
   27191 		default:
   27192 			break;
   27193 		}
   27194 		break;
   27195 
   27196 	case TEST_GS:
   27197 		source = BufferTestBase::getShaderSource(test_case_index, stage);
   27198 		break;
   27199 
   27200 	default:
   27201 		TCU_FAIL("Invalid enum");
   27202 		break;
   27203 	}
   27204 
   27205 	/* */
   27206 	return source;
   27207 }
   27208 
   27209 /** Get name of test case
   27210  *
   27211  * @param test_case_index Index of test case
   27212  *
   27213  * @return Name of tested stage
   27214  **/
   27215 std::string XFBCaptureStructTest::getTestCaseName(glw::GLuint test_case_index)
   27216 {
   27217 	const GLchar* name = 0;
   27218 
   27219 	switch (test_case_index)
   27220 	{
   27221 	case TEST_VS:
   27222 		name = "vertex";
   27223 		break;
   27224 	case TEST_TES:
   27225 		name = "tessellation evaluation";
   27226 		break;
   27227 	case TEST_GS:
   27228 		name = "geometry";
   27229 		break;
   27230 	default:
   27231 		TCU_FAIL("Invalid enum");
   27232 	}
   27233 
   27234 	return name;
   27235 }
   27236 
   27237 /** Returns number of test cases
   27238  *
   27239  * @return TEST_MAX
   27240  **/
   27241 glw::GLuint XFBCaptureStructTest::getTestCaseNumber()
   27242 {
   27243 	return TEST_MAX;
   27244 }
   27245 
   27246 /** Verify contents of buffers
   27247  *
   27248  * @param buffers Collection of buffers to be verified
   27249  *
   27250  * @return true if everything is as expected, false otherwise
   27251  **/
   27252 bool XFBCaptureStructTest::verifyBuffers(bufferCollection& buffers)
   27253 {
   27254 	bool result = true;
   27255 
   27256 	bufferCollection::pair& pair	   = buffers.m_vector[1] /* xfb */;
   27257 	Utils::Buffer*			buffer	 = pair.m_buffer;
   27258 	bufferDescriptor*		descriptor = pair.m_descriptor;
   27259 
   27260 	/* Get pointer to contents of buffer */
   27261 	buffer->Bind();
   27262 	GLubyte* buffer_data = (GLubyte*)buffer->Map(Utils::Buffer::ReadOnly);
   27263 
   27264 	/* Get pointer to expected data */
   27265 	GLubyte* expected_data = (GLubyte*)&descriptor->m_expected_data[0];
   27266 
   27267 	/* Compare */
   27268 	static const GLuint vec4_size = 16;
   27269 
   27270 	int res_before = memcmp(buffer_data, expected_data, vec4_size);
   27271 	int res_gohan  = memcmp(buffer_data + 1 * vec4_size, expected_data + 1 * vec4_size, vec4_size);
   27272 	int res_chichi = memcmp(buffer_data + 3 * vec4_size, expected_data + 3 * vec4_size, vec4_size);
   27273 
   27274 	if ((0 != res_before) || (0 != res_gohan) || (0 != res_chichi))
   27275 	{
   27276 		m_context.getTestContext().getLog()
   27277 			<< tcu::TestLog::Message << "Invalid result. Buffer: " << Utils::Buffer::GetBufferName(descriptor->m_target)
   27278 			<< ". Index: " << descriptor->m_index << tcu::TestLog::EndMessage;
   27279 
   27280 		result = false;
   27281 	}
   27282 
   27283 	/* Release buffer mapping */
   27284 	buffer->UnMap();
   27285 
   27286 	return result;
   27287 }
   27288 
   27289 /** Constructor
   27290  *
   27291  * @param context Test framework context
   27292  **/
   27293 XFBCaptureUnsizedArrayTest::XFBCaptureUnsizedArrayTest(deqp::Context& context)
   27294 	: NegativeTestBase(context, "xfb_capture_unsized_array",
   27295 					   "Test verifies that compiler reports error when unsized array is qualified with xfb_offset")
   27296 {
   27297 }
   27298 
   27299 /** Source for given test case and stage
   27300  *
   27301  * @param test_case_index Index of test case
   27302  * @param stage           Shader stage
   27303  *
   27304  * @return Shader source
   27305  **/
   27306 std::string XFBCaptureUnsizedArrayTest::getShaderSource(GLuint test_case_index, Utils::Shader::STAGES stage)
   27307 {
   27308 	static const GLchar* var_definition = "layout (xfb_offset = 0) out vec4 gokuARRAY[];\n";
   27309 	static const GLchar* var_use		= "    gokuINDEX[0] = result / 2;\n";
   27310 	static const GLchar* fs				= "#version 430 core\n"
   27311 							  "#extension GL_ARB_enhanced_layouts : require\n"
   27312 							  "\n"
   27313 							  "in  vec4 gs_fs;\n"
   27314 							  "out vec4 fs_out;\n"
   27315 							  "\n"
   27316 							  "void main()\n"
   27317 							  "{\n"
   27318 							  "    fs_out = gs_fs;\n"
   27319 							  "}\n"
   27320 							  "\n";
   27321 	static const GLchar* gs_tested = "#version 430 core\n"
   27322 									 "#extension GL_ARB_enhanced_layouts : require\n"
   27323 									 "\n"
   27324 									 "layout(points)                           in;\n"
   27325 									 "layout(triangle_strip, max_vertices = 4) out;\n"
   27326 									 "\n"
   27327 									 "VAR_DEFINITION"
   27328 									 "\n"
   27329 									 "in  vec4 tes_gs[];\n"
   27330 									 "out vec4 gs_fs;\n"
   27331 									 "\n"
   27332 									 "void main()\n"
   27333 									 "{\n"
   27334 									 "    vec4 result = tes_gs[0];\n"
   27335 									 "\n"
   27336 									 "VARIABLE_USE"
   27337 									 "\n"
   27338 									 "    gs_fs = result;\n"
   27339 									 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
   27340 									 "    EmitVertex();\n"
   27341 									 "    gs_fs = result;\n"
   27342 									 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
   27343 									 "    EmitVertex();\n"
   27344 									 "    gs_fs = result;\n"
   27345 									 "    gl_Position  = vec4(1, -1, 0, 1);\n"
   27346 									 "    EmitVertex();\n"
   27347 									 "    gs_fs = result;\n"
   27348 									 "    gl_Position  = vec4(1, 1, 0, 1);\n"
   27349 									 "    EmitVertex();\n"
   27350 									 "}\n"
   27351 									 "\n";
   27352 	static const GLchar* tcs = "#version 430 core\n"
   27353 							   "#extension GL_ARB_enhanced_layouts : require\n"
   27354 							   "\n"
   27355 							   "layout(vertices = 1) out;\n"
   27356 							   "\n"
   27357 							   "in  vec4 vs_tcs[];\n"
   27358 							   "out vec4 tcs_tes[];\n"
   27359 							   "\n"
   27360 							   "void main()\n"
   27361 							   "{\n"
   27362 							   "\n"
   27363 							   "    tcs_tes[gl_InvocationID] = vs_tcs[gl_InvocationID];\n"
   27364 							   "\n"
   27365 							   "    gl_TessLevelOuter[0] = 1.0;\n"
   27366 							   "    gl_TessLevelOuter[1] = 1.0;\n"
   27367 							   "    gl_TessLevelOuter[2] = 1.0;\n"
   27368 							   "    gl_TessLevelOuter[3] = 1.0;\n"
   27369 							   "    gl_TessLevelInner[0] = 1.0;\n"
   27370 							   "    gl_TessLevelInner[1] = 1.0;\n"
   27371 							   "}\n"
   27372 							   "\n";
   27373 	static const GLchar* tcs_tested = "#version 430 core\n"
   27374 									  "#extension GL_ARB_enhanced_layouts : require\n"
   27375 									  "\n"
   27376 									  "layout(vertices = 1) out;\n"
   27377 									  "\n"
   27378 									  "VAR_DEFINITION"
   27379 									  "\n"
   27380 									  "in  vec4 vs_tcs[];\n"
   27381 									  "out vec4 tcs_tes[];\n"
   27382 									  "\n"
   27383 									  "void main()\n"
   27384 									  "{\n"
   27385 									  "    vec4 result = vs_tcs[gl_InvocationID];\n"
   27386 									  "\n"
   27387 									  "VARIABLE_USE"
   27388 									  "\n"
   27389 									  "    tcs_tes[gl_InvocationID] = result;\n"
   27390 									  "\n"
   27391 									  "    gl_TessLevelOuter[0] = 1.0;\n"
   27392 									  "    gl_TessLevelOuter[1] = 1.0;\n"
   27393 									  "    gl_TessLevelOuter[2] = 1.0;\n"
   27394 									  "    gl_TessLevelOuter[3] = 1.0;\n"
   27395 									  "    gl_TessLevelInner[0] = 1.0;\n"
   27396 									  "    gl_TessLevelInner[1] = 1.0;\n"
   27397 									  "}\n"
   27398 									  "\n";
   27399 	static const GLchar* tes_tested = "#version 430 core\n"
   27400 									  "#extension GL_ARB_enhanced_layouts : require\n"
   27401 									  "\n"
   27402 									  "layout(isolines, point_mode) in;\n"
   27403 									  "\n"
   27404 									  "VAR_DEFINITION"
   27405 									  "\n"
   27406 									  "in  vec4 tcs_tes[];\n"
   27407 									  "out vec4 tes_gs;\n"
   27408 									  "\n"
   27409 									  "void main()\n"
   27410 									  "{\n"
   27411 									  "    vec4 result = tcs_tes[0];\n"
   27412 									  "\n"
   27413 									  "VARIABLE_USE"
   27414 									  "\n"
   27415 									  "    tes_gs += result;\n"
   27416 									  "}\n"
   27417 									  "\n";
   27418 	static const GLchar* vs = "#version 430 core\n"
   27419 							  "#extension GL_ARB_enhanced_layouts : require\n"
   27420 							  "\n"
   27421 							  "in  vec4 in_vs;\n"
   27422 							  "out vec4 vs_tcs;\n"
   27423 							  "\n"
   27424 							  "void main()\n"
   27425 							  "{\n"
   27426 							  "    vs_tcs = in_vs;\n"
   27427 							  "}\n"
   27428 							  "\n";
   27429 	static const GLchar* vs_tested = "#version 430 core\n"
   27430 									 "#extension GL_ARB_enhanced_layouts : require\n"
   27431 									 "\n"
   27432 									 "VAR_DEFINITION"
   27433 									 "\n"
   27434 									 "in  vec4 in_vs;\n"
   27435 									 "out vec4 vs_tcs;\n"
   27436 									 "\n"
   27437 									 "void main()\n"
   27438 									 "{\n"
   27439 									 "    vec4 result = in_vs;\n"
   27440 									 "\n"
   27441 									 "VARIABLE_USE"
   27442 									 "\n"
   27443 									 "    vs_tcs = result;\n"
   27444 									 "}\n"
   27445 									 "\n";
   27446 
   27447 	std::string source;
   27448 	testCase&   test_case = m_test_cases[test_case_index];
   27449 
   27450 	if (test_case.m_stage == stage)
   27451 	{
   27452 		const GLchar* array	= "";
   27453 		const GLchar* index	= "";
   27454 		size_t		  position = 0;
   27455 
   27456 		switch (stage)
   27457 		{
   27458 		case Utils::Shader::GEOMETRY:
   27459 			source = gs_tested;
   27460 			array  = "[]";
   27461 			index  = "[0]";
   27462 			break;
   27463 		case Utils::Shader::TESS_CTRL:
   27464 			source = tcs_tested;
   27465 			array  = "[]";
   27466 			index  = "[gl_InvocationID]";
   27467 			break;
   27468 		case Utils::Shader::TESS_EVAL:
   27469 			source = tes_tested;
   27470 			array  = "[]";
   27471 			index  = "[0]";
   27472 			break;
   27473 		case Utils::Shader::VERTEX:
   27474 			source = vs_tested;
   27475 			break;
   27476 		default:
   27477 			TCU_FAIL("Invalid enum");
   27478 		}
   27479 
   27480 		Utils::replaceToken("VAR_DEFINITION", position, var_definition, source);
   27481 		position = 0;
   27482 		Utils::replaceToken("ARRAY", position, array, source);
   27483 		Utils::replaceToken("VARIABLE_USE", position, var_use, source);
   27484 
   27485 		Utils::replaceAllTokens("INDEX", index, source);
   27486 	}
   27487 	else
   27488 	{
   27489 		switch (test_case.m_stage)
   27490 		{
   27491 		case Utils::Shader::GEOMETRY:
   27492 			switch (stage)
   27493 			{
   27494 			case Utils::Shader::FRAGMENT:
   27495 				source = fs;
   27496 				break;
   27497 			case Utils::Shader::VERTEX:
   27498 				source = vs;
   27499 				break;
   27500 			default:
   27501 				source = "";
   27502 			}
   27503 			break;
   27504 		case Utils::Shader::TESS_CTRL:
   27505 			switch (stage)
   27506 			{
   27507 			case Utils::Shader::FRAGMENT:
   27508 				source = fs;
   27509 				break;
   27510 			case Utils::Shader::VERTEX:
   27511 				source = vs;
   27512 				break;
   27513 			default:
   27514 				source = "";
   27515 			}
   27516 			break;
   27517 		case Utils::Shader::TESS_EVAL:
   27518 			switch (stage)
   27519 			{
   27520 			case Utils::Shader::FRAGMENT:
   27521 				source = fs;
   27522 				break;
   27523 			case Utils::Shader::TESS_CTRL:
   27524 				source = tcs;
   27525 				break;
   27526 			case Utils::Shader::VERTEX:
   27527 				source = vs;
   27528 				break;
   27529 			default:
   27530 				source = "";
   27531 			}
   27532 			break;
   27533 		case Utils::Shader::VERTEX:
   27534 			switch (stage)
   27535 			{
   27536 			case Utils::Shader::FRAGMENT:
   27537 				source = fs;
   27538 				break;
   27539 			default:
   27540 				source = "";
   27541 			}
   27542 			break;
   27543 		default:
   27544 			TCU_FAIL("Invalid enum");
   27545 			break;
   27546 		}
   27547 	}
   27548 
   27549 	return source;
   27550 }
   27551 
   27552 /** Get description of test case
   27553  *
   27554  * @param test_case_index Index of test case
   27555  *
   27556  * @return Test case description
   27557  **/
   27558 std::string XFBCaptureUnsizedArrayTest::getTestCaseName(GLuint test_case_index)
   27559 {
   27560 	std::stringstream stream;
   27561 	testCase&		  test_case = m_test_cases[test_case_index];
   27562 
   27563 	stream << "Stage: " << Utils::Shader::GetStageName(test_case.m_stage);
   27564 
   27565 	return stream.str();
   27566 }
   27567 
   27568 /** Get number of test cases
   27569  *
   27570  * @return Number of test cases
   27571  **/
   27572 GLuint XFBCaptureUnsizedArrayTest::getTestCaseNumber()
   27573 {
   27574 	return static_cast<GLuint>(m_test_cases.size());
   27575 }
   27576 
   27577 /** Selects if "compute" stage is relevant for test
   27578  *
   27579  * @param ignored
   27580  *
   27581  * @return false
   27582  **/
   27583 bool XFBCaptureUnsizedArrayTest::isComputeRelevant(GLuint /* test_case_index */)
   27584 {
   27585 	return false;
   27586 }
   27587 
   27588 /** Prepare all test cases
   27589  *
   27590  **/
   27591 void XFBCaptureUnsizedArrayTest::testInit()
   27592 {
   27593 	for (GLuint stage = 0; stage < Utils::Shader::STAGE_MAX; ++stage)
   27594 	{
   27595 		/* Not aplicable for */
   27596 		if ((Utils::Shader::COMPUTE == stage) || (Utils::Shader::FRAGMENT == stage) ||
   27597 			(Utils::Shader::GEOMETRY == stage) || (Utils::Shader::TESS_EVAL == stage))
   27598 		{
   27599 			continue;
   27600 		}
   27601 
   27602 		testCase test_case = { (Utils::Shader::STAGES)stage };
   27603 
   27604 		m_test_cases.push_back(test_case);
   27605 	}
   27606 }
   27607 } /* EnhancedLayouts namespace */
   27608 
   27609 /** Constructor.
   27610  *
   27611  *  @param context Rendering context.
   27612  **/
   27613 EnhancedLayoutsTests::EnhancedLayoutsTests(deqp::Context& context)
   27614 	: TestCaseGroup(context, "enhanced_layouts", "Verifies \"enhanced layouts\" functionality")
   27615 {
   27616 	/* Left blank on purpose */
   27617 }
   27618 
   27619 /** Initializes a texture_storage_multisample test group.
   27620  *
   27621  **/
   27622 void EnhancedLayoutsTests::init(void)
   27623 {
   27624 	addChild(new EnhancedLayouts::APIConstantValuesTest(m_context));
   27625 	addChild(new EnhancedLayouts::APIErrorsTest(m_context));
   27626 	addChild(new EnhancedLayouts::GLSLContantValuesTest(m_context));
   27627 	addChild(new EnhancedLayouts::GLSLContantImmutablityTest(m_context));
   27628 	addChild(new EnhancedLayouts::GLSLConstantIntegralExpressionTest(m_context));
   27629 	addChild(new EnhancedLayouts::UniformBlockLayoutQualifierConflictTest(m_context));
   27630 	addChild(new EnhancedLayouts::SSBMemberInvalidOffsetAlignmentTest(m_context));
   27631 	addChild(new EnhancedLayouts::SSBMemberOverlappingOffsetsTest(m_context));
   27632 	addChild(new EnhancedLayouts::VaryingExceedingComponentsTest(m_context));
   27633 	addChild(new EnhancedLayouts::VaryingComponentOfInvalidTypeTest(m_context));
   27634 	addChild(new EnhancedLayouts::OutputComponentAliasingTest(m_context));
   27635 	addChild(new EnhancedLayouts::VertexAttribLocationAPITest(m_context));
   27636 	addChild(new EnhancedLayouts::XFBInputTest(m_context));
   27637 	addChild(new EnhancedLayouts::XFBAllStagesTest(m_context));
   27638 	addChild(new EnhancedLayouts::XFBCaptureInactiveOutputVariableTest(m_context));
   27639 	addChild(new EnhancedLayouts::XFBCaptureInactiveOutputComponentTest(m_context));
   27640 	addChild(new EnhancedLayouts::XFBCaptureInactiveOutputBlockMemberTest(m_context));
   27641 	addChild(new EnhancedLayouts::XFBStrideTest(m_context));
   27642 
   27643 	addChild(new EnhancedLayouts::UniformBlockMemberOffsetAndAlignTest(m_context));
   27644 	addChild(new EnhancedLayouts::UniformBlockMemberInvalidOffsetAlignmentTest(m_context));
   27645 	addChild(new EnhancedLayouts::UniformBlockMemberOverlappingOffsetsTest(m_context));
   27646 	addChild(new EnhancedLayouts::UniformBlockMemberAlignNonPowerOf2Test(m_context));
   27647 	addChild(new EnhancedLayouts::SSBLayoutQualifierConflictTest(m_context));
   27648 	addChild(new EnhancedLayouts::SSBMemberAlignNonPowerOf2Test(m_context));
   27649 	addChild(new EnhancedLayouts::SSBAlignmentTest(m_context));
   27650 	addChild(new EnhancedLayouts::VaryingStructureMemberLocationTest(m_context));
   27651 	addChild(new EnhancedLayouts::VaryingBlockAutomaticMemberLocationsTest(m_context));
   27652 	addChild(new EnhancedLayouts::VaryingComponentWithoutLocationTest(m_context));
   27653 	addChild(new EnhancedLayouts::InputComponentAliasingTest(m_context));
   27654 	addChild(new EnhancedLayouts::VaryingLocationAliasingWithMixedTypesTest(m_context));
   27655 	addChild(new EnhancedLayouts::VaryingLocationAliasingWithMixedInterpolationTest(m_context));
   27656 	addChild(new EnhancedLayouts::VaryingLocationAliasingWithMixedAuxiliaryStorageTest(m_context));
   27657 	addChild(new EnhancedLayouts::XFBStrideOfEmptyListTest(m_context));
   27658 	addChild(new EnhancedLayouts::XFBStrideOfEmptyListAndAPITest(m_context));
   27659 	addChild(new EnhancedLayouts::XFBTooSmallStrideTest(m_context));
   27660 	addChild(new EnhancedLayouts::XFBBlockMemberStrideTest(m_context));
   27661 	addChild(new EnhancedLayouts::XFBDuplicatedStrideTest(m_context));
   27662 	addChild(new EnhancedLayouts::XFBGetProgramResourceAPITest(m_context));
   27663 	addChild(new EnhancedLayouts::XFBMultipleVertexStreamsTest(m_context));
   27664 	addChild(new EnhancedLayouts::XFBExceedBufferLimitTest(m_context));
   27665 	addChild(new EnhancedLayouts::XFBExceedOffsetLimitTest(m_context));
   27666 	addChild(new EnhancedLayouts::XFBBlockMemberBufferTest(m_context));
   27667 	addChild(new EnhancedLayouts::XFBOutputOverlappingTest(m_context));
   27668 	addChild(new EnhancedLayouts::XFBInvalidOffsetAlignmentTest(m_context));
   27669 	addChild(new EnhancedLayouts::XFBCaptureStructTest(m_context));
   27670 	addChild(new EnhancedLayouts::XFBCaptureUnsizedArrayTest(m_context));
   27671 	addChild(new EnhancedLayouts::UniformBlockAlignmentTest(m_context));
   27672 	addChild(new EnhancedLayouts::SSBMemberOffsetAndAlignTest(m_context));
   27673 	addChild(new EnhancedLayouts::VertexAttribLocationsTest(m_context));
   27674 	addChild(new EnhancedLayouts::VaryingLocationsTest(m_context));
   27675 	addChild(new EnhancedLayouts::VaryingArrayLocationsTest(m_context));
   27676 	addChild(new EnhancedLayouts::VaryingStructureLocationsTest(m_context));
   27677 	addChild(new EnhancedLayouts::VaryingBlockLocationsTest(m_context));
   27678 	addChild(new EnhancedLayouts::VaryingBlockMemberLocationsTest(m_context));
   27679 	addChild(new EnhancedLayouts::XFBVariableStrideTest(m_context));
   27680 	addChild(new EnhancedLayouts::XFBBlockStrideTest(m_context));
   27681 	addChild(new EnhancedLayouts::XFBOverrideQualifiersWithAPITest(m_context));
   27682 	addChild(new EnhancedLayouts::XFBVertexStreamsTest(m_context));
   27683 	addChild(new EnhancedLayouts::XFBGlobalBufferTest(m_context));
   27684 	addChild(new EnhancedLayouts::FragmentDataLocationAPITest(m_context));
   27685 	addChild(new EnhancedLayouts::VaryingLocationLimitTest(m_context));
   27686 	addChild(new EnhancedLayouts::VaryingComponentsTest(m_context));
   27687 	addChild(new EnhancedLayouts::VaryingArrayComponentsTest(m_context));
   27688 }
   27689 
   27690 } /* gl4cts namespace */
   27691