Merge "Release EGL resources in CTS worker threads" am: fde96926aa
[platform/upstream/VK-GL-CTS.git] / external / openglcts / modules / gles31 / es31cArrayOfArraysTests.cpp
1 /*-------------------------------------------------------------------------
2  * OpenGL Conformance Test Suite
3  * -----------------------------
4  *
5  * Copyright (c) 2014-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 #include "es31cArrayOfArraysTests.hpp"
25 #include "gluContextInfo.hpp"
26 #include "gluDefs.hpp"
27 #include "gluRenderContext.hpp"
28 #include "glwFunctions.hpp"
29 #include "tcuTestLog.hpp"
30
31 #include <algorithm>
32 #include <cassert>
33 #include <cstdio>
34 #include <string>
35 using std::string;
36
37 /* Selects if debug output is enabled */
38 #define IS_DEBUG 0
39 #define IS_DEBUG_DUMP_ALL_SHADERS 0
40
41 /* Selects if workaround in ExpressionsInvalid2 test is enabled */
42 #define WRKARD_EXPRESSIONSINVALID2 0
43
44 #if IS_DEBUG
45 #include "tcuTestLog.hpp"
46 #endif
47
48 namespace glcts
49 {
50 namespace ArraysOfArrays
51 {
52 namespace Interface
53 {
54 /* Sets limits on number of dimensions. Value 8 comes from ogirinal "ES" implementation.
55  * Explanation was as follows:
56  *
57  *     "The current specifations allow up to 8 array dimensions."
58  */
59 const size_t ES::MAX_ARRAY_DIMENSIONS = 8;
60 const size_t GL::MAX_ARRAY_DIMENSIONS = 8;
61
62 /* API specific shader parts */
63 const char* ES::shader_version_gpu5 =
64         "#version 310 es\n#extension GL_EXT_gpu_shader5 : require\nprecision mediump float;\n\n";
65 const char* ES::shader_version = "#version 310 es\nprecision mediump float;\n\n";
66
67 const char* GL::shader_version_gpu5 = "#version 430 core\n\n";
68 const char* GL::shader_version          = "#version 430 core\n\n";
69 } /* namespace Interface */
70
71 /* Dummy fragment shader source code.
72  * Used when testing the vertex shader. */
73 const std::string default_fragment_shader_source = "//default fragment shader\n"
74                                                                                                    "out vec4 color;\n"
75                                                                                                    "void main()\n"
76                                                                                                    "{\n"
77                                                                                                    "    color = vec4(1.0);\n"
78                                                                                                    "}\n";
79
80 /* Dummy vertex shader source code.
81  * Used when testing the fragment shader. */
82 const std::string default_vertex_shader_source = "//default vertex shader\n"
83                                                                                                  "\n"
84                                                                                                  "void main()\n"
85                                                                                                  "{\n"
86                                                                                                  "    gl_Position = vec4(0.0,0.0,0.0,1.0);\n"
87                                                                                                  "}\n";
88
89 /* Dummy geometry shader source code.
90  * Used when testing the other shaders. */
91 const std::string default_geometry_shader_source = "//default geometry\n"
92                                                                                                    "\n"
93                                                                                                    "void main()\n"
94                                                                                                    "{\n"
95                                                                                                    "    gl_Position  = vec4(-1, -1, 0, 1);\n"
96                                                                                                    "    EmitVertex();\n"
97                                                                                                    "    gl_Position  = vec4(-1, 1, 0, 1);\n"
98                                                                                                    "    EmitVertex();\n"
99                                                                                                    "    gl_Position  = vec4(1, -1, 0, 1);\n"
100                                                                                                    "    EmitVertex();\n"
101                                                                                                    "    gl_Position  = vec4(1, 1, 0, 1);\n"
102                                                                                                    "    EmitVertex();\n"
103                                                                                                    "}\n";
104
105 /* Dummy tesselation control shader source code.
106  * Used when testing the other shaders. */
107 const std::string default_tc_shader_source = "//default tcs\n"
108                                                                                          "\n"
109                                                                                          "void main()\n"
110                                                                                          "{\n"
111                                                                                          "    gl_TessLevelOuter[0] = 1.0;\n"
112                                                                                          "    gl_TessLevelOuter[1] = 1.0;\n"
113                                                                                          "    gl_TessLevelOuter[2] = 1.0;\n"
114                                                                                          "    gl_TessLevelOuter[3] = 1.0;\n"
115                                                                                          "    gl_TessLevelInner[0] = 1.0;\n"
116                                                                                          "    gl_TessLevelInner[1] = 1.0;\n"
117                                                                                          "}\n";
118
119 /* Dummy tesselation evaluation shader source code.
120  * Used when testing the other shaders. */
121 const std::string default_te_shader_source = "//default tes\n"
122                                                                                          "\n"
123                                                                                          "void main()\n"
124                                                                                          "{\n"
125                                                                                          "}\n";
126
127 /* Pass-through shaders source code. Used when testing other stage. */
128 const std::string pass_fragment_shader_source = "//pass fragment shader\n"
129                                                                                                 "in float fs_result;\n"
130                                                                                                 "out vec4 color;\n"
131                                                                                                 "\n"
132                                                                                                 "void main()\n"
133                                                                                                 "{\n"
134                                                                                                 "    color = vec4(fs_result);\n"
135                                                                                                 "}\n";
136
137 const std::string pass_geometry_shader_source = "//pass geometry\n"
138                                                                                                 "in  float gs_result[];\n"
139                                                                                                 "out float fs_result;\n"
140                                                                                                 "\n"
141                                                                                                 "void main()\n"
142                                                                                                 "{\n"
143                                                                                                 "    gl_Position  = vec4(-1, -1, 0, 1);\n"
144                                                                                                 "    fs_result = gs_result[0];\n"
145                                                                                                 "    EmitVertex();\n"
146                                                                                                 "    gl_Position  = vec4(-1, 1, 0, 1);\n"
147                                                                                                 "    fs_result = gs_result[0];\n"
148                                                                                                 "    EmitVertex();\n"
149                                                                                                 "    gl_Position  = vec4(1, -1, 0, 1);\n"
150                                                                                                 "    fs_result = gs_result[0];\n"
151                                                                                                 "    EmitVertex();\n"
152                                                                                                 "    gl_Position  = vec4(1, 1, 0, 1);\n"
153                                                                                                 "    fs_result = gs_result[0];\n"
154                                                                                                 "    EmitVertex();\n"
155                                                                                                 "}\n";
156
157 const std::string pass_te_shader_source = "//pass tes\n"
158                                                                                   "in  float tcs_result[];\n"
159                                                                                   "out float fs_result;\n"
160                                                                                   "\n"
161                                                                                   "void main()\n"
162                                                                                   "{\n"
163                                                                                   "    fs_result = tcs_result[0];\n"
164                                                                                   "}\n";
165
166 /* Empty string */
167 static const std::string empty_string = "";
168
169 /* Beginning of a shader source code. */
170 const std::string shader_start = "void main()\n"
171                                                                  "{\n";
172
173 /* End of a shader source code. */
174 const std::string shader_end = "}\n";
175
176 /* Emit full screen quad from GS */
177 const std::string emit_quad = "    gl_Position  = vec4(-1, -1, 0, 1);\n"
178                                                           "    EmitVertex();\n"
179                                                           "    gl_Position  = vec4(-1, 1, 0, 1);\n"
180                                                           "    EmitVertex();\n"
181                                                           "    gl_Position  = vec4(1, -1, 0, 1);\n"
182                                                           "    EmitVertex();\n"
183                                                           "    gl_Position  = vec4(1, 1, 0, 1);\n"
184                                                           "    EmitVertex();\n";
185
186 /* Set tesselation levels */
187 const std::string set_tesseation = "    gl_TessLevelOuter[0] = 1.0;\n"
188                                                                    "    gl_TessLevelOuter[1] = 1.0;\n"
189                                                                    "    gl_TessLevelOuter[2] = 1.0;\n"
190                                                                    "    gl_TessLevelOuter[3] = 1.0;\n"
191                                                                    "    gl_TessLevelInner[0] = 1.0;\n"
192                                                                    "    gl_TessLevelInner[1] = 1.0;\n";
193
194 /* Input and output data type modifiers. */
195 const std::string in_out_type_modifiers[] = { "in", "out", "uniform" };
196
197 /* Types and appropriate initialisers, used throughout these tests */
198 const var_descriptor var_descriptors[] = {
199         { "bool", "", "true", "false", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
200         { "int", "", "1", "0", "0", "int", "", "iterator", "1", "N/A", "N/A" },
201         { "uint", "", "1u", "0u", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
202         { "float", "", "1.0", "0.0", "0.0", "float", "", "iterator", "1.0", "N/A", "N/A" },
203         { "vec2", "", "vec2(1.0)", "vec2(0.0)", "0.0", "float", "[0]", "vec2(iterator)", "vec2(1.0)", "N/A", "N/A" },
204         { "vec3", "", "vec3(1.0)", "vec3(0.0)", "0.0", "float", "[0]", "vec3(iterator)", "vec3(1.0)", "N/A", "N/A" },
205         { "vec4", "", "vec4(1.0)", "vec4(0.0)", "0.0", "float", "[0]", "vec4(iterator)", "vec4(1.0)", "N/A", "N/A" },
206         { "bvec2", "", "bvec2(1)", "bvec2(0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
207         { "bvec3", "", "bvec3(1)", "bvec3(0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
208         { "bvec4", "", "bvec4(1)", "bvec4(0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
209         { "ivec2", "", "ivec2(1)", "ivec2(0)", "0", "int", "[0]", "ivec2(iterator)", "ivec2(1)", "N/A", "N/A" },
210         { "ivec3", "", "ivec3(1)", "ivec3(0)", "0", "int", "[0]", "ivec3(iterator)", "ivec3(1)", "N/A", "N/A" },
211         { "ivec4", "", "ivec4(1)", "ivec4(0)", "0", "int", "[0]", "ivec4(iterator)", "ivec4(1)", "N/A", "N/A" },
212         { "uvec2", "", "uvec2(1u)", "uvec2(0u)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
213         { "uvec3", "", "uvec3(1u)", "uvec3(0u)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
214         { "uvec4", "", "uvec4(1u)", "uvec4(0u)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
215         { "mat2", "", "mat2(1.0)", "mat2(0.0)", "0.0", "float", "[0][0]", "mat2(iterator)", "mat2(1.0)", "N/A", "N/A" },
216         { "mat3", "", "mat3(1.0)", "mat3(0.0)", "0.0", "float", "[0][0]", "mat3(iterator)", "mat3(1.0)", "N/A", "N/A" },
217         { "mat4", "", "mat4(1.0)", "mat4(0.0)", "0.0", "float", "[0][0]", "mat4(iterator)", "mat4(1.0)", "N/A", "N/A" },
218         { "mat2x2", "", "mat2x2(1.0)", "mat2x2(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
219         { "mat2x3", "", "mat2x3(1.0)", "mat2x3(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
220         { "mat2x4", "", "mat2x4(1.0)", "mat2x4(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
221         { "mat3x2", "", "mat3x2(1.0)", "mat3x2(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
222         { "mat3x3", "", "mat3x3(1.0)", "mat3x3(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
223         { "mat3x4", "", "mat3x4(1.0)", "mat3x4(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
224         { "mat4x2", "", "mat4x2(1.0)", "mat4x2(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
225         { "mat4x3", "", "mat4x3(1.0)", "mat4x3(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
226         { "mat4x4", "", "mat4x4(1.0)", "mat4x4(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
227         { "imageBuffer", "", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
228         { "iimageBuffer", "", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
229         { "uimageBuffer", "", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
230         { "samplerBuffer", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
231         { "isamplerBuffer", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
232         { "usamplerBuffer", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
233         { "sampler2D", "", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec2(0.0)", "vec4" },
234         { "sampler3D", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec3(0.0)", "vec4" },
235         { "samplerCube", "", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec3(0.0)", "vec4" },
236         {
237                 "samplerCubeShadow", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec4(0.0)", "float",
238         },
239         { "sampler2DShadow", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec3(0.0)", "float" },
240         { "sampler2DArray", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec3(0.0)", "vec4" },
241         { "sampler2DArrayShadow", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec4(0.0)", "float" },
242         { "isampler2D", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec2(0.0)", "ivec4" },
243         { "isampler3D", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec3(0.0)", "ivec4" },
244         { "isamplerCube", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec3(0.0)", "ivec4" },
245         { "isampler2DArray", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec3(0.0)", "ivec4" },
246         { "usampler2D", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec2(0.0)", "uvec4" },
247         { "usampler3D", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec3(0.0)", "uvec4" },
248         { "usamplerCube", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec3(0.0)", "uvec4" },
249         { "usampler2DArray", "lowp", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "vec3(0.0)", "uvec4" },
250 };
251
252 const var_descriptor var_double_descriptors[] = {
253         { "double", "", "1.0", "0.0", "0.0", "double", "", "iterator", "1.0", "N/A", "N/A" },
254         { "dmat2", "", "dmat2(1.0)", "dmat2(0.0)", "0.0", "double", "[0][0]", "dmat2(iterator)", "dmat2(1.0)", "N/A",
255           "N/A" },
256         { "dmat3", "", "dmat3(1.0)", "dmat3(0.0)", "0.0", "double", "[0][0]", "dmat3(iterator)", "dmat3(1.0)", "N/A",
257           "N/A" },
258         { "dmat4", "", "dmat4(1.0)", "dmat4(0.0)", "0.0", "double", "[0][0]", "dmat4(iterator)", "dmat4(1.0)", "N/A",
259           "N/A" },
260         { "dmat2x2", "", "dmat2x2(1.0)", "dmat2x2(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
261         { "dmat2x3", "", "dmat2x3(1.0)", "dmat2x3(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
262         { "dmat2x4", "", "dmat2x4(1.0)", "dmat2x4(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
263         { "dmat3x2", "", "dmat3x2(1.0)", "dmat3x2(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
264         { "dmat3x3", "", "dmat3x3(1.0)", "dmat3x3(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
265         { "dmat3x4", "", "dmat3x4(1.0)", "dmat3x4(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
266         { "dmat4x2", "", "dmat4x2(1.0)", "dmat4x2(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
267         { "dmat4x3", "", "dmat4x3(1.0)", "dmat4x3(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
268         { "dmat4x4", "", "dmat4x4(1.0)", "dmat4x4(0.0)", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A", "N/A" },
269 };
270
271 _supported_variable_types_map supported_variable_types_map;
272
273 /** List of all supported variable types for es. */
274 const test_var_type var_types_es[] = {
275         VAR_TYPE_BOOL,   VAR_TYPE_INT,  VAR_TYPE_UINT,   VAR_TYPE_FLOAT,  VAR_TYPE_VEC2,   VAR_TYPE_VEC3,
276         VAR_TYPE_VEC4,   VAR_TYPE_BVEC2,  VAR_TYPE_BVEC3,  VAR_TYPE_BVEC4,  VAR_TYPE_IVEC2,  VAR_TYPE_IVEC3,
277         VAR_TYPE_IVEC4,  VAR_TYPE_UVEC2,  VAR_TYPE_UVEC3,  VAR_TYPE_UVEC4,  VAR_TYPE_MAT2,   VAR_TYPE_MAT3,
278         VAR_TYPE_MAT4,   VAR_TYPE_MAT2X2, VAR_TYPE_MAT2X3, VAR_TYPE_MAT2X4, VAR_TYPE_MAT3X2, VAR_TYPE_MAT3X3,
279         VAR_TYPE_MAT3X4, VAR_TYPE_MAT4X2, VAR_TYPE_MAT4X3, VAR_TYPE_MAT4X4,
280 };
281
282 const test_var_type* Interface::ES::var_types   = var_types_es;
283 const size_t             Interface::ES::n_var_types = sizeof(var_types_es) / sizeof(var_types_es[0]);
284
285 /** List of all supported variable types for gl. */
286 static const glcts::test_var_type var_types_gl[] = {
287         VAR_TYPE_BOOL,  VAR_TYPE_INT,           VAR_TYPE_UINT,  VAR_TYPE_FLOAT,   VAR_TYPE_VEC2,        VAR_TYPE_VEC3,
288         VAR_TYPE_VEC4,  VAR_TYPE_BVEC2,   VAR_TYPE_BVEC3,   VAR_TYPE_BVEC4,   VAR_TYPE_IVEC2,   VAR_TYPE_IVEC3,
289         VAR_TYPE_IVEC4,   VAR_TYPE_UVEC2,   VAR_TYPE_UVEC3,   VAR_TYPE_UVEC4,   VAR_TYPE_MAT2,  VAR_TYPE_MAT3,
290         VAR_TYPE_MAT4,  VAR_TYPE_MAT2X2,  VAR_TYPE_MAT2X3,  VAR_TYPE_MAT2X4,  VAR_TYPE_MAT3X2,  VAR_TYPE_MAT3X3,
291         VAR_TYPE_MAT3X4,  VAR_TYPE_MAT4X2,  VAR_TYPE_MAT4X3,  VAR_TYPE_MAT4X4,  VAR_TYPE_DOUBLE,  VAR_TYPE_DMAT2,
292         VAR_TYPE_DMAT3,   VAR_TYPE_DMAT4,   VAR_TYPE_DMAT2X2, VAR_TYPE_DMAT2X3, VAR_TYPE_DMAT2X4, VAR_TYPE_DMAT3X2,
293         VAR_TYPE_DMAT3X3, VAR_TYPE_DMAT3X4, VAR_TYPE_DMAT4X2, VAR_TYPE_DMAT4X3, VAR_TYPE_DMAT4X4,
294 };
295
296 const test_var_type* Interface::GL::var_types   = var_types_gl;
297 const size_t             Interface::GL::n_var_types = sizeof(var_types_gl) / sizeof(var_types_gl[0]);
298
299 /** List of all supported opaque types. */
300 const glcts::test_var_type opaque_var_types[] = {
301         //Floating Point Sampler Types (opaque)
302         VAR_TYPE_SAMPLER2D, VAR_TYPE_SAMPLER3D, VAR_TYPE_SAMPLERCUBE, VAR_TYPE_SAMPLERCUBESHADOW, VAR_TYPE_SAMPLER2DSHADOW,
303         VAR_TYPE_SAMPLER2DARRAY, VAR_TYPE_SAMPLER2DARRAYSHADOW,
304         //Signed Integer Sampler Types (opaque)
305         VAR_TYPE_ISAMPLER2D, VAR_TYPE_ISAMPLER3D, VAR_TYPE_ISAMPLERCUBE, VAR_TYPE_ISAMPLER2DARRAY,
306         //Unsigned Integer Sampler Types (opaque)
307         VAR_TYPE_USAMPLER2D, VAR_TYPE_USAMPLER3D, VAR_TYPE_USAMPLERCUBE, VAR_TYPE_USAMPLER2DARRAY,
308 };
309
310 /** Sets up the type map that will be used to look up the type names, initialisation
311  *  values, etc., associated with each of the types used within the array tests
312  *
313  **/
314 template <class API>
315 void initializeMap()
316 {
317         int temp_index = 0;
318
319         // Set up the map
320         supported_variable_types_map[VAR_TYPE_BOOL]                                     = var_descriptors[temp_index++];
321         supported_variable_types_map[VAR_TYPE_INT]                                      = var_descriptors[temp_index++];
322         supported_variable_types_map[VAR_TYPE_UINT]                                     = var_descriptors[temp_index++];
323         supported_variable_types_map[VAR_TYPE_FLOAT]                            = var_descriptors[temp_index++];
324         supported_variable_types_map[VAR_TYPE_VEC2]                                     = var_descriptors[temp_index++];
325         supported_variable_types_map[VAR_TYPE_VEC3]                                     = var_descriptors[temp_index++];
326         supported_variable_types_map[VAR_TYPE_VEC4]                                     = var_descriptors[temp_index++];
327         supported_variable_types_map[VAR_TYPE_BVEC2]                            = var_descriptors[temp_index++];
328         supported_variable_types_map[VAR_TYPE_BVEC3]                            = var_descriptors[temp_index++];
329         supported_variable_types_map[VAR_TYPE_BVEC4]                            = var_descriptors[temp_index++];
330         supported_variable_types_map[VAR_TYPE_IVEC2]                            = var_descriptors[temp_index++];
331         supported_variable_types_map[VAR_TYPE_IVEC3]                            = var_descriptors[temp_index++];
332         supported_variable_types_map[VAR_TYPE_IVEC4]                            = var_descriptors[temp_index++];
333         supported_variable_types_map[VAR_TYPE_UVEC2]                            = var_descriptors[temp_index++];
334         supported_variable_types_map[VAR_TYPE_UVEC3]                            = var_descriptors[temp_index++];
335         supported_variable_types_map[VAR_TYPE_UVEC4]                            = var_descriptors[temp_index++];
336         supported_variable_types_map[VAR_TYPE_MAT2]                                     = var_descriptors[temp_index++];
337         supported_variable_types_map[VAR_TYPE_MAT3]                                     = var_descriptors[temp_index++];
338         supported_variable_types_map[VAR_TYPE_MAT4]                                     = var_descriptors[temp_index++];
339         supported_variable_types_map[VAR_TYPE_MAT2X2]                           = var_descriptors[temp_index++];
340         supported_variable_types_map[VAR_TYPE_MAT2X3]                           = var_descriptors[temp_index++];
341         supported_variable_types_map[VAR_TYPE_MAT2X4]                           = var_descriptors[temp_index++];
342         supported_variable_types_map[VAR_TYPE_MAT3X2]                           = var_descriptors[temp_index++];
343         supported_variable_types_map[VAR_TYPE_MAT3X3]                           = var_descriptors[temp_index++];
344         supported_variable_types_map[VAR_TYPE_MAT3X4]                           = var_descriptors[temp_index++];
345         supported_variable_types_map[VAR_TYPE_MAT4X2]                           = var_descriptors[temp_index++];
346         supported_variable_types_map[VAR_TYPE_MAT4X3]                           = var_descriptors[temp_index++];
347         supported_variable_types_map[VAR_TYPE_MAT4X4]                           = var_descriptors[temp_index++];
348         supported_variable_types_map[VAR_TYPE_IMAGEBUFFER]                      = var_descriptors[temp_index++];
349         supported_variable_types_map[VAR_TYPE_IIMAGEBUFFER]                     = var_descriptors[temp_index++];
350         supported_variable_types_map[VAR_TYPE_UIMAGEBUFFER]                     = var_descriptors[temp_index++];
351         supported_variable_types_map[VAR_TYPE_SAMPLERBUFFER]            = var_descriptors[temp_index++];
352         supported_variable_types_map[VAR_TYPE_ISAMPLERBUFFER]           = var_descriptors[temp_index++];
353         supported_variable_types_map[VAR_TYPE_USAMPLERBUFFER]           = var_descriptors[temp_index++];
354         supported_variable_types_map[VAR_TYPE_SAMPLER2D]                        = var_descriptors[temp_index++];
355         supported_variable_types_map[VAR_TYPE_SAMPLER3D]                        = var_descriptors[temp_index++];
356         supported_variable_types_map[VAR_TYPE_SAMPLERCUBE]                      = var_descriptors[temp_index++];
357         supported_variable_types_map[VAR_TYPE_SAMPLERCUBESHADOW]        = var_descriptors[temp_index++];
358         supported_variable_types_map[VAR_TYPE_SAMPLER2DSHADOW]          = var_descriptors[temp_index++];
359         supported_variable_types_map[VAR_TYPE_SAMPLER2DARRAY]           = var_descriptors[temp_index++];
360         supported_variable_types_map[VAR_TYPE_SAMPLER2DARRAYSHADOW] = var_descriptors[temp_index++];
361         supported_variable_types_map[VAR_TYPE_ISAMPLER2D]                       = var_descriptors[temp_index++];
362         supported_variable_types_map[VAR_TYPE_ISAMPLER3D]                       = var_descriptors[temp_index++];
363         supported_variable_types_map[VAR_TYPE_ISAMPLERCUBE]                     = var_descriptors[temp_index++];
364         supported_variable_types_map[VAR_TYPE_ISAMPLER2DARRAY]          = var_descriptors[temp_index++];
365         supported_variable_types_map[VAR_TYPE_USAMPLER2D]                       = var_descriptors[temp_index++];
366         supported_variable_types_map[VAR_TYPE_USAMPLER3D]                       = var_descriptors[temp_index++];
367         supported_variable_types_map[VAR_TYPE_USAMPLERCUBE]                     = var_descriptors[temp_index++];
368         supported_variable_types_map[VAR_TYPE_USAMPLER2DARRAY]          = var_descriptors[temp_index++];
369
370         if (API::USE_DOUBLE)
371         {
372                 temp_index = 0;
373
374                 supported_variable_types_map[VAR_TYPE_DOUBLE]  = var_double_descriptors[temp_index++];
375                 supported_variable_types_map[VAR_TYPE_DMAT2]   = var_double_descriptors[temp_index++];
376                 supported_variable_types_map[VAR_TYPE_DMAT3]   = var_double_descriptors[temp_index++];
377                 supported_variable_types_map[VAR_TYPE_DMAT4]   = var_double_descriptors[temp_index++];
378                 supported_variable_types_map[VAR_TYPE_DMAT2X2] = var_double_descriptors[temp_index++];
379                 supported_variable_types_map[VAR_TYPE_DMAT2X3] = var_double_descriptors[temp_index++];
380                 supported_variable_types_map[VAR_TYPE_DMAT2X4] = var_double_descriptors[temp_index++];
381                 supported_variable_types_map[VAR_TYPE_DMAT3X2] = var_double_descriptors[temp_index++];
382                 supported_variable_types_map[VAR_TYPE_DMAT3X3] = var_double_descriptors[temp_index++];
383                 supported_variable_types_map[VAR_TYPE_DMAT3X4] = var_double_descriptors[temp_index++];
384                 supported_variable_types_map[VAR_TYPE_DMAT4X2] = var_double_descriptors[temp_index++];
385                 supported_variable_types_map[VAR_TYPE_DMAT4X3] = var_double_descriptors[temp_index++];
386                 supported_variable_types_map[VAR_TYPE_DMAT4X4] = var_double_descriptors[temp_index++];
387         }
388 }
389
390 /** Macro appends default ending of main function to source string
391  *
392  * @param SOURCE Tested shader source
393  **/
394 #define DEFAULT_MAIN_ENDING(TYPE, SOURCE)                           \
395         {                                                               \
396                 /* Apply stage specific stuff */                            \
397                 switch (TYPE)                                               \
398                 {                                                           \
399                 case TestCaseBase<API>::VERTEX_SHADER_TYPE:                 \
400                         SOURCE += "\n   gl_Position = vec4(0.0);\n";            \
401                         break;                                                  \
402                 case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:               \
403                         break;                                                  \
404                 case TestCaseBase<API>::COMPUTE_SHADER_TYPE:                \
405                         break;                                                  \
406                 case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:               \
407                         SOURCE += emit_quad;                                    \
408                         break;                                                  \
409                 case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:    \
410                         SOURCE += set_tesseation;                               \
411                         break;                                                  \
412                 case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE: \
413                         break;                                                  \
414                 default:                                                    \
415                         TCU_FAIL("Unrecognized shader type.");                  \
416                         break;                                                  \
417                 }                                                           \
418                                                                     \
419                 /* End main function */                                     \
420                 SOURCE += shader_end;                                       \
421         }
422
423 /** Macro executes positive test selected on USE_ALL_SHADER_STAGES
424  *
425  * @param TYPE  Tested shader stage
426  * @param SOURCE Tested shader source
427  * @param DELETE Selects if program should be deleted afterwards
428  **/
429 #define EXECUTE_POSITIVE_TEST(TYPE, SOURCE, DELETE, GPU5)                              \
430         {                                                                                  \
431                 const std::string* cs  = &empty_string;                                        \
432                 const std::string* vs  = &default_vertex_shader_source;                        \
433                 const std::string* tcs = &default_tc_shader_source;                            \
434                 const std::string* tes = &default_te_shader_source;                            \
435                 const std::string* gs  = &default_geometry_shader_source;                      \
436                 const std::string* fs  = &default_fragment_shader_source;                      \
437                                                                                        \
438                 switch (TYPE)                                                                  \
439                 {                                                                              \
440                 case TestCaseBase<API>::COMPUTE_SHADER_TYPE:                                   \
441                         cs  = &SOURCE;                                                             \
442                         vs  = &empty_string;                                                       \
443                         tcs = &empty_string;                                                       \
444                         tes = &empty_string;                                                       \
445                         gs  = &empty_string;                                                       \
446                         fs  = &empty_string;                                                       \
447                         break;                                                                     \
448                 case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:                                  \
449                         fs = &SOURCE;                                                              \
450                         break;                                                                     \
451                 case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:                                  \
452                         gs = &SOURCE;                                                              \
453                         break;                                                                     \
454                 case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:                       \
455                         tcs = &SOURCE;                                                             \
456                         break;                                                                     \
457                 case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:                    \
458                         tes = &SOURCE;                                                             \
459                         break;                                                                     \
460                 case TestCaseBase<API>::VERTEX_SHADER_TYPE:                                    \
461                         vs = &SOURCE;                                                              \
462                         break;                                                                     \
463                 default:                                                                       \
464                         TCU_FAIL("Invalid enum");                                                  \
465                         break;                                                                     \
466                 };                                                                             \
467                                                                                        \
468                 if (API::USE_ALL_SHADER_STAGES)                                                \
469                 {                                                                              \
470                         this->execute_positive_test(*vs, *tcs, *tes, *gs, *fs, *cs, DELETE, GPU5); \
471                 }                                                                              \
472                 else                                                                           \
473                 {                                                                              \
474                         this->execute_positive_test(*vs, *fs, DELETE, GPU5);                       \
475                 }                                                                              \
476         }
477
478 /** Macro executes either positive or negative test
479  *
480  * @param S             Selects negative test when 0, positive test otherwise
481  * @param TYPE  Tested shader stage
482  * @param SOURCE Tested shader source
483  **/
484 #define EXECUTE_SHADER_TEST(S, TYPE, SOURCE)              \
485         if (S)                                                \
486         {                                                     \
487                 EXECUTE_POSITIVE_TEST(TYPE, SOURCE, true, false); \
488         }                                                     \
489         else                                                  \
490         {                                                     \
491                 this->execute_negative_test(TYPE, SOURCE);        \
492         }
493
494 /** Test case constructor.
495  *
496  * @tparam API        Tested API descriptor
497  *
498  * @param context     EGL context ID.
499  * @param name        Name of a test case.
500  * @param description Test case description.
501  **/
502 template <class API>
503 TestCaseBase<API>::TestCaseBase(Context& context, const char* name, const char* description)
504         : tcu::TestCase(context.getTestContext(), name, description)
505         , context_id(context)
506         , program_object_id(0)
507         , compute_shader_object_id(0)
508         , fragment_shader_object_id(0)
509         , geometry_shader_object_id(0)
510         , tess_ctrl_shader_object_id(0)
511         , tess_eval_shader_object_id(0)
512         , vertex_shader_object_id(0)
513 {
514         /* Left blank on purpose */
515 }
516
517 /** Clears up the shaders and program that were created during the tests
518  *
519  * @tparam API Tested API descriptor
520  */
521 template <class API>
522 void TestCaseBase<API>::delete_objects(void)
523 {
524         const glw::Functions& gl = context_id.getRenderContext().getFunctions();
525
526         /* Release all ES objects that may have been created by iterate() */
527         if (program_object_id != 0)
528         {
529                 gl.deleteProgram(program_object_id);
530                 program_object_id = 0;
531         }
532
533         /* Use default program object to be sure the objects were released. */
534         gl.useProgram(0);
535 }
536
537 /** Releases all OpenGL ES objects that were created for test case purposes.
538  *
539  * @tparam API Tested API descriptor
540  */
541 template <class API>
542 void TestCaseBase<API>::deinit(void)
543 {
544         this->delete_objects();
545 }
546
547 /** Runs the actual test for each shader type.
548  *
549  * @tparam API               Tested API descriptor
550  *
551  *  @return QP_TEST_RESULT_FAIL - test has failed;
552  *          QP_TEST_RESULT_PASS - test has succeeded;
553  **/
554 template <class API>
555 tcu::TestNode::IterateResult TestCaseBase<API>::iterate(void)
556 {
557         test_shader_compilation(TestCaseBase<API>::VERTEX_SHADER_TYPE);
558         test_shader_compilation(TestCaseBase<API>::FRAGMENT_SHADER_TYPE);
559
560         if (API::USE_ALL_SHADER_STAGES)
561         {
562                 test_shader_compilation(TestCaseBase<API>::COMPUTE_SHADER_TYPE);
563                 test_shader_compilation(TestCaseBase<API>::GEOMETRY_SHADER_TYPE);
564                 test_shader_compilation(TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE);
565                 test_shader_compilation(TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE);
566         }
567
568         return STOP;
569 }
570
571 /** Generates a shader object of the specified type,
572  *  attaches the specified shader source,
573  *  compiles it, and returns the compilation result.
574  *
575  * @tparam API               Tested API descriptor
576  *
577  * @param shader_source      The source for the shader object.
578  * @param tested_shader_type The type of shader being compiled (vertex or fragment).
579  *
580  * @return Compilation result (GL_TRUE if the shader compilation succeeded, GL_FALSE otherwise).
581  **/
582 template <class API>
583 glw::GLint TestCaseBase<API>::compile_shader_and_get_compilation_result(const std::string& tested_snippet,
584                                                                                                                                                 TestShaderType   tested_shader_type,
585                                                                                                                                                 bool                       require_gpu_shader5)
586 {
587         static const char* preamble_cs = "\n"
588                                                                          "layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;\n"
589                                                                          "\n";
590
591         static const char* preamble_gs = "\n"
592                                                                          "layout(points)                           in;\n"
593                                                                          "layout(triangle_strip, max_vertices = 4) out;\n"
594                                                                          "\n";
595
596         static const char* preamble_tcs = "\n"
597                                                                           "layout(vertices = 1) out;\n"
598                                                                           "\n";
599
600         static const char* preamble_tes = "\n"
601                                                                           "layout(isolines, point_mode) in;\n"
602                                                                           "\n";
603
604         glw::GLint                        compile_status   = GL_TRUE;
605         const glw::Functions& gl                           = context_id.getRenderContext().getFunctions();
606         glw::GLint                        shader_object_id = 0;
607
608         std::string shader_source;
609
610         if (true == tested_snippet.empty())
611         {
612                 return compile_status;
613         }
614
615         if (require_gpu_shader5)
616         {
617                 // Add the version number here, rather than in each individual test
618                 shader_source = API::shader_version_gpu5;
619         }
620         else
621         {
622                 // Add the version number here, rather than in each individual test
623                 shader_source = API::shader_version;
624         }
625
626         /* Apply stage specific stuff */
627         switch (tested_shader_type)
628         {
629         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
630                 break;
631         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
632                 break;
633         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
634                 shader_source += preamble_cs;
635                 break;
636         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
637                 shader_source += preamble_gs;
638                 break;
639         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
640                 shader_source += preamble_tcs;
641                 break;
642         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
643                 shader_source += preamble_tes;
644                 break;
645         default:
646                 TCU_FAIL("Unrecognized shader type.");
647                 break;
648         }
649
650         shader_source += tested_snippet;
651
652         /* Prepare shader object */
653         switch (tested_shader_type)
654         {
655         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
656         {
657                 shader_object_id = gl.createShader(GL_VERTEX_SHADER);
658                 assert(0 == vertex_shader_object_id);
659                 vertex_shader_object_id = shader_object_id;
660
661                 GLU_EXPECT_NO_ERROR(gl.getError(), "Could not create a vertex shader.");
662
663                 break;
664         } /* case TestCaseBase<API>::VERTEX_SHADER_TYPE: */
665         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
666         {
667                 shader_object_id = gl.createShader(GL_FRAGMENT_SHADER);
668                 assert(0 == fragment_shader_object_id);
669                 fragment_shader_object_id = shader_object_id;
670
671                 GLU_EXPECT_NO_ERROR(gl.getError(), "Could not create a fragment shader.");
672
673                 break;
674         } /* case TestCaseBase<API>::FRAGMENT_SHADER_TYPE: */
675         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
676         {
677                 shader_object_id = gl.createShader(GL_COMPUTE_SHADER);
678                 assert(0 == compute_shader_object_id);
679                 compute_shader_object_id = shader_object_id;
680
681                 GLU_EXPECT_NO_ERROR(gl.getError(), "Could not create a compute shader.");
682
683                 break;
684         } /* case TestCaseBase<API>::COMPUTE_SHADER_TYPE: */
685         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
686         {
687                 shader_object_id = gl.createShader(GL_GEOMETRY_SHADER);
688                 assert(0 == geometry_shader_object_id);
689                 geometry_shader_object_id = shader_object_id;
690
691                 GLU_EXPECT_NO_ERROR(gl.getError(), "Could not create a geometry shader.");
692
693                 break;
694         } /* case TestCaseBase<API>::GEOMETRY_SHADER_TYPE: */
695         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
696         {
697                 shader_object_id = gl.createShader(GL_TESS_CONTROL_SHADER);
698                 assert(0 == tess_ctrl_shader_object_id);
699                 tess_ctrl_shader_object_id = shader_object_id;
700
701                 GLU_EXPECT_NO_ERROR(gl.getError(), "Could not create a tesselation control shader.");
702
703                 break;
704         } /* case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: */
705         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
706         {
707                 shader_object_id = gl.createShader(GL_TESS_EVALUATION_SHADER);
708                 assert(0 == tess_eval_shader_object_id);
709                 tess_eval_shader_object_id = shader_object_id;
710
711                 GLU_EXPECT_NO_ERROR(gl.getError(), "Could not create a tesselation evaluation shader.");
712
713                 break;
714         } /* case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE: */
715         default:
716         {
717                 TCU_FAIL("Unrecognized shader type.");
718
719                 break;
720         } /* default: */
721         } /* switch (tested_shader_type) */
722
723         /* Assign source code to the objects */
724         const char* code_ptr = shader_source.c_str();
725
726 #if IS_DEBUG_DUMP_ALL_SHADERS
727         context_id.getTestContext().getLog() << tcu::TestLog::Message << "Compiling: " << tcu::TestLog::EndMessage;
728         context_id.getTestContext().getLog() << tcu::TestLog::KernelSource(code_ptr);
729 #endif /* IS_DEBUG_DUMP_ALL_SHADERS */
730
731         gl.shaderSource(shader_object_id, 1 /* count */, &code_ptr, NULL);
732         GLU_EXPECT_NO_ERROR(gl.getError(), "glShaderSource() failed");
733
734         /* Compile the shader */
735         gl.compileShader(shader_object_id);
736         GLU_EXPECT_NO_ERROR(gl.getError(), "glCompileShader() failed");
737
738         /* Get the compilation result. */
739         gl.getShaderiv(shader_object_id, GL_COMPILE_STATUS, &compile_status);
740         GLU_EXPECT_NO_ERROR(gl.getError(), "glGetShaderiv() failed");
741
742 #if IS_DEBUG
743         if (GL_TRUE != compile_status)
744         {
745                 glw::GLint  length = 0;
746                 std::string message;
747
748                 /* Error log length */
749                 gl.getShaderiv(shader_object_id, GL_INFO_LOG_LENGTH, &length);
750                 GLU_EXPECT_NO_ERROR(gl.getError(), "GetShaderiv");
751
752                 /* Prepare storage */
753                 message.resize(length, 0);
754
755                 /* Get error log */
756                 gl.getShaderInfoLog(shader_object_id, length, 0, &message[0]);
757                 GLU_EXPECT_NO_ERROR(gl.getError(), "GetShaderInfoLog");
758
759                 context_id.getTestContext().getLog() << tcu::TestLog::Message << "Error message: " << &message[0]
760                                                                                          << tcu::TestLog::EndMessage;
761
762 #if IS_DEBUG_DUMP_ALL_SHADERS
763 #else  /* IS_DEBUG_DUMP_ALL_SHADERS */
764                 context_id.getTestContext().getLog() << tcu::TestLog::KernelSource(code_ptr);
765 #endif /* IS_DEBUG_DUMP_ALL_SHADERS */
766         }
767 #endif /* IS_DEBUG */
768
769         return compile_status;
770 }
771
772 /** Runs the negative test.
773  *  The shader sources are considered as invalid,
774  *  and the compilation of a shader object with the specified
775  *  shader source is expected to fail.
776  *
777  * @tparam API               Tested API descriptor
778  *
779  * @param tested_shader_type The type of shader object (can be fragment or vertex).
780  * @param shader_source      The source for the shader object to be used for this test.
781  *
782  *  @return QP_TEST_RESULT_FAIL - test has failed;
783  *          QP_TEST_RESULT_PASS - test has succeeded;
784  **/
785 template <class API>
786 tcu::TestNode::IterateResult TestCaseBase<API>::execute_negative_test(
787         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& shader_source)
788 {
789         glw::GLint                        compile_status = GL_FALSE;
790         const char*                       error_message  = 0;
791         const glw::Functions& gl                         = context_id.getRenderContext().getFunctions();
792         bool                              test_result   = true;
793
794         /* Try to generate and compile the shader object. */
795         switch (tested_shader_type)
796         {
797         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
798                 error_message =
799                         "The fragment shader was expected to fail to compile, but the compilation process was successful.";
800                 break;
801
802         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
803                 error_message =
804                         "The vertex shader was expected to fail to compile, but the compilation process was successful.";
805
806                 break;
807
808         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
809                 error_message =
810                         "The compute shader was expected to fail to compile, but the compilation process was successful.";
811                 break;
812
813         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
814                 error_message =
815                         "The geometry shader was expected to fail to compile, but the compilation process was successful.";
816                 break;
817
818         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
819                 error_message = "The tesselation control shader was expected to fail to compile, but the compilation process "
820                                                 "was successful.";
821                 break;
822
823         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
824                 error_message = "The tesselation evaluation shader was expected to fail to compile, but the compilation "
825                                                 "process was successful.";
826                 break;
827
828         default:
829                 TCU_FAIL("Unrecognized shader type.");
830                 test_result = false;
831
832                 break;
833         } /* switch (shader_type) */
834
835         compile_status = compile_shader_and_get_compilation_result(shader_source, tested_shader_type);
836
837         if (compile_status == GL_TRUE)
838         {
839                 TCU_FAIL(error_message);
840
841                 test_result = false;
842         }
843
844         /* Deallocate any resources used. */
845         this->delete_objects();
846         if (0 != compute_shader_object_id)
847         {
848                 gl.deleteShader(compute_shader_object_id);
849                 compute_shader_object_id = 0;
850         }
851         if (0 != fragment_shader_object_id)
852         {
853                 gl.deleteShader(fragment_shader_object_id);
854                 fragment_shader_object_id = 0;
855         }
856         if (0 != geometry_shader_object_id)
857         {
858                 gl.deleteShader(geometry_shader_object_id);
859                 geometry_shader_object_id = 0;
860         }
861         if (0 != tess_ctrl_shader_object_id)
862         {
863                 gl.deleteShader(tess_ctrl_shader_object_id);
864                 tess_ctrl_shader_object_id = 0;
865         }
866         if (0 != tess_eval_shader_object_id)
867         {
868                 gl.deleteShader(tess_eval_shader_object_id);
869                 tess_eval_shader_object_id = 0;
870         }
871         if (0 != vertex_shader_object_id)
872         {
873                 gl.deleteShader(vertex_shader_object_id);
874                 vertex_shader_object_id = 0;
875         }
876
877         /* Return test pass if true. */
878         if (true == test_result)
879         {
880                 m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
881         }
882
883         return CONTINUE;
884 }
885
886 /** Runs the positive test.
887  *  The shader sources are considered as valid,
888  *  and the compilation and program linking are expected to succeed.
889  *
890  * @tparam API                     Tested API descriptor
891  *
892  * @param vertex_shader_source     The source for the vertex shader to be used for this test.
893  * @param fragment_shader_source   The source for the fragment shader to be used for this test.
894  * @param delete_generated_objects If true, the compiled shader objects will be deleted before returning.
895  *
896  *  @return QP_TEST_RESULT_FAIL - test has failed;
897  *          QP_TEST_RESULT_PASS - test has succeeded;
898  **/
899 template <class API>
900 tcu::TestNode::IterateResult TestCaseBase<API>::execute_positive_test(const std::string& vertex_shader_source,
901                                                                                                                                           const std::string& fragment_shader_source,
902                                                                                                                                           bool                           delete_generated_objects,
903                                                                                                                                           bool                           require_gpu_shader5)
904 {
905         glw::GLint                        compile_status = GL_TRUE;
906         const glw::Functions& gl                         = context_id.getRenderContext().getFunctions();
907         glw::GLint                        link_status   = GL_TRUE;
908         bool                              test_result   = true;
909
910         /* Compile, and check the compilation result for the fragment shader object. */
911         compile_status = compile_shader_and_get_compilation_result(
912                 fragment_shader_source, TestCaseBase<API>::FRAGMENT_SHADER_TYPE, require_gpu_shader5);
913
914         if (compile_status == GL_FALSE)
915         {
916                 TCU_FAIL("The fragment shader was expected to compile successfully, but failed to compile.");
917
918                 test_result = false;
919         }
920
921         /* Compile, and check the compilation result for the vertex shader object. */
922         compile_status = compile_shader_and_get_compilation_result(
923                 vertex_shader_source, TestCaseBase<API>::VERTEX_SHADER_TYPE, require_gpu_shader5);
924
925         if (compile_status == GL_FALSE)
926         {
927                 TCU_FAIL("The vertex shader was expected to compile successfully, but failed to compile.");
928
929                 test_result = false;
930         }
931
932         if (true == test_result)
933         {
934                 /* Create program object. */
935                 assert(0 == program_object_id);
936                 program_object_id = gl.createProgram();
937                 GLU_EXPECT_NO_ERROR(gl.getError(), "Could not create a program object.");
938
939                 /* Configure the program object */
940                 gl.attachShader(program_object_id, fragment_shader_object_id);
941                 gl.attachShader(program_object_id, vertex_shader_object_id);
942                 GLU_EXPECT_NO_ERROR(gl.getError(), "glAttachShader() failed.");
943
944                 gl.deleteShader(fragment_shader_object_id);
945                 gl.deleteShader(vertex_shader_object_id);
946                 fragment_shader_object_id = 0;
947                 vertex_shader_object_id   = 0;
948
949                 /* Link the program object */
950                 gl.linkProgram(program_object_id);
951                 GLU_EXPECT_NO_ERROR(gl.getError(), "glLinkProgram() failed.");
952
953                 /* Make sure the linking operation succeeded. */
954                 gl.getProgramiv(program_object_id, GL_LINK_STATUS, &link_status);
955                 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetProgramiv() failed.");
956
957                 if (link_status != GL_TRUE)
958                 {
959 #if IS_DEBUG
960                         glw::GLint  length = 0;
961                         std::string message;
962
963                         /* Get error log length */
964                         gl.getProgramiv(program_object_id, GL_INFO_LOG_LENGTH, &length);
965                         GLU_EXPECT_NO_ERROR(gl.getError(), "GetProgramiv");
966
967                         message.resize(length, 0);
968
969                         /* Get error log */
970                         gl.getProgramInfoLog(program_object_id, length, 0, &message[0]);
971                         GLU_EXPECT_NO_ERROR(gl.getError(), "GetProgramInfoLog");
972
973                         context_id.getTestContext().getLog() << tcu::TestLog::Message << "Error message: " << &message[0]
974                                                                                                  << tcu::TestLog::EndMessage;
975
976 #if IS_DEBUG_DUMP_ALL_SHADERS
977 #else  /* IS_DEBUG_DUMP_ALL_SHADERS */
978                         context_id.getTestContext().getLog() << tcu::TestLog::KernelSource(vertex_shader_source);
979                         context_id.getTestContext().getLog() << tcu::TestLog::KernelSource(fragment_shader_source);
980 #endif /* IS_DEBUG_DUMP_ALL_SHADERS */
981 #endif /* IS_DEBUG */
982
983                         TCU_FAIL("Linking was expected to succeed, but the process was unsuccessful.");
984
985                         test_result = false;
986                 }
987         }
988
989         if (delete_generated_objects)
990         {
991                 /* Deallocate any resources used. */
992                 this->delete_objects();
993         }
994
995         /* Return test pass if true. */
996         if (true == test_result)
997         {
998                 m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
999         }
1000
1001         return CONTINUE;
1002 }
1003
1004 /** Runs the positive test.
1005  *  The shader sources are considered as valid,
1006  *  and the compilation and program linking are expected to succeed.
1007  *
1008  * @tparam API                     Tested API descriptor
1009  *
1010  * @param vertex_shader_source     The source for the vertex shader to be used for this test.
1011  * @param tess_ctrl_shader_source  The source for the vertex shader to be used for this test.
1012  * @param tess_eval_shader_source  The source for the vertex shader to be used for this test.
1013  * @param geometry_shader_source   The source for the vertex shader to be used for this test.
1014  * @param fragment_shader_source   The source for the vertex shader to be used for this test.
1015  * @param compute_shader_source    The source for the fragment shader to be used for this test.
1016  * @param delete_generated_objects If true, the compiled shader objects will be deleted before returning.
1017  *
1018  *  @return QP_TEST_RESULT_FAIL - test has failed;
1019  *          QP_TEST_RESULT_PASS - test has succeeded;
1020  **/
1021 template <class API>
1022 tcu::TestNode::IterateResult TestCaseBase<API>::execute_positive_test(
1023         const std::string& vertex_shader_source, const std::string& tess_ctrl_shader_source,
1024         const std::string& tess_eval_shader_source, const std::string& geometry_shader_source,
1025         const std::string& fragment_shader_source, const std::string& compute_shader_source, bool delete_generated_objects,
1026         bool require_gpu_shader5)
1027 {
1028         glw::GLint                        compile_status = GL_TRUE;
1029         const glw::Functions& gl                         = context_id.getRenderContext().getFunctions();
1030         glw::GLint                        link_status   = GL_TRUE;
1031         bool                              test_compute   = !compute_shader_source.empty();
1032         bool                              test_result   = true;
1033
1034         if (false == test_compute)
1035         {
1036                 /* Compile, and check the compilation result for the fragment shader object. */
1037                 compile_status = compile_shader_and_get_compilation_result(
1038                         fragment_shader_source, TestCaseBase<API>::FRAGMENT_SHADER_TYPE, require_gpu_shader5);
1039
1040                 if (compile_status == GL_FALSE)
1041                 {
1042                         TCU_FAIL("The fragment shader was expected to compile successfully, but failed to compile.");
1043
1044                         test_result = false;
1045                 }
1046
1047                 /* Compile, and check the compilation result for the geometry shader object. */
1048                 compile_status = compile_shader_and_get_compilation_result(
1049                         geometry_shader_source, TestCaseBase<API>::GEOMETRY_SHADER_TYPE, require_gpu_shader5);
1050
1051                 if (compile_status == GL_FALSE)
1052                 {
1053                         TCU_FAIL("The geometry shader was expected to compile successfully, but failed to compile.");
1054
1055                         test_result = false;
1056                 }
1057
1058                 /* Compile, and check the compilation result for the te shader object. */
1059                 compile_status = compile_shader_and_get_compilation_result(
1060                         tess_eval_shader_source, TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE, require_gpu_shader5);
1061
1062                 if (compile_status == GL_FALSE)
1063                 {
1064                         TCU_FAIL("The tesselation evaluation shader was expected to compile successfully, but failed to compile.");
1065
1066                         test_result = false;
1067                 }
1068
1069                 /* Compile, and check the compilation result for the tc shader object. */
1070                 compile_status = compile_shader_and_get_compilation_result(
1071                         tess_ctrl_shader_source, TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE, require_gpu_shader5);
1072
1073                 if (compile_status == GL_FALSE)
1074                 {
1075                         TCU_FAIL("The tesselation control shader was expected to compile successfully, but failed to compile.");
1076
1077                         test_result = false;
1078                 }
1079
1080                 /* Compile, and check the compilation result for the vertex shader object. */
1081                 compile_status = compile_shader_and_get_compilation_result(
1082                         vertex_shader_source, TestCaseBase<API>::VERTEX_SHADER_TYPE, require_gpu_shader5);
1083
1084                 if (compile_status == GL_FALSE)
1085                 {
1086                         TCU_FAIL("The vertex shader was expected to compile successfully, but failed to compile.");
1087
1088                         test_result = false;
1089                 }
1090         }
1091         else
1092         {
1093                 /* Compile, and check the compilation result for the compute shader object. */
1094                 compile_status = compile_shader_and_get_compilation_result(
1095                         compute_shader_source, TestCaseBase<API>::COMPUTE_SHADER_TYPE, require_gpu_shader5);
1096
1097                 if (compile_status == GL_FALSE)
1098                 {
1099                         TCU_FAIL("The compute shader was expected to compile successfully, but failed to compile.");
1100
1101                         test_result = false;
1102                 }
1103         }
1104
1105         if (true == test_result)
1106         {
1107                 /* Create program object. */
1108                 program_object_id = gl.createProgram();
1109                 GLU_EXPECT_NO_ERROR(gl.getError(), "Could not create a program object.");
1110
1111                 /* Configure the program object */
1112                 if (false == test_compute)
1113                 {
1114                         gl.attachShader(program_object_id, fragment_shader_object_id);
1115
1116                         if (geometry_shader_object_id)
1117                         {
1118                                 gl.attachShader(program_object_id, geometry_shader_object_id);
1119                         }
1120
1121                         if (tess_ctrl_shader_object_id)
1122                         {
1123                                 gl.attachShader(program_object_id, tess_ctrl_shader_object_id);
1124                         }
1125
1126                         if (tess_eval_shader_object_id)
1127                         {
1128                                 gl.attachShader(program_object_id, tess_eval_shader_object_id);
1129                         }
1130
1131                         gl.attachShader(program_object_id, vertex_shader_object_id);
1132                 }
1133                 else
1134                 {
1135                         gl.attachShader(program_object_id, compute_shader_object_id);
1136                 }
1137                 GLU_EXPECT_NO_ERROR(gl.getError(), "glAttachShader() failed.");
1138
1139                 if (false == test_compute)
1140                 {
1141                         gl.deleteShader(fragment_shader_object_id);
1142
1143                         if (geometry_shader_object_id)
1144                         {
1145                                 gl.deleteShader(geometry_shader_object_id);
1146                         }
1147
1148                         if (tess_ctrl_shader_object_id)
1149                         {
1150                                 gl.deleteShader(tess_ctrl_shader_object_id);
1151                         }
1152
1153                         if (tess_eval_shader_object_id)
1154                         {
1155                                 gl.deleteShader(tess_eval_shader_object_id);
1156                         }
1157
1158                         gl.deleteShader(vertex_shader_object_id);
1159                 }
1160                 else
1161                 {
1162                         gl.deleteShader(compute_shader_object_id);
1163                 }
1164
1165                 fragment_shader_object_id  = 0;
1166                 vertex_shader_object_id = 0;
1167                 geometry_shader_object_id  = 0;
1168                 tess_ctrl_shader_object_id = 0;
1169                 tess_eval_shader_object_id = 0;
1170                 compute_shader_object_id   = 0;
1171
1172                 /* Link the program object */
1173                 gl.linkProgram(program_object_id);
1174                 GLU_EXPECT_NO_ERROR(gl.getError(), "glLinkProgram() failed.");
1175
1176                 /* Make sure the linking operation succeeded. */
1177                 gl.getProgramiv(program_object_id, GL_LINK_STATUS, &link_status);
1178                 GLU_EXPECT_NO_ERROR(gl.getError(), "glGetProgramiv() failed.");
1179
1180                 if (link_status != GL_TRUE)
1181                 {
1182 #if IS_DEBUG
1183                         glw::GLint  length = 0;
1184                         std::string message;
1185
1186                         /* Get error log length */
1187                         gl.getProgramiv(program_object_id, GL_INFO_LOG_LENGTH, &length);
1188                         GLU_EXPECT_NO_ERROR(gl.getError(), "GetProgramiv");
1189
1190                         message.resize(length, 0);
1191
1192                         /* Get error log */
1193                         gl.getProgramInfoLog(program_object_id, length, 0, &message[0]);
1194                         GLU_EXPECT_NO_ERROR(gl.getError(), "GetProgramInfoLog");
1195
1196                         context_id.getTestContext().getLog() << tcu::TestLog::Message << "Error message: " << &message[0]
1197                                                                                                  << tcu::TestLog::EndMessage;
1198
1199 #if IS_DEBUG_DUMP_ALL_SHADERS
1200                         if (false == test_compute)
1201                         {
1202                                 context_id.getTestContext().getLog() << tcu::TestLog::KernelSource(vertex_shader_source);
1203                                 context_id.getTestContext().getLog() << tcu::TestLog::KernelSource(tess_ctrl_shader_source);
1204                                 context_id.getTestContext().getLog() << tcu::TestLog::KernelSource(tess_eval_shader_source);
1205                                 context_id.getTestContext().getLog() << tcu::TestLog::KernelSource(geometry_shader_source);
1206                                 context_id.getTestContext().getLog() << tcu::TestLog::KernelSource(fragment_shader_source);
1207                         }
1208                         else
1209                         {
1210                                 context_id.getTestContext().getLog() << tcu::TestLog::KernelSource(compute_shader_source);
1211                         }
1212 #endif /* IS_DEBUG_DUMP_ALL_SHADERS */
1213 #endif /* IS_DEBUG */
1214
1215                         TCU_FAIL("Linking was expected to succeed, but the process was unsuccessful.");
1216
1217                         test_result = false;
1218                 }
1219         }
1220
1221         if (delete_generated_objects)
1222         {
1223                 /* Deallocate any resources used. */
1224                 this->delete_objects();
1225         }
1226
1227         /* Return test pass if true. */
1228         if (true == test_result)
1229         {
1230                 m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
1231         }
1232
1233         return CONTINUE;
1234 }
1235
1236 /** Adds the specified @param sub_script onto the base_string @param number_of_elements times.
1237  *  E.g. extend_string("a", [2], 3) would give a[2][2][2].
1238  *
1239  * @tparam API               Tested API descriptor
1240  *
1241  * @param base_string        The base string that is to be added to.
1242  * @param sub_string         The string to be repeatedly added
1243  * @param number_of_elements The number of repetitions.
1244  *
1245  *  @return The extended string.
1246  **/
1247 template <class API>
1248 std::string TestCaseBase<API>::extend_string(std::string base_string, std::string sub_string, size_t number_of_elements)
1249 {
1250         std::string temp_string = base_string;
1251
1252         for (size_t sub_script_index = 0; sub_script_index < number_of_elements; sub_script_index++)
1253         {
1254                 temp_string += sub_string;
1255         }
1256
1257         return temp_string;
1258 }
1259
1260 /* Generates the shader source code for the SizedDeclarationsPrimitive
1261  * array tests, and attempts to compile each test shader, for both
1262  * vertex and fragment shaders.
1263  *
1264  * @tparam API               Tested API descriptor
1265  *
1266  * @param tested_shader_type The type of shader that is being tested
1267  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1268  *
1269  **/
1270 template <class API>
1271 void SizedDeclarationsPrimitive<API>::test_shader_compilation(
1272         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1273 {
1274         for (size_t var_type_index = 0; var_type_index < API::n_var_types; var_type_index++)
1275         {
1276                 _supported_variable_types_map_const_iterator var_iterator =
1277                         supported_variable_types_map.find(API::var_types[var_type_index]);
1278
1279                 if (var_iterator != supported_variable_types_map.end())
1280                 {
1281                         /* Loop round for each var_types ("int", "uint", "float", etc.)
1282                          * We are testing a[][] to a [][][][][][][][], so start counter at 2. */
1283                         for (size_t max_dimension_limit = 2; max_dimension_limit <= API::MAX_ARRAY_DIMENSIONS;
1284                                  max_dimension_limit++)
1285                         {
1286                                 // Record the base varTypeModifier + varType
1287                                 std::string base_var_type                = var_iterator->second.type;
1288                                 std::string base_variable_string = base_var_type;
1289
1290                                 for (size_t base_sub_script_index = 0; base_sub_script_index <= max_dimension_limit;
1291                                          base_sub_script_index++)
1292                                 {
1293                                         std::string shader_source = "";
1294
1295                                         // Add the shader body start, and the base varTypeModifier + varType + variable name.
1296                                         shader_source += shader_start + "    " + base_variable_string + " a";
1297
1298                                         for (size_t remaining_sub_script_index = base_sub_script_index;
1299                                                  remaining_sub_script_index < max_dimension_limit; remaining_sub_script_index++)
1300                                         {
1301                                                 /* Add as many array sub_scripts as we can, up to the current dimension limit. */
1302                                                 shader_source += "[2]";
1303                                         }
1304
1305                                         /* End line */
1306                                         shader_source += ";\n";
1307
1308                                         /* End main */
1309                                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1310
1311                                         /* Execute test */
1312                                         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
1313
1314                                         /* From now on, we'll have an extra sub_script each time. */
1315                                         base_variable_string += "[2]";
1316                                 } /* for (int base_sub_script_index = 0; ...) */
1317                         }        /* for (int max_dimension_limit = 2; ...) */
1318                 }                 /* if var_type iterator found */
1319                 else
1320                 {
1321                         TCU_FAIL("Type not found.");
1322                 }
1323         } /* for (int var_type_index = 0; ...) */
1324 }
1325
1326 /* Generates the shader source code for the SizedDeclarationsStructTypes1
1327  * array tests, and attempts to compile each test shader, for both
1328  * vertex and fragment shaders.
1329  *
1330  * @tparam API               Tested API descriptor
1331  *
1332  * @param tested_shader_type The type of shader that is being tested
1333  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1334  */
1335 template <class API>
1336 void SizedDeclarationsStructTypes1<API>::test_shader_compilation(
1337         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1338 {
1339         std::string example_struct("struct light {\n"
1340                                                            "    float intensity;\n"
1341                                                            "    int   position;\n"
1342                                                            "};\n\n");
1343         std::string shader_source;
1344
1345         for (size_t max_dimension_index = 1; max_dimension_index < API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
1346         {
1347                 shader_source = example_struct;
1348                 shader_source += shader_start;
1349                 shader_source += "    light[2]";
1350
1351                 for (size_t temp_dimension_index = 0; temp_dimension_index < max_dimension_index; temp_dimension_index++)
1352                 {
1353                         shader_source += "[2]";
1354                 }
1355
1356                 shader_source += " x;\n";
1357
1358                 /* End main */
1359                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1360
1361                 /* Execute test */
1362                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
1363
1364         } /* for (int max_dimension_index = 1; ...) */
1365 }
1366
1367 /* Generates the shader source code for the SizedDeclarationsStructTypes2
1368  * array tests, and attempts to compile each test shader, for both
1369  * vertex and fragment shaders.
1370  *
1371  * @tparam API               Tested API descriptor
1372  *
1373  * @param tested_shader_type The type of shader that is being tested
1374  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1375  */
1376 template <class API>
1377 void SizedDeclarationsStructTypes2<API>::test_shader_compilation(
1378         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1379 {
1380         std::string structure_declaration = "struct MyStructure {\n"
1381                                                                                 "   float a[2], "
1382                                                                                 "b[2][2], "
1383                                                                                 "c[2][2][2], "
1384                                                                                 "d[2][2][2][2], "
1385                                                                                 "e[2][2][2][2][2], "
1386                                                                                 "f[2][2][2][2][2][2], "
1387                                                                                 "g[2][2][2][2][2][2][2], "
1388                                                                                 "h[2][2][2][2][2][2][2][2];\n"
1389                                                                                 "} myStructureObject;\n\n";
1390         std::string shader_source = structure_declaration;
1391
1392         shader_source += shader_start;
1393
1394         /* End main */
1395         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1396
1397         /* Execute test */
1398         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
1399 }
1400
1401 /* Generates the shader source code for the SizedDeclarationsStructTypes3
1402  * array tests, and attempts to compile each test shader, for both
1403  * vertex and fragment shaders.
1404  *
1405  * @tparam API               Tested API descriptor
1406  *
1407  * @param tested_shader_type The type of shader that is being tested
1408  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1409  */
1410 template <class API>
1411 void SizedDeclarationsStructTypes3<API>::test_shader_compilation(
1412         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1413 {
1414         std::string example_struct("struct light {\n"
1415                                                            "    float[2] intensity;\n"
1416                                                            "    int[2] position;\n"
1417                                                            "};\n");
1418         std::string shader_source;
1419
1420         for (size_t max_dimension_index = 1; max_dimension_index <= API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
1421         {
1422                 shader_source = example_struct;
1423                 shader_source += shader_start;
1424                 shader_source += this->extend_string("    light my_light_object", "[2]", max_dimension_index);
1425                 shader_source += ";\n";
1426
1427                 /* End main */
1428                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1429
1430                 /* Execute test */
1431                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
1432         } /* for (int max_dimension_index = 1; ...) */
1433 }
1434
1435 /* Generates the shader source code for the SizedDeclarationsStructTypes4
1436  * array tests, and attempts to compile each test shader, for both
1437  * vertex and fragment shaders.
1438  *
1439  * @tparam API               Tested API descriptor
1440  *
1441  * @param tested_shader_type The type of shader that is being tested
1442  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1443  */
1444 template <class API>
1445 void SizedDeclarationsStructTypes4<API>::test_shader_compilation(
1446         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1447 {
1448         std::string example_struct("struct light {\n"
1449                                                            "    float[2] intensity;\n"
1450                                                            "    int[2] position;\n"
1451                                                            "} lightVar[2]");
1452         std::string shader_source;
1453
1454         for (size_t max_dimension_index = 1; max_dimension_index < API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
1455         {
1456                 shader_source = example_struct;
1457
1458                 for (size_t temp_dimension_index = 0; temp_dimension_index < max_dimension_index; temp_dimension_index++)
1459                 {
1460                         shader_source += "[2]";
1461                 }
1462                 shader_source += ";\n\n";
1463                 shader_source += shader_start;
1464
1465                 /* End main */
1466                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1467
1468                 /* Execute test */
1469                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
1470         } /* for (int max_dimension_index = 1; ...) */
1471 }
1472
1473 /* Generates the shader source code for the SizedDeclarationsTypenameStyle1
1474  * array tests, and attempts to compile each test shader, for both
1475  * vertex and fragment shaders.
1476  *
1477  * @tparam API               Tested API descriptor
1478  *
1479  * @param tested_shader_type The type of shader that is being tested
1480  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1481  */
1482 template <class API>
1483 void SizedDeclarationsTypenameStyle1<API>::test_shader_compilation(
1484         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1485 {
1486         for (size_t max_dimension_index = 1; max_dimension_index <= API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
1487         {
1488                 std::string shader_source = shader_start;
1489
1490                 shader_source += this->extend_string("    float", "[2]", max_dimension_index);
1491                 shader_source += this->extend_string(" x", "[2]", API::MAX_ARRAY_DIMENSIONS - max_dimension_index);
1492                 shader_source += ";\n";
1493
1494                 /* End main */
1495                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1496
1497                 /* Execute test */
1498                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
1499         } /* for (int max_dimension_index = 1; ...) */
1500 }
1501
1502 /* Generates the shader source code for the SizedDeclarationsTypenameStyle2
1503  * array tests, and attempts to compile each test shader, for both
1504  * vertex and fragment shaders.
1505  *
1506  * @tparam API               Tested API descriptor
1507  *
1508  * @param tested_shader_type The type of shader that is being tested
1509  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1510  */
1511 template <class API>
1512 void SizedDeclarationsTypenameStyle2<API>::test_shader_compilation(
1513         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1514 {
1515         std::string shader_source = shader_start;
1516
1517         shader_source += this->extend_string("    float", "[2]", 2);
1518         shader_source += this->extend_string(" a", "[2]", 0);
1519         shader_source += ", ";
1520         shader_source += this->extend_string("b", "[2]", 1);
1521         shader_source += ", ";
1522         shader_source += this->extend_string("c", "[2]", 2);
1523         shader_source += ", ";
1524         shader_source += this->extend_string("d", "[2]", 3);
1525         shader_source += ", ";
1526         shader_source += this->extend_string("e", "[2]", 4);
1527         shader_source += ", ";
1528         shader_source += this->extend_string("f", "[2]", 5);
1529         shader_source += ", ";
1530         shader_source += this->extend_string("g", "[2]", 6);
1531         shader_source += ";\n";
1532
1533         /* End main */
1534         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1535
1536         /* Execute test */
1537         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
1538 }
1539
1540 /* Generates the shader source code for the SizedDeclarationsTypenameStyle3
1541  * array tests, and attempts to compile each test shader, for both
1542  * vertex and fragment shaders.
1543  *
1544  * @tparam API               Tested API descriptor
1545  *
1546  * @param tested_shader_type The type of shader that is being tested
1547  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1548  */
1549 template <class API>
1550 void SizedDeclarationsTypenameStyle3<API>::test_shader_compilation(
1551         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1552 {
1553         std::string shader_source = "struct{\n" + this->extend_string("    float", "[2]", 2);
1554
1555         shader_source += this->extend_string(" a", "[2]", API::MAX_ARRAY_DIMENSIONS - API::MAX_ARRAY_DIMENSIONS);
1556         shader_source += ",";
1557         shader_source += this->extend_string("    b", "[2]", 1);
1558         shader_source += ",";
1559         shader_source += this->extend_string("    c", "[2]", 2);
1560         shader_source += ",";
1561         shader_source += this->extend_string("    d", "[2]", 3);
1562         shader_source += ",";
1563         shader_source += this->extend_string("    e", "[2]", 4);
1564         shader_source += ",";
1565         shader_source += this->extend_string("    f", "[2]", 5);
1566         shader_source += ",";
1567         shader_source += this->extend_string("    g", "[2]", 6);
1568         shader_source += ";\n} x;\n\n";
1569         shader_source += shader_start;
1570
1571         /* End main */
1572         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1573
1574         /* Execute test */
1575         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
1576 }
1577
1578 /* Generates the shader source code for the SizedDeclarationsTypenameStyle4
1579  * array tests, and attempts to compile each test shader, for both
1580  * vertex and fragment shaders.
1581  *
1582  * @tparam API               Tested API descriptor
1583  *
1584  * @param tested_shader_type The type of shader that is being tested
1585  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1586  */
1587 template <class API>
1588 void SizedDeclarationsTypenameStyle4<API>::test_shader_compilation(
1589         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1590 {
1591         std::string example_struct_begin("struct light {\n");
1592         std::string example_struct_end("};\n\n");
1593
1594         for (size_t max_dimension_index = 1; max_dimension_index <= API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
1595         {
1596                 std::string shader_source = example_struct_begin;
1597
1598                 shader_source += this->extend_string("    float", "[2]", max_dimension_index);
1599                 shader_source += this->extend_string(" x", "[2]", API::MAX_ARRAY_DIMENSIONS - max_dimension_index);
1600                 shader_source += ";\n";
1601                 shader_source += example_struct_end;
1602                 shader_source += shader_start;
1603
1604                 /* End main */
1605                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1606
1607                 /* Execute test */
1608                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
1609         } /* for (int max_dimension_index = 1; ...) */
1610 }
1611
1612 /* Generates the shader source code for the SizedDeclarationsTypenameStyle5
1613  * array tests, and attempts to compile each test shader, for both
1614  * vertex and fragment shaders.
1615  *
1616  * @tparam API               Tested API descriptor
1617  *
1618  * @param tested_shader_type The type of shader that is being tested
1619  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1620  */
1621 template <class API>
1622 void SizedDeclarationsTypenameStyle5<API>::test_shader_compilation(
1623         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1624 {
1625         std::string example_struct_begin("struct light {\n");
1626         std::string example_struct_end("};\n\n");
1627
1628         std::string shader_source = example_struct_begin;
1629
1630         shader_source += this->extend_string("    float", "[2]", 2);
1631         shader_source += this->extend_string(" a", "[2]", API::MAX_ARRAY_DIMENSIONS - API::MAX_ARRAY_DIMENSIONS);
1632         shader_source += ", ";
1633         shader_source += this->extend_string("b", "[2]", 2);
1634         shader_source += ", ";
1635         shader_source += this->extend_string("c", "[2]", 3);
1636         shader_source += ", ";
1637         shader_source += this->extend_string("d", "[2]", 4);
1638         shader_source += ", ";
1639         shader_source += this->extend_string("e", "[2]", 5);
1640         shader_source += ", ";
1641         shader_source += this->extend_string("f", "[2]", 6);
1642         shader_source += ";\n";
1643         shader_source += example_struct_end;
1644         shader_source += shader_start;
1645
1646         /* End main */
1647         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1648
1649         /* Execute test */
1650         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
1651 }
1652
1653 /* Generates the shader source code for the SizedDeclarationsFunctionParams
1654  * array tests, and attempts to compile each test shader, for both
1655  * vertex and fragment shaders.
1656  *
1657  * @tparam API               Tested API descriptor
1658  *
1659  * @param tested_shader_type The type of shader that is being tested
1660  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1661  */
1662 template <class API>
1663 void SizedDeclarationsFunctionParams<API>::test_shader_compilation(
1664         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1665 {
1666         size_t          dimension_index = 0;
1667         std::string example_struct1("\nvoid my_function(");
1668         std::string example_struct2(")\n"
1669                                                                 "{\n"
1670                                                                 "}\n\n");
1671         std::string base_variable_string;
1672         std::string variable_basenames[API::MAX_ARRAY_DIMENSIONS] = { "v1", "v2", "v3", "v4", "v5", "v6", "v7", "v8" };
1673         std::string full_variable_names[API::MAX_ARRAY_DIMENSIONS];
1674
1675         for (size_t max_dimension_index = 0; max_dimension_index < API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
1676         {
1677                 full_variable_names[max_dimension_index] =
1678                         this->extend_string(variable_basenames[max_dimension_index], "[2]", max_dimension_index + 1);
1679         }
1680
1681         for (size_t max_dimension_index = 0; max_dimension_index < API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
1682         {
1683                 base_variable_string += "float ";
1684                 base_variable_string += full_variable_names[max_dimension_index];
1685                 base_variable_string += ";\n";
1686         }
1687
1688         base_variable_string += example_struct1;
1689         base_variable_string += this->extend_string("float a", "[2]", 1);
1690         base_variable_string += ", ";
1691         base_variable_string += this->extend_string("float b", "[2]", 2);
1692         base_variable_string += ", ";
1693         base_variable_string += this->extend_string("float c", "[2]", 3);
1694         base_variable_string += ", ";
1695         base_variable_string += this->extend_string("float d", "[2]", 4);
1696         base_variable_string += ", ";
1697         base_variable_string += this->extend_string("float e", "[2]", 5);
1698         base_variable_string += ", ";
1699         base_variable_string += this->extend_string("float f", "[2]", 6);
1700         base_variable_string += ", ";
1701         base_variable_string += this->extend_string("float g", "[2]", 7);
1702         base_variable_string += ", ";
1703         base_variable_string += this->extend_string("float h", "[2]", 8);
1704         base_variable_string += example_struct2;
1705
1706         std::string shader_source = base_variable_string;
1707
1708         shader_source += shader_start;
1709         shader_source += "    my_function(";
1710
1711         for (dimension_index = 0; dimension_index < API::MAX_ARRAY_DIMENSIONS - 1; dimension_index++)
1712         {
1713                 shader_source += variable_basenames[dimension_index];
1714                 shader_source += ", ";
1715         }
1716
1717         shader_source += variable_basenames[dimension_index];
1718         shader_source += ");\n";
1719
1720         /* End main */
1721         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1722
1723         /* Execute test */
1724         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
1725
1726         /* Only the previous case should succeed, so start from index 1 rather than 0.
1727          * The other cases should fail, so only compile them, rather than trying to also link them.
1728          * We'll swap items 2/3, then 2/4, then 2/5, then 2/6, ...
1729          * Then we'll swap items 3/4, then 3/5, ...
1730          * Repeat, starting for 4/5-8, 5/6-8, 6/7-8...
1731          * Finally, we'll swap items 7/8
1732          */
1733         for (size_t swap_item = 1; swap_item < API::MAX_ARRAY_DIMENSIONS; swap_item++)
1734         {
1735                 for (size_t max_dimension_index = swap_item + 1; max_dimension_index < API::MAX_ARRAY_DIMENSIONS;
1736                          max_dimension_index++)
1737                 {
1738                         std::string temp = variable_basenames[swap_item];
1739
1740                         shader_source                                                   = base_variable_string;
1741                         variable_basenames[swap_item]                   = variable_basenames[max_dimension_index];
1742                         variable_basenames[max_dimension_index] = temp;
1743
1744                         shader_source += shader_start;
1745                         shader_source += "    my_function(";
1746
1747                         for (dimension_index = 0; dimension_index < API::MAX_ARRAY_DIMENSIONS - 1; dimension_index++)
1748                         {
1749                                 shader_source += variable_basenames[dimension_index];
1750                                 shader_source += ", ";
1751                         }
1752
1753                         shader_source += variable_basenames[dimension_index];
1754                         shader_source += ");\n";
1755
1756                         temp                                                                    = variable_basenames[swap_item];
1757                         variable_basenames[swap_item]                   = variable_basenames[max_dimension_index];
1758                         variable_basenames[max_dimension_index] = temp;
1759
1760                         /* End main */
1761                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1762
1763                         /* Execute test */
1764                         this->execute_negative_test(tested_shader_type, shader_source);
1765                 } /* for (int max_dimension_index = swap_item + 1; ...) */
1766         }        /* for (int swap_item = 1; ...) */
1767 }
1768
1769 /* Generates the shader source code for the sized_declarations_invalid_sizes1
1770  * array tests, and attempts to compile each test shader, for both
1771  * vertex and fragment shaders.
1772  *
1773  * @tparam API               Tested API descriptor
1774  *
1775  * @param tested_shader_type The type of shader that is being tested
1776  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1777  */
1778 template <class API>
1779 void sized_declarations_invalid_sizes1<API>::test_shader_compilation(
1780         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1781 {
1782         std::string invalid_declarations[] = {
1783                 "float x[2][2][2][0];\n", "float x[2][2][0][2];\n", "float x[2][0][2][2];\n", "float x[0][2][2][2];\n",
1784                 "float x[2][2][0][0];\n", "float x[2][0][2][0];\n", "float x[0][2][2][0];\n", "float x[2][0][0][2];\n",
1785                 "float x[0][2][0][2];\n", "float x[0][0][2][2];\n", "float x[2][0][0][0];\n", "float x[0][2][0][0];\n",
1786                 "float x[0][0][2][0];\n", "float x[0][0][0][2];\n", "float x[0][0][0][0];\n"
1787         };
1788
1789         for (size_t invalid_declarations_index = 0;
1790                  invalid_declarations_index < sizeof(invalid_declarations) / sizeof(invalid_declarations);
1791                  invalid_declarations_index++)
1792         {
1793                 std::string shader_source;
1794
1795                 shader_source = shader_start;
1796                 shader_source += invalid_declarations[invalid_declarations_index];
1797
1798                 /* End main */
1799                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1800
1801                 /* Execute test */
1802                 this->execute_negative_test(tested_shader_type, shader_source);
1803         } /* for (int invalid_declarations_index = 0; ...) */
1804 }
1805
1806 /* Generates the shader source code for the sized_declarations_invalid_sizes2
1807  * array tests, and attempts to compile each test shader, for both
1808  * vertex and fragment shaders.
1809  *
1810  * @tparam API               Tested API descriptor
1811  *
1812  * @param tested_shader_type The type of shader that is being tested
1813  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1814  */
1815 template <class API>
1816 void sized_declarations_invalid_sizes2<API>::test_shader_compilation(
1817         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1818 {
1819         std::string invalid_declarations[] = {
1820                 "    float x[2][2][2][-1];\n",   "    float x[2][2][-1][2];\n",   "    float x[2][-1][2][2];\n",
1821                 "    float x[-1][2][2][2];\n",   "    float x[2][2][-1][-1];\n",  "    float x[2][-1][2][-1];\n",
1822                 "    float x[-1][2][2][-1];\n",  "    float x[2][-1][-1][2];\n",  "    float x[-1][2][-1][2];\n",
1823                 "    float x[-1][-1][2][2];\n",  "    float x[2][-1][-1][-1];\n", "    float x[-1][2][-1][-1];\n",
1824                 "    float x[-1][-1][2][-1];\n", "    float x[-1][-1][-1][2];\n", "    float x[-1][-1][-1][-1];\n"
1825         };
1826
1827         for (size_t invalid_declarations_index = 0;
1828                  invalid_declarations_index < sizeof(invalid_declarations) / sizeof(invalid_declarations);
1829                  invalid_declarations_index++)
1830         {
1831                 std::string shader_source;
1832
1833                 shader_source = shader_start;
1834                 shader_source += invalid_declarations[invalid_declarations_index];
1835
1836                 /* End main */
1837                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1838
1839                 /* Execute test */
1840                 this->execute_negative_test(tested_shader_type, shader_source);
1841         } /* for (int invalid_declarations_index = 0; ...) */
1842 }
1843
1844 /* Generates the shader source code for the sized_declarations_invalid_sizes3
1845  * array tests, and attempts to compile each test shader, for both
1846  * vertex and fragment shaders.
1847  *
1848  * @tparam API               Tested API descriptor
1849  *
1850  * @param tested_shader_type The type of shader that is being tested
1851  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1852  */
1853 template <class API>
1854 void sized_declarations_invalid_sizes3<API>::test_shader_compilation(
1855         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1856 {
1857         std::string invalid_declarations[] = {
1858                 "    float x[2][2][2][a];\n", "    float x[2][2][a][2];\n", "    float x[2][a][2][2];\n",
1859                 "    float x[a][2][2][2];\n", "    float x[2][2][a][a];\n", "    float x[2][a][2][a];\n",
1860                 "    float x[a][2][2][a];\n", "    float x[2][a][a][2];\n", "    float x[a][2][a][2];\n",
1861                 "    float x[a][a][2][2];\n", "    float x[2][a][a][a];\n", "    float x[a][2][a][a];\n",
1862                 "    float x[a][a][2][a];\n", "    float x[a][a][a][2];\n", "    float x[a][a][a][a];\n"
1863         };
1864         std::string non_constant_variable_declaration = "    uint a = 2u;\n";
1865
1866         for (size_t invalid_declarations_index = 0;
1867                  invalid_declarations_index < sizeof(invalid_declarations) / sizeof(invalid_declarations);
1868                  invalid_declarations_index++)
1869         {
1870                 std::string shader_source;
1871
1872                 shader_source = shader_start;
1873                 shader_source += non_constant_variable_declaration;
1874                 shader_source += invalid_declarations[invalid_declarations_index];
1875
1876                 /* End main */
1877                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1878
1879                 /* Execute test */
1880                 this->execute_negative_test(tested_shader_type, shader_source);
1881         } /* for (int invalid_declarations_index = 0; ...) */
1882 }
1883
1884 /* Generates the shader source code for the sized_declarations_invalid_sizes4
1885  * array tests, and attempts to compile each test shader, for both
1886  * vertex and fragment shaders.
1887  *
1888  * @tparam API               Tested API descriptor
1889  *
1890  * @param tested_shader_type The type of shader that is being tested
1891  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1892  */
1893 template <class API>
1894 void sized_declarations_invalid_sizes4<API>::test_shader_compilation(
1895         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1896 {
1897         std::string input[] = { "    float x[2,2][2][2];\n", "    float x[2][2,2][2];\n", "    float x[2][2][2,2];\n",
1898                                                         "    float x[2,2,2][2];\n",  "    float x[2][2,2,2];\n",  "    float x[2,2,2,2];\n" };
1899
1900         for (size_t string_index = 0; string_index < sizeof(input) / sizeof(input[0]); string_index++)
1901         {
1902                 std::string shader_source;
1903
1904                 shader_source += shader_start;
1905                 shader_source += input[string_index];
1906
1907                 /* End main */
1908                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1909
1910                 /* Execute test */
1911                 this->execute_negative_test(tested_shader_type, shader_source);
1912         } /* for (int string_index = 0; ...) */
1913 }
1914
1915 /* Constructs a suitable constructor for the specified number of dimensions.
1916  *
1917  * @tparam API            Tested API descriptor
1918  *
1919  * @param var_type        The type of the variable
1920  * @param dimension_index The current recursion level (counts down)
1921  * @param init_string     The initialisation string
1922  */
1923 template <class API>
1924 std::string ConstructorsAndUnsizedDeclConstructors1<API>::recursively_initialise(std::string var_type,
1925                                                                                                                                                                  size_t          dimension_index,
1926                                                                                                                                                                  std::string init_string)
1927 {
1928         std::string temp_string;
1929
1930         if (dimension_index == 0)
1931         {
1932                 temp_string = init_string;
1933         }
1934         else
1935         {
1936                 std::string prefix = "\n";
1937
1938                 for (size_t indent_index = dimension_index; indent_index < (API::MAX_ARRAY_DIMENSIONS + 1); indent_index++)
1939                 {
1940                         prefix += "    ";
1941                 }
1942
1943                 prefix += this->extend_string(var_type, "[]", dimension_index);
1944                 prefix += "(";
1945                 for (int sub_script_index = 0; sub_script_index < 2; sub_script_index++)
1946                 {
1947                         temp_string += prefix;
1948                         temp_string += recursively_initialise(var_type, dimension_index - 1, init_string);
1949                         prefix = ", ";
1950                         if (sub_script_index == 1)
1951                         {
1952                                 break;
1953                         }
1954                 }
1955                 temp_string += ")";
1956         }
1957
1958         return temp_string;
1959 }
1960
1961 /* Generates the shader source code for the ConstructorsAndUnsizedDeclConstructors1
1962  * array tests, and attempts to compile each test shader, for both
1963  * vertex and fragment shaders.
1964  *
1965  * @tparam API               Tested API descriptor
1966  *
1967  * @param tested_shader_type The type of shader that is being tested
1968  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
1969  */
1970 template <class API>
1971 void ConstructorsAndUnsizedDeclConstructors1<API>::test_shader_compilation(
1972         typename TestCaseBase<API>::TestShaderType tested_shader_type)
1973 {
1974         //vec4 color = vec4(0.0, 1.0, 0.0, 1.0);
1975         int num_var_types = API::n_var_types;
1976
1977         for (int var_type_index = 0; var_type_index < num_var_types; var_type_index++)
1978         {
1979                 _supported_variable_types_map_const_iterator var_iterator =
1980                         supported_variable_types_map.find(API::var_types[var_type_index]);
1981
1982                 if (var_iterator != supported_variable_types_map.end())
1983                 {
1984                         for (size_t max_dimension_index = 2; max_dimension_index < API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
1985                         {
1986                                 std::string base_variable_string =
1987                                         this->extend_string("    " + var_iterator->second.type + " a", "[]", max_dimension_index);
1988
1989                                 base_variable_string += " = ";
1990                                 base_variable_string += recursively_initialise(var_iterator->second.type, max_dimension_index,
1991                                                                                                                            var_iterator->second.initializer_with_ones);
1992                                 base_variable_string += ";\n\n";
1993
1994                                 std::string shader_source = shader_start + base_variable_string;
1995
1996                                 /* End main */
1997                                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
1998
1999                                 /* Execute test */
2000                                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
2001                         } /* for (int max_dimension_index = 1; ...) */
2002                 }        /* if var_type iterator found */
2003                 else
2004                 {
2005                         TCU_FAIL("Type not found.");
2006                 }
2007         } /* for (int var_type_index = 0; ...) */
2008
2009         for (int var_type_index = 0; var_type_index < num_var_types; var_type_index++)
2010         {
2011                 _supported_variable_types_map_const_iterator var_iterator =
2012                         supported_variable_types_map.find(API::var_types[var_type_index]);
2013
2014                 if (var_iterator != supported_variable_types_map.end())
2015                 {
2016                         std::string base_structure = "struct my_structure\n";
2017
2018                         base_structure += "{\n";
2019                         base_structure += "    " + var_iterator->second.type + " b;\n";
2020                         base_structure += "    " + var_iterator->second.type + " c;\n";
2021                         base_structure += "};\n\n";
2022
2023                         for (size_t max_dimension_index = 1; max_dimension_index < API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
2024                         {
2025                                 std::string outer_separator = "(";
2026                                 std::string base_variable_string;
2027
2028                                 base_variable_string +=
2029                                         this->extend_string("    " + var_iterator->second.type + " a", "[2]", max_dimension_index);
2030                                 base_variable_string += " = ";
2031                                 base_variable_string += recursively_initialise(var_iterator->second.type, max_dimension_index,
2032                                                                                                                            var_iterator->second.initializer_with_ones);
2033                                 base_variable_string += ";\n\n";
2034
2035                                 std::string shader_source = base_structure + shader_start + base_variable_string;
2036
2037                                 /* End main */
2038                                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2039
2040                                 /* Execute test */
2041                                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
2042                         } /* for (int max_dimension_index = 1; ...) */
2043                 }        /* if var_type iterator found */
2044                 else
2045                 {
2046                         TCU_FAIL("Type not found.");
2047                 }
2048         } /* for (int var_type_index = 0; ...) */
2049 }
2050
2051 /* Generates the shader source code for the ConstructorsAndUnsizedDeclConstructors2
2052  * array tests, and attempts to compile each test shader, for both
2053  * vertex and fragment shaders.
2054  *
2055  * @tparam API               Tested API descriptor
2056  *
2057  * @param tested_shader_type The type of shader that is being tested
2058  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2059  */
2060 template <class API>
2061 void ConstructorsAndUnsizedDeclConstructors2<API>::test_shader_compilation(
2062         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2063 {
2064         std::string base_variable_string = "    float[2][2] x = float[2][2](float[4](1.0, 2.0, 3.0, 4.0));\n";
2065         std::string shader_source                = shader_start + base_variable_string;
2066
2067         /* End main */
2068         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2069
2070         /* Execute test */
2071         this->execute_negative_test(tested_shader_type, shader_source);
2072
2073         base_variable_string = "float[2][2] x = float[2][2](float[1][4](float[4](1.0, 2.0, 3.0, 4.0)));\n\n";
2074         shader_source            = base_variable_string + shader_start;
2075
2076         /* End main */
2077         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2078
2079         /* Execute test */
2080         this->execute_negative_test(tested_shader_type, shader_source);
2081 }
2082
2083 /* Generates the shader source code for the ConstructorsAndUnsizedDeclUnsizedConstructors
2084  * array tests, and attempts to compile each test shader, for both
2085  * vertex and fragment shaders.
2086  *
2087  * @tparam API               Tested API descriptor
2088  *
2089  * @param tested_shader_type The type of shader that is being tested
2090  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2091  */
2092 template <class API>
2093 void ConstructorsAndUnsizedDeclUnsizedConstructors<API>::test_shader_compilation(
2094         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2095 {
2096         std::string shader_variable_declarations = "= float[2][1][2][1](\n"
2097                                                                                            "        float[1][2][1](\n"
2098                                                                                            "            float[2][1]( \n"
2099                                                                                            "                float[1](12.3), float[1](54.2) \n"
2100                                                                                            "            )\n"
2101                                                                                            "        ),\n"
2102                                                                                            "        float[1][2][1](\n"
2103                                                                                            "            float[2][1]( \n"
2104                                                                                            "                float[1]( 3.2), float[1]( 7.4) \n"
2105                                                                                            "            )\n"
2106                                                                                            "        )\n"
2107                                                                                            "    );\n\n";
2108
2109         std::string input[] = { "float a[2][1][2][]", "float a[2][1][][1]", "float a[2][1][][]", "float a[2][][2][1]",
2110                                                         "float a[2][][2][]",  "float a[2][][][1]",  "float a[2][][][]",  "float a[][1][2][1]",
2111                                                         "float a[][1][2][]",  "float a[][1][][1]",  "float a[][1][][]",  "float a[][][2][1]",
2112                                                         "float a[][][2][]",   "float a[][][][1]",   "float a[][][][]" };
2113
2114         for (size_t string_index = 0; string_index < sizeof(input) / sizeof(input[0]); string_index++)
2115         {
2116                 std::string shader_source = shader_start + "    " + input[string_index] + shader_variable_declarations;
2117
2118                 /* End main */
2119                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2120
2121                 /* Execute test */
2122                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
2123         } /* for (int string_index = 0; ...) */
2124 }
2125
2126 /* Generates the shader source code for the ConstructorsAndUnsizedDeclConst
2127  * array tests, and attempts to compile each test shader, for both
2128  * vertex and fragment shaders.
2129  *
2130  * @tparam API               Tested API descriptor
2131  *
2132  * @param tested_shader_type The type of shader that is being tested
2133  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2134  */
2135 template <class API>
2136 void ConstructorsAndUnsizedDeclConst<API>::test_shader_compilation(
2137         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2138 {
2139         std::string shader_source = "const float[2][2] x = float[2][2](float[2](1.0, 2.0), float[2](3.0, 4.0));\n\n";
2140         shader_source += shader_start;
2141
2142         /* End main */
2143         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2144
2145         /* Execute test */
2146         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
2147 }
2148
2149 /* Generates the shader source code for the ConstructorsAndUnsizedDeclInvalidConstructors1
2150  * array tests, and attempts to compile each test shader, for both
2151  * vertex and fragment shaders.
2152  *
2153  * @tparam API               Tested API descriptor
2154  *
2155  * @param tested_shader_type The type of shader that is being tested
2156  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2157  */
2158 template <class API>
2159 void ConstructorsAndUnsizedDeclInvalidConstructors1<API>::test_shader_compilation(
2160         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2161 {
2162         int num_var_types = sizeof(opaque_var_types) / sizeof(opaque_var_types[0]);
2163
2164         for (int var_type_index = 0; var_type_index < num_var_types; var_type_index++)
2165         {
2166                 _supported_variable_types_map_const_iterator var_iterator =
2167                         supported_variable_types_map.find(opaque_var_types[var_type_index]);
2168
2169                 if (var_iterator != supported_variable_types_map.end())
2170                 {
2171                         std::string base_variable_string =
2172                                 "uniform " + var_iterator->second.precision + " " + var_iterator->second.type + " my_sampler1;\n" +
2173                                 "uniform " + var_iterator->second.precision + " " + var_iterator->second.type + " my_sampler2;\n" +
2174                                 "uniform " + var_iterator->second.precision + " " + var_iterator->second.type + " my_sampler3;\n" +
2175                                 "uniform " + var_iterator->second.precision + " " + var_iterator->second.type + " my_sampler4;\n\n";
2176
2177                         std::string shader_source = base_variable_string + shader_start;
2178                         shader_source += "    const " + var_iterator->second.type + "[2][2] x = " + var_iterator->second.type +
2179                                                          "[2][2](" + var_iterator->second.type + "[2](my_sampler1, my_sampler2), " +
2180                                                          var_iterator->second.type + "[2](my_sampler3, my_sampler4));\n\n";
2181
2182                         /* End main */
2183                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2184
2185                         /* Execute test */
2186                         this->execute_negative_test(tested_shader_type, shader_source);
2187                 } /* if var_type iterator found */
2188                 else
2189                 {
2190                         TCU_FAIL("Type not found.");
2191                 }
2192         } /* for (int var_type_index = 0; ...) */
2193 }
2194
2195 /* Generates the shader source code for the ConstructorsAndUnsizedDeclInvalidConstructors2
2196  * array tests, and attempts to compile each test shader, for both
2197  * vertex and fragment shaders.
2198  *
2199  * @tparam API               Tested API descriptor
2200  *
2201  * @param tested_shader_type The type of shader that is being tested
2202  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2203  */
2204 template <class API>
2205 void ConstructorsAndUnsizedDeclInvalidConstructors2<API>::test_shader_compilation(
2206         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2207 {
2208         std::string invalid_initializers[] = { "    int x[2][2][0]; \n", "    int x[2][0][2]; \n", "    int x[0][2][2]; \n",
2209                                                                                    "    int x[2][0][0]; \n", "    int x[0][2][0]; \n", "    int x[0][0][2]; \n",
2210                                                                                    "    int x[0][0][0]; \n" };
2211
2212         for (size_t invalid_initializers_index = 0;
2213                  invalid_initializers_index < sizeof(invalid_initializers) / sizeof(invalid_initializers[0]);
2214                  invalid_initializers_index++)
2215         {
2216                 std::string shader_source;
2217
2218                 shader_source = shader_start;
2219                 shader_source += invalid_initializers[invalid_initializers_index];
2220
2221                 /* End main */
2222                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2223
2224                 /* Execute test */
2225                 this->execute_negative_test(tested_shader_type, shader_source);
2226         } /* for (int invalid_initializers_index = 0; ...) */
2227 }
2228
2229 /* Generates the shader source code for the ConstructorsAndUnsizedDeclInvalidConstructors3
2230  * array tests, and attempts to compile each test shader, for both
2231  * vertex and fragment shaders.
2232  *
2233  * @tparam API               Tested API descriptor
2234  *
2235  * @param tested_shader_type The type of shader that is being tested
2236  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2237  */
2238 template <class API>
2239 void ConstructorsAndUnsizedDeclInvalidConstructors3<API>::test_shader_compilation(
2240         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2241 {
2242         std::string invalid_initializers[] = { "    int x[2][2][-1]; \n",  "    int x[2][-1][2]; \n",
2243                                                                                    "    int x[-1][2][2]; \n",  "    int x[2][-1][-1]; \n",
2244                                                                                    "    int x[-1][2][-1]; \n", "    int x[-1][-1][2]; \n",
2245                                                                                    "    int x[-1][-1][-1]; \n" };
2246
2247         for (size_t invalid_initializers_index = 0;
2248                  invalid_initializers_index < sizeof(invalid_initializers) / sizeof(invalid_initializers[0]);
2249                  invalid_initializers_index++)
2250         {
2251                 std::string shader_source;
2252
2253                 shader_source = shader_start;
2254                 shader_source += invalid_initializers[invalid_initializers_index];
2255
2256                 /* End main */
2257                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2258
2259                 /* Execute test */
2260                 this->execute_negative_test(tested_shader_type, shader_source);
2261         } /* for (int invalid_initializers_index = 0; ...) */
2262 }
2263
2264 /* Generates the shader source code for the ConstructorsAndUnsizedDeclInvalidConstructors4
2265  * array tests, and attempts to compile each test shader, for both
2266  * vertex and fragment shaders.
2267  *
2268  * @tparam API               Tested API descriptor
2269  *
2270  * @param tested_shader_type The type of shader that is being tested
2271  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2272  */
2273 template <class API>
2274 void ConstructorsAndUnsizedDeclInvalidConstructors4<API>::test_shader_compilation(
2275         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2276 {
2277         std::string invalid_initializers[] = { "    int x[2][2][a]; \n", "    int x[2][a][2]; \n", "    int x[a][2][2]; \n",
2278                                                                                    "    int x[2][a][a]; \n", "    int x[a][2][a]; \n", "    int x[a][a][2]; \n",
2279                                                                                    "    int x[a][a][a]; \n" };
2280         std::string non_constant_variable_init = "    uint a = 2u;\n";
2281
2282         for (size_t invalid_initializers_index = 0;
2283                  invalid_initializers_index < sizeof(invalid_initializers) / sizeof(invalid_initializers[0]);
2284                  invalid_initializers_index++)
2285         {
2286                 std::string shader_source;
2287
2288                 shader_source = shader_start;
2289                 shader_source += non_constant_variable_init;
2290                 shader_source += invalid_initializers[invalid_initializers_index];
2291
2292                 /* End main */
2293                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2294
2295                 /* Execute test */
2296                 this->execute_negative_test(tested_shader_type, shader_source);
2297         } /* for (int invalid_initializers_index = 0; ...) */
2298 }
2299
2300 /* Generates the shader source code for the ConstructorsAndUnsizedDeclConstructorSizing1
2301  * array tests, and attempts to compile each test shader, for both
2302  * vertex and fragment shaders.
2303  *
2304  * @tparam API               Tested API descriptor
2305  *
2306  * @param tested_shader_type The type of shader that is being tested
2307  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2308  */
2309 template <class API>
2310 void ConstructorsAndUnsizedDeclConstructorSizing1<API>::test_shader_compilation(
2311         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2312 {
2313         std::string valid_size_initializers[] = { "[1][1][1][]", "[1][1][][1]", "[1][][1][1]", "[][1][1][1]", "[1][1][][]",
2314                                                                                           "[1][][1][]",  "[][1][1][]",  "[1][][][1]",  "[][1][][1]",  "[][][1][1]",
2315                                                                                           "[1][][][]",   "[][1][][]",   "[][][1][]",   "[][][][1]",   "[][][][]" };
2316
2317         for (size_t var_type_index = 0; var_type_index < API::n_var_types; var_type_index++)
2318         {
2319                 _supported_variable_types_map_const_iterator var_iterator =
2320                         supported_variable_types_map.find(API::var_types[var_type_index]);
2321
2322                 if (var_iterator != supported_variable_types_map.end())
2323                 {
2324                         for (size_t valid_size_initializers_index = 0;
2325                                  valid_size_initializers_index < sizeof(valid_size_initializers) / sizeof(valid_size_initializers[0]);
2326                                  valid_size_initializers_index++)
2327                         {
2328                                 std::string shader_source;
2329                                 std::string variable_constructor =
2330                                         "    " + var_iterator->second.type + " x" + valid_size_initializers[valid_size_initializers_index] +
2331                                         " = " + var_iterator->second.type + "[1][1][1][1](" + var_iterator->second.type + "[1][1][1](" +
2332                                         var_iterator->second.type + "[1][1](" + var_iterator->second.type + "[1](" +
2333                                         var_iterator->second.initializer_with_zeroes + "))));\n";
2334
2335                                 shader_source = shader_start;
2336                                 shader_source += variable_constructor;
2337
2338                                 /* End main */
2339                                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2340
2341                                 /* Execute test */
2342                                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
2343                         } /* for (int valid_size_initializers_index = 0; ...) */
2344                 }        /* if var_type iterator found */
2345                 else
2346                 {
2347                         TCU_FAIL("Type not found.");
2348                 }
2349         } /* for (int var_type_index = 0; ...) */
2350 }
2351
2352 /* Generates the shader source code for the ConstructorsAndUnsizedDeclConstructorSizing2
2353  * array tests, and attempts to compile each test shader, for both
2354  * vertex and fragment shaders.
2355  *
2356  * @tparam API               Tested API descriptor
2357  *
2358  * @param tested_shader_type The type of shader that is being tested
2359  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2360  */
2361 template <class API>
2362 void ConstructorsAndUnsizedDeclConstructorSizing2<API>::test_shader_compilation(
2363         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2364 {
2365         std::string shader_source = shader_start;
2366
2367         shader_source += "    float[] a ="
2368                                          "            float[](1.0, 2.0),"
2369                                          "        b[] ="
2370                                          "         float[][]("
2371                                          "             float[](1.0, 2.0),"
2372                                          "             float[](3.0, 4.0)"
2373                                          "         ),"
2374                                          "        c[][] ="
2375                                          "         float[][][]("
2376                                          "             float[][]("
2377                                          "                 float[](1.0),"
2378                                          "                 float[](2.0)"
2379                                          "             )"
2380                                          "         ),"
2381                                          "        d[][][] ="
2382                                          "         float[][][][]("
2383                                          "             float[][][]("
2384                                          "                 float[][]("
2385                                          "                     float[](1.0, 2.0),"
2386                                          "                     float[](3.0, 4.0),"
2387                                          "                     float[](5.0, 6.0)"
2388                                          "                 )"
2389                                          "             ),"
2390                                          "             float[][][]("
2391                                          "                 float[][]("
2392                                          "                     float[](1.0, 2.0),"
2393                                          "                     float[](3.0, 4.0),"
2394                                          "                     float[](5.0, 6.0)"
2395                                          "                 )"
2396                                          "             )"
2397                                          "         ),"
2398                                          "        e[][][][]="
2399                                          "         float[][][][][]("
2400                                          "             float[][][][]("
2401                                          "                 float[][][]("
2402                                          "                     float[][]("
2403                                          "                         float[](1.0),"
2404                                          "                         float[](2.0)"
2405                                          "                     ),"
2406                                          "                     float[][]("
2407                                          "                         float[](1.0),"
2408                                          "                         float[](2.0)"
2409                                          "                     ),"
2410                                          "                     float[][]("
2411                                          "                         float[](1.0),"
2412                                          "                         float[](2.0)"
2413                                          "                     )"
2414                                          "                 ),"
2415                                          "                 float[][][]("
2416                                          "                     float[][]("
2417                                          "                         float[](1.0),"
2418                                          "                         float[](2.0)"
2419                                          "                     ),"
2420                                          "                     float[][]("
2421                                          "                         float[](1.0),"
2422                                          "                         float[](2.0)"
2423                                          "                     ),"
2424                                          "                     float[][]("
2425                                          "                         float[](1.0),"
2426                                          "                         float[](2.0)"
2427                                          "                     )"
2428                                          "                 )"
2429                                          "             )"
2430                                          "         ),"
2431                                          "        f[][][][][]="
2432                                          "         float[][][][][][]("
2433                                          "             float[][][][][]("
2434                                          "                 float[][][][]("
2435                                          "                     float[][][]("
2436                                          "                         float[][]("
2437                                          "                             float[](1.0)"
2438                                          "                         )"
2439                                          "                     )"
2440                                          "                 )"
2441                                          "             )"
2442                                          "         ),"
2443                                          "        g[][][][][][]="
2444                                          "         float[][][][][][][]("
2445                                          "             float[][][][][][]("
2446                                          "                 float[][][][][]("
2447                                          "                     float[][][][]("
2448                                          "                         float[][][]("
2449                                          "                             float[][]("
2450                                          "                                 float[](1.0)"
2451                                          "                             )"
2452                                          "                         )"
2453                                          "                     )"
2454                                          "                 )"
2455                                          "             )"
2456                                          "         ),"
2457                                          "        h[][][][][][][]="
2458                                          "         float[][][][][][][][]("
2459                                          "             float[][][][][][][]("
2460                                          "                 float[][][][][][]("
2461                                          "                     float[][][][][]("
2462                                          "                         float[][][][]("
2463                                          "                             float[][][]("
2464                                          "                                 float[][]("
2465                                          "                                     float[](1.0)"
2466                                          "                                 )"
2467                                          "                             )"
2468                                          "                         )"
2469                                          "                     )"
2470                                          "                 )"
2471                                          "             )"
2472                                          "         );\n";
2473
2474         /* End main */
2475         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2476
2477         /* Execute test */
2478         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
2479 }
2480
2481 /* Constructs a suitable constructor for the specified number of dimensions.
2482  *
2483  * @tparam API            Tested API descriptor
2484  *
2485  * @param var_type        The type of the variable
2486  * @param dimension_index The current recursion level (counts down)
2487  * @param init_string     The initialisation string
2488  */
2489 template <class API>
2490 std::string ConstructorsAndUnsizedDeclStructConstructors<API>::recursively_initialise(std::string var_type,
2491                                                                                                                                                                           size_t          dimension_index,
2492                                                                                                                                                                           std::string init_string)
2493 {
2494         std::string temp_string;
2495
2496         if (dimension_index == 0)
2497         {
2498                 temp_string = var_type + "(" + init_string + ")";
2499         }
2500         else
2501         {
2502                 std::string prefix = "\n";
2503
2504                 for (size_t indent_index = dimension_index; indent_index < (API::MAX_ARRAY_DIMENSIONS + 1); indent_index++)
2505                 {
2506                         prefix += "    ";
2507                 }
2508
2509                 prefix += this->extend_string(var_type, "[]", dimension_index);
2510                 prefix += "(";
2511
2512                 for (int sub_script_index = 0; sub_script_index < 2; sub_script_index++)
2513                 {
2514                         temp_string += prefix;
2515                         temp_string += recursively_initialise(var_type, dimension_index - 1, init_string);
2516                         prefix = ", ";
2517
2518                         if (dimension_index == 1)
2519                         {
2520                                 break;
2521                         }
2522                 }
2523                 temp_string += ")";
2524         }
2525
2526         return temp_string;
2527 }
2528
2529 /* Generates the shader source code for the ConstructorsAndUnsizedDeclStructConstructors
2530  * array tests, and attempts to compile each test shader, for both
2531  * vertex and fragment shaders.
2532  *
2533  * @tparam API               Tested API descriptor
2534  *
2535  * @param tested_shader_type The type of shader that is being tested
2536  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2537  */
2538 template <class API>
2539 void ConstructorsAndUnsizedDeclStructConstructors<API>::test_shader_compilation(
2540         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2541 {
2542         std::string example_structure_definition("struct light {\n"
2543                                                                                          "    float intensity;\n"
2544                                                                                          "    int position;\n"
2545                                                                                          "};\n");
2546         std::string example_structure_object("    light my_light_variable");
2547
2548         for (size_t max_dimension_index = 2; max_dimension_index <= API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
2549         {
2550                 std::string base_variable_string = this->extend_string(example_structure_object, "[]", max_dimension_index);
2551                 base_variable_string += " = ";
2552                 base_variable_string += recursively_initialise("light", max_dimension_index, "1.0, 2");
2553                 base_variable_string += ";\n\n";
2554
2555                 std::string shader_source = example_structure_definition + shader_start + base_variable_string;
2556
2557                 /* End main */
2558                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2559
2560                 /* Execute test */
2561                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
2562         } /* for (int max_dimension_index = 2; ...) */
2563 }
2564
2565 /* Generates the shader source code for the ConstructorsAndUnsizedDeclUnsizedArrays1
2566  * array tests, and attempts to compile each test shader, for both
2567  * vertex and fragment shaders.
2568  *
2569  * @tparam API               Tested API descriptor
2570  *
2571  * @param tested_shader_type The type of shader that is being tested
2572  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2573  */
2574 template <class API>
2575 void ConstructorsAndUnsizedDeclUnsizedArrays1<API>::test_shader_compilation(
2576         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2577 {
2578         std::string base_variable_string;
2579
2580         for (size_t max_dimension_index = 2; max_dimension_index <= API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
2581         {
2582                 base_variable_string = this->extend_string("    int x", "[]", max_dimension_index);
2583                 base_variable_string += ";\n\n";
2584
2585                 std::string shader_source = shader_start + base_variable_string;
2586
2587                 /* End main */
2588                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2589
2590                 /* Execute test */
2591                 this->execute_negative_test(tested_shader_type, shader_source);
2592         } /* for (int max_dimension_index = 2; ...) */
2593 }
2594
2595 /* Generates the shader source code for the ConstructorsAndUnsizedDeclUnsizedArrays2
2596  * array tests, and attempts to compile each test shader, for both
2597  * vertex and fragment shaders.
2598  *
2599  * @tparam API               Tested API descriptor
2600  *
2601  * @param tested_shader_type The type of shader that is being tested
2602  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2603  */
2604 template <class API>
2605 void ConstructorsAndUnsizedDeclUnsizedArrays2<API>::test_shader_compilation(
2606         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2607 {
2608         std::string input[] = { "    float [] x = float[](1), y;\n\n" };
2609
2610         for (size_t string_index = 0; string_index < sizeof(input) / sizeof(input[0]); string_index++)
2611         {
2612                 std::string shader_source;
2613
2614                 shader_source += shader_start;
2615                 shader_source += input[string_index];
2616
2617                 /* End main */
2618                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2619
2620                 /* Execute test */
2621                 EXECUTE_SHADER_TEST(API::ALLOW_UNSIZED_DECLARATION, tested_shader_type, shader_source);
2622         } /* for (int string_index = 0; ...) */
2623 }
2624
2625 /* Generates the shader source code for the ConstructorsAndUnsizedDeclUnsizedArrays3
2626  * array tests, and attempts to compile each test shader, for both
2627  * vertex and fragment shaders.
2628  *
2629  * @tparam API               Tested API descriptor
2630  *
2631  * @param tested_shader_type The type of shader that is being tested
2632  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2633  */
2634 template <class API>
2635 void ConstructorsAndUnsizedDeclUnsizedArrays3<API>::test_shader_compilation(
2636         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2637 {
2638         std::string base_variable_string("    float[][] x = mat4(0);\n\n");
2639
2640         std::string shader_source = shader_start + base_variable_string;
2641
2642         /* End main */
2643         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2644
2645         /* Execute test */
2646         this->execute_negative_test(tested_shader_type, shader_source);
2647 }
2648
2649 /* Generates the shader source code for the ConstructorsAndUnsizedDeclUnsizedArrays4
2650  * array tests, and attempts to compile each test shader, for both
2651  * vertex and fragment shaders.
2652  *
2653  * @tparam API               Tested API descriptor
2654  *
2655  * @param tested_shader_type The type of shader that is being tested
2656  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2657  */
2658 template <class API>
2659 void ConstructorsAndUnsizedDeclUnsizedArrays4<API>::test_shader_compilation(
2660         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2661 {
2662         std::string example_struct("struct light {\n"
2663                                                            "    float[][] intensity;\n"
2664                                                            "    int       position;\n"
2665                                                            "} myLight;\n\n");
2666
2667         std::string shader_source = example_struct + shader_start;
2668
2669         /* End main */
2670         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2671
2672         /* Execute test */
2673         this->execute_negative_test(tested_shader_type, shader_source);
2674 }
2675
2676 /* Constructs a suitable constructor for the specified number of dimensions.
2677  *
2678  * @tparam API            Tested API descriptor
2679  *
2680  * @param dimension_index The current recursion level (counts down)
2681  * @param init_string     The initialisation string
2682  */
2683 template <class API>
2684 std::string ExpressionsAssignment1<API>::recursively_initialise(std::string var_type, size_t dimension_index,
2685                                                                                                                                 std::string init_string)
2686 {
2687         std::string temp_string;
2688
2689         if (dimension_index == 0)
2690         {
2691                 temp_string = init_string;
2692         }
2693         else
2694         {
2695                 std::string prefix = "\n";
2696
2697                 for (size_t indent_index = dimension_index; indent_index < (API::MAX_ARRAY_DIMENSIONS + 1); indent_index++)
2698                 {
2699                         prefix += "    ";
2700                 }
2701
2702                 prefix += this->extend_string(var_type, "[]", dimension_index);
2703                 prefix += "(";
2704                 for (int sub_script_index = 0; sub_script_index < 2; sub_script_index++)
2705                 {
2706                         temp_string += prefix;
2707                         temp_string += recursively_initialise(var_type, dimension_index - 1, init_string);
2708                         prefix = ", ";
2709                         if (dimension_index == 1)
2710                         {
2711                                 break;
2712                         }
2713                 }
2714                 temp_string += ")";
2715         }
2716
2717         return temp_string;
2718 }
2719
2720 /* Generates the shader source code for the ExpressionsAssignment1
2721  * array tests, and attempts to compile each test shader, for both
2722  * vertex and fragment shaders.
2723  *
2724  * @tparam API               Tested API descriptor
2725  *
2726  * @param tested_shader_type The type of shader that is being tested
2727  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2728  */
2729 template <class API>
2730 void ExpressionsAssignment1<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
2731 {
2732         for (size_t max_dimension_index = 2; max_dimension_index <= API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
2733         {
2734                 std::string prefix = "(";
2735                 std::string base_variable_string;
2736
2737                 base_variable_string += this->extend_string("    float x", "[2]", max_dimension_index);
2738                 base_variable_string += " = ";
2739                 base_variable_string += recursively_initialise("float", max_dimension_index, "4.0, 6.0");
2740                 base_variable_string += ";\n";
2741                 base_variable_string += this->extend_string("    float y", "[2]", max_dimension_index);
2742                 base_variable_string += " = ";
2743                 base_variable_string += recursively_initialise("float", max_dimension_index, "1.0, 2.0");
2744                 base_variable_string += ";\n\n";
2745
2746                 std::string shader_source = shader_start + base_variable_string;
2747
2748                 shader_source += "    x = y;\n";
2749
2750                 /* End main */
2751                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2752
2753                 /* Execute test */
2754                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
2755         } /* for (int max_dimension_index = 2; ...) */
2756 }
2757
2758 /* Generates the shader source code for the ExpressionsAssignment2
2759  * array tests, and attempts to compile each test shader, for both
2760  * vertex and fragment shaders.
2761  *
2762  * @tparam API               Tested API descriptor
2763  *
2764  * @param tested_shader_type The type of shader that is being tested
2765  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2766  */
2767 template <class API>
2768 void ExpressionsAssignment2<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
2769 {
2770         std::string shader_body("    float a[2] = float[](1.0, 2.0);\n"
2771                                                         "    float b[2][2] = float[][](float[](1.0, 2.0), float[](1.0, 2.0));\n"
2772                                                         "    float c[2][2][2] = float[][][]("
2773                                                         "float[][](float[](1.0, 2.0), float[](1.0, 2.0)),"
2774                                                         "float[][](float[](1.0, 2.0), float[](1.0, 2.0)));\n"
2775                                                         "    float d[2][2][2][2] = float[][][][]("
2776                                                         "float[][][]("
2777                                                         "float[][](float[](1.0, 2.0), float[](1.0, 2.0)), "
2778                                                         "float[][](float[](1.0, 2.0), float[](1.0, 2.0))),"
2779                                                         "float[][][]("
2780                                                         "float[][](float[](1.0, 2.0), float[](1.0, 2.0)), "
2781                                                         "float[][](float[](1.0, 2.0), float[](1.0, 2.0))));\n\n");
2782
2783         std::string variable_basenames[] = { "a", "b", "c", "d" };
2784         int                     number_of_elements   = sizeof(variable_basenames) / sizeof(variable_basenames[0]);
2785
2786         for (int variable_index = 0; variable_index < number_of_elements; variable_index++)
2787         {
2788                 for (int value_index = variable_index; value_index < number_of_elements; value_index++)
2789                 {
2790                         std::string shader_source = shader_start + shader_body;
2791
2792                         /* Avoid the situation when a variable is assign to itself. */
2793                         if (variable_index != value_index)
2794                         {
2795                                 shader_source += "    " + variable_basenames[variable_index] + " = " + variable_basenames[value_index];
2796                                 shader_source += ";\n";
2797
2798                                 /* End main */
2799                                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2800
2801                                 /* Execute test */
2802                                 this->execute_negative_test(tested_shader_type, shader_source);
2803                         } /* if(variable_index != value_index) */
2804                 }        /* for (int value_index = variable_index; ...) */
2805         }                 /* for (int variable_index = 0; ...) */
2806 }
2807
2808 /* Generates the shader source code for the ExpressionsAssignment3
2809  * array tests, and attempts to compile each test shader, for both
2810  * vertex and fragment shaders.
2811  *
2812  * @tparam API               Tested API descriptor
2813  *
2814  * @param tested_shader_type The type of shader that is being tested
2815  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2816  */
2817 template <class API>
2818 void ExpressionsAssignment3<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
2819 {
2820         std::string prefix, base_variable_string;
2821
2822         const int test_array_dimensions = 4;
2823
2824         prefix = this->extend_string("    float a", "[1]", 4);
2825         prefix += " = float[][][][](\n"
2826                           "       float[][][](\n"
2827                           "           float[][](\n"
2828                           "               float[](1.0))));\n";
2829
2830         prefix += "    float b";
2831
2832         for (int permutation = 0; permutation < (1 << test_array_dimensions); permutation++)
2833         {
2834                 base_variable_string = prefix;
2835
2836                 for (int sub_script_index = test_array_dimensions - 1; sub_script_index >= 0; sub_script_index--)
2837                 {
2838                         if (permutation & (1 << sub_script_index))
2839                         {
2840                                 base_variable_string += "[1]";
2841                         }
2842                         else
2843                         {
2844                                 base_variable_string += "[2]";
2845                         }
2846                 }
2847
2848                 base_variable_string += ";\n\n";
2849
2850                 if (permutation != (1 << test_array_dimensions) - 1)
2851                 {
2852                         std::string shader_source = shader_start + base_variable_string;
2853
2854                         shader_source += "    b = a;\n";
2855
2856                         /* End main */
2857                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2858
2859                         /* Execute test */
2860                         this->execute_negative_test(tested_shader_type, shader_source);
2861                 } /* if (permutation != (1 << test_array_dimensions) - 1) */
2862         }        /* for (int permutation = 0; ...) */
2863 }
2864
2865 /* Generates the shader source code for the ExpressionsTypeRestrictions1
2866  * array tests, and attempts to compile each test shader, for both
2867  * vertex and fragment shaders.
2868  *
2869  * @tparam API               Tested API descriptor
2870  *
2871  * @param tested_shader_type The type of shader that is being tested
2872  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2873  */
2874 template <class API>
2875 void ExpressionsTypeRestrictions1<API>::test_shader_compilation(
2876         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2877 {
2878         int num_var_types = sizeof(opaque_var_types) / sizeof(opaque_var_types[0]);
2879
2880         for (int var_type_index = 0; var_type_index < num_var_types; var_type_index++)
2881         {
2882                 _supported_variable_types_map_const_iterator var_iterator =
2883                         supported_variable_types_map.find(opaque_var_types[var_type_index]);
2884
2885                 if (var_iterator != supported_variable_types_map.end())
2886                 {
2887                         std::string shader_source =
2888                                 "uniform " + var_iterator->second.precision + " " + var_iterator->second.type + " var1[2][2];\n"
2889                                                                                                                                                                                                 "uniform " +
2890                                 var_iterator->second.precision + " " + var_iterator->second.type + " var2[2][2];\n\n";
2891                         shader_source += shader_start;
2892
2893                         shader_source += "    var1 = var2;\n";
2894
2895                         /* End main */
2896                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2897
2898                         /* Execute test */
2899                         this->execute_negative_test(tested_shader_type, shader_source);
2900                 } /* if var_type iterator found */
2901                 else
2902                 {
2903                         TCU_FAIL("Type not found.");
2904                 }
2905         } /* for (int var_type_index = 0; ...) */
2906 }
2907
2908 /* Generates the shader source code for the ExpressionsTypeRestrictions2
2909  * array tests, and attempts to compile each test shader, for both
2910  * vertex and fragment shaders.
2911  *
2912  * @tparam API               Tested API descriptor
2913  *
2914  * @param tested_shader_type The type of shader that is being tested
2915  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2916  */
2917 template <class API>
2918 void ExpressionsTypeRestrictions2<API>::test_shader_compilation(
2919         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2920 {
2921         int num_var_types = sizeof(opaque_var_types) / sizeof(opaque_var_types[0]);
2922
2923         for (int var_type_index = 0; var_type_index < num_var_types; var_type_index++)
2924         {
2925                 _supported_variable_types_map_const_iterator var_iterator =
2926                         supported_variable_types_map.find(opaque_var_types[var_type_index]);
2927
2928                 if (var_iterator != supported_variable_types_map.end())
2929                 {
2930                         std::string shader_source =
2931                                 "uniform " + var_iterator->second.precision + " " + var_iterator->second.type + " sampler1;\n"
2932                                                                                                                                                                                                 "uniform " +
2933                                 var_iterator->second.precision + " " + var_iterator->second.type + " sampler2;\n"
2934                                                                                                                                                                    "uniform " +
2935                                 var_iterator->second.precision + " " + var_iterator->second.type + " sampler3;\n"
2936                                                                                                                                                                    "uniform " +
2937                                 var_iterator->second.precision + " " + var_iterator->second.type + " sampler4;\n"
2938                                                                                                                                                                    "struct light1 {\n"
2939                                                                                                                                                                    "    " +
2940                                 var_iterator->second.type + " var1[2][2];\n"
2941                                                                                         "};\n\n";
2942                         shader_source += shader_start;
2943
2944                         shader_source +=
2945                                 ("    light1 x = light1(" + var_iterator->second.type + "[][](" + var_iterator->second.type +
2946                                  "[](sampler1, sampler2), " + var_iterator->second.type + "[](sampler3, sampler4)));\n");
2947                         shader_source += "    light1 y = x;\n\n";
2948
2949                         /* End main */
2950                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2951
2952                         /* Execute test */
2953                         this->execute_negative_test(tested_shader_type, shader_source);
2954                 } /* if var_type iterator found */
2955                 else
2956                 {
2957                         TCU_FAIL("Type not found.");
2958                 }
2959         } /* for (int var_type_index = 0; ...) */
2960 }
2961
2962 /* Generates the shader source code for the ExpressionsIndexingScalar1
2963  * array tests, and attempts to compile each test shader, for both
2964  * vertex and fragment shaders.
2965  *
2966  * @tparam API               Tested API descriptor
2967  *
2968  * @param tested_shader_type The type of shader that is being tested
2969  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
2970  */
2971 template <class API>
2972 void ExpressionsIndexingScalar1<API>::test_shader_compilation(
2973         typename TestCaseBase<API>::TestShaderType tested_shader_type)
2974 {
2975         for (size_t var_type_index = 0; var_type_index < API::n_var_types; var_type_index++)
2976         {
2977                 _supported_variable_types_map_const_iterator var_iterator =
2978                         supported_variable_types_map.find(API::var_types[var_type_index]);
2979
2980                 if (var_iterator != supported_variable_types_map.end())
2981                 {
2982                         std::string shader_source = shader_start + "    " + var_iterator->second.type + " x[1][2][3][4];\n\n";
2983
2984                         shader_source += "    for (uint i = 0u; i < 2u; i++) {\n";
2985                         shader_source += "        for (uint j = 0u; j < 3u; j++) {\n";
2986                         shader_source += "            for (uint k = 0u; k < 4u; k++) {\n";
2987                         shader_source += "                x[0][i][j][k] = " + var_iterator->second.initializer_with_ones + ";\n";
2988                         shader_source += "            }\n";
2989                         shader_source += "        }\n";
2990                         shader_source += "    }\n";
2991
2992                         /* End main */
2993                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
2994
2995                         /* Execute test */
2996                         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
2997                 } /* if var_type iterator found */
2998                 else
2999                 {
3000                         TCU_FAIL("Type not found.");
3001                 }
3002         }
3003 }
3004
3005 /* Generates the shader source code for the ExpressionsIndexingScalar2
3006  * array tests, and attempts to compile each test shader, for both
3007  * vertex and fragment shaders.
3008  *
3009  * @tparam API               Tested API descriptor
3010  *
3011  * @param tested_shader_type The type of shader that is being tested
3012  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
3013  */
3014 template <class API>
3015 void ExpressionsIndexingScalar2<API>::test_shader_compilation(
3016         typename TestCaseBase<API>::TestShaderType tested_shader_type)
3017 {
3018         std::string base_shader_string, shader_source;
3019
3020         // This test tests arrays with 4 dimensions, e.g. x[1][1][1][1]
3021         const int test_array_dimensions = 4;
3022
3023         base_shader_string = "float a[1][2][3][4];\n";
3024         base_shader_string += "float b = 2.0;\n\n";
3025         base_shader_string += shader_start;
3026
3027         // There are 16 permutations, so loop 4x4 times.
3028         for (int permutation = 0; permutation < (1 << test_array_dimensions); permutation++)
3029         {
3030                 shader_source = base_shader_string + "    a"; // a var called 'a'
3031
3032                 for (int sub_script_index = test_array_dimensions - 1; sub_script_index >= 0; sub_script_index--)
3033                 {
3034                         /* If any bit is set for a particular number then add
3035                          * a valid array sub_script at that place, otherwise
3036                          * add an invalid array sub_script. */
3037                         if (permutation & (1 << sub_script_index))
3038                         {
3039                                 shader_source += "[0]";
3040                         }
3041                         else
3042                         {
3043                                 shader_source += "[-1]";
3044                         }
3045                 }
3046
3047                 shader_source += " = b;\n";
3048
3049                 if (permutation != (1 << test_array_dimensions) - 1)
3050                 {
3051                         /* End main */
3052                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
3053
3054                         /* Execute test */
3055                         this->execute_negative_test(tested_shader_type, shader_source);
3056                 } /* if (permutation != (1 << test_array_dimensions) - 1) */
3057         }        /* for (int permutation = 0; ...) */
3058 }
3059
3060 /* Generates the shader source code for the ExpressionsIndexingScalar3
3061  * array tests, and attempts to compile each test shader, for both
3062  * vertex and fragment shaders.
3063  *
3064  * @tparam API               Tested API descriptor
3065  *
3066  * @param tested_shader_type The type of shader that is being tested
3067  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
3068  */
3069 template <class API>
3070 void ExpressionsIndexingScalar3<API>::test_shader_compilation(
3071         typename TestCaseBase<API>::TestShaderType tested_shader_type)
3072 {
3073         std::string base_shader_string;
3074         std::string shader_source;
3075         const int   test_array_dimensions = 4;
3076
3077         base_shader_string = "float a[1][2][3][4];\n";
3078         base_shader_string += "float b = 2.0;\n\n";
3079         base_shader_string += shader_start;
3080
3081         for (int permutation = 0; permutation < (1 << test_array_dimensions); permutation++)
3082         {
3083                 shader_source = base_shader_string + "    a";
3084
3085                 for (int sub_script_index = test_array_dimensions - 1; sub_script_index >= 0; sub_script_index--)
3086                 {
3087                         if (permutation & (1 << sub_script_index))
3088                         {
3089                                 shader_source += "[0]";
3090                         }
3091                         else
3092                         {
3093                                 shader_source += "[4]";
3094                         }
3095                 }
3096
3097                 shader_source += " = b;\n";
3098
3099                 if (permutation != (1 << test_array_dimensions) - 1)
3100                 {
3101                         /* End main */
3102                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
3103
3104                         /* Execute test */
3105                         this->execute_negative_test(tested_shader_type, shader_source);
3106                 } /* if (permutation != (1 << test_array_dimensions) - 1) */
3107         }        /* for (int permutation = 0; ...) */
3108 }
3109
3110 /* Generates the shader source code for the ExpressionsIndexingScalar4
3111  * array tests, and attempts to compile each test shader, for both
3112  * vertex and fragment shaders.
3113  *
3114  * @tparam API               Tested API descriptor
3115  *
3116  * @param tested_shader_type The type of shader that is being tested
3117  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
3118  */
3119 template <class API>
3120 void ExpressionsIndexingScalar4<API>::test_shader_compilation(
3121         typename TestCaseBase<API>::TestShaderType tested_shader_type)
3122 {
3123         std::string base_shader_string;
3124         std::string shader_source;
3125
3126         const int test_array_dimensions = 4;
3127
3128         base_shader_string = "float a[1][2][3][4];\n";
3129         base_shader_string += "float b = 2.0;\n\n";
3130         base_shader_string += shader_start;
3131
3132         for (int permutation = 0; permutation < (1 << test_array_dimensions); permutation++)
3133         {
3134                 shader_source = base_shader_string + "    a";
3135
3136                 for (int sub_script_index = test_array_dimensions - 1; sub_script_index >= 0; sub_script_index--)
3137                 {
3138                         if (permutation & (1 << sub_script_index))
3139                         {
3140                                 shader_source += "[0]";
3141                         }
3142                         else
3143                         {
3144                                 shader_source += "[]";
3145                         }
3146                 }
3147
3148                 shader_source += " = b;\n";
3149
3150                 if (permutation != (1 << test_array_dimensions) - 1)
3151                 {
3152                         /* End main */
3153                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
3154
3155                         /* Execute test */
3156                         this->execute_negative_test(tested_shader_type, shader_source);
3157                 } /* if (permutation != (1 << test_array_dimensions) - 1) */
3158         }        /* for (int permutation = 0; ...) */
3159 }
3160
3161 /* Generates the shader source code for the ExpressionsIndexingArray1
3162  * array tests, and attempts to compile each test shader, for both
3163  * vertex and fragment shaders.
3164  *
3165  * @tparam API               Tested API descriptor
3166  *
3167  * @param tested_shader_type The type of shader that is being tested
3168  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
3169  */
3170 template <class API>
3171 void ExpressionsIndexingArray1<API>::test_shader_compilation(
3172         typename TestCaseBase<API>::TestShaderType tested_shader_type)
3173 {
3174         std::string shader_source;
3175         std::string variable_declaration = "float x[1][1][1][1][1][1][1][1];\n\n";
3176
3177         std::string variable_initializations[] = {
3178                 "x[0]                      = float[1][1][1][1][1][1][1]("
3179                 "float[1][1][1][1][1][1](float[1][1][1][1][1](float[1][1][1][1](float[1][1][1](float[1][1](float[1](1.0)))))));"
3180                 "\n",
3181                 "x[0][0]                   = "
3182                 "float[1][1][1][1][1][1](float[1][1][1][1][1](float[1][1][1][1](float[1][1][1](float[1][1](float[1](1.0))))));"
3183                 "\n",
3184                 "x[0][0][0]                = "
3185                 "float[1][1][1][1][1](float[1][1][1][1](float[1][1][1](float[1][1](float[1](1.0)))));\n",
3186                 "x[0][0][0][0]             = float[1][1][1][1](float[1][1][1](float[1][1](float[1](1.0))));\n",
3187                 "x[0][0][0][0][0]          = float[1][1][1](float[1][1](float[1](1.0)));\n",
3188                 "x[0][0][0][0][0][0]       = float[1][1](float[1](1.0));\n", "x[0][0][0][0][0][0][0]    = float[1](1.0);\n",
3189                 "x[0][0][0][0][0][0][0][0] = 1.0;\n"
3190         };
3191
3192         for (size_t string_index = 0; string_index < sizeof(variable_initializations) / sizeof(variable_initializations[0]);
3193                  string_index++)
3194         {
3195                 shader_source = variable_declaration + shader_start;
3196                 shader_source += "    " + variable_initializations[string_index];
3197
3198                 /* End main */
3199                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
3200
3201                 /* Execute test */
3202                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
3203         } /* for (int string_index = 0; ...) */
3204 }
3205
3206 /* Constructs a suitable constructor for the specified number of dimensions.
3207  *
3208  * @tparam API            Tested API descriptor
3209  *
3210  * @param dimension_index The current recursion level (counts down)
3211  * @param init_string     The initialisation string
3212  */
3213 template <class API>
3214 std::string ExpressionsIndexingArray2<API>::recursively_initialise(std::string var_type, size_t dimension_index,
3215                                                                                                                                    std::string init_string)
3216 {
3217         std::string temp_string;
3218
3219         if (dimension_index == 0)
3220         {
3221                 temp_string = init_string;
3222         }
3223         else
3224         {
3225                 std::string prefix = "\n";
3226
3227                 for (size_t indent_index = dimension_index; indent_index < (API::MAX_ARRAY_DIMENSIONS + 1); indent_index++)
3228                 {
3229                         prefix += "    ";
3230                 }
3231
3232                 prefix += this->extend_string(var_type, "[]", dimension_index);
3233                 prefix += "(";
3234                 for (int sub_script_index = 0; sub_script_index < 2; sub_script_index++)
3235                 {
3236                         temp_string += prefix;
3237                         temp_string += recursively_initialise(var_type, dimension_index - 1, init_string);
3238                         prefix = ", ";
3239                         if (dimension_index == 1)
3240                         {
3241                                 break;
3242                         }
3243                 }
3244                 temp_string += ")";
3245         }
3246
3247         return temp_string;
3248 }
3249
3250 /* Generates the shader source code for the ExpressionsIndexingArray2
3251  * array tests, and attempts to compile each test shader, for both
3252  * vertex and fragment shaders.
3253  *
3254  * @tparam API               Tested API descriptor
3255  *
3256  * @param tested_shader_type The type of shader that is being tested
3257  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
3258  */
3259 template <class API>
3260 void ExpressionsIndexingArray2<API>::test_shader_compilation(
3261         typename TestCaseBase<API>::TestShaderType tested_shader_type)
3262 {
3263         std::string variable_initialiser = "    float[](float[](float(float(float(float(float(float(1.0))))))));\n";
3264
3265         std::string x_variable_initializaton =
3266                 "    float x[2][2][2][2][2][2][2][1] = " + recursively_initialise("float", API::MAX_ARRAY_DIMENSIONS, "1.0") +
3267                 ";\n";
3268         std::string y_variable_initializaton =
3269                 "    float y[2][2][2][2][2][2][2][1] = " + recursively_initialise("float", API::MAX_ARRAY_DIMENSIONS, "1.0") +
3270                 ";\n";
3271
3272         std::string shader_code_common_part = shader_start + x_variable_initializaton + y_variable_initializaton;
3273
3274         for (size_t max_dimension_index = 1; max_dimension_index <= API::MAX_ARRAY_DIMENSIONS; max_dimension_index++)
3275         {
3276                 std::string iteration_specific_shader_code_part;
3277
3278                 iteration_specific_shader_code_part += this->extend_string("    x", "[0]", max_dimension_index);
3279                 iteration_specific_shader_code_part += " = ";
3280                 iteration_specific_shader_code_part += this->extend_string("y", "[0]", max_dimension_index);
3281                 iteration_specific_shader_code_part += ";\n";
3282
3283                 std::string shader_source = shader_code_common_part + iteration_specific_shader_code_part;
3284
3285                 /* End main */
3286                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
3287
3288                 /* Execute test */
3289                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
3290         }
3291 }
3292
3293 /* Generates the shader source code for the ExpressionsIndexingArray3
3294  * array tests, and attempts to compile each test shader, for both
3295  * vertex and fragment shaders.
3296  *
3297  * @tparam API               Tested API descriptor
3298  *
3299  * @param tested_shader_type The type of shader that is being tested
3300  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
3301  */
3302 template <class API>
3303 void ExpressionsIndexingArray3<API>::test_shader_compilation(
3304         typename TestCaseBase<API>::TestShaderType tested_shader_type)
3305 {
3306         std::string input[] = { "    x[ivec2(0)] = 1.0;\n\n", "    x[ivec3(0)] = 1.0;\n\n", "    x[ivec4(0)] = 1.0;\n\n" };
3307
3308         for (size_t string_index = 0; string_index < sizeof(input) / sizeof(input[0]); string_index++)
3309         {
3310                 std::string shader_source = shader_start + this->extend_string("    float x", "[2]", (int)string_index + 2) +
3311                                                                         ";\n\n" + input[string_index];
3312
3313                 /* End main */
3314                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
3315
3316                 /* Execute test */
3317                 this->execute_negative_test(tested_shader_type, shader_source);
3318         } /* for (int string_index = 0; ...) */
3319 }
3320
3321 /* Generates the shader source code for the ExpressionsDynamicIndexing1
3322  * array tests, and attempts to compile each test shader, for both
3323  * vertex and fragment shaders.
3324  *
3325  * @tparam API               Tested API descriptor
3326  *
3327  * @param tested_shader_type The type of shader that is being tested
3328  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
3329  */
3330 template <class API>
3331 void ExpressionsDynamicIndexing1<API>::test_shader_compilation(
3332         typename TestCaseBase<API>::TestShaderType tested_shader_type)
3333 {
3334         std::string expression_type_declarations = "uniform int a;\n"
3335                                                                                            "const int b = 0;\n"
3336                                                                                            "int c = 0;\n"
3337                                                                                            "float x[2][2];\n";
3338
3339         std::string expressions[] = { "a", "b", "c", "0 + 1" };
3340         std::string shader_source;
3341
3342         for (size_t write_index = 0; write_index < sizeof(expressions) / sizeof(expressions[0]); write_index++)
3343         {
3344                 for (size_t read_index = 0; read_index < sizeof(expressions) / sizeof(expressions[0]); read_index++)
3345                 {
3346                         shader_source = expression_type_declarations;
3347                         shader_source += shader_start;
3348                         shader_source += "    x[";
3349                         shader_source += expressions[write_index];
3350                         shader_source += "][";
3351                         shader_source += expressions[read_index];
3352                         shader_source += "] = 1.0;\n\n";
3353
3354                         /* End main */
3355                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
3356
3357                         /* Execute test */
3358                         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
3359                 } /* for (int read_index = 0; ...) */
3360         }        /* for (int write_index = 0; ...) */
3361 }
3362
3363 /* Generates the shader source code for the ExpressionsDynamicIndexing2
3364  * array tests, and attempts to compile each test shader, for both
3365  * vertex and fragment shaders.
3366  *
3367  * @tparam API               Tested API descriptor
3368  *
3369  * @param tested_shader_type The type of shader that is being tested
3370  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
3371  */
3372 template <class API>
3373 void ExpressionsDynamicIndexing2<API>::test_shader_compilation(
3374         typename TestCaseBase<API>::TestShaderType tested_shader_type)
3375 {
3376         int                               num_var_types                           = sizeof(opaque_var_types) / sizeof(opaque_var_types[0]);
3377         const std::string invalid_size_declarations[] = { "[0][0][0][y]", "[0][0][y][0]", "[0][y][0][0]", "[y][0][0][0]",
3378                                                                                                           "[0][0][y][y]", "[0][y][0][y]", "[y][0][0][y]", "[0][y][y][0]",
3379                                                                                                           "[y][0][y][0]", "[y][y][0][0]", "[0][y][y][y]", "[y][0][y][y]",
3380                                                                                                           "[y][y][0][y]", "[y][y][y][0]", "[y][y][y][y]" };
3381
3382         bool dynamic_indexing_supported = false;
3383         if (glu::contextSupports(this->context_id.getRenderContext().getType(), glu::ApiType::es(3, 2)) ||
3384                 glu::contextSupports(this->context_id.getRenderContext().getType(), glu::ApiType::core(4, 0)) ||
3385                 this->context_id.getContextInfo().isExtensionSupported("GL_EXT_gpu_shader5"))
3386         {
3387                 dynamic_indexing_supported = true;
3388         }
3389
3390         for (int var_type_index = 0; var_type_index < num_var_types; var_type_index++)
3391         {
3392                 _supported_variable_types_map_const_iterator var_iterator =
3393                         supported_variable_types_map.find(opaque_var_types[var_type_index]);
3394
3395                 if (var_iterator != supported_variable_types_map.end())
3396                 {
3397                         int num_invalid_size_declarations =
3398                                 sizeof(invalid_size_declarations) / sizeof(invalid_size_declarations[0]);
3399
3400                         for (int invalid_size_index = 0; invalid_size_index < num_invalid_size_declarations; invalid_size_index++)
3401                         {
3402                                 std::string shader_source = "int y = 1;\n";
3403
3404                                 shader_source += "uniform " + var_iterator->second.precision + " " + var_iterator->second.type +
3405                                                                  " x[2][2][2][2];\n\n";
3406                                 shader_source += "void main()\n";
3407                                 shader_source += "{\n";
3408                                 shader_source += ("    " + var_iterator->second.type_of_result_of_texture_function +
3409                                                                   " color = texture(x" + invalid_size_declarations[invalid_size_index] + ", " +
3410                                                                   var_iterator->second.coord_param_for_texture_function + ");\n");
3411
3412                                 /* End main */
3413                                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
3414
3415                                 if (dynamic_indexing_supported)
3416                                 {
3417                                         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, true);
3418                                 }
3419                                 else
3420                                 {
3421                                         this->execute_negative_test(tested_shader_type, shader_source);
3422                                 }
3423                         } /* for (int invalid_size_index = 0; ...) */
3424                 }        /* if var_type iterator found */
3425                 else
3426                 {
3427                         TCU_FAIL("Type not found.");
3428                 }
3429         } /* for (int var_type_index = 0; ...) */
3430 }
3431
3432 /* Generates the shader source code for the ExpressionsEquality1
3433  * array tests, and attempts to compile each test shader, for both
3434  * vertex and fragment shaders.
3435  *
3436  * @tparam API               Tested API descriptor
3437  *
3438  * @param tested_shader_type The type of shader that is being tested
3439  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
3440  */
3441 template <class API>
3442 void ExpressionsEquality1<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
3443 {
3444         int num_var_types = API::n_var_types;
3445
3446         for (int var_type_index = 0; var_type_index < num_var_types; var_type_index++)
3447         {
3448                 _supported_variable_types_map_const_iterator var_iterator =
3449                         supported_variable_types_map.find(API::var_types[var_type_index]);
3450
3451                 if (var_iterator != supported_variable_types_map.end())
3452                 {
3453                         std::string shader_source = shader_start;
3454
3455                         shader_source += "    ";
3456                         shader_source += var_iterator->second.type;
3457                         shader_source += "[][] x = ";
3458                         shader_source += var_iterator->second.type;
3459                         shader_source += "[][](";
3460                         shader_source += var_iterator->second.type;
3461                         shader_source += "[](";
3462                         shader_source += var_iterator->second.initializer_with_zeroes;
3463                         shader_source += ",";
3464                         shader_source += var_iterator->second.initializer_with_zeroes;
3465                         shader_source += "),";
3466                         shader_source += var_iterator->second.type;
3467                         shader_source += "[](";
3468                         shader_source += var_iterator->second.initializer_with_zeroes;
3469                         shader_source += ",";
3470                         shader_source += var_iterator->second.initializer_with_zeroes;
3471                         shader_source += "));\n";
3472                         shader_source += "    ";
3473                         shader_source += var_iterator->second.type;
3474                         shader_source += "[][] y = ";
3475                         shader_source += var_iterator->second.type;
3476                         shader_source += "[][](";
3477                         shader_source += var_iterator->second.type;
3478                         shader_source += "[](";
3479                         shader_source += var_iterator->second.initializer_with_zeroes;
3480                         shader_source += ",";
3481                         shader_source += var_iterator->second.initializer_with_zeroes;
3482                         shader_source += "),";
3483                         shader_source += var_iterator->second.type;
3484                         shader_source += "[](";
3485                         shader_source += var_iterator->second.initializer_with_zeroes;
3486                         shader_source += ",";
3487                         shader_source += var_iterator->second.initializer_with_zeroes;
3488                         shader_source += "));\n\n";
3489                         shader_source += "    float result = 0.0;\n\n";
3490                         shader_source += "    if (x == y)\n";
3491                         shader_source += "    {\n";
3492                         shader_source += "        result = 1.0;\n";
3493                         shader_source += "    }\n";
3494                         shader_source += "    if (y != x)\n";
3495                         shader_source += "    {\n";
3496                         shader_source += "        result = 2.0;\n";
3497                         shader_source += "    }\n";
3498
3499                         /* End main */
3500                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
3501
3502                         /* Execute test */
3503                         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
3504                 } /* if var_type iterator found */
3505                 else
3506                 {
3507                         TCU_FAIL("Type not found.");
3508                 }
3509         }
3510 }
3511
3512 /* Generates the shader source code for the ExpressionsEquality2
3513  * array tests, and attempts to compile each test shader, for both
3514  * vertex and fragment shaders.
3515  *
3516  * @tparam API               Tested API descriptor
3517  *
3518  * @param tested_shader_type The type of shader that is being tested
3519  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
3520  */
3521 template <class API>
3522 void ExpressionsEquality2<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
3523 {
3524         int num_var_types = API::n_var_types;
3525
3526         for (int var_type_index = 0; var_type_index < num_var_types; var_type_index++)
3527         {
3528                 _supported_variable_types_map_const_iterator var_iterator =
3529                         supported_variable_types_map.find(API::var_types[var_type_index]);
3530
3531                 if (var_iterator != supported_variable_types_map.end())
3532                 {
3533                         std::string shader_source = "struct light {\n    float intensity;\n    int position;\n};\n\n";
3534
3535                         shader_source += shader_start;
3536                         shader_source += "    light[][] x =";
3537                         shader_source += "light";
3538                         shader_source += "[][](";
3539                         shader_source += "light";
3540                         shader_source += "[](light(1.0, 1)),";
3541                         shader_source += "light";
3542                         shader_source += "[](light(2.0, 2)));\n\n";
3543                         shader_source += "    light[][] y =";
3544                         shader_source += "light";
3545                         shader_source += "[][](";
3546                         shader_source += "light";
3547                         shader_source += "[](light(3.0, 3)),";
3548                         shader_source += "light";
3549                         shader_source += "[](light(4.0, 4)));\n\n";
3550                         shader_source += "    float result = 0.0;\n\n";
3551                         shader_source += "    if (x == y)\n";
3552                         shader_source += "    {\n";
3553                         shader_source += "        result = 1.0;\n";
3554                         shader_source += "    }\n";
3555                         shader_source += "    if (y != x)\n";
3556                         shader_source += "    {\n";
3557                         shader_source += "        result = 2.0;\n";
3558                         shader_source += "    }\n";
3559
3560                         /* Apply stage specific stuff */
3561                         switch (tested_shader_type)
3562                         {
3563                         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
3564                                 shader_source += "\n    gl_Position = vec4(0.0,0.0,0.0,1.0);\n";
3565                                 break;
3566                         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
3567                                 shader_source += "\n    gl_FragDepth = result;\n";
3568                                 break;
3569                         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
3570                                 break;
3571                         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
3572                                 shader_source += emit_quad;
3573                                 break;
3574                         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
3575                                 shader_source += set_tesseation;
3576                                 break;
3577                         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
3578                                 break;
3579                         default:
3580                                 TCU_FAIL("Unrecognized shader type.");
3581                                 break;
3582                         }
3583
3584                         /* End main function */
3585                         shader_source += shader_end;
3586
3587                         /* Execute test */
3588                         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
3589                 } /* if var_type iterator found */
3590                 else
3591                 {
3592                         TCU_FAIL("Type not found.");
3593                 }
3594         }
3595 }
3596
3597 /* Generates the shader source code for the ExpressionsLength1
3598  * array tests, and attempts to compile each test shader, for both
3599  * vertex and fragment shaders.
3600  *
3601  * @tparam API               Tested API descriptor
3602  *
3603  * @param tested_shader_type The type of shader that is being tested
3604  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
3605  */
3606 template <class API>
3607 void ExpressionsLength1<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
3608 {
3609         std::string array_declaration     = "    int x[4][3][2][1];\n\n";
3610         std::string case_specific_string[] = { "    if (x.length() != 4) {\n"
3611                                                                                    "        result = 0.0f;\n    }\n",
3612                                                                                    "    if (x[0].length() != 3) {\n"
3613                                                                                    "        result = 0.0f;\n    }\n",
3614                                                                                    "    if (x[0][0].length() != 2) {\n"
3615                                                                                    "        result = 0.0f;\n    }\n",
3616                                                                                    "    if (x[0][0][0].length() != 1) {\n"
3617                                                                                    "        result = 0.0f;\n    }\n" };
3618         const bool test_compute = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
3619
3620         for (size_t case_specific_string_index = 0;
3621                  case_specific_string_index < sizeof(case_specific_string) / sizeof(case_specific_string[0]);
3622                  case_specific_string_index++)
3623         {
3624                 const std::string& test_snippet = case_specific_string[case_specific_string_index];
3625
3626                 if (false == test_compute)
3627                 {
3628                         execute_draw_test(tested_shader_type, array_declaration, test_snippet);
3629                 }
3630                 else
3631                 {
3632                         execute_dispatch_test(tested_shader_type, array_declaration, test_snippet);
3633                 }
3634
3635                 /* Deallocate any resources used. */
3636                 this->delete_objects();
3637         } /* for (int case_specific_string_index = 0; ...) */
3638 }
3639
3640 /** Executes test for compute program
3641  *
3642  * @tparam API               Tested API descriptor
3643  *
3644  * @param tested_shader_type The type of shader that is being tested
3645  * @param tested_declaration Declaration used to prepare shader
3646  * @param tested_snippet     Snippet used to prepare shader
3647  **/
3648 template <class API>
3649 void ExpressionsLength1<API>::execute_dispatch_test(typename TestCaseBase<API>::TestShaderType tested_shader_type,
3650                                                                                                         const std::string&                                                 tested_declaration,
3651                                                                                                         const std::string&                                                 tested_snippet)
3652 {
3653         const std::string& compute_shader_source =
3654                 prepare_compute_shader(tested_shader_type, tested_declaration, tested_snippet);
3655         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
3656
3657         this->execute_positive_test(empty_string, empty_string, empty_string, empty_string, empty_string,
3658                                                                 compute_shader_source, false, false);
3659
3660         /* We are now ready to verify whether the returned size is correct. */
3661         unsigned char buffer[4]                         = { 0 };
3662         glw::GLuint   framebuffer_object_id = 0;
3663         glw::GLint      location                                = -1;
3664         glw::GLuint   texture_object_id         = 0;
3665         glw::GLuint   vao_id                            = 0;
3666
3667         gl.useProgram(this->program_object_id);
3668         GLU_EXPECT_NO_ERROR(gl.getError(), "glUseProgram() failed.");
3669
3670         gl.genTextures(1, &texture_object_id);
3671         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenTextures() failed.");
3672
3673         gl.bindTexture(GL_TEXTURE_2D, texture_object_id);
3674         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindTexture() failed.");
3675
3676         gl.texStorage2D(GL_TEXTURE_2D, 1, GL_RGBA8, 1, 1);
3677         GLU_EXPECT_NO_ERROR(gl.getError(), "glTexStorage2D() failed.");
3678
3679         gl.bindImageTexture(0 /* image unit */, texture_object_id, 0 /* level */, GL_FALSE /* layered */, 0 /* layer */,
3680                                                 GL_WRITE_ONLY, GL_RGBA8);
3681         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindImageTexture() failed.");
3682
3683         location = gl.getUniformLocation(this->program_object_id, "uni_image");
3684         GLU_EXPECT_NO_ERROR(gl.getError(), "glGetUniformLocation() failed.");
3685
3686         if (-1 == location)
3687         {
3688                 TCU_FAIL("Uniform is inactive");
3689         }
3690
3691         gl.uniform1i(location, 0 /* image unit */);
3692         GLU_EXPECT_NO_ERROR(gl.getError(), "glUniform1i() failed.");
3693
3694         gl.genVertexArrays(1, &vao_id);
3695         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenVertexArrays() failed.");
3696
3697         gl.bindVertexArray(vao_id);
3698         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindVertexArray() failed.");
3699
3700         gl.dispatchCompute(1, 1, 1);
3701         GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
3702
3703         gl.genFramebuffers(1, &framebuffer_object_id);
3704         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenFramebuffers() failed.");
3705
3706         gl.bindFramebuffer(GL_FRAMEBUFFER, framebuffer_object_id);
3707         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindFramebuffer() failed.");
3708
3709         gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texture_object_id, 0);
3710         GLU_EXPECT_NO_ERROR(gl.getError(), "glFramebufferTexture2D() failed.");
3711
3712         gl.viewport(0, 0, 1, 1);
3713         GLU_EXPECT_NO_ERROR(gl.getError(), "glViewport() failed.");
3714
3715         gl.readBuffer(GL_COLOR_ATTACHMENT0);
3716         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadBuffer() failed.");
3717
3718         gl.readPixels(0, 0, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
3719         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadPixels() failed.");
3720
3721         if (buffer[0] != 255)
3722         {
3723                 TCU_FAIL("Invalid array size was returned.");
3724         }
3725
3726         /* Delete generated objects. */
3727         gl.deleteTextures(1, &texture_object_id);
3728         gl.deleteFramebuffers(1, &framebuffer_object_id);
3729         gl.deleteVertexArrays(1, &vao_id);
3730         GLU_EXPECT_NO_ERROR(gl.getError(), "An error ocurred while deleting generated objects.");
3731 }
3732
3733 /** Executes test for draw program
3734  *
3735  * @tparam API               Tested API descriptor
3736  *
3737  * @param tested_shader_type The type of shader that is being tested
3738  * @param tested_declaration Declaration used to prepare shader
3739  * @param tested_snippet     Snippet used to prepare shader
3740  **/
3741 template <class API>
3742 void ExpressionsLength1<API>::execute_draw_test(typename TestCaseBase<API>::TestShaderType tested_shader_type,
3743                                                                                                 const std::string&                                                 tested_declaration,
3744                                                                                                 const std::string&                                                 tested_snippet)
3745 {
3746         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
3747
3748         if (API::USE_ALL_SHADER_STAGES)
3749         {
3750                 const std::string& compute_shader_source = empty_string;
3751                 const std::string& fragment_shader_source =
3752                         this->prepare_fragment_shader(tested_shader_type, tested_declaration, tested_snippet);
3753                 const std::string& geometry_shader_source =
3754                         this->prepare_geometry_shader(tested_shader_type, tested_declaration, tested_snippet);
3755                 const std::string& tess_ctrl_shader_source =
3756                         this->prepare_tess_ctrl_shader(tested_shader_type, tested_declaration, tested_snippet);
3757                 const std::string& tess_eval_shader_source =
3758                         this->prepare_tess_eval_shader(tested_shader_type, tested_declaration, tested_snippet);
3759                 const std::string& vertex_shader_source =
3760                         this->prepare_vertex_shader(tested_shader_type, tested_declaration, tested_snippet);
3761
3762                 switch (tested_shader_type)
3763                 {
3764                 case TestCaseBase<API>::VERTEX_SHADER_TYPE: /* Fall through */
3765                 case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
3766                         this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
3767                         break;
3768
3769                 case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
3770                 case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
3771                 case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
3772                 case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
3773                         this->execute_positive_test(vertex_shader_source, tess_ctrl_shader_source, tess_eval_shader_source,
3774                                                                                 geometry_shader_source, fragment_shader_source, compute_shader_source, false,
3775                                                                                 false);
3776                         break;
3777
3778                 default:
3779                         TCU_FAIL("Invalid enum");
3780                         break;
3781                 }
3782         }
3783         else
3784         {
3785                 const std::string& fragment_shader_source =
3786                         this->prepare_fragment_shader(tested_shader_type, tested_declaration, tested_snippet);
3787                 const std::string& vertex_shader_source =
3788                         this->prepare_vertex_shader(tested_shader_type, tested_declaration, tested_snippet);
3789
3790                 this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
3791         }
3792
3793         /* We are now ready to verify whether the returned size is correct. */
3794         unsigned char buffer[4]                         = { 0 };
3795         glw::GLuint   framebuffer_object_id = 0;
3796         glw::GLuint   texture_object_id         = 0;
3797         glw::GLuint   vao_id                            = 0;
3798
3799         gl.useProgram(this->program_object_id);
3800         GLU_EXPECT_NO_ERROR(gl.getError(), "glUseProgram() failed.");
3801
3802         gl.genTextures(1, &texture_object_id);
3803         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenTextures() failed.");
3804
3805         gl.bindTexture(GL_TEXTURE_2D, texture_object_id);
3806         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindTexture() failed.");
3807
3808         gl.texStorage2D(GL_TEXTURE_2D, 1, GL_RGBA8, 1, 1);
3809         GLU_EXPECT_NO_ERROR(gl.getError(), "glTexStorage2D() failed.");
3810
3811         gl.genFramebuffers(1, &framebuffer_object_id);
3812         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenFramebuffers() failed.");
3813
3814         gl.bindFramebuffer(GL_FRAMEBUFFER, framebuffer_object_id);
3815         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindFramebuffer() failed.");
3816
3817         gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texture_object_id, 0);
3818         GLU_EXPECT_NO_ERROR(gl.getError(), "glFramebufferTexture2D() failed.");
3819
3820         gl.viewport(0, 0, 1, 1);
3821         GLU_EXPECT_NO_ERROR(gl.getError(), "glViewport() failed.");
3822
3823         gl.genVertexArrays(1, &vao_id);
3824         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenVertexArrays() failed.");
3825
3826         gl.bindVertexArray(vao_id);
3827         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindVertexArray() failed.");
3828
3829         switch (tested_shader_type)
3830         {
3831         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE: /* Fall through */
3832         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
3833                 gl.drawArrays(GL_TRIANGLE_FAN, 0, 4);
3834                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
3835                 break;
3836
3837         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
3838         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
3839                 /* Tesselation patch set up */
3840                 gl.patchParameteri(GL_PATCH_VERTICES, 1);
3841                 GLU_EXPECT_NO_ERROR(gl.getError(), "PatchParameteri");
3842
3843                 gl.drawArrays(GL_PATCHES, 0, 1);
3844                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
3845                 break;
3846
3847         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
3848                 gl.drawArrays(GL_POINTS, 0, 1);
3849                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
3850                 break;
3851
3852         default:
3853                 TCU_FAIL("Invalid enum");
3854                 break;
3855         }
3856
3857         gl.readBuffer(GL_COLOR_ATTACHMENT0);
3858         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadBuffer() failed.");
3859
3860         gl.readPixels(0, 0, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
3861         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadPixels() failed.");
3862
3863         if (buffer[0] != 255)
3864         {
3865                 TCU_FAIL("Invalid array size was returned.");
3866         }
3867
3868         /* Delete generated objects. */
3869         gl.deleteTextures(1, &texture_object_id);
3870         gl.deleteFramebuffers(1, &framebuffer_object_id);
3871         gl.deleteVertexArrays(1, &vao_id);
3872         GLU_EXPECT_NO_ERROR(gl.getError(), "An error ocurred while deleting generated objects.");
3873 }
3874
3875 /** Prepare shader
3876  *
3877  * @tparam API               Tested API descriptor
3878  *
3879  * @param tested_shader_type The type of shader that is being tested
3880  * @param tested_declaration Declaration used to prepare shader
3881  * @param tested_snippet     Snippet used to prepare shader
3882  **/
3883 template <class API>
3884 std::string ExpressionsLength1<API>::prepare_compute_shader(
3885         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& tested_declaration,
3886         const std::string& tested_snippet)
3887 {
3888         std::string compute_shader_source;
3889
3890         if (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type)
3891         {
3892                 compute_shader_source = "writeonly uniform image2D uni_image;\n"
3893                                                                 "\n"
3894                                                                 "void main()\n"
3895                                                                 "{\n"
3896                                                                 "    float result = 1u;\n"
3897                                                                 "\n";
3898                 compute_shader_source += tested_declaration;
3899                 compute_shader_source += tested_snippet;
3900                 compute_shader_source += "\n"
3901                                                                  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), vec4(result, 0, 0, 0));\n"
3902                                                                  "}\n"
3903                                                                  "\n";
3904         }
3905
3906         return compute_shader_source;
3907 }
3908
3909 /** Prepare shader
3910  *
3911  * @tparam API               Tested API descriptor
3912  *
3913  * @param tested_shader_type The type of shader that is being tested
3914  * @param tested_declaration Declaration used to prepare shader
3915  * @param tested_snippet     Snippet used to prepare shader
3916  **/
3917 template <class API>
3918 std::string ExpressionsLength1<API>::prepare_fragment_shader(
3919         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& tested_declaration,
3920         const std::string& tested_snippet)
3921 {
3922         std::string fragment_shader_source;
3923
3924         switch (tested_shader_type)
3925         {
3926         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
3927                 break;
3928
3929         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
3930                 fragment_shader_source = "out vec4 colour;\n"
3931                                                                  "\n"
3932                                                                  "void main()\n"
3933                                                                  "{\n";
3934                 fragment_shader_source += tested_declaration;
3935                 fragment_shader_source += "    float result = 1.0f;\n";
3936                 fragment_shader_source += tested_snippet;
3937                 fragment_shader_source += "    colour = vec4(result);\n"
3938                                                                   "}\n\n";
3939                 break;
3940
3941         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
3942         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
3943         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
3944         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
3945                 fragment_shader_source = "in float fs_result;\n\n"
3946                                                                  "out vec4 colour;\n\n"
3947                                                                  "void main()\n"
3948                                                                  "{\n"
3949                                                                  "    colour =  vec4(fs_result);\n"
3950                                                                  "}\n"
3951                                                                  "\n";
3952                 break;
3953
3954         default:
3955                 TCU_FAIL("Unrecognized shader object type.");
3956                 break;
3957         }
3958
3959         return fragment_shader_source;
3960 }
3961
3962 /** Prepare shader
3963  *
3964  * @tparam API               Tested API descriptor
3965  *
3966  * @param tested_shader_type The type of shader that is being tested
3967  * @param tested_declaration Declaration used to prepare shader
3968  * @param tested_snippet     Snippet used to prepare shader
3969  **/
3970 template <class API>
3971 std::string ExpressionsLength1<API>::prepare_geometry_shader(
3972         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& tested_declaration,
3973         const std::string& tested_snippet)
3974 {
3975         std::string geometry_shader_source;
3976
3977         switch (tested_shader_type)
3978         {
3979         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
3980         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
3981         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
3982                 break;
3983
3984         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
3985         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
3986                 geometry_shader_source = "layout(points)                           in;\n"
3987                                                                  "layout(triangle_strip, max_vertices = 4) out;\n"
3988                                                                  "\n"
3989                                                                  "in  float tes_result[];\n"
3990                                                                  "out float fs_result;\n"
3991                                                                  "\n"
3992                                                                  "void main()\n"
3993                                                                  "{\n"
3994                                                                  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
3995                                                                  "    fs_result    = tes_result[0];\n"
3996                                                                  "    EmitVertex();\n"
3997                                                                  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
3998                                                                  "    fs_result    = tes_result[0];\n"
3999                                                                  "    EmitVertex();\n"
4000                                                                  "    gl_Position  = vec4(1, -1, 0, 1);\n"
4001                                                                  "    fs_result    = tes_result[0];\n"
4002                                                                  "    EmitVertex();\n"
4003                                                                  "    gl_Position  = vec4(1, 1, 0, 1);\n"
4004                                                                  "    fs_result    = tes_result[0];\n"
4005                                                                  "    EmitVertex();\n"
4006                                                                  "}\n";
4007                 break;
4008
4009         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
4010                 geometry_shader_source = "layout(points)                           in;\n"
4011                                                                  "layout(triangle_strip, max_vertices = 4) out;\n"
4012                                                                  "\n"
4013                                                                  "out float fs_result;\n"
4014                                                                  "\n"
4015                                                                  "void main()\n"
4016                                                                  "{\n";
4017                 geometry_shader_source += tested_declaration;
4018                 geometry_shader_source += "    float result = 1.0;\n\n";
4019                 geometry_shader_source += tested_snippet;
4020                 geometry_shader_source += "\n    gl_Position  = vec4(-1, -1, 0, 1);\n"
4021                                                                   "    fs_result    = result;\n"
4022                                                                   "    EmitVertex();\n"
4023                                                                   "    gl_Position  = vec4(-1, 1, 0, 1);\n"
4024                                                                   "    fs_result    = result;\n"
4025                                                                   "    EmitVertex();\n"
4026                                                                   "    gl_Position  = vec4(1, -1, 0, 1);\n"
4027                                                                   "    fs_result    = result;\n"
4028                                                                   "    EmitVertex();\n"
4029                                                                   "    gl_Position  = vec4(1, 1, 0, 1);\n"
4030                                                                   "    fs_result    = result;\n"
4031                                                                   "    EmitVertex();\n"
4032                                                                   "}\n";
4033                 break;
4034
4035         default:
4036                 TCU_FAIL("Unrecognized shader object type.");
4037                 break;
4038         }
4039
4040         return geometry_shader_source;
4041 }
4042
4043 /** Prepare shader
4044  *
4045  * @tparam API               Tested API descriptor
4046  *
4047  * @param tested_shader_type The type of shader that is being tested
4048  * @param tested_declaration Declaration used to prepare shader
4049  * @param tested_snippet     Snippet used to prepare shader
4050  **/
4051 template <class API>
4052 std::string ExpressionsLength1<API>::prepare_tess_ctrl_shader(
4053         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& tested_declaration,
4054         const std::string& tested_snippet)
4055 {
4056         std::string tess_ctrl_shader_source;
4057
4058         switch (tested_shader_type)
4059         {
4060         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
4061         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
4062         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
4063         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
4064                 break;
4065
4066         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
4067                 tess_ctrl_shader_source = "layout(vertices = 1) out;\n"
4068                                                                   "\n"
4069                                                                   "out float tcs_result[];\n"
4070                                                                   "\n"
4071                                                                   "void main()\n"
4072                                                                   "{\n";
4073                 tess_ctrl_shader_source += tested_declaration;
4074                 tess_ctrl_shader_source += "    float result = 1.0;\n\n";
4075                 tess_ctrl_shader_source += tested_snippet;
4076                 tess_ctrl_shader_source += "    tcs_result[gl_InvocationID] = result;\n"
4077                                                                    "\n"
4078                                                                    "    gl_TessLevelOuter[0] = 1.0;\n"
4079                                                                    "    gl_TessLevelOuter[1] = 1.0;\n"
4080                                                                    "    gl_TessLevelOuter[2] = 1.0;\n"
4081                                                                    "    gl_TessLevelOuter[3] = 1.0;\n"
4082                                                                    "    gl_TessLevelInner[0] = 1.0;\n"
4083                                                                    "    gl_TessLevelInner[1] = 1.0;\n"
4084                                                                    "}\n";
4085                 break;
4086
4087         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
4088                 tess_ctrl_shader_source = default_tc_shader_source;
4089                 break;
4090
4091         default:
4092                 TCU_FAIL("Unrecognized shader object type.");
4093                 break;
4094         }
4095
4096         return tess_ctrl_shader_source;
4097 }
4098
4099 /** Prepare shader
4100  *
4101  * @tparam API               Tested API descriptor
4102  *
4103  * @param tested_shader_type The type of shader that is being tested
4104  * @param tested_declaration Declaration used to prepare shader
4105  * @param tested_snippet     Snippet used to prepare shader
4106  **/
4107 template <class API>
4108 std::string ExpressionsLength1<API>::prepare_tess_eval_shader(
4109         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& tested_declaration,
4110         const std::string& tested_snippet)
4111 {
4112         std::string tess_eval_shader_source;
4113
4114         switch (tested_shader_type)
4115         {
4116         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
4117         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
4118         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
4119         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
4120                 break;
4121
4122         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
4123                 tess_eval_shader_source = "layout(isolines, point_mode) in;\n"
4124                                                                   "\n"
4125                                                                   "in  float tcs_result[];\n"
4126                                                                   "out float tes_result;\n"
4127                                                                   "\n"
4128                                                                   "void main()\n"
4129                                                                   "{\n"
4130                                                                   "    tes_result = tcs_result[0];\n"
4131                                                                   "}\n";
4132                 break;
4133
4134         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
4135                 tess_eval_shader_source = "layout(isolines, point_mode) in;\n"
4136                                                                   "\n"
4137                                                                   "out float tes_result;\n"
4138                                                                   "\n"
4139                                                                   "void main()\n"
4140                                                                   "{\n";
4141                 tess_eval_shader_source += tested_declaration;
4142                 tess_eval_shader_source += "    float result = 1.0;\n\n";
4143                 tess_eval_shader_source += tested_snippet;
4144                 tess_eval_shader_source += "    tes_result = result;\n"
4145                                                                    "}\n";
4146                 break;
4147
4148         default:
4149                 TCU_FAIL("Unrecognized shader object type.");
4150                 break;
4151         }
4152
4153         return tess_eval_shader_source;
4154 }
4155
4156 /** Prepare shader
4157  *
4158  * @tparam API               Tested API descriptor
4159  *
4160  * @param tested_shader_type The type of shader that is being tested
4161  * @param tested_declaration Declaration used to prepare shader
4162  * @param tested_snippet     Snippet used to prepare shader
4163  **/
4164 template <class API>
4165 std::string ExpressionsLength1<API>::prepare_vertex_shader(
4166         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& tested_declaration,
4167         const std::string& tested_snippet)
4168 {
4169         std::string vertex_shader_source;
4170
4171         switch (tested_shader_type)
4172         {
4173         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
4174                 break;
4175
4176         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
4177                 vertex_shader_source = "/** GL_TRIANGLE_FAN-type quad vertex data. */\n"
4178                                                            "const vec4 vertex_positions[4] = vec4[4](vec4( 1.0, -1.0, 0.0, 1.0),\n"
4179                                                            "                                         vec4(-1.0, -1.0, 0.0, 1.0),\n"
4180                                                            "                                         vec4(-1.0,  1.0, 0.0, 1.0),\n"
4181                                                            "                                         vec4( 1.0,  1.0, 0.0, 1.0) );\n"
4182                                                            "\n"
4183                                                            "void main()\n"
4184                                                            "{\n"
4185                                                            "    gl_Position = vertex_positions[gl_VertexID];"
4186                                                            "}\n\n";
4187                 break;
4188
4189         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
4190         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
4191         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
4192                 vertex_shader_source = default_vertex_shader_source;
4193                 break;
4194
4195         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
4196                 vertex_shader_source = "out float fs_result;\n"
4197                                                            "\n"
4198                                                            "/** GL_TRIANGLE_FAN-type quad vertex data. */\n"
4199                                                            "const vec4 vertex_positions[4] = vec4[4](vec4( 1.0, -1.0, 0.0, 1.0),\n"
4200                                                            "                                         vec4(-1.0, -1.0, 0.0, 1.0),\n"
4201                                                            "                                         vec4(-1.0,  1.0, 0.0, 1.0),\n"
4202                                                            "                                         vec4( 1.0,  1.0, 0.0, 1.0) );\n"
4203                                                            "\n"
4204                                                            "void main()\n"
4205                                                            "{\n";
4206                 vertex_shader_source += tested_declaration;
4207                 vertex_shader_source += "    float result = 1.0;\n\n";
4208                 vertex_shader_source += tested_snippet;
4209                 vertex_shader_source += "    gl_Position = vertex_positions[gl_VertexID];\n"
4210                                                                 "    fs_result = result;\n";
4211                 vertex_shader_source += shader_end;
4212                 break;
4213
4214         default:
4215                 TCU_FAIL("Unrecognized shader object type.");
4216                 break;
4217         }
4218
4219         return vertex_shader_source;
4220 }
4221
4222 /* Generates the shader source code for the ExpressionsLength2
4223  * array tests, and attempts to compile each test shader, for both
4224  * vertex and fragment shaders.
4225  *
4226  * @tparam API               Tested API descriptor
4227  *
4228  * @param tested_shader_type The type of shader that is being tested
4229  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
4230  */
4231 template <class API>
4232 void ExpressionsLength2<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
4233 {
4234         std::string array_declaration     = "    int x[1][2][3][4];\n\n";
4235         std::string case_specific_string[] = { "    if (x.length() != 1) {\n"
4236                                                                                    "        result = 0.0f;\n    }\n",
4237                                                                                    "    if (x[0].length() != 2) {\n"
4238                                                                                    "        result = 0.0f;\n    }\n",
4239                                                                                    "    if (x[0][0].length() != 3) {\n"
4240                                                                                    "        result = 0.0f;\n    }\n",
4241                                                                                    "    if (x[0][0][0].length() != 4) {\n"
4242                                                                                    "        result = 0.0f;\n    }\n" };
4243         const bool test_compute = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
4244
4245         for (size_t case_specific_string_index = 0;
4246                  case_specific_string_index < sizeof(case_specific_string) / sizeof(case_specific_string[0]);
4247                  case_specific_string_index++)
4248         {
4249                 const std::string& test_snippet = case_specific_string[case_specific_string_index];
4250
4251                 if (false == test_compute)
4252                 {
4253                         this->execute_draw_test(tested_shader_type, array_declaration, test_snippet);
4254                 }
4255                 else
4256                 {
4257                         this->execute_dispatch_test(tested_shader_type, array_declaration, test_snippet);
4258                 }
4259
4260                 /* Deallocate any resources used. */
4261                 this->delete_objects();
4262         } /* for (int case_specific_string_index = 0; ...) */
4263 }
4264
4265 /* Generates the shader source code for the ExpressionsLength3
4266  * array tests, and attempts to compile each test shader, for both
4267  * vertex and fragment shaders.
4268  *
4269  * @tparam API               Tested API descriptor
4270  *
4271  * @param tested_shader_type The type of shader that is being tested
4272  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
4273  */
4274 template <class API>
4275 void ExpressionsLength3<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
4276 {
4277         std::string array_declaration = "    int x[1][1][1][1];\n\n";
4278         std::string input[]                       = { "    if (x[].length() != 2) {\n"
4279                                                         "        result = 0.0f;\n    }\n",
4280                                                         "    if (x[][].length() != 2)  {\n"
4281                                                         "        result = 0.0f;\n    }\n",
4282                                                         "    if (x[][][].length() != 2)  {\n"
4283                                                         "        result = 0.0f;\n    }\n" };
4284
4285         for (size_t string_index = 0; string_index < sizeof(input) / sizeof(input[0]); string_index++)
4286         {
4287                 std::string                shader_source;
4288                 const std::string& test_snippet = input[string_index];
4289
4290                 switch (tested_shader_type)
4291                 {
4292                 case TestCaseBase<API>::VERTEX_SHADER_TYPE:
4293                         shader_source = this->prepare_vertex_shader(tested_shader_type, array_declaration, test_snippet);
4294                         break;
4295
4296                 case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
4297                         shader_source = this->prepare_fragment_shader(tested_shader_type, array_declaration, test_snippet);
4298                         break;
4299
4300                 case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
4301                         shader_source = this->prepare_compute_shader(tested_shader_type, array_declaration, test_snippet);
4302                         break;
4303
4304                 case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
4305                         shader_source = this->prepare_geometry_shader(tested_shader_type, array_declaration, test_snippet);
4306                         break;
4307
4308                 case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
4309                         shader_source = this->prepare_tess_ctrl_shader(tested_shader_type, array_declaration, test_snippet);
4310                         break;
4311
4312                 case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
4313                         shader_source = this->prepare_tess_eval_shader(tested_shader_type, array_declaration, test_snippet);
4314                         break;
4315
4316                 default:
4317                         TCU_FAIL("Unrecognized shader type.");
4318                         break;
4319                 } /* switch (tested_shader_type) */
4320
4321                 this->execute_negative_test(tested_shader_type, shader_source);
4322         } /* for (int string_index = 0; ...) */
4323 }
4324
4325 /* Generates the shader source code for the ExpressionsInvalid1
4326  * array tests, and attempts to compile each test shader, for both
4327  * vertex and fragment shaders.
4328  *
4329  * @tparam API               Tested API descriptor
4330  *
4331  * @param tested_shader_type The type of shader that is being tested
4332  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
4333  */
4334 template <class API>
4335 void ExpressionsInvalid1<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
4336 {
4337         std::string shader_variable_declarations =
4338                 "    mat2  y       = mat2(0.0);\n"
4339                 "    float x[2][2] = float[2][2](float[2](4.0, 5.0), float[2](6.0, 7.0));\n\n";
4340
4341         std::string shader_source = shader_start + shader_variable_declarations;
4342
4343         shader_source += "    y = x;\n";
4344
4345         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
4346
4347         this->execute_negative_test(tested_shader_type, shader_source);
4348 }
4349
4350 /* Generates the shader source code for the ExpressionsInvalid2
4351  * array tests, and attempts to compile each test shader, for both
4352  * vertex and fragment shaders.
4353  *
4354  * @tparam API               Tested API descriptor
4355  *
4356  * @param tested_shader_type The type of shader that is being tested
4357  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
4358  */
4359 template <class API>
4360 void ExpressionsInvalid2<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
4361 {
4362
4363         std::string shader_variable_declarations[] = { " x", " y" };
4364         std::string variable_relation_opeartors[]  = {
4365                 "    float result = 0.0;\n\n    if(x < y)\n    {\n        result = 1.0;\n    }\n\n\n",
4366                 "    float result = 0.0;\n\n    if(x <= y)\n    {\n        result = 1.0;\n    }\n\n\n",
4367                 "    float result = 0.0;\n\n    if(x > y)\n    {\n        result = 1.0;\n    }\n\n\n",
4368                 "    float result = 0.0;\n\n    if(x >= y)\n    {\n        result = 1.0;\n    }\n\n\n"
4369         };
4370         std::string valid_relation_opeartors =
4371                 "    float result = 0.0;\n\n    if(x == y)\n    {\n        result = 1.0;\n    }\n\n\n";
4372
4373         for (size_t var_type_index = 0; var_type_index < API::n_var_types; var_type_index++)
4374         {
4375                 _supported_variable_types_map_const_iterator var_iterator =
4376                         supported_variable_types_map.find(API::var_types[var_type_index]);
4377
4378                 if (var_iterator != supported_variable_types_map.end())
4379                 {
4380                         std::string base_variable_string;
4381
4382                         for (size_t variable_declaration_index = 0;
4383                                  variable_declaration_index <
4384                                  sizeof(shader_variable_declarations) / sizeof(shader_variable_declarations[0]);
4385                                  variable_declaration_index++)
4386                         {
4387                                 base_variable_string += var_iterator->second.type;
4388                                 base_variable_string += shader_variable_declarations[variable_declaration_index];
4389
4390                                 base_variable_string += "[1][1][1][1][1][1][1][1] = ";
4391
4392                                 for (size_t sub_script_index = 0; sub_script_index < API::MAX_ARRAY_DIMENSIONS; sub_script_index++)
4393                                 {
4394                                         base_variable_string += this->extend_string(var_iterator->second.type, "[1]",
4395                                                                                                                                 API::MAX_ARRAY_DIMENSIONS - sub_script_index);
4396                                         base_variable_string += "(";
4397                                 }
4398
4399                                 base_variable_string += var_iterator->second.initializer_with_ones;
4400
4401                                 for (size_t sub_script_index = 0; sub_script_index < API::MAX_ARRAY_DIMENSIONS; sub_script_index++)
4402                                 {
4403                                         base_variable_string += ")";
4404                                 }
4405
4406                                 base_variable_string += ";\n";
4407                         } /* for (int variable_declaration_index = 0; ...) */
4408
4409                         /* Run positive case */
4410                         {
4411                                 std::string shader_source;
4412
4413                                 shader_source = base_variable_string + "\n";
4414                                 shader_source += shader_start + valid_relation_opeartors;
4415
4416                                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
4417
4418                                 EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
4419                         }
4420
4421                         /* Run negative cases */
4422                         for (size_t string_index = 0;
4423                                  string_index < sizeof(variable_relation_opeartors) / sizeof(variable_relation_opeartors[0]);
4424                                  string_index++)
4425                         {
4426                                 std::string shader_source;
4427
4428                                 shader_source = base_variable_string + "\n";
4429                                 shader_source += shader_start + variable_relation_opeartors[string_index];
4430
4431                                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
4432
4433                                 this->execute_negative_test(tested_shader_type, shader_source);
4434                         } /* for (int string_index = 0; ...) */
4435                 }        /* if var_type iterator found */
4436                 else
4437                 {
4438                         TCU_FAIL("Type not found.");
4439                 }
4440         } /* for (int var_type_index = 0; ...) */
4441 }
4442
4443 /* Generates the shader source code for the InteractionFunctionCalls1
4444  * array tests, and attempts to compile each test shader, for both
4445  * vertex and fragment shaders.
4446  *
4447  * @tparam API               Tested API descriptor
4448  *
4449  * @param tested_shader_type The type of shader that is being tested
4450  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
4451  */
4452 template <class API>
4453 void InteractionFunctionCalls1<API>::test_shader_compilation(
4454         typename TestCaseBase<API>::TestShaderType tested_shader_type)
4455 {
4456         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
4457                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
4458                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
4459                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4 };
4460         static const size_t num_var_types_es = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
4461
4462         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
4463                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
4464                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
4465                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4,  VAR_TYPE_DOUBLE,
4466                                                                                                                          VAR_TYPE_DMAT2, VAR_TYPE_DMAT3, VAR_TYPE_DMAT4 };
4467         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
4468
4469         const std::string iteration_loop_end = "                               }\n"
4470                                                                                    "                           }\n"
4471                                                                                    "                        }\n"
4472                                                                                    "                    }\n"
4473                                                                                    "                }\n"
4474                                                                                    "            }\n"
4475                                                                                    "        }\n"
4476                                                                                    "    }\n";
4477         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
4478                                                                                          "    {\n"
4479                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
4480                                                                                          "        {\n"
4481                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
4482                                                                                          "            {\n"
4483                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
4484                                                                                          "                {\n"
4485                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
4486                                                                                          "                    {\n"
4487                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
4488                                                                                          "                        {\n"
4489                                                                                          "                           for (uint g = 0u; g < 2u; g++)\n"
4490                                                                                          "                           {\n"
4491                                                                                          "                               for (uint h = 0u; h < 2u; h++)\n"
4492                                                                                          "                               {\n";
4493         const glcts::test_var_type* var_types_set = var_types_set_es;
4494         size_t                                          num_var_types = num_var_types_es;
4495         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
4496
4497         if (API::USE_DOUBLE)
4498         {
4499                 var_types_set = var_types_set_gl;
4500                 num_var_types = num_var_types_gl;
4501         }
4502
4503         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
4504         {
4505                 _supported_variable_types_map_const_iterator var_iterator =
4506                         supported_variable_types_map.find(var_types_set[var_type_index]);
4507
4508                 if (var_iterator != supported_variable_types_map.end())
4509                 {
4510                         std::string iterator_declaration = "    " + var_iterator->second.iterator_type +
4511                                                                                            " iterator = " + var_iterator->second.iterator_initialization + ";\n";
4512
4513                         std::string function_definition;
4514                         std::string function_use;
4515                         std::string verification;
4516
4517                         function_definition = "void my_function(out ";
4518                         function_definition += var_iterator->second.type;
4519                         function_definition += " output_array[2][2][2][2][2][2][2][2]) {\n";
4520                         function_definition += iterator_declaration;
4521                         function_definition += iteration_loop_start;
4522                         function_definition += "                                   output_array[a][b][c][d][e][f][g][h] = " +
4523                                                                    var_iterator->second.variable_type_initializer1 + ";\n";
4524                         function_definition +=
4525                                 "                                   iterator += " + var_iterator->second.iterator_type + "(1);\n";
4526                         function_definition += iteration_loop_end;
4527                         function_definition += "}";
4528
4529                         function_use = "    " + var_iterator->second.type + " my_array[2][2][2][2][2][2][2][2];\n";
4530                         function_use += "    my_function(my_array);";
4531
4532                         verification = iterator_declaration;
4533                         verification += "    float result = 1.0;\n";
4534                         verification += iteration_loop_start;
4535                         verification += "                                   if (my_array[a][b][c][d][e][f][g][h] " +
4536                                                         var_iterator->second.specific_element +
4537                                                         " != iterator)\n"
4538                                                         "                                   {\n"
4539                                                         "                                       result = 0.0;\n"
4540                                                         "                                   }\n"
4541                                                         "                                   iterator += " +
4542                                                         var_iterator->second.iterator_type + "(1);\n";
4543                         verification += iteration_loop_end;
4544
4545                         if (false == test_compute)
4546                         {
4547                                 execute_draw_test(tested_shader_type, function_definition, function_use, verification);
4548                         }
4549                         else
4550                         {
4551                                 execute_dispatch_test(tested_shader_type, function_definition, function_use, verification);
4552                         }
4553
4554                         /* Deallocate any resources used. */
4555                         this->delete_objects();
4556                 } /* if var_type iterator found */
4557                 else
4558                 {
4559                         TCU_FAIL("Type not found.");
4560                 }
4561         } /* for (int var_type_index = 0; ...) */
4562 }
4563
4564 /** Executes test for compute program
4565  *
4566  * @tparam API                Tested API descriptor
4567  *
4568  * @param tested_shader_type  The type of shader that is being tested
4569  * @param function_definition Definition used to prepare shader
4570  * @param function_use        Snippet that makes use of defined function
4571  * @param verification        Snippet that verifies results
4572  **/
4573 template <class API>
4574 void InteractionFunctionCalls1<API>::execute_dispatch_test(
4575         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
4576         const std::string& function_use, const std::string& verification)
4577 {
4578         const std::string& compute_shader_source =
4579                 prepare_compute_shader(tested_shader_type, function_definition, function_use, verification);
4580         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
4581
4582         this->execute_positive_test(empty_string, empty_string, empty_string, empty_string, empty_string,
4583                                                                 compute_shader_source, false, false);
4584
4585         /* We are now ready to verify whether the returned size is correct. */
4586         unsigned char buffer[4]                         = { 0 };
4587         glw::GLuint   framebuffer_object_id = 0;
4588         glw::GLint      location                                = -1;
4589         glw::GLuint   texture_object_id         = 0;
4590         glw::GLuint   vao_id                            = 0;
4591
4592         gl.useProgram(this->program_object_id);
4593         GLU_EXPECT_NO_ERROR(gl.getError(), "glUseProgram() failed.");
4594
4595         gl.genTextures(1, &texture_object_id);
4596         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenTextures() failed.");
4597
4598         gl.bindTexture(GL_TEXTURE_2D, texture_object_id);
4599         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindTexture() failed.");
4600
4601         gl.texStorage2D(GL_TEXTURE_2D, 1, GL_RGBA8, 1, 1);
4602         GLU_EXPECT_NO_ERROR(gl.getError(), "glTexStorage2D() failed.");
4603
4604         gl.bindImageTexture(0 /* image unit */, texture_object_id, 0 /* level */, GL_FALSE /* layered */, 0 /* layer */,
4605                                                 GL_WRITE_ONLY, GL_RGBA8);
4606         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindImageTexture() failed.");
4607
4608         location = gl.getUniformLocation(this->program_object_id, "uni_image");
4609         GLU_EXPECT_NO_ERROR(gl.getError(), "glGetUniformLocation() failed.");
4610
4611         if (-1 == location)
4612         {
4613                 TCU_FAIL("Uniform is inactive");
4614         }
4615
4616         gl.uniform1i(location, 0 /* image unit */);
4617         GLU_EXPECT_NO_ERROR(gl.getError(), "glUniform1i() failed.");
4618
4619         gl.genVertexArrays(1, &vao_id);
4620         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenVertexArrays() failed.");
4621
4622         gl.bindVertexArray(vao_id);
4623         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindVertexArray() failed.");
4624
4625         gl.dispatchCompute(1, 1, 1);
4626         GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
4627
4628         gl.genFramebuffers(1, &framebuffer_object_id);
4629         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenFramebuffers() failed.");
4630
4631         gl.bindFramebuffer(GL_FRAMEBUFFER, framebuffer_object_id);
4632         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindFramebuffer() failed.");
4633
4634         gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texture_object_id, 0);
4635         GLU_EXPECT_NO_ERROR(gl.getError(), "glFramebufferTexture2D() failed.");
4636
4637         gl.viewport(0, 0, 1, 1);
4638         GLU_EXPECT_NO_ERROR(gl.getError(), "glViewport() failed.");
4639
4640         gl.readBuffer(GL_COLOR_ATTACHMENT0);
4641         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadBuffer() failed.");
4642
4643         gl.readPixels(0, 0, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
4644         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadPixels() failed.");
4645
4646         if (buffer[0] != 255)
4647         {
4648                 TCU_FAIL("Invalid array size was returned.");
4649         }
4650
4651         /* Delete generated objects. */
4652         gl.deleteTextures(1, &texture_object_id);
4653         gl.deleteFramebuffers(1, &framebuffer_object_id);
4654         gl.deleteVertexArrays(1, &vao_id);
4655         GLU_EXPECT_NO_ERROR(gl.getError(), "An error ocurred while deleting generated objects.");
4656 }
4657
4658 /** Executes test for draw program
4659  *
4660  * @tparam API                Tested API descriptor
4661  *
4662  * @param tested_shader_type  The type of shader that is being tested
4663  * @param function_definition Definition used to prepare shader
4664  * @param function_use        Snippet that makes use of defined function
4665  * @param verification        Snippet that verifies results
4666  **/
4667 template <class API>
4668 void InteractionFunctionCalls1<API>::execute_draw_test(typename TestCaseBase<API>::TestShaderType tested_shader_type,
4669                                                                                                            const std::string&                                             function_definition,
4670                                                                                                            const std::string& function_use, const std::string& verification)
4671 {
4672         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
4673
4674         if (API::USE_ALL_SHADER_STAGES)
4675         {
4676                 const std::string& compute_shader_source = empty_string;
4677                 const std::string& fragment_shader_source =
4678                         this->prepare_fragment_shader(tested_shader_type, function_definition, function_use, verification);
4679                 const std::string& geometry_shader_source =
4680                         this->prepare_geometry_shader(tested_shader_type, function_definition, function_use, verification);
4681                 const std::string& tess_ctrl_shader_source =
4682                         this->prepare_tess_ctrl_shader(tested_shader_type, function_definition, function_use, verification);
4683                 const std::string& tess_eval_shader_source =
4684                         this->prepare_tess_eval_shader(tested_shader_type, function_definition, function_use, verification);
4685                 const std::string& vertex_shader_source =
4686                         this->prepare_vertex_shader(tested_shader_type, function_definition, function_use, verification);
4687
4688                 switch (tested_shader_type)
4689                 {
4690                 case TestCaseBase<API>::VERTEX_SHADER_TYPE: /* Fall through */
4691                 case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
4692                         this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
4693                         break;
4694
4695                 case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
4696                 case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
4697                 case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
4698                 case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
4699                         this->execute_positive_test(vertex_shader_source, tess_ctrl_shader_source, tess_eval_shader_source,
4700                                                                                 geometry_shader_source, fragment_shader_source, compute_shader_source, false,
4701                                                                                 false);
4702                         break;
4703
4704                 default:
4705                         TCU_FAIL("Invalid enum");
4706                         break;
4707                 }
4708         }
4709         else
4710         {
4711                 const std::string& fragment_shader_source =
4712                         this->prepare_fragment_shader(tested_shader_type, function_definition, function_use, verification);
4713                 const std::string& vertex_shader_source =
4714                         this->prepare_vertex_shader(tested_shader_type, function_definition, function_use, verification);
4715
4716                 this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
4717         }
4718
4719         /* We are now ready to verify whether the returned size is correct. */
4720         unsigned char buffer[4]                         = { 0 };
4721         glw::GLuint   framebuffer_object_id = 0;
4722         glw::GLuint   texture_object_id         = 0;
4723         glw::GLuint   vao_id                            = 0;
4724
4725         gl.useProgram(this->program_object_id);
4726         GLU_EXPECT_NO_ERROR(gl.getError(), "glUseProgram() failed.");
4727
4728         gl.genTextures(1, &texture_object_id);
4729         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenTextures() failed.");
4730
4731         gl.bindTexture(GL_TEXTURE_2D, texture_object_id);
4732         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindTexture() failed.");
4733
4734         gl.texStorage2D(GL_TEXTURE_2D, 1, GL_RGBA8, 1, 1);
4735         GLU_EXPECT_NO_ERROR(gl.getError(), "glTexStorage2D() failed.");
4736
4737         gl.genFramebuffers(1, &framebuffer_object_id);
4738         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenFramebuffers() failed.");
4739
4740         gl.bindFramebuffer(GL_FRAMEBUFFER, framebuffer_object_id);
4741         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindFramebuffer() failed.");
4742
4743         gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texture_object_id, 0);
4744         GLU_EXPECT_NO_ERROR(gl.getError(), "glFramebufferTexture2D() failed.");
4745
4746         gl.viewport(0, 0, 1, 1);
4747         GLU_EXPECT_NO_ERROR(gl.getError(), "glViewport() failed.");
4748
4749         gl.genVertexArrays(1, &vao_id);
4750         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenVertexArrays() failed.");
4751
4752         gl.bindVertexArray(vao_id);
4753         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindVertexArray() failed.");
4754
4755         switch (tested_shader_type)
4756         {
4757         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE: /* Fall through */
4758         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
4759                 gl.drawArrays(GL_TRIANGLE_FAN, 0, 4);
4760                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
4761                 break;
4762
4763         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
4764         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
4765                 /* Tesselation patch set up */
4766                 gl.patchParameteri(GL_PATCH_VERTICES, 1);
4767                 GLU_EXPECT_NO_ERROR(gl.getError(), "PatchParameteri");
4768
4769                 gl.drawArrays(GL_PATCHES, 0, 1);
4770                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
4771                 break;
4772
4773         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
4774                 gl.drawArrays(GL_POINTS, 0, 1);
4775                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
4776                 break;
4777
4778         default:
4779                 TCU_FAIL("Invalid enum");
4780                 break;
4781         }
4782
4783         gl.readBuffer(GL_COLOR_ATTACHMENT0);
4784         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadBuffer() failed.");
4785
4786         gl.readPixels(0, 0, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
4787         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadPixels() failed.");
4788
4789         if (buffer[0] != 255)
4790         {
4791                 TCU_FAIL("Invalid array size was returned.");
4792         }
4793
4794         /* Delete generated objects. */
4795         gl.bindTexture(GL_TEXTURE_2D, 0);
4796         gl.bindFramebuffer(GL_FRAMEBUFFER, 0);
4797         gl.bindVertexArray(0);
4798         gl.deleteTextures(1, &texture_object_id);
4799         gl.deleteFramebuffers(1, &framebuffer_object_id);
4800         gl.deleteVertexArrays(1, &vao_id);
4801         GLU_EXPECT_NO_ERROR(gl.getError(), "An error ocurred while deleting generated objects.");
4802 }
4803
4804 /** Prepare shader
4805  *
4806  * @tparam API                Tested API descriptor
4807  *
4808  * @param tested_shader_type  The type of shader that is being tested
4809  * @param function_definition Definition used to prepare shader
4810  * @param function_use        Snippet that makes use of defined function
4811  * @param verification        Snippet that verifies results
4812  **/
4813 template <class API>
4814 std::string InteractionFunctionCalls1<API>::prepare_compute_shader(
4815         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
4816         const std::string& function_use, const std::string& verification)
4817 {
4818         std::string compute_shader_source;
4819
4820         if (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type)
4821         {
4822                 compute_shader_source = "writeonly uniform image2D uni_image;\n"
4823                                                                 "\n";
4824
4825                 /* User-defined function definition. */
4826                 compute_shader_source += function_definition;
4827                 compute_shader_source += "\n\n";
4828
4829                 /* Main function definition. */
4830                 compute_shader_source += shader_start;
4831                 compute_shader_source += function_use;
4832                 compute_shader_source += "\n\n";
4833                 compute_shader_source += verification;
4834                 compute_shader_source += "\n\n";
4835                 compute_shader_source += "\n"
4836                                                                  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), vec4(result, 0, 0, 0));\n"
4837                                                                  "}\n"
4838                                                                  "\n";
4839         }
4840
4841         return compute_shader_source;
4842 }
4843
4844 /** Prepare shader
4845  *
4846  * @tparam API                Tested API descriptor
4847  *
4848  * @param tested_shader_type  The type of shader that is being tested
4849  * @param function_definition Definition used to prepare shader
4850  * @param function_use        Snippet that makes use of defined function
4851  * @param verification        Snippet that verifies results
4852  **/
4853 template <class API>
4854 std::string InteractionFunctionCalls1<API>::prepare_fragment_shader(
4855         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
4856         const std::string& function_use, const std::string& verification)
4857 {
4858         std::string fragment_shader_source;
4859
4860         switch (tested_shader_type)
4861         {
4862         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
4863                 break;
4864
4865         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
4866                 fragment_shader_source = "out vec4 colour;\n\n";
4867
4868                 /* User-defined function definition. */
4869                 fragment_shader_source += function_definition;
4870                 fragment_shader_source += "\n\n";
4871
4872                 /* Main function definition. */
4873                 fragment_shader_source += shader_start;
4874                 fragment_shader_source += function_use;
4875                 fragment_shader_source += "\n\n";
4876                 fragment_shader_source += verification;
4877                 fragment_shader_source += "\n\n";
4878                 fragment_shader_source += "    colour = vec4(result);\n";
4879                 fragment_shader_source += shader_end;
4880                 break;
4881
4882         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
4883         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
4884         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
4885         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
4886                 fragment_shader_source = "in float fs_result;\n\n"
4887                                                                  "out vec4 colour;\n\n"
4888                                                                  "void main()\n"
4889                                                                  "{\n"
4890                                                                  "    colour =  vec4(fs_result);\n"
4891                                                                  "}\n"
4892                                                                  "\n";
4893                 break;
4894
4895         default:
4896                 TCU_FAIL("Unrecognized shader object type.");
4897                 break;
4898         }
4899
4900         return fragment_shader_source;
4901 }
4902
4903 /** Prepare shader
4904  *
4905  * @tparam API                Tested API descriptor
4906  *
4907  * @param tested_shader_type  The type of shader that is being tested
4908  * @param function_definition Definition used to prepare shader
4909  * @param function_use        Snippet that makes use of defined function
4910  * @param verification        Snippet that verifies results
4911  **/
4912 template <class API>
4913 std::string InteractionFunctionCalls1<API>::prepare_geometry_shader(
4914         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
4915         const std::string& function_use, const std::string& verification)
4916 {
4917         std::string geometry_shader_source;
4918
4919         switch (tested_shader_type)
4920         {
4921         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
4922         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
4923         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
4924                 break;
4925
4926         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
4927         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
4928                 geometry_shader_source = "layout(points)                           in;\n"
4929                                                                  "layout(triangle_strip, max_vertices = 4) out;\n"
4930                                                                  "\n"
4931                                                                  "in  float tes_result[];\n"
4932                                                                  "out float fs_result;\n"
4933                                                                  "\n"
4934                                                                  "void main()\n"
4935                                                                  "{\n"
4936                                                                  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
4937                                                                  "    fs_result    = tes_result[0];\n"
4938                                                                  "    EmitVertex();\n"
4939                                                                  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
4940                                                                  "    fs_result    = tes_result[0];\n"
4941                                                                  "    EmitVertex();\n"
4942                                                                  "    gl_Position  = vec4(1, -1, 0, 1);\n"
4943                                                                  "    fs_result    = tes_result[0];\n"
4944                                                                  "    EmitVertex();\n"
4945                                                                  "    gl_Position  = vec4(1, 1, 0, 1);\n"
4946                                                                  "    fs_result    = tes_result[0];\n"
4947                                                                  "    EmitVertex();\n"
4948                                                                  "}\n";
4949                 break;
4950
4951         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
4952                 geometry_shader_source = "layout(points)                           in;\n"
4953                                                                  "layout(triangle_strip, max_vertices = 4) out;\n"
4954                                                                  "\n"
4955                                                                  "out float fs_result;\n"
4956                                                                  "\n";
4957
4958                 /* User-defined function definition. */
4959                 geometry_shader_source += function_definition;
4960                 geometry_shader_source += "\n\n";
4961
4962                 /* Main function definition. */
4963                 geometry_shader_source += shader_start;
4964                 geometry_shader_source += function_use;
4965                 geometry_shader_source += "\n\n";
4966                 geometry_shader_source += verification;
4967                 geometry_shader_source += "\n\n";
4968                 geometry_shader_source += "\n    gl_Position  = vec4(-1, -1, 0, 1);\n"
4969                                                                   "    fs_result    = result;\n"
4970                                                                   "    EmitVertex();\n"
4971                                                                   "    gl_Position  = vec4(-1, 1, 0, 1);\n"
4972                                                                   "    fs_result    = result;\n"
4973                                                                   "    EmitVertex();\n"
4974                                                                   "    gl_Position  = vec4(1, -1, 0, 1);\n"
4975                                                                   "    fs_result    = result;\n"
4976                                                                   "    EmitVertex();\n"
4977                                                                   "    gl_Position  = vec4(1, 1, 0, 1);\n"
4978                                                                   "    fs_result    = result;\n"
4979                                                                   "    EmitVertex();\n"
4980                                                                   "}\n";
4981                 break;
4982
4983         default:
4984                 TCU_FAIL("Unrecognized shader object type.");
4985                 break;
4986         }
4987
4988         return geometry_shader_source;
4989 }
4990
4991 /** Prepare shader
4992  *
4993  * @tparam API                Tested API descriptor
4994  *
4995  * @param tested_shader_type  The type of shader that is being tested
4996  * @param function_definition Definition used to prepare shader
4997  * @param function_use        Snippet that makes use of defined function
4998  * @param verification        Snippet that verifies results
4999  **/
5000 template <class API>
5001 std::string InteractionFunctionCalls1<API>::prepare_tess_ctrl_shader(
5002         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
5003         const std::string& function_use, const std::string& verification)
5004 {
5005         std::string tess_ctrl_shader_source;
5006
5007         switch (tested_shader_type)
5008         {
5009         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
5010         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
5011         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
5012         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
5013                 break;
5014
5015         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
5016                 tess_ctrl_shader_source = "layout(vertices = 1) out;\n"
5017                                                                   "\n"
5018                                                                   "out float tcs_result[];\n"
5019                                                                   "\n";
5020
5021                 /* User-defined function definition. */
5022                 tess_ctrl_shader_source += function_definition;
5023                 tess_ctrl_shader_source += "\n\n";
5024
5025                 /* Main function definition. */
5026                 tess_ctrl_shader_source += shader_start;
5027                 tess_ctrl_shader_source += function_use;
5028                 tess_ctrl_shader_source += "\n\n";
5029                 tess_ctrl_shader_source += verification;
5030                 tess_ctrl_shader_source += "\n\n";
5031                 tess_ctrl_shader_source += "    tcs_result[gl_InvocationID] = result;\n"
5032                                                                    "\n"
5033                                                                    "    gl_TessLevelOuter[0] = 1.0;\n"
5034                                                                    "    gl_TessLevelOuter[1] = 1.0;\n"
5035                                                                    "    gl_TessLevelOuter[2] = 1.0;\n"
5036                                                                    "    gl_TessLevelOuter[3] = 1.0;\n"
5037                                                                    "    gl_TessLevelInner[0] = 1.0;\n"
5038                                                                    "    gl_TessLevelInner[1] = 1.0;\n"
5039                                                                    "}\n";
5040                 break;
5041
5042         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
5043                 tess_ctrl_shader_source = default_tc_shader_source;
5044                 break;
5045
5046         default:
5047                 TCU_FAIL("Unrecognized shader object type.");
5048                 break;
5049         }
5050
5051         return tess_ctrl_shader_source;
5052 }
5053
5054 /** Prepare shader
5055  *
5056  * @tparam API                Tested API descriptor
5057  *
5058  * @param tested_shader_type  The type of shader that is being tested
5059  * @param function_definition Definition used to prepare shader
5060  * @param function_use        Snippet that makes use of defined function
5061  * @param verification        Snippet that verifies results
5062  **/
5063 template <class API>
5064 std::string InteractionFunctionCalls1<API>::prepare_tess_eval_shader(
5065         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
5066         const std::string& function_use, const std::string& verification)
5067 {
5068         std::string tess_eval_shader_source;
5069
5070         switch (tested_shader_type)
5071         {
5072         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
5073         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
5074         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
5075         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
5076                 break;
5077
5078         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
5079                 tess_eval_shader_source = "layout(isolines, point_mode) in;\n"
5080                                                                   "\n"
5081                                                                   "in  float tcs_result[];\n"
5082                                                                   "out float tes_result;\n"
5083                                                                   "\n"
5084                                                                   "void main()\n"
5085                                                                   "{\n"
5086                                                                   "    tes_result = tcs_result[0];\n"
5087                                                                   "}\n";
5088                 break;
5089
5090         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
5091                 tess_eval_shader_source = "layout(isolines, point_mode) in;\n"
5092                                                                   "\n"
5093                                                                   "out float tes_result;\n"
5094                                                                   "\n";
5095
5096                 /* User-defined function definition. */
5097                 tess_eval_shader_source += function_definition;
5098                 tess_eval_shader_source += "\n\n";
5099
5100                 /* Main function definition. */
5101                 tess_eval_shader_source += shader_start;
5102                 tess_eval_shader_source += function_use;
5103                 tess_eval_shader_source += "\n\n";
5104                 tess_eval_shader_source += verification;
5105                 tess_eval_shader_source += "\n\n";
5106                 tess_eval_shader_source += "    tes_result = result;\n"
5107                                                                    "}\n";
5108                 break;
5109
5110         default:
5111                 TCU_FAIL("Unrecognized shader object type.");
5112                 break;
5113         }
5114
5115         return tess_eval_shader_source;
5116 }
5117
5118 /** Prepare shader
5119  *
5120  * @tparam API                Tested API descriptor
5121  *
5122  * @param tested_shader_type  The type of shader that is being tested
5123  * @param function_definition Definition used to prepare shader
5124  * @param function_use        Snippet that makes use of defined function
5125  * @param verification        Snippet that verifies results
5126  **/
5127 template <class API>
5128 std::string InteractionFunctionCalls1<API>::prepare_vertex_shader(
5129         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
5130         const std::string& function_use, const std::string& verification)
5131 {
5132         std::string vertex_shader_source;
5133
5134         switch (tested_shader_type)
5135         {
5136         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
5137                 break;
5138
5139         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
5140                 vertex_shader_source = "/** GL_TRIANGLE_FAN-type quad vertex data. */\n"
5141                                                            "const vec4 vertex_positions[4] = vec4[4](vec4( 1.0, -1.0, 0.0, 1.0),\n"
5142                                                            "                                         vec4(-1.0, -1.0, 0.0, 1.0),\n"
5143                                                            "                                         vec4(-1.0,  1.0, 0.0, 1.0),\n"
5144                                                            "                                         vec4( 1.0,  1.0, 0.0, 1.0) );\n"
5145                                                            "\n"
5146                                                            "void main()\n"
5147                                                            "{\n"
5148                                                            "    gl_Position = vertex_positions[gl_VertexID];"
5149                                                            "}\n\n";
5150                 break;
5151
5152         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
5153         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
5154         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
5155                 vertex_shader_source = default_vertex_shader_source;
5156                 break;
5157
5158         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
5159                 /* Vertex shader source. */
5160                 vertex_shader_source = "out float fs_result;\n\n";
5161                 vertex_shader_source += "/** GL_TRIANGLE_FAN-type quad vertex data. */\n"
5162                                                                 "const vec4 vertex_positions[4] = vec4[4](vec4( 1.0, -1.0, 0.0, 1.0),\n"
5163                                                                 "                                         vec4(-1.0, -1.0, 0.0, 1.0),\n"
5164                                                                 "                                         vec4(-1.0,  1.0, 0.0, 1.0),\n"
5165                                                                 "                                         vec4( 1.0,  1.0, 0.0, 1.0) );\n\n";
5166
5167                 /* User-defined function definition. */
5168                 vertex_shader_source += function_definition;
5169                 vertex_shader_source += "\n\n";
5170
5171                 /* Main function definition. */
5172                 vertex_shader_source += shader_start;
5173                 vertex_shader_source += function_use;
5174                 vertex_shader_source += "\n\n";
5175                 vertex_shader_source += verification;
5176                 vertex_shader_source += "\n\n";
5177                 vertex_shader_source += "    fs_result   = result;\n"
5178                                                                 "    gl_Position = vertex_positions[gl_VertexID];\n";
5179                 vertex_shader_source += shader_end;
5180                 break;
5181
5182         default:
5183                 TCU_FAIL("Unrecognized shader object type.");
5184                 break;
5185         }
5186
5187         return vertex_shader_source;
5188 }
5189
5190 /* Generates the shader source code for the InteractionFunctionCalls2
5191  * array tests, and attempts to compile each test shader, for both
5192  * vertex and fragment shaders.
5193  *
5194  * @tparam API               Tested API descriptor
5195  *
5196  * @param tested_shader_type The type of shader that is being tested
5197  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
5198  */
5199 template <class API>
5200 void InteractionFunctionCalls2<API>::test_shader_compilation(
5201         typename TestCaseBase<API>::TestShaderType tested_shader_type)
5202 {
5203         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
5204                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
5205                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
5206                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4 };
5207         static const size_t num_var_types_es = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
5208
5209         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
5210                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
5211                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
5212                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4,  VAR_TYPE_DOUBLE,
5213                                                                                                                          VAR_TYPE_DMAT2, VAR_TYPE_DMAT3, VAR_TYPE_DMAT4 };
5214         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
5215
5216         const std::string iteration_loop_end = "                               }\n"
5217                                                                                    "                           }\n"
5218                                                                                    "                        }\n"
5219                                                                                    "                    }\n"
5220                                                                                    "                }\n"
5221                                                                                    "            }\n"
5222                                                                                    "        }\n"
5223                                                                                    "    }\n";
5224         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
5225                                                                                          "    {\n"
5226                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
5227                                                                                          "        {\n"
5228                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
5229                                                                                          "            {\n"
5230                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
5231                                                                                          "                {\n"
5232                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
5233                                                                                          "                    {\n"
5234                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
5235                                                                                          "                        {\n"
5236                                                                                          "                           for (uint g = 0u; g < 2u; g++)\n"
5237                                                                                          "                           {\n"
5238                                                                                          "                               for (uint h = 0u; h < 2u; h++)\n"
5239                                                                                          "                               {\n";
5240         const std::string multiplier_array = "const int[] multiplier_array = int[]( 1,  2,  3,  4,  5,  6,  7,  8,\n"
5241                                                                                  "                                     11, 12, 13, 14, 15, 16, 17, 18,\n"
5242                                                                                  "                                     21, 22, 23, 24, 25, 26, 27, 28,\n"
5243                                                                                  "                                     31, 32, 33, 34, 35, 36, 37, 38,\n"
5244                                                                                  "                                     41, 42, 43, 44, 45, 46, 47, 48,\n"
5245                                                                                  "                                     51, 52, 53, 54, 55, 56, 57, 58,\n"
5246                                                                                  "                                     61, 62, 63, 64, 65, 66, 67, 68,\n"
5247                                                                                  "                                     71, 72, 73, 74, 75, 76, 77, 78,\n"
5248                                                                                  "                                     81, 82, 83, 84, 85, 86, 87, 88);\n";
5249         const glcts::test_var_type* var_types_set = var_types_set_es;
5250         size_t                                          num_var_types = num_var_types_es;
5251         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
5252
5253         if (API::USE_DOUBLE)
5254         {
5255                 var_types_set = var_types_set_gl;
5256                 num_var_types = num_var_types_gl;
5257         }
5258
5259         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
5260         {
5261                 _supported_variable_types_map_const_iterator var_iterator =
5262                         supported_variable_types_map.find(var_types_set[var_type_index]);
5263
5264                 if (var_iterator != supported_variable_types_map.end())
5265                 {
5266                         std::string function_definition;
5267                         std::string function_use;
5268                         std::string verification;
5269
5270                         function_definition += multiplier_array;
5271                         function_definition += "void my_function(inout ";
5272                         function_definition += var_iterator->second.type;
5273                         function_definition += " inout_array[2][2][2][2][2][2][2][2]) {\n"
5274                                                                    "    uint i = 0u;\n";
5275                         function_definition += iteration_loop_start;
5276                         function_definition += "                                   inout_array[a][b][c][d][e][f][g][h] *= " +
5277                                                                    var_iterator->second.iterator_type + "(multiplier_array[i % 64u]);\n";
5278                         function_definition += "                                   i+= 1u;\n";
5279                         function_definition += iteration_loop_end;
5280                         function_definition += "}";
5281
5282                         function_use += "    float result = 1.0;\n";
5283                         function_use += "    uint iterator = 0u;\n";
5284                         function_use += "    " + var_iterator->second.type + " my_array[2][2][2][2][2][2][2][2];\n";
5285                         function_use += iteration_loop_start;
5286                         function_use += "                                   my_array[a][b][c][d][e][f][g][h] = " +
5287                                                         var_iterator->second.variable_type_initializer2 + ";\n";
5288                         function_use += iteration_loop_end;
5289                         function_use += "    my_function(my_array);";
5290
5291                         verification += iteration_loop_start;
5292                         verification += "                                   if (my_array[a][b][c][d][e][f][g][h] " +
5293                                                         var_iterator->second.specific_element + "!= " + var_iterator->second.iterator_type +
5294                                                         "(multiplier_array[iterator % 64u]))\n"
5295                                                         "                                   {\n"
5296                                                         "                                       result = 0.0;\n"
5297                                                         "                                   }\n"
5298                                                         "                                   iterator += 1u;\n";
5299                         verification += iteration_loop_end;
5300
5301                         if (false == test_compute)
5302                         {
5303                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification);
5304                         }
5305                         else
5306                         {
5307                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification);
5308                         }
5309
5310                         /* Deallocate any resources used. */
5311                         this->delete_objects();
5312                 } /* if var_type iterator found */
5313                 else
5314                 {
5315                         TCU_FAIL("Type not found.");
5316                 }
5317         } /* for (int var_type_index = 0; ...) */
5318 }
5319
5320 /* Generates the shader source code for the InteractionArgumentAliasing1
5321  * array tests, and attempts to compile each test shader, for both
5322  * vertex and fragment shaders.
5323  *
5324  * @tparam API               Tested API descriptor
5325  *
5326  * @param tested_shader_type The type of shader that is being tested
5327  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
5328  */
5329 template <class API>
5330 void InteractionArgumentAliasing1<API>::test_shader_compilation(
5331         typename TestCaseBase<API>::TestShaderType tested_shader_type)
5332 {
5333         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4 };
5334         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
5335
5336         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4,
5337                                                                                                                          VAR_TYPE_DOUBLE, VAR_TYPE_DMAT4 };
5338         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
5339
5340         const std::string iteration_loop_end = "                               }\n"
5341                                                                                    "                           }\n"
5342                                                                                    "                        }\n"
5343                                                                                    "                    }\n"
5344                                                                                    "                }\n"
5345                                                                                    "            }\n"
5346                                                                                    "        }\n"
5347                                                                                    "    }\n";
5348         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
5349                                                                                          "    {\n"
5350                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
5351                                                                                          "        {\n"
5352                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
5353                                                                                          "            {\n"
5354                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
5355                                                                                          "                {\n"
5356                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
5357                                                                                          "                    {\n"
5358                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
5359                                                                                          "                        {\n"
5360                                                                                          "                           for (uint g = 0u; g < 2u; g++)\n"
5361                                                                                          "                           {\n"
5362                                                                                          "                               for (uint h = 0u; h < 2u; h++)\n"
5363                                                                                          "                               {\n";
5364         const glcts::test_var_type* var_types_set = var_types_set_es;
5365         size_t                                          num_var_types = num_var_types_es;
5366         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
5367
5368         if (API::USE_DOUBLE)
5369         {
5370                 var_types_set = var_types_set_gl;
5371                 num_var_types = num_var_types_gl;
5372         }
5373
5374         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
5375         {
5376                 _supported_variable_types_map_const_iterator var_iterator =
5377                         supported_variable_types_map.find(var_types_set[var_type_index]);
5378
5379                 if (var_iterator != supported_variable_types_map.end())
5380                 {
5381                         std::string array_declaration = var_iterator->second.type + " z[2][2][2][2][2][2][2][2];\n\n";
5382
5383                         std::string function_definition;
5384                         std::string function_use;
5385                         std::string verification;
5386
5387                         function_definition += "bool gfunc(" + var_iterator->second.type + " x[2][2][2][2][2][2][2][2], ";
5388                         function_definition += var_iterator->second.type + " y[2][2][2][2][2][2][2][2])\n";
5389                         function_definition += "{\n";
5390                         function_definition += "    " + iteration_loop_start;
5391                         function_definition +=
5392                                 "                               x[a][b][c][d][e][f][g][h] = " + var_iterator->second.type + "(123);\n";
5393                         function_definition += "    " + iteration_loop_end;
5394                         function_definition += "\n";
5395                         function_definition += "    " + iteration_loop_start;
5396                         function_definition += "                                   if(y[a][b][c][d][e][f][g][h]";
5397                         if (var_iterator->second.type == "mat4") // mat4 comparison
5398                         {
5399                                 function_definition += "[0][0]";
5400                                 function_definition += " != float";
5401                         }
5402                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
5403                         {
5404                                 function_definition += "[0][0]";
5405                                 function_definition += " != double";
5406                         }
5407                         else
5408                         {
5409                                 function_definition += " != ";
5410                                 function_definition += var_iterator->second.type;
5411                         }
5412                         function_definition += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h))) {return false;}\n";
5413                         function_definition += "    " + iteration_loop_end;
5414                         function_definition += "  return true;\n";
5415                         function_definition += "}";
5416
5417                         function_use += "    " + array_declaration;
5418                         function_use += "    " + iteration_loop_start;
5419                         function_use += "                                   z[a][b][c][d][e][f][g][h] = ";
5420                         function_use += var_iterator->second.type;
5421                         function_use += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h));\n";
5422                         function_use += "    " + iteration_loop_end;
5423
5424                         verification += "    float result = 0.0;\n";
5425                         verification += "    if(gfunc(z, z) == true)\n";
5426                         verification += "    {\n";
5427                         verification += "        result = 1.0;\n\n";
5428                         verification += "    }\n";
5429                         verification += "    else\n";
5430                         verification += "    {\n";
5431                         verification += "        result = 0.0;\n\n";
5432                         verification += "    }\n";
5433
5434                         if (false == test_compute)
5435                         {
5436                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification);
5437                         }
5438                         else
5439                         {
5440                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification);
5441                         }
5442
5443                         /* Deallocate any resources used. */
5444                         this->delete_objects();
5445                 } /* if var_type iterator found */
5446                 else
5447                 {
5448                         TCU_FAIL("Type not found.");
5449                 }
5450         }
5451 }
5452
5453 /* Generates the shader source code for the InteractionArgumentAliasing2
5454  * array tests, and attempts to compile each test shader, for both
5455  * vertex and fragment shaders.
5456  *
5457  * @tparam API               Tested API descriptor
5458  *
5459  * @param tested_shader_type The type of shader that is being tested
5460  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
5461  */
5462 template <class API>
5463 void InteractionArgumentAliasing2<API>::test_shader_compilation(
5464         typename TestCaseBase<API>::TestShaderType tested_shader_type)
5465 {
5466         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4 };
5467         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
5468
5469         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4,
5470                                                                                                                          VAR_TYPE_DOUBLE, VAR_TYPE_DMAT4 };
5471         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
5472
5473         const std::string iteration_loop_end = "                               }\n"
5474                                                                                    "                           }\n"
5475                                                                                    "                        }\n"
5476                                                                                    "                    }\n"
5477                                                                                    "                }\n"
5478                                                                                    "            }\n"
5479                                                                                    "        }\n"
5480                                                                                    "    }\n";
5481         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
5482                                                                                          "    {\n"
5483                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
5484                                                                                          "        {\n"
5485                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
5486                                                                                          "            {\n"
5487                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
5488                                                                                          "                {\n"
5489                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
5490                                                                                          "                    {\n"
5491                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
5492                                                                                          "                        {\n"
5493                                                                                          "                           for (uint g = 0u; g < 2u; g++)\n"
5494                                                                                          "                           {\n"
5495                                                                                          "                               for (uint h = 0u; h < 2u; h++)\n"
5496                                                                                          "                               {\n";
5497         const glcts::test_var_type* var_types_set = var_types_set_es;
5498         size_t                                          num_var_types = num_var_types_es;
5499         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
5500
5501         if (API::USE_DOUBLE)
5502         {
5503                 var_types_set = var_types_set_gl;
5504                 num_var_types = num_var_types_gl;
5505         }
5506
5507         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
5508         {
5509                 _supported_variable_types_map_const_iterator var_iterator =
5510                         supported_variable_types_map.find(var_types_set[var_type_index]);
5511
5512                 if (var_iterator != supported_variable_types_map.end())
5513                 {
5514                         std::string array_declaration = var_iterator->second.type + " z[2][2][2][2][2][2][2][2];\n\n";
5515
5516                         std::string function_definition;
5517                         std::string function_use;
5518                         std::string verification;
5519
5520                         function_definition += "bool gfunc(" + var_iterator->second.type + " x[2][2][2][2][2][2][2][2], ";
5521                         function_definition += var_iterator->second.type + " y[2][2][2][2][2][2][2][2])\n";
5522                         function_definition += "{\n";
5523                         function_definition += "    " + iteration_loop_start;
5524                         function_definition +=
5525                                 "                                   y[a][b][c][d][e][f][g][h] = " + var_iterator->second.type +
5526                                 "(123);\n";
5527                         function_definition += "    " + iteration_loop_end;
5528                         function_definition += "\n";
5529                         function_definition += "    " + iteration_loop_start;
5530                         function_definition += "                                   if(x[a][b][c][d][e][f][g][h]";
5531                         if (var_iterator->second.type == "mat4") // mat4 comparison
5532                         {
5533                                 function_definition += "[0][0]";
5534                                 function_definition += " != float";
5535                         }
5536                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
5537                         {
5538                                 function_definition += "[0][0]";
5539                                 function_definition += " != double";
5540                         }
5541                         else
5542                         {
5543                                 function_definition += " != ";
5544                                 function_definition += var_iterator->second.type;
5545                         }
5546                         function_definition += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h))) {return false;}\n";
5547                         function_definition += "    " + iteration_loop_end;
5548                         function_definition += "  return true;\n";
5549                         function_definition += "}";
5550
5551                         function_use += "    " + array_declaration;
5552                         function_use += "    " + iteration_loop_start;
5553                         function_use += "                                   z[a][b][c][d][e][f][g][h] = ";
5554                         function_use += var_iterator->second.type;
5555                         function_use += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h));\n";
5556                         function_use += "    " + iteration_loop_end;
5557
5558                         verification += "    float result = 0.0;\n";
5559                         verification += "    if(gfunc(z, z) == true)\n";
5560                         verification += "    {\n";
5561                         verification += "        result = 1.0;\n\n";
5562                         verification += "    }\n";
5563                         verification += "    else\n";
5564                         verification += "    {\n";
5565                         verification += "        result = 0.0;\n\n";
5566                         verification += "    }\n";
5567
5568                         if (false == test_compute)
5569                         {
5570                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification);
5571                         }
5572                         else
5573                         {
5574                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification);
5575                         }
5576
5577                         /* Deallocate any resources used. */
5578                         this->delete_objects();
5579                 } /* if var_type iterator found */
5580                 else
5581                 {
5582                         TCU_FAIL("Type not found.");
5583                 }
5584         }
5585 }
5586
5587 /* Generates the shader source code for the InteractionArgumentAliasing3
5588  * array tests, and attempts to compile each test shader, for both
5589  * vertex and fragment shaders.
5590  *
5591  * @tparam API               Tested API descriptor
5592  *
5593  * @param tested_shader_type The type of shader that is being tested
5594  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
5595  */
5596 template <class API>
5597 void InteractionArgumentAliasing3<API>::test_shader_compilation(
5598         typename TestCaseBase<API>::TestShaderType tested_shader_type)
5599 {
5600         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4 };
5601         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
5602
5603         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4,
5604                                                                                                                          VAR_TYPE_DOUBLE, VAR_TYPE_DMAT4 };
5605         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
5606
5607         const std::string iteration_loop_end = "                               }\n"
5608                                                                                    "                           }\n"
5609                                                                                    "                        }\n"
5610                                                                                    "                    }\n"
5611                                                                                    "                }\n"
5612                                                                                    "            }\n"
5613                                                                                    "        }\n"
5614                                                                                    "    }\n";
5615         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
5616                                                                                          "    {\n"
5617                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
5618                                                                                          "        {\n"
5619                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
5620                                                                                          "            {\n"
5621                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
5622                                                                                          "                {\n"
5623                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
5624                                                                                          "                    {\n"
5625                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
5626                                                                                          "                        {\n"
5627                                                                                          "                           for (uint g = 0u; g < 2u; g++)\n"
5628                                                                                          "                           {\n"
5629                                                                                          "                               for (uint h = 0u; h < 2u; h++)\n"
5630                                                                                          "                               {\n";
5631         const glcts::test_var_type* var_types_set = var_types_set_es;
5632         size_t                                          num_var_types = num_var_types_es;
5633         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
5634
5635         if (API::USE_DOUBLE)
5636         {
5637                 var_types_set = var_types_set_gl;
5638                 num_var_types = num_var_types_gl;
5639         }
5640
5641         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
5642         {
5643                 _supported_variable_types_map_const_iterator var_iterator =
5644                         supported_variable_types_map.find(var_types_set[var_type_index]);
5645
5646                 if (var_iterator != supported_variable_types_map.end())
5647                 {
5648                         std::string array_declaration = var_iterator->second.type + " z[2][2][2][2][2][2][2][2];\n\n";
5649
5650                         std::string function_definition;
5651                         std::string function_use;
5652                         std::string verification;
5653
5654                         function_definition += "bool gfunc(out " + var_iterator->second.type + " x[2][2][2][2][2][2][2][2], ";
5655                         function_definition += var_iterator->second.type + " y[2][2][2][2][2][2][2][2])\n";
5656                         function_definition += "{\n";
5657                         function_definition += "    " + iteration_loop_start;
5658                         function_definition +=
5659                                 "                                   x[a][b][c][d][e][f][g][h] = " + var_iterator->second.type +
5660                                 "(123);\n";
5661                         function_definition += "    " + iteration_loop_end;
5662                         function_definition += "\n";
5663                         function_definition += "    " + iteration_loop_start;
5664                         function_definition += "                                   if(y[a][b][c][d][e][f][g][h]";
5665                         if (var_iterator->second.type == "mat4") // mat4 comparison
5666                         {
5667                                 function_definition += "[0][0]";
5668                                 function_definition += " != float";
5669                         }
5670                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
5671                         {
5672                                 function_definition += "[0][0]";
5673                                 function_definition += " != double";
5674                         }
5675                         else
5676                         {
5677                                 function_definition += " != ";
5678                                 function_definition += var_iterator->second.type;
5679                         }
5680                         function_definition += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h))) {return false;}\n";
5681                         function_definition += "    " + iteration_loop_end;
5682                         function_definition += "  return true;\n";
5683                         function_definition += "}\n\n";
5684
5685                         function_use += "    " + array_declaration;
5686                         function_use += "    " + iteration_loop_start;
5687                         function_use += "                                   z[a][b][c][d][e][f][g][h] = ";
5688                         function_use += var_iterator->second.type;
5689                         function_use += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h));\n";
5690                         function_use += "    " + iteration_loop_end;
5691
5692                         verification += "    float result = 0.0;\n";
5693                         verification += "    if(gfunc(z, z) == true)\n";
5694                         verification += "    {\n";
5695                         verification += "        result = 1.0;\n\n";
5696                         verification += "    }\n";
5697                         verification += "    else\n";
5698                         verification += "    {\n";
5699                         verification += "        result = 0.0;\n\n";
5700                         verification += "    }\n";
5701
5702                         if (false == test_compute)
5703                         {
5704                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification);
5705                         }
5706                         else
5707                         {
5708                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification);
5709                         }
5710
5711                         /* Deallocate any resources used. */
5712                         this->delete_objects();
5713                 } /* if var_type iterator found */
5714                 else
5715                 {
5716                         TCU_FAIL("Type not found.");
5717                 }
5718         }
5719 }
5720
5721 /* Generates the shader source code for the InteractionArgumentAliasing4
5722  * array tests, and attempts to compile each test shader, for both
5723  * vertex and fragment shaders.
5724  *
5725  * @tparam API               Tested API descriptor
5726  *
5727  * @param tested_shader_type The type of shader that is being tested
5728  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
5729  */
5730 template <class API>
5731 void InteractionArgumentAliasing4<API>::test_shader_compilation(
5732         typename TestCaseBase<API>::TestShaderType tested_shader_type)
5733 {
5734         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4 };
5735         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
5736
5737         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4,
5738                                                                                                                          VAR_TYPE_DOUBLE, VAR_TYPE_DMAT4 };
5739         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
5740
5741         const std::string iteration_loop_end = "                               }\n"
5742                                                                                    "                           }\n"
5743                                                                                    "                        }\n"
5744                                                                                    "                    }\n"
5745                                                                                    "                }\n"
5746                                                                                    "            }\n"
5747                                                                                    "        }\n"
5748                                                                                    "    }\n";
5749         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
5750                                                                                          "    {\n"
5751                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
5752                                                                                          "        {\n"
5753                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
5754                                                                                          "            {\n"
5755                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
5756                                                                                          "                {\n"
5757                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
5758                                                                                          "                    {\n"
5759                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
5760                                                                                          "                        {\n"
5761                                                                                          "                           for (uint g = 0u; g < 2u; g++)\n"
5762                                                                                          "                           {\n"
5763                                                                                          "                               for (uint h = 0u; h < 2u; h++)\n"
5764                                                                                          "                               {\n";
5765         const glcts::test_var_type* var_types_set = var_types_set_es;
5766         size_t                                          num_var_types = num_var_types_es;
5767         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
5768
5769         if (API::USE_DOUBLE)
5770         {
5771                 var_types_set = var_types_set_gl;
5772                 num_var_types = num_var_types_gl;
5773         }
5774
5775         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
5776         {
5777                 _supported_variable_types_map_const_iterator var_iterator =
5778                         supported_variable_types_map.find(var_types_set[var_type_index]);
5779
5780                 if (var_iterator != supported_variable_types_map.end())
5781                 {
5782                         std::string array_declaration = var_iterator->second.type + "[2][2][2][2][2][2][2][2] z;\n\n";
5783
5784                         std::string function_definition;
5785                         std::string function_use;
5786                         std::string verification;
5787
5788                         function_definition += "bool gfunc(" + var_iterator->second.type + " x[2][2][2][2][2][2][2][2], ";
5789                         function_definition += "out " + var_iterator->second.type + " y[2][2][2][2][2][2][2][2])\n";
5790                         function_definition += "{\n";
5791                         function_definition += "    " + iteration_loop_start;
5792                         function_definition +=
5793                                 "                                   y[a][b][c][d][e][f][g][h] = " + var_iterator->second.type +
5794                                 "(123);\n";
5795                         function_definition += "    " + iteration_loop_end;
5796                         function_definition += "\n";
5797                         function_definition += "    " + iteration_loop_start;
5798                         function_definition += "                                   if(x[a][b][c][d][e][f][g][h]";
5799                         if (var_iterator->second.type == "mat4") // mat4 comparison
5800                         {
5801                                 function_definition += "[0][0]";
5802                                 function_definition += " != float";
5803                         }
5804                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
5805                         {
5806                                 function_definition += "[0][0]";
5807                                 function_definition += " != double";
5808                         }
5809                         else
5810                         {
5811                                 function_definition += " != ";
5812                                 function_definition += var_iterator->second.type;
5813                         }
5814                         function_definition += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h))) {return false;}\n";
5815                         function_definition += "    " + iteration_loop_end;
5816                         function_definition += "  return true;\n";
5817                         function_definition += "}\n\n";
5818
5819                         function_use += "    " + array_declaration;
5820                         function_use += "    " + iteration_loop_start;
5821                         function_use += "                                   z[a][b][c][d][e][f][g][h] = ";
5822                         function_use += var_iterator->second.type;
5823                         function_use += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h));\n";
5824                         function_use += "    " + iteration_loop_end;
5825
5826                         verification += "    float result = 0.0;\n";
5827                         verification += "    if(gfunc(z, z) == true)\n";
5828                         verification += "    {\n";
5829                         verification += "        result = 1.0;\n\n";
5830                         verification += "    }\n";
5831                         verification += "    else\n";
5832                         verification += "    {\n";
5833                         verification += "        result = 0.0;\n\n";
5834                         verification += "    }\n";
5835
5836                         if (false == test_compute)
5837                         {
5838                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification);
5839                         }
5840                         else
5841                         {
5842                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification);
5843                         }
5844
5845                         /* Deallocate any resources used. */
5846                         this->delete_objects();
5847                 } /* if var_type iterator found */
5848                 else
5849                 {
5850                         TCU_FAIL("Type not found.");
5851                 }
5852         }
5853 }
5854
5855 /* Generates the shader source code for the InteractionArgumentAliasing3
5856  * array tests, and attempts to compile each test shader, for both
5857  * vertex and fragment shaders.
5858  *
5859  * @tparam API               Tested API descriptor
5860  *
5861  * @param tested_shader_type The type of shader that is being tested
5862  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
5863  */
5864 template <class API>
5865 void InteractionArgumentAliasing5<API>::test_shader_compilation(
5866         typename TestCaseBase<API>::TestShaderType tested_shader_type)
5867 {
5868         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4 };
5869         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
5870
5871         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4,
5872                                                                                                                          VAR_TYPE_DOUBLE, VAR_TYPE_DMAT4 };
5873         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
5874
5875         const std::string iteration_loop_end = "                               }\n"
5876                                                                                    "                           }\n"
5877                                                                                    "                        }\n"
5878                                                                                    "                    }\n"
5879                                                                                    "                }\n"
5880                                                                                    "            }\n"
5881                                                                                    "        }\n"
5882                                                                                    "    }\n";
5883         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
5884                                                                                          "    {\n"
5885                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
5886                                                                                          "        {\n"
5887                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
5888                                                                                          "            {\n"
5889                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
5890                                                                                          "                {\n"
5891                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
5892                                                                                          "                    {\n"
5893                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
5894                                                                                          "                        {\n"
5895                                                                                          "                           for (uint g = 0u; g < 2u; g++)\n"
5896                                                                                          "                           {\n"
5897                                                                                          "                               for (uint h = 0u; h < 2u; h++)\n"
5898                                                                                          "                               {\n";
5899         const glcts::test_var_type* var_types_set = var_types_set_es;
5900         size_t                                          num_var_types = num_var_types_es;
5901         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
5902
5903         if (API::USE_DOUBLE)
5904         {
5905                 var_types_set = var_types_set_gl;
5906                 num_var_types = num_var_types_gl;
5907         }
5908
5909         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
5910         {
5911                 _supported_variable_types_map_const_iterator var_iterator =
5912                         supported_variable_types_map.find(var_types_set[var_type_index]);
5913
5914                 if (var_iterator != supported_variable_types_map.end())
5915                 {
5916                         std::string array_declaration = var_iterator->second.type + "[2][2][2][2][2][2][2][2] z;\n\n";
5917
5918                         std::string function_definition;
5919                         std::string function_use;
5920                         std::string verification;
5921
5922                         function_definition += "bool gfunc(inout " + var_iterator->second.type + " x[2][2][2][2][2][2][2][2], ";
5923                         function_definition += var_iterator->second.type + " y[2][2][2][2][2][2][2][2])\n";
5924                         function_definition += "{\n";
5925                         function_definition += "    " + iteration_loop_start;
5926                         function_definition +=
5927                                 "                                   x[a][b][c][d][e][f][g][h] = " + var_iterator->second.type +
5928                                 "(123);\n";
5929                         function_definition += "    " + iteration_loop_end;
5930                         function_definition += "\n";
5931                         function_definition += "    " + iteration_loop_start;
5932                         function_definition += "                                   if(y[a][b][c][d][e][f][g][h]";
5933                         if (var_iterator->second.type == "mat4") // mat4 comparison
5934                         {
5935                                 function_definition += "[0][0]";
5936                                 function_definition += " != float";
5937                         }
5938                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
5939                         {
5940                                 function_definition += "[0][0]";
5941                                 function_definition += " != double";
5942                         }
5943                         else
5944                         {
5945                                 function_definition += " != ";
5946                                 function_definition += var_iterator->second.type;
5947                         }
5948                         function_definition += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h))) {return false;}\n";
5949                         function_definition += "    " + iteration_loop_end;
5950                         function_definition += "  return true;\n";
5951                         function_definition += "}\n\n";
5952
5953                         function_use += "    " + array_declaration;
5954                         function_use += "    " + iteration_loop_start;
5955                         function_use += "                                   z[a][b][c][d][e][f][g][h] = ";
5956                         function_use += var_iterator->second.type;
5957                         function_use += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h));\n";
5958                         function_use += "    " + iteration_loop_end;
5959
5960                         verification += "    float result = 0.0;\n";
5961                         verification += "    if(gfunc(z, z) == true)\n";
5962                         verification += "    {\n";
5963                         verification += "        result = 1.0;\n\n";
5964                         verification += "    }\n";
5965                         verification += "    else\n";
5966                         verification += "    {\n";
5967                         verification += "        result = 0.0;\n\n";
5968                         verification += "    }\n";
5969
5970                         if (false == test_compute)
5971                         {
5972                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification);
5973                         }
5974                         else
5975                         {
5976                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification);
5977                         }
5978
5979                         /* Deallocate any resources used. */
5980                         this->delete_objects();
5981                 } /* if var_type iterator found */
5982                 else
5983                 {
5984                         TCU_FAIL("Type not found.");
5985                 }
5986         }
5987 }
5988
5989 /* Generates the shader source code for the InteractionArgumentAliasing4
5990  * array tests, and attempts to compile each test shader, for both
5991  * vertex and fragment shaders.
5992  *
5993  * @tparam API               Tested API descriptor
5994  *
5995  * @param tested_shader_type The type of shader that is being tested
5996  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
5997  */
5998 template <class API>
5999 void InteractionArgumentAliasing6<API>::test_shader_compilation(
6000         typename TestCaseBase<API>::TestShaderType tested_shader_type)
6001 {
6002         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4 };
6003         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
6004
6005         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4,
6006                                                                                                                          VAR_TYPE_DOUBLE, VAR_TYPE_DMAT4 };
6007         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
6008
6009         const std::string iteration_loop_end = "                               }\n"
6010                                                                                    "                           }\n"
6011                                                                                    "                        }\n"
6012                                                                                    "                    }\n"
6013                                                                                    "                }\n"
6014                                                                                    "            }\n"
6015                                                                                    "        }\n"
6016                                                                                    "    }\n";
6017         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
6018                                                                                          "    {\n"
6019                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
6020                                                                                          "        {\n"
6021                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
6022                                                                                          "            {\n"
6023                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
6024                                                                                          "                {\n"
6025                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
6026                                                                                          "                    {\n"
6027                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
6028                                                                                          "                        {\n"
6029                                                                                          "                           for (uint g = 0u; g < 2u; g++)\n"
6030                                                                                          "                           {\n"
6031                                                                                          "                               for (uint h = 0u; h < 2u; h++)\n"
6032                                                                                          "                               {\n";
6033         const glcts::test_var_type* var_types_set = var_types_set_es;
6034         size_t                                          num_var_types = num_var_types_es;
6035         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
6036
6037         if (API::USE_DOUBLE)
6038         {
6039                 var_types_set = var_types_set_gl;
6040                 num_var_types = num_var_types_gl;
6041         }
6042
6043         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
6044         {
6045                 _supported_variable_types_map_const_iterator var_iterator =
6046                         supported_variable_types_map.find(var_types_set[var_type_index]);
6047
6048                 if (var_iterator != supported_variable_types_map.end())
6049                 {
6050                         std::string array_declaration = var_iterator->second.type + "[2][2][2][2][2][2][2][2] z;\n\n";
6051
6052                         std::string function_definition;
6053                         std::string function_use;
6054                         std::string verification;
6055
6056                         function_definition += "bool gfunc(" + var_iterator->second.type + " x[2][2][2][2][2][2][2][2], ";
6057                         function_definition += "inout " + var_iterator->second.type + " y[2][2][2][2][2][2][2][2])\n";
6058                         function_definition += "{\n";
6059                         function_definition += "    " + iteration_loop_start;
6060                         function_definition +=
6061                                 "                                   y[a][b][c][d][e][f][g][h] = " + var_iterator->second.type +
6062                                 "(123);\n";
6063                         function_definition += "    " + iteration_loop_end;
6064                         function_definition += "\n";
6065                         function_definition += "    " + iteration_loop_start;
6066                         function_definition += "                                   if(x[a][b][c][d][e][f][g][h]";
6067                         if (var_iterator->second.type == "mat4") // mat4 comparison
6068                         {
6069                                 function_definition += "[0][0]";
6070                                 function_definition += " != float";
6071                         }
6072                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
6073                         {
6074                                 function_definition += "[0][0]";
6075                                 function_definition += " != double";
6076                         }
6077                         else
6078                         {
6079                                 function_definition += " != ";
6080                                 function_definition += var_iterator->second.type;
6081                         }
6082                         function_definition += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h))) {return false;}\n";
6083                         function_definition += "    " + iteration_loop_end;
6084                         function_definition += "  return true;\n";
6085                         function_definition += "}\n\n";
6086
6087                         function_use += "    " + array_declaration;
6088                         function_use += "    " + iteration_loop_start;
6089                         function_use += "                                   z[a][b][c][d][e][f][g][h] = ";
6090                         function_use += var_iterator->second.type;
6091                         function_use += "(((a*128u)+(b*64u)+(c*32u)+(d*16u)+(e*8u)+(f*4u)+(g*2u)+h));\n";
6092                         function_use += "    " + iteration_loop_end;
6093
6094                         verification += "    float result = 0.0;\n";
6095                         verification += "    if(gfunc(z, z) == true)\n";
6096                         verification += "    {\n";
6097                         verification += "        result = 1.0;\n\n";
6098                         verification += "    }\n";
6099                         verification += "    else\n";
6100                         verification += "    {\n";
6101                         verification += "        result = 0.0;\n\n";
6102                         verification += "    }\n";
6103
6104                         if (false == test_compute)
6105                         {
6106                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification);
6107                         }
6108                         else
6109                         {
6110                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification);
6111                         }
6112
6113                         /* Deallocate any resources used. */
6114                         this->delete_objects();
6115                 } /* if var_type iterator found */
6116                 else
6117                 {
6118                         TCU_FAIL("Type not found.");
6119                 }
6120         }
6121 }
6122
6123 /* Generates the shader source code for the InteractionUniforms1
6124  * array tests, and attempts to compile each test shader, for both
6125  * vertex and fragment shaders.
6126  *
6127  * @tparam API               Tested API descriptor
6128  *
6129  * @param tested_shader_type The type of shader that is being tested
6130  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
6131  */
6132 template <class API>
6133 void InteractionUniforms1<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
6134 {
6135         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT };
6136         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
6137
6138         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT,
6139                                                                                                                          VAR_TYPE_DOUBLE };
6140         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
6141
6142         const glw::Functions&           gl                        = this->context_id.getRenderContext().getFunctions();
6143         const glcts::test_var_type* var_types_set = var_types_set_es;
6144         size_t                                          num_var_types = num_var_types_es;
6145
6146         if (API::USE_DOUBLE)
6147         {
6148                 var_types_set = var_types_set_gl;
6149                 num_var_types = num_var_types_gl;
6150         }
6151
6152         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
6153         {
6154                 _supported_variable_types_map_const_iterator var_iterator =
6155                         supported_variable_types_map.find(var_types_set[var_type_index]);
6156
6157                 if (var_iterator != supported_variable_types_map.end())
6158                 {
6159                         std::string uniform_definition;
6160                         std::string uniform_use;
6161
6162                         uniform_definition += "uniform ";
6163                         uniform_definition += var_iterator->second.precision;
6164                         uniform_definition += " ";
6165                         uniform_definition += var_iterator->second.type;
6166                         uniform_definition += " my_uniform_1[1][1][1][1];\n\n";
6167
6168                         uniform_use = "    float result = float(my_uniform_1[0][0][0][0]);\n";
6169
6170                         if (API::USE_ALL_SHADER_STAGES)
6171                         {
6172                                 const std::string& compute_shader_source =
6173                                         this->prepare_compute_shader(tested_shader_type, uniform_definition, uniform_use);
6174                                 const std::string& fragment_shader_source =
6175                                         this->prepare_fragment_shader(tested_shader_type, uniform_definition, uniform_use);
6176                                 const std::string& geometry_shader_source =
6177                                         this->prepare_geometry_shader(tested_shader_type, uniform_definition, uniform_use);
6178                                 const std::string& tess_ctrl_shader_source =
6179                                         this->prepare_tess_ctrl_shader(tested_shader_type, uniform_definition, uniform_use);
6180                                 const std::string& tess_eval_shader_source =
6181                                         this->prepare_tess_eval_shader(tested_shader_type, uniform_definition, uniform_use);
6182                                 const std::string& vertex_shader_source =
6183                                         this->prepare_vertex_shader(tested_shader_type, uniform_definition, uniform_use);
6184
6185                                 switch (tested_shader_type)
6186                                 {
6187                                 case TestCaseBase<API>::VERTEX_SHADER_TYPE: /* Fall through */
6188                                 case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
6189                                         this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
6190                                         break;
6191
6192                                 case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
6193                                 case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
6194                                 case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
6195                                 case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
6196                                         this->execute_positive_test(vertex_shader_source, tess_ctrl_shader_source, tess_eval_shader_source,
6197                                                                                                 geometry_shader_source, fragment_shader_source, compute_shader_source,
6198                                                                                                 false, false);
6199                                         break;
6200
6201                                 default:
6202                                         TCU_FAIL("Invalid enum");
6203                                         break;
6204                                 }
6205                         }
6206                         else
6207                         {
6208                                 const std::string& fragment_shader_source =
6209                                         this->prepare_fragment_shader(tested_shader_type, uniform_definition, uniform_use);
6210                                 const std::string& vertex_shader_source =
6211                                         this->prepare_vertex_shader(tested_shader_type, uniform_definition, uniform_use);
6212
6213                                 this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
6214                         }
6215
6216                         glw::GLint uniform_location = -1;
6217
6218                         /* Make program object active. */
6219                         gl.useProgram(this->program_object_id);
6220                         GLU_EXPECT_NO_ERROR(gl.getError(), "glUseProgram() failed.");
6221
6222                         /* Get uniform location. */
6223                         uniform_location = gl.getUniformLocation(this->program_object_id, "my_uniform_1[0][0][0][0]");
6224                         GLU_EXPECT_NO_ERROR(gl.getError(), "glGetUniformLocation() failed.");
6225
6226                         if (uniform_location == -1)
6227                         {
6228                                 TCU_FAIL("Uniform is not found or is considered as not active.");
6229                         }
6230
6231                         switch (var_type_index)
6232                         {
6233                         case 0: //float type of uniform is considered
6234                         {
6235                                 glw::GLfloat uniform_value = 1.0f;
6236
6237                                 gl.uniform1f(uniform_location, uniform_value);
6238                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glUniform1f() failed.");
6239
6240                                 break;
6241                         }
6242                         case 1: //int type of uniform is considered
6243                         {
6244                                 glw::GLint uniform_value = 1;
6245
6246                                 gl.uniform1i(uniform_location, uniform_value);
6247                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glUniform1i() failed.");
6248
6249                                 break;
6250                         }
6251                         case 2: //uint type of uniform is considered
6252                         {
6253                                 glw::GLuint uniform_value = 1;
6254
6255                                 gl.uniform1ui(uniform_location, uniform_value);
6256                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glUniform1ui() failed.");
6257
6258                                 break;
6259                         }
6260                         case 3: //double type of uniform is considered
6261                         {
6262                                 glw::GLdouble uniform_value = 1.0;
6263
6264                                 gl.uniform1d(uniform_location, uniform_value);
6265                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glUniform1d() failed.");
6266
6267                                 break;
6268                         }
6269                         default:
6270                         {
6271                                 TCU_FAIL("Invalid variable-type index.");
6272
6273                                 break;
6274                         }
6275                         } /* switch (var_type_index) */
6276
6277                         /* Deallocate any resources used. */
6278                         this->delete_objects();
6279                 } /* if var_type iterator found */
6280                 else
6281                 {
6282                         TCU_FAIL("Type not found.");
6283                 }
6284         } /* for (int var_type_index = 0; ...) */
6285 }
6286
6287 /** Prepare shader
6288  *
6289  * @tparam API               Tested API descriptor
6290  *
6291  * @param tested_shader_type The type of shader that is being tested
6292  * @param uniform_definition Definition used to prepare shader
6293  * @param uniform_use        Snippet that use defined uniform
6294  **/
6295 template <class API>
6296 std::string InteractionUniforms1<API>::prepare_compute_shader(
6297         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& uniform_definition,
6298         const std::string& uniform_use)
6299 {
6300         std::string compute_shader_source;
6301
6302         if (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type)
6303         {
6304                 compute_shader_source = "writeonly uniform image2D uni_image;\n"
6305                                                                 "\n";
6306
6307                 /* User-defined function definition. */
6308                 compute_shader_source += uniform_definition;
6309                 compute_shader_source += "\n\n";
6310
6311                 /* Main function definition. */
6312                 compute_shader_source += shader_start;
6313                 compute_shader_source += uniform_use;
6314                 compute_shader_source += "\n\n";
6315                 compute_shader_source += "\n"
6316                                                                  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), vec4(result, 0, 0, 0));\n"
6317                                                                  "}\n"
6318                                                                  "\n";
6319         }
6320
6321         return compute_shader_source;
6322 }
6323
6324 /** Prepare shader
6325  *
6326  * @tparam API               Tested API descriptor
6327  *
6328  * @param tested_shader_type The type of shader that is being tested
6329  * @param uniform_definition Definition used to prepare shader
6330  * @param uniform_use        Snippet that use defined uniform
6331  **/
6332 template <class API>
6333 std::string InteractionUniforms1<API>::prepare_fragment_shader(
6334         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& uniform_definition,
6335         const std::string& uniform_use)
6336 {
6337         std::string fragment_shader_source;
6338
6339         switch (tested_shader_type)
6340         {
6341         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
6342                 break;
6343
6344         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
6345                 fragment_shader_source = "out vec4 colour;\n\n";
6346
6347                 /* User-defined function definition. */
6348                 fragment_shader_source += uniform_definition;
6349                 fragment_shader_source += "\n\n";
6350
6351                 /* Main function definition. */
6352                 fragment_shader_source += shader_start;
6353                 fragment_shader_source += uniform_use;
6354                 fragment_shader_source += "\n\n";
6355                 fragment_shader_source += "    colour = vec4(result);\n";
6356                 fragment_shader_source += shader_end;
6357                 break;
6358
6359         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
6360         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
6361         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
6362                 fragment_shader_source = "in float fs_result;\n\n"
6363                                                                  "out vec4 colour;\n\n"
6364                                                                  "void main()\n"
6365                                                                  "{\n"
6366                                                                  "    colour =  vec4(fs_result);\n"
6367                                                                  "}\n"
6368                                                                  "\n";
6369                 break;
6370
6371         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
6372                 fragment_shader_source = default_fragment_shader_source;
6373                 break;
6374
6375         default:
6376                 TCU_FAIL("Unrecognized shader object type.");
6377                 break;
6378         }
6379
6380         return fragment_shader_source;
6381 }
6382
6383 /** Prepare shader
6384  *
6385  * @tparam API               Tested API descriptor
6386  *
6387  * @param tested_shader_type The type of shader that is being tested
6388  * @param uniform_definition Definition used to prepare shader
6389  * @param uniform_use        Snippet that use defined uniform
6390  **/
6391 template <class API>
6392 std::string InteractionUniforms1<API>::prepare_geometry_shader(
6393         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& uniform_definition,
6394         const std::string& uniform_use)
6395 {
6396         std::string geometry_shader_source;
6397
6398         switch (tested_shader_type)
6399         {
6400         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
6401         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
6402         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
6403                 break;
6404
6405         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
6406         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
6407                 geometry_shader_source = "layout(points)                           in;\n"
6408                                                                  "layout(triangle_strip, max_vertices = 4) out;\n"
6409                                                                  "\n"
6410                                                                  "in  float tes_result[];\n"
6411                                                                  "out float fs_result;\n"
6412                                                                  "\n"
6413                                                                  "void main()\n"
6414                                                                  "{\n"
6415                                                                  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
6416                                                                  "    fs_result    = tes_result[0];\n"
6417                                                                  "    EmitVertex();\n"
6418                                                                  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
6419                                                                  "    fs_result    = tes_result[0];\n"
6420                                                                  "    EmitVertex();\n"
6421                                                                  "    gl_Position  = vec4(1, -1, 0, 1);\n"
6422                                                                  "    fs_result    = tes_result[0];\n"
6423                                                                  "    EmitVertex();\n"
6424                                                                  "    gl_Position  = vec4(1, 1, 0, 1);\n"
6425                                                                  "    fs_result    = tes_result[0];\n"
6426                                                                  "    EmitVertex();\n"
6427                                                                  "}\n";
6428                 break;
6429
6430         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
6431                 geometry_shader_source = "layout(points)                           in;\n"
6432                                                                  "layout(triangle_strip, max_vertices = 4) out;\n"
6433                                                                  "\n"
6434                                                                  "out float fs_result;\n"
6435                                                                  "\n";
6436
6437                 /* User-defined function definition. */
6438                 geometry_shader_source += uniform_definition;
6439                 geometry_shader_source += "\n\n";
6440
6441                 /* Main function definition. */
6442                 geometry_shader_source += shader_start;
6443                 geometry_shader_source += uniform_use;
6444                 geometry_shader_source += "\n\n";
6445                 geometry_shader_source += "\n    gl_Position  = vec4(-1, -1, 0, 1);\n"
6446                                                                   "    fs_result    = result;\n"
6447                                                                   "    EmitVertex();\n"
6448                                                                   "    gl_Position  = vec4(-1, 1, 0, 1);\n"
6449                                                                   "    fs_result    = result;\n"
6450                                                                   "    EmitVertex();\n"
6451                                                                   "    gl_Position  = vec4(1, -1, 0, 1);\n"
6452                                                                   "    fs_result    = result;\n"
6453                                                                   "    EmitVertex();\n"
6454                                                                   "    gl_Position  = vec4(1, 1, 0, 1);\n"
6455                                                                   "    fs_result    = result;\n"
6456                                                                   "    EmitVertex();\n"
6457                                                                   "}\n";
6458                 break;
6459
6460         default:
6461                 TCU_FAIL("Unrecognized shader object type.");
6462                 break;
6463         }
6464
6465         return geometry_shader_source;
6466 }
6467
6468 /** Prepare shader
6469  *
6470  * @tparam API               Tested API descriptor
6471  *
6472  * @param tested_shader_type The type of shader that is being tested
6473  * @param uniform_definition Definition used to prepare shader
6474  * @param uniform_use        Snippet that use defined uniform
6475  **/
6476 template <class API>
6477 std::string InteractionUniforms1<API>::prepare_tess_ctrl_shader(
6478         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& uniform_definition,
6479         const std::string& uniform_use)
6480 {
6481         std::string tess_ctrl_shader_source;
6482
6483         switch (tested_shader_type)
6484         {
6485         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
6486         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
6487         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
6488         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
6489                 break;
6490
6491         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
6492                 tess_ctrl_shader_source = "layout(vertices = 1) out;\n"
6493                                                                   "\n"
6494                                                                   "out float tcs_result[];\n"
6495                                                                   "\n";
6496
6497                 /* User-defined function definition. */
6498                 tess_ctrl_shader_source += uniform_definition;
6499                 tess_ctrl_shader_source += "\n\n";
6500
6501                 /* Main function definition. */
6502                 tess_ctrl_shader_source += shader_start;
6503                 tess_ctrl_shader_source += uniform_use;
6504                 tess_ctrl_shader_source += "\n\n";
6505                 tess_ctrl_shader_source += "    tcs_result[gl_InvocationID] = result;\n"
6506                                                                    "\n"
6507                                                                    "    gl_TessLevelOuter[0] = 1.0;\n"
6508                                                                    "    gl_TessLevelOuter[1] = 1.0;\n"
6509                                                                    "    gl_TessLevelOuter[2] = 1.0;\n"
6510                                                                    "    gl_TessLevelOuter[3] = 1.0;\n"
6511                                                                    "    gl_TessLevelInner[0] = 1.0;\n"
6512                                                                    "    gl_TessLevelInner[1] = 1.0;\n"
6513                                                                    "}\n";
6514                 break;
6515
6516         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
6517                 tess_ctrl_shader_source = default_tc_shader_source;
6518                 break;
6519
6520         default:
6521                 TCU_FAIL("Unrecognized shader object type.");
6522                 break;
6523         }
6524
6525         return tess_ctrl_shader_source;
6526 }
6527
6528 /** Prepare shader
6529  *
6530  * @tparam API               Tested API descriptor
6531  *
6532  * @param tested_shader_type The type of shader that is being tested
6533  * @param uniform_definition Definition used to prepare shader
6534  * @param uniform_use        Snippet that use defined uniform
6535  **/
6536 template <class API>
6537 std::string InteractionUniforms1<API>::prepare_tess_eval_shader(
6538         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& uniform_definition,
6539         const std::string& uniform_use)
6540 {
6541         std::string tess_eval_shader_source;
6542
6543         switch (tested_shader_type)
6544         {
6545         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
6546         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
6547         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
6548         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
6549                 break;
6550
6551         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
6552                 tess_eval_shader_source = "layout(isolines, point_mode) in;\n"
6553                                                                   "\n"
6554                                                                   "in  float tcs_result[];\n"
6555                                                                   "out float tes_result;\n"
6556                                                                   "\n"
6557                                                                   "void main()\n"
6558                                                                   "{\n"
6559                                                                   "    tes_result = tcs_result[0];\n"
6560                                                                   "}\n";
6561                 break;
6562
6563         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
6564                 tess_eval_shader_source = "layout(isolines, point_mode) in;\n"
6565                                                                   "\n"
6566                                                                   "out float tes_result;\n"
6567                                                                   "\n";
6568
6569                 /* User-defined function definition. */
6570                 tess_eval_shader_source += uniform_definition;
6571                 tess_eval_shader_source += "\n\n";
6572
6573                 /* Main function definition. */
6574                 tess_eval_shader_source += shader_start;
6575                 tess_eval_shader_source += uniform_use;
6576                 tess_eval_shader_source += "\n\n";
6577                 tess_eval_shader_source += "    tes_result = result;\n"
6578                                                                    "}\n";
6579                 break;
6580
6581         default:
6582                 TCU_FAIL("Unrecognized shader object type.");
6583                 break;
6584         }
6585
6586         return tess_eval_shader_source;
6587 }
6588
6589 /** Prepare shader
6590  *
6591  * @tparam API               Tested API descriptor
6592  *
6593  * @param tested_shader_type The type of shader that is being tested
6594  * @param uniform_definition Definition used to prepare shader
6595  * @param uniform_use        Snippet that use defined uniform
6596  **/
6597 template <class API>
6598 std::string InteractionUniforms1<API>::prepare_vertex_shader(
6599         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& uniform_definition,
6600         const std::string& uniform_use)
6601 {
6602         std::string vertex_shader_source;
6603
6604         switch (tested_shader_type)
6605         {
6606         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
6607                 break;
6608
6609         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
6610         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
6611         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
6612         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
6613                 vertex_shader_source = default_vertex_shader_source;
6614                 break;
6615
6616         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
6617                 /* User-defined function definition. */
6618                 vertex_shader_source += uniform_definition;
6619
6620                 /* Main function definition. */
6621                 vertex_shader_source += shader_start;
6622                 vertex_shader_source += uniform_use;
6623                 vertex_shader_source += "    gl_Position = vec4(result);\n";
6624                 vertex_shader_source += shader_end;
6625                 break;
6626
6627         default:
6628                 TCU_FAIL("Unrecognized shader object type.");
6629                 break;
6630         }
6631
6632         return vertex_shader_source;
6633 }
6634
6635 /* Generates the shader source code for the InteractionUniforms2
6636  * array tests, and attempts to compile each test shader, for both
6637  * vertex and fragment shaders.
6638  *
6639  * @tparam API               Tested API descriptor
6640  *
6641  * @param tested_shader_type The type of shader that is being tested
6642  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
6643  */
6644 template <class API>
6645 void InteractionUniforms2<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
6646 {
6647         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4 };
6648         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
6649
6650         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT, VAR_TYPE_FLOAT, VAR_TYPE_MAT4,
6651                                                                                                                          VAR_TYPE_DOUBLE, VAR_TYPE_DMAT4 };
6652         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
6653
6654         const std::string array_initializers[] = { "int[2][2][2][2](\n"
6655                                                                                            "    int[2][2][2](\n"
6656                                                                                            "        int[2][2](\n"
6657                                                                                            "            int[2]( 1,  2),\n"
6658                                                                                            "            int[2]( 3,  4)\n"
6659                                                                                            "        ),\n"
6660                                                                                            "        int[2][2](\n"
6661                                                                                            "            int[2]( 5,  6),\n"
6662                                                                                            "            int[2]( 7,  8)\n"
6663                                                                                            "        )\n"
6664                                                                                            "    ),\n"
6665                                                                                            "    int[2][2][2](\n"
6666                                                                                            "        int[2][2](\n"
6667                                                                                            "            int[2](11, 12),\n"
6668                                                                                            "            int[2](13, 14)\n"
6669                                                                                            "        ),\n"
6670                                                                                            "        int[2][2](\n"
6671                                                                                            "            int[2](15, 16),\n"
6672                                                                                            "            int[2](17, 18)\n"
6673                                                                                            "        )\n"
6674                                                                                            "    )\n"
6675                                                                                            ")",
6676
6677                                                                                            "float[2][2][2][2](\n"
6678                                                                                            "    float[2][2][2](\n"
6679                                                                                            "        float[2][2](\n"
6680                                                                                            "            float[2](1.0, 2.0),\n"
6681                                                                                            "            float[2](3.0, 4.0)),\n"
6682                                                                                            "        float[2][2](\n"
6683                                                                                            "            float[2](5.0, 6.0),\n"
6684                                                                                            "            float[2](7.0, 8.0))),\n"
6685                                                                                            "    float[2][2][2](\n"
6686                                                                                            "        float[2][2](\n"
6687                                                                                            "            float[2](1.1, 2.1),\n"
6688                                                                                            "            float[2](3.1, 4.1)\n"
6689                                                                                            "        ),\n"
6690                                                                                            "        float[2][2](\n"
6691                                                                                            "            float[2](5.1, 6.1),\n"
6692                                                                                            "            float[2](7.1, 8.1)\n"
6693                                                                                            "        )\n"
6694                                                                                            "    )\n"
6695                                                                                            ")",
6696
6697                                                                                            "mat4[2][2][2][2](\n"
6698                                                                                            "    mat4[2][2][2](\n"
6699                                                                                            "        mat4[2][2](\n"
6700                                                                                            "            mat4[2]( mat4(1),  mat4(2)),\n"
6701                                                                                            "            mat4[2]( mat4(3),  mat4(4))\n"
6702                                                                                            "        ),\n"
6703                                                                                            "        mat4[2][2](\n"
6704                                                                                            "            mat4[2](mat4(5),  mat4(6)),\n"
6705                                                                                            "            mat4[2](mat4(7),  mat4(8))\n"
6706                                                                                            "        )\n"
6707                                                                                            "    ),\n"
6708                                                                                            "    mat4[2][2][2](\n"
6709                                                                                            "        mat4[2][2](\n"
6710                                                                                            "            mat4[2](mat4(9),  mat4(10)),\n"
6711                                                                                            "            mat4[2](mat4(11),  mat4(12))\n"
6712                                                                                            "        ),\n"
6713                                                                                            "        mat4[2][2](\n"
6714                                                                                            "            mat4[2](mat4(13),  mat4(14)),\n"
6715                                                                                            "            mat4[2](mat4(15),  mat4(16))\n"
6716                                                                                            "        )\n"
6717                                                                                            "    )\n"
6718                                                                                            ")",
6719
6720                                                                                            "double[2][2][2][2](\n"
6721                                                                                            "    double[2][2][2](\n"
6722                                                                                            "        double[2][2](\n"
6723                                                                                            "            double[2](1.0, 2.0),\n"
6724                                                                                            "            double[2](3.0, 4.0)),\n"
6725                                                                                            "        double[2][2](\n"
6726                                                                                            "            double[2](5.0, 6.0),\n"
6727                                                                                            "            double[2](7.0, 8.0))),\n"
6728                                                                                            "    double[2][2][2](\n"
6729                                                                                            "        double[2][2](\n"
6730                                                                                            "            double[2](1.1, 2.1),\n"
6731                                                                                            "            double[2](3.1, 4.1)\n"
6732                                                                                            "        ),\n"
6733                                                                                            "        double[2][2](\n"
6734                                                                                            "            double[2](5.1, 6.1),\n"
6735                                                                                            "            double[2](7.1, 8.1)\n"
6736                                                                                            "        )\n"
6737                                                                                            "    )\n"
6738                                                                                            ")",
6739
6740                                                                                            "dmat4[2][2][2][2](\n"
6741                                                                                            "    dmat4[2][2][2](\n"
6742                                                                                            "        dmat4[2][2](\n"
6743                                                                                            "            dmat4[2]( dmat4(1),  dmat4(2)),\n"
6744                                                                                            "            dmat4[2]( dmat4(3),  dmat4(4))\n"
6745                                                                                            "        ),\n"
6746                                                                                            "        dmat4[2][2](\n"
6747                                                                                            "            dmat4[2](dmat4(5),  dmat4(6)),\n"
6748                                                                                            "            dmat4[2](dmat4(7),  dmat4(8))\n"
6749                                                                                            "        )\n"
6750                                                                                            "    ),\n"
6751                                                                                            "    dmat4[2][2][2](\n"
6752                                                                                            "        dmat4[2][2](\n"
6753                                                                                            "            dmat4[2](dmat4(9),   dmat4(10)),\n"
6754                                                                                            "            dmat4[2](dmat4(11),  dmat4(12))\n"
6755                                                                                            "        ),\n"
6756                                                                                            "        dmat4[2][2](\n"
6757                                                                                            "            dmat4[2](dmat4(13),  dmat4(14)),\n"
6758                                                                                            "            dmat4[2](dmat4(15),  dmat4(16))\n"
6759                                                                                            "        )\n"
6760                                                                                            "    )\n"
6761                                                                                            ")" };
6762
6763         const glcts::test_var_type* var_types_set = var_types_set_es;
6764         size_t                                          num_var_types = num_var_types_es;
6765
6766         if (API::USE_DOUBLE)
6767         {
6768                 var_types_set = var_types_set_gl;
6769                 num_var_types = num_var_types_gl;
6770         }
6771
6772         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
6773         {
6774                 _supported_variable_types_map_const_iterator var_iterator =
6775                         supported_variable_types_map.find(var_types_set[var_type_index]);
6776
6777                 if (var_iterator != supported_variable_types_map.end())
6778                 {
6779                         std::string base_variable_string;
6780
6781                         for (int initialiser_selector = 1; initialiser_selector >= 0; initialiser_selector--)
6782                         {
6783                                 // We normally do all 16 possible permutations of [4][4][4][4] items (15..0).
6784                                 // However, in this case we will skip the case that will work,
6785                                 // so we'll merely process permutations 14..0
6786                                 for (int permutation_index = 14; permutation_index >= 0; permutation_index--)
6787                                 {
6788                                         base_variable_string =
6789                                                 "uniform " + var_iterator->second.precision + " " + var_iterator->second.type + " x";
6790
6791                                         // for all 4 possible sub_script entries
6792                                         for (int sub_script_entry_index = 3; sub_script_entry_index >= 0; sub_script_entry_index--)
6793                                         {
6794                                                 if (permutation_index & (1 << sub_script_entry_index))
6795                                                 {
6796                                                         // In this case, we'll use a valid sub_script
6797                                                         base_variable_string += "[2]";
6798                                                 }
6799                                                 else
6800                                                 {
6801                                                         // In this case, we'll use an invalid sub_script
6802                                                         base_variable_string += "[]";
6803                                                 }
6804                                         }
6805
6806                                         if (initialiser_selector == 0)
6807                                         {
6808                                                 // We'll use an initialiser
6809                                                 base_variable_string += " = " + array_initializers[var_type_index];
6810                                         }
6811
6812                                         base_variable_string += ";\n\n";
6813
6814                                         std::string shader_source = base_variable_string + shader_start;
6815
6816                                         /* End main */
6817                                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
6818
6819                                         /* Execute test:
6820                                          *
6821                                          * This will succeed in case of allowed unsized
6822                                          * declarations and when at least one of these is
6823                                          * true:
6824                                          *   1. There is an initialiser.
6825                                          *   2. Only the outermost dimension is unsized,
6826                                          *      as in [][2][2][2].
6827                                          */
6828                                         EXECUTE_SHADER_TEST(API::ALLOW_UNSIZED_DECLARATION &&
6829                                                                                         (initialiser_selector == 0 || permutation_index == 7),
6830                                                                                 tested_shader_type, shader_source);
6831                                 } /* for (int permutation_index = 14; ...) */
6832                         }        /* for (int initialiser_selector  = 1; ...) */
6833                 }                 /* if var_type iterator found */
6834                 else
6835                 {
6836                         TCU_FAIL("Type not found.");
6837                 }
6838         } /* for (int var_type_index = 0; ...) */
6839 }
6840
6841 /* Generates the shader source code for the InteractionUniformBuffers1
6842  * array tests, and attempts to compile each test shader, for both
6843  * vertex and fragment shaders.
6844  *
6845  * @tparam API               Tested API descriptor
6846  *
6847  * @param tested_shader_type The type of shader that is being tested
6848  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
6849  */
6850 template <class API>
6851 void InteractionUniformBuffers1<API>::test_shader_compilation(
6852         typename TestCaseBase<API>::TestShaderType tested_shader_type)
6853 {
6854         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT };
6855         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
6856
6857         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT,
6858                                                                                                                          VAR_TYPE_DOUBLE };
6859         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
6860
6861         const glcts::test_var_type* var_types_set = var_types_set_es;
6862         size_t                                          num_var_types = num_var_types_es;
6863
6864         if (API::USE_DOUBLE)
6865         {
6866                 var_types_set = var_types_set_gl;
6867                 num_var_types = num_var_types_gl;
6868         }
6869
6870         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
6871         {
6872                 _supported_variable_types_map_const_iterator var_iterator =
6873                         supported_variable_types_map.find(var_types_set[var_type_index]);
6874
6875                 if (var_iterator != supported_variable_types_map.end())
6876                 {
6877                         std::string shader_source;
6878
6879                         shader_source += "uniform uBlocka {\n";
6880                         shader_source += "    " + var_iterator->second.type + " x[1][1][1][1][1][1];\n";
6881                         shader_source += "};\n\n";
6882                         shader_source += shader_start;
6883
6884                         /* End main */
6885                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
6886
6887                         /* Execute test */
6888                         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
6889                 } /* if var_type iterator found */
6890                 else
6891                 {
6892                         TCU_FAIL("Type not found.");
6893                 }
6894         }
6895 }
6896
6897 /* Generates the shader source code for the InteractionUniformBuffers2
6898  * array tests, and attempts to compile each test shader, for both
6899  * vertex and fragment shaders.
6900  *
6901  * @tparam API               Tested API descriptor
6902  *
6903  * @param tested_shader_type The type of shader that is being tested
6904  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
6905  */
6906 template <class API>
6907 void InteractionUniformBuffers2<API>::test_shader_compilation(
6908         typename TestCaseBase<API>::TestShaderType tested_shader_type)
6909 {
6910         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT };
6911         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
6912
6913         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT,
6914                                                                                                                          VAR_TYPE_DOUBLE };
6915         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
6916
6917         const glw::Functions&           gl                        = this->context_id.getRenderContext().getFunctions();
6918         const glcts::test_var_type* var_types_set = var_types_set_es;
6919         size_t                                          num_var_types = num_var_types_es;
6920
6921         if (API::USE_DOUBLE)
6922         {
6923                 var_types_set = var_types_set_gl;
6924                 num_var_types = num_var_types_gl;
6925         }
6926
6927         /* Iterate through float / int / uint values. */
6928         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
6929         {
6930                 _supported_variable_types_map_const_iterator var_iterator =
6931                         supported_variable_types_map.find(var_types_set[var_type_index]);
6932
6933                 if (var_iterator != supported_variable_types_map.end())
6934                 {
6935                         std::string uniform_definition;
6936                         std::string uniform_use;
6937
6938                         uniform_definition += "layout (std140) uniform uniform_block_name\n"
6939                                                                   "{\n";
6940                         uniform_definition += "    ";
6941                         uniform_definition += var_iterator->second.type;
6942                         uniform_definition += " my_uniform_1[1][1][1][1];\n"
6943                                                                   "};\n";
6944
6945                         uniform_use = "    float result = float(my_uniform_1[0][0][0][0]);\n";
6946
6947                         if (API::USE_ALL_SHADER_STAGES)
6948                         {
6949                                 const std::string& compute_shader_source =
6950                                         this->prepare_compute_shader(tested_shader_type, uniform_definition, uniform_use);
6951                                 const std::string& fragment_shader_source =
6952                                         this->prepare_fragment_shader(tested_shader_type, uniform_definition, uniform_use);
6953                                 const std::string& geometry_shader_source =
6954                                         this->prepare_geometry_shader(tested_shader_type, uniform_definition, uniform_use);
6955                                 const std::string& tess_ctrl_shader_source =
6956                                         this->prepare_tess_ctrl_shader(tested_shader_type, uniform_definition, uniform_use);
6957                                 const std::string& tess_eval_shader_source =
6958                                         this->prepare_tess_eval_shader(tested_shader_type, uniform_definition, uniform_use);
6959                                 const std::string& vertex_shader_source =
6960                                         this->prepare_vertex_shader(tested_shader_type, uniform_definition, uniform_use);
6961
6962                                 switch (tested_shader_type)
6963                                 {
6964                                 case TestCaseBase<API>::VERTEX_SHADER_TYPE: /* Fall through */
6965                                 case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
6966                                         this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
6967                                         break;
6968
6969                                 case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
6970                                 case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
6971                                 case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
6972                                 case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
6973                                         this->execute_positive_test(vertex_shader_source, tess_ctrl_shader_source, tess_eval_shader_source,
6974                                                                                                 geometry_shader_source, fragment_shader_source, compute_shader_source,
6975                                                                                                 false, false);
6976                                         break;
6977
6978                                 default:
6979                                         TCU_FAIL("Invalid enum");
6980                                         break;
6981                                 }
6982                         }
6983                         else
6984                         {
6985                                 const std::string& fragment_shader_source =
6986                                         this->prepare_fragment_shader(tested_shader_type, uniform_definition, uniform_use);
6987                                 const std::string& vertex_shader_source =
6988                                         this->prepare_vertex_shader(tested_shader_type, uniform_definition, uniform_use);
6989
6990                                 this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
6991                         }
6992
6993                         glw::GLuint buffer_object_id       = 0;
6994                         glw::GLint  my_uniform_block_index = GL_INVALID_INDEX;
6995
6996                         gl.useProgram(this->program_object_id);
6997                         GLU_EXPECT_NO_ERROR(gl.getError(), "glUseProgram() failed.");
6998
6999                         my_uniform_block_index = gl.getUniformBlockIndex(this->program_object_id, "uniform_block_name");
7000                         GLU_EXPECT_NO_ERROR(gl.getError(), "glGetUniformBlockIndex() failed.");
7001
7002                         if ((unsigned)my_uniform_block_index == GL_INVALID_INDEX)
7003                         {
7004                                 TCU_FAIL("Uniform block not found or is considered as not active.");
7005                         }
7006
7007                         gl.genBuffers(1, &buffer_object_id);
7008                         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenBuffers() failed.");
7009
7010                         gl.bindBuffer(GL_UNIFORM_BUFFER, buffer_object_id);
7011                         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindBuffer() failed.");
7012
7013                         switch (var_type_index)
7014                         {
7015                         case 0: //float type of uniform is considered
7016                         {
7017                                 glw::GLfloat buffer_data[] = { 0.0f, 1.0f, 2.0f,  3.0f,  4.0f,  5.0f,  6.0f,  7.0f,
7018                                                                                            8.0f, 9.0f, 10.0f, 11.0f, 12.0f, 13.0f, 14.0f, 15.0f };
7019
7020                                 gl.bufferData(GL_UNIFORM_BUFFER, sizeof(buffer_data), buffer_data, GL_STATIC_DRAW);
7021                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glBufferData() failed.");
7022
7023                                 break;
7024                         }               /* float case */
7025                         case 1: //int type of uniform is considered
7026                         {
7027
7028                                 glw::GLint buffer_data[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 };
7029
7030                                 gl.bufferData(GL_UNIFORM_BUFFER, sizeof(buffer_data), buffer_data, GL_STATIC_DRAW);
7031                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glBufferData() failed.");
7032
7033                                 break;
7034                         }               /* int case */
7035                         case 2: //uint type of uniform is considered
7036                         {
7037                                 glw::GLuint buffer_data[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 };
7038
7039                                 gl.bufferData(GL_UNIFORM_BUFFER, sizeof(buffer_data), buffer_data, GL_STATIC_DRAW);
7040                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glBufferData() failed.");
7041
7042                                 break;
7043                         }               /* uint case */
7044                         case 3: //double type of uniform is considered
7045                         {
7046                                 glw::GLdouble buffer_data[] = { 0.0, 1.0, 2.0,  3.0,  4.0,  5.0,  6.0,  7.0,
7047                                                                                                 8.0, 9.0, 10.0, 11.0, 12.0, 13.0, 14.0, 15.0 };
7048
7049                                 gl.bufferData(GL_UNIFORM_BUFFER, sizeof(buffer_data), buffer_data, GL_STATIC_DRAW);
7050                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glBufferData() failed.");
7051
7052                                 break;
7053                         } /* double case */
7054                         default:
7055                         {
7056                                 TCU_FAIL("Invalid variable-type index.");
7057
7058                                 break;
7059                         }
7060                         } /* switch (var_type_index) */
7061
7062                         gl.uniformBlockBinding(this->program_object_id, my_uniform_block_index, 0);
7063                         GLU_EXPECT_NO_ERROR(gl.getError(), "glUniformBlockBinding() failed.");
7064
7065                         gl.bindBufferBase(GL_UNIFORM_BUFFER, 0, buffer_object_id);
7066                         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindBufferBase() failed.");
7067
7068                         if (TestCaseBase<API>::COMPUTE_SHADER_TYPE != tested_shader_type)
7069                         {
7070                                 execute_draw_test(tested_shader_type);
7071                         }
7072                         else
7073                         {
7074                                 execute_dispatch_test();
7075                         }
7076
7077                         /* Deallocate any resources used. */
7078                         gl.deleteBuffers(1, &buffer_object_id);
7079                         this->delete_objects();
7080                 } /* if var_type iterator found */
7081                 else
7082                 {
7083                         TCU_FAIL("Type not found.");
7084                 }
7085         } /* for (int var_type_index = 0; ...) */
7086 }
7087
7088 /** Executes test for compute program
7089  *
7090  * @tparam API Tested API descriptor
7091  **/
7092 template <class API>
7093 void InteractionUniformBuffers2<API>::execute_dispatch_test()
7094 {
7095         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
7096
7097         gl.dispatchCompute(1, 1, 1);
7098         GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
7099 }
7100
7101 /** Executes test for draw program
7102  *
7103  * @tparam API               Tested API descriptor
7104  *
7105  * @param tested_shader_type The type of shader that is being tested
7106  **/
7107 template <class API>
7108 void InteractionUniformBuffers2<API>::execute_draw_test(typename TestCaseBase<API>::TestShaderType tested_shader_type)
7109 {
7110         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
7111
7112         glw::GLuint vao_id = 0;
7113
7114         gl.genVertexArrays(1, &vao_id);
7115         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenVertexArrays() failed.");
7116
7117         gl.bindVertexArray(vao_id);
7118         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindVertexArray() failed.");
7119
7120         switch (tested_shader_type)
7121         {
7122         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
7123         case TestCaseBase<API>::VERTEX_SHADER_TYPE: /* Fall through */
7124         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
7125                 gl.drawArrays(GL_POINTS, 0, 1);
7126                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
7127                 break;
7128
7129         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
7130         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
7131                 /* Tesselation patch set up */
7132                 gl.patchParameteri(GL_PATCH_VERTICES, 1);
7133                 GLU_EXPECT_NO_ERROR(gl.getError(), "PatchParameteri");
7134
7135                 gl.drawArrays(GL_PATCHES, 0, 1);
7136                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
7137                 break;
7138
7139         default:
7140                 TCU_FAIL("Invalid enum");
7141                 break;
7142         }
7143
7144         gl.deleteVertexArrays(1, &vao_id);
7145         GLU_EXPECT_NO_ERROR(gl.getError(), "glDeleteVertexArrays() failed.");
7146 }
7147
7148 /* Generates the shader source code for the InteractionUniformBuffers3
7149  * array tests, and attempts to compile each test shader, for both
7150  * vertex and fragment shaders.
7151  *
7152  * @tparam API               Tested API descriptor
7153  *
7154  * @param tested_shader_type The type of shader that is being tested
7155  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
7156  */
7157 template <class API>
7158 void InteractionUniformBuffers3<API>::test_shader_compilation(
7159         typename TestCaseBase<API>::TestShaderType tested_shader_type)
7160 {
7161         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT };
7162         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
7163
7164         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT,
7165                                                                                                                          VAR_TYPE_DOUBLE };
7166         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
7167
7168         const std::string invalid_size_declarations[] = { "[2][2][2][]", "[2][2][][2]", "[2][][2][2]", "[][2][2][2]",
7169                                                                                                           "[2][2][][]",  "[2][][2][]",  "[][2][2][]",  "[2][][][2]",
7170                                                                                                           "[][2][][2]",  "[][][2][2]",  "[2][][][]",   "[][2][][]",
7171                                                                                                           "[][][2][]",   "[][][][2]",   "[][][][]" };
7172
7173         const std::string array_initializers[] = { "float[2][2][2][2](float[2][2][2](float[2][2](float[2](1.0, 2.0),"
7174                                                                                            "float[2](3.0, 4.0)),"
7175                                                                                            "float[2][2](float[2](5.0, 6.0),"
7176                                                                                            "float[2](7.0, 8.0))),"
7177                                                                                            "float[2][2][2](float[2][2](float[2](1.1, 2.1),"
7178                                                                                            "float[2](3.1, 4.1)),"
7179                                                                                            "float[2][2](float[2](5.1, 6.1),"
7180                                                                                            "float[2](7.1, 8.1))));\n",
7181
7182                                                                                            "int[2][2][2][2](int[2][2][2](int[2][2](int[2]( 1,  2),"
7183                                                                                            "int[2]( 3,  4)),"
7184                                                                                            "int[2][2](int[2]( 5,  6),"
7185                                                                                            "int[2]( 7,  8))),"
7186                                                                                            "int[2][2][2](int[2][2](int[2](11, 12),"
7187                                                                                            "int[2](13, 14)),"
7188                                                                                            "int[2][2](int[2](15, 16),"
7189                                                                                            "int[2](17, 18))));\n",
7190
7191                                                                                            "uint[2][2][2][2](uint[2][2][2](uint[2][2](uint[2]( 1u,  2u),"
7192                                                                                            "uint[2]( 3u,  4u)),"
7193                                                                                            "uint[2][2](uint[2]( 5u,  6u),"
7194                                                                                            "uint[2]( 7u,  8u))),"
7195                                                                                            "uint[2][2][2](uint[2][2](uint[2](11u, 12u),"
7196                                                                                            "uint[2](13u, 14u)),"
7197                                                                                            "uint[2][2](uint[2](15u, 16u),"
7198                                                                                            "uint[2](17u, 18u))));\n",
7199
7200                                                                                            "double[2][2][2][2](double[2][2][2](double[2][2](double[2](1.0, 2.0),"
7201                                                                                            "double[2](3.0, 4.0)),"
7202                                                                                            "double[2][2](double[2](5.0, 6.0),"
7203                                                                                            "double[2](7.0, 8.0))),"
7204                                                                                            "double[2][2][2](double[2][2](double[2](1.1, 2.1),"
7205                                                                                            "double[2](3.1, 4.1)),"
7206                                                                                            "double[2][2](double[2](5.1, 6.1),"
7207                                                                                            "double[2](7.1, 8.1))));\n" };
7208         const glcts::test_var_type* var_types_set = var_types_set_es;
7209         size_t                                          num_var_types = num_var_types_es;
7210
7211         if (API::USE_DOUBLE)
7212         {
7213                 var_types_set = var_types_set_gl;
7214                 num_var_types = num_var_types_gl;
7215         }
7216
7217         /* Iterate through float/ int/ uint types.
7218          * Case: without initializer.
7219          */
7220         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
7221         {
7222                 _supported_variable_types_map_const_iterator var_iterator =
7223                         supported_variable_types_map.find(var_types_set[var_type_index]);
7224
7225                 if (var_iterator != supported_variable_types_map.end())
7226                 {
7227                         for (size_t invalid_size_declarations_index = 0;
7228                                  invalid_size_declarations_index <
7229                                  sizeof(invalid_size_declarations) / sizeof(invalid_size_declarations[0]);
7230                                  invalid_size_declarations_index++)
7231                         {
7232                                 std::string shader_source;
7233
7234                                 shader_source = "layout (std140) uniform MyUniform {\n";
7235                                 shader_source += "    " + var_iterator->second.type +
7236                                                                  invalid_size_declarations[invalid_size_declarations_index] + " my_variable;\n";
7237                                 shader_source += "};\n\n";
7238                                 shader_source += shader_start;
7239
7240                                 /* End main */
7241                                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
7242
7243                                 /* Execute test */
7244                                 EXECUTE_SHADER_TEST(API::ALLOW_UNSIZED_DECLARATION && invalid_size_declarations_index == 3,
7245                                                                         tested_shader_type, shader_source);
7246                         } /* for (int invalid_size_declarations_index = 0; ...) */
7247                 }
7248                 else
7249                 {
7250                         TCU_FAIL("Type not found.");
7251                 }
7252         } /* for (int var_type_index = 0; ...) */
7253
7254         /* Iterate through float/ int/ uint types.
7255          * Case: with initializer.
7256          */
7257         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
7258         {
7259                 _supported_variable_types_map_const_iterator var_iterator =
7260                         supported_variable_types_map.find(var_types_set[var_type_index]);
7261
7262                 if (var_iterator != supported_variable_types_map.end())
7263                 {
7264                         for (size_t invalid_size_declarations_index = 0;
7265                                  invalid_size_declarations_index <
7266                                  sizeof(invalid_size_declarations) / sizeof(invalid_size_declarations[0]);
7267                                  invalid_size_declarations_index++)
7268                         {
7269                                 std::string shader_source;
7270
7271                                 shader_source = "layout (std140) uniform MyUniform {\n";
7272                                 shader_source += "    " + var_iterator->second.type +
7273                                                                  invalid_size_declarations[invalid_size_declarations_index] +
7274                                                                  " my_variable = " + array_initializers[var_type_index];
7275
7276                                 var_iterator->second.type + invalid_size_declarations[invalid_size_declarations_index] +
7277                                         " my_variable = " + array_initializers[var_type_index];
7278                                 shader_source += "};\n\n";
7279                                 shader_source += shader_start;
7280
7281                                 /* End main */
7282                                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
7283
7284                                 /* Execute test */
7285                                 this->execute_negative_test(tested_shader_type, shader_source);
7286                         } /* for (int invalid_size_declarations_index = 0; ...) */
7287                 }        /* if var_type iterator found */
7288                 else
7289                 {
7290                         TCU_FAIL("Type not found.");
7291                 }
7292         } /* for (int var_type_index = 0; ...) */
7293 }
7294
7295 /* Generates the shader source code for the InteractionStorageBuffers1
7296  * array tests, and attempts to compile each test shader, for both
7297  * vertex and fragment shaders.
7298  *
7299  * @tparam API               Tested API descriptor
7300  *
7301  * @param tested_shader_type The type of shader that is being tested
7302  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
7303  */
7304 template <class API>
7305 void InteractionStorageBuffers1<API>::test_shader_compilation(
7306         typename TestCaseBase<API>::TestShaderType tested_shader_type)
7307 {
7308         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT };
7309         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
7310
7311         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT,
7312                                                                                                                          VAR_TYPE_DOUBLE };
7313         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
7314
7315         const glcts::test_var_type* var_types_set = var_types_set_es;
7316         size_t                                          num_var_types = num_var_types_es;
7317
7318         if (API::USE_DOUBLE)
7319         {
7320                 var_types_set = var_types_set_gl;
7321                 num_var_types = num_var_types_gl;
7322         }
7323
7324         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
7325         {
7326                 _supported_variable_types_map_const_iterator var_iterator =
7327                         supported_variable_types_map.find(var_types_set[var_type_index]);
7328
7329                 if (var_iterator != supported_variable_types_map.end())
7330                 {
7331                         std::string shader_source;
7332
7333                         shader_source += "buffer uBlocka {\n";
7334                         shader_source += "    " + var_iterator->second.type + " x[1][1][1][1][1][1];\n";
7335                         shader_source += "};\n\n";
7336                         shader_source += shader_start;
7337
7338                         /* End main */
7339                         DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
7340
7341                         /* Execute test */
7342                         EXECUTE_POSITIVE_TEST(tested_shader_type, shader_source, true, false);
7343                 } /* if var_type iterator found */
7344                 else
7345                 {
7346                         TCU_FAIL("Type not found.");
7347                 }
7348         }
7349 }
7350
7351 /* Generates the shader source code for the InteractionUniformBuffers2
7352  * array tests, and attempts to compile each test shader, for both
7353  * vertex and fragment shaders.
7354  *
7355  * @tparam API               Tested API descriptor
7356  *
7357  * @param tested_shader_type The type of shader that is being tested
7358  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
7359  */
7360 template <class API>
7361 void InteractionStorageBuffers2<API>::test_shader_compilation(
7362         typename TestCaseBase<API>::TestShaderType tested_shader_type)
7363 {
7364         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT };
7365         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
7366
7367         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT,
7368                                                                                                                          VAR_TYPE_DOUBLE };
7369         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
7370
7371         const glw::Functions&           gl                        = this->context_id.getRenderContext().getFunctions();
7372         const glcts::test_var_type* var_types_set = var_types_set_es;
7373         size_t                                          num_var_types = num_var_types_es;
7374
7375         if (API::USE_DOUBLE)
7376         {
7377                 var_types_set = var_types_set_gl;
7378                 num_var_types = num_var_types_gl;
7379         }
7380
7381         /* Iterate through float / int / uint values. */
7382         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
7383         {
7384                 _supported_variable_types_map_const_iterator var_iterator =
7385                         supported_variable_types_map.find(var_types_set[var_type_index]);
7386
7387                 if (var_iterator != supported_variable_types_map.end())
7388                 {
7389                         std::string uniform_definition;
7390                         std::string uniform_use;
7391
7392                         uniform_definition += "layout (std140) buffer storage_block_name\n"
7393                                                                   "{\n";
7394                         uniform_definition += "    ";
7395                         uniform_definition += var_iterator->second.type;
7396                         uniform_definition += " my_storage_1[1][1][1][1];\n"
7397                                                                   "};\n";
7398
7399                         uniform_use = "    float result = float(my_storage_1[0][0][0][0]);\n";
7400
7401                         if (API::USE_ALL_SHADER_STAGES)
7402                         {
7403                                 const std::string& compute_shader_source =
7404                                         this->prepare_compute_shader(tested_shader_type, uniform_definition, uniform_use);
7405                                 const std::string& fragment_shader_source =
7406                                         this->prepare_fragment_shader(tested_shader_type, uniform_definition, uniform_use);
7407                                 const std::string& geometry_shader_source =
7408                                         this->prepare_geometry_shader(tested_shader_type, uniform_definition, uniform_use);
7409                                 const std::string& tess_ctrl_shader_source =
7410                                         this->prepare_tess_ctrl_shader(tested_shader_type, uniform_definition, uniform_use);
7411                                 const std::string& tess_eval_shader_source =
7412                                         this->prepare_tess_eval_shader(tested_shader_type, uniform_definition, uniform_use);
7413                                 const std::string& vertex_shader_source =
7414                                         this->prepare_vertex_shader(tested_shader_type, uniform_definition, uniform_use);
7415
7416                                 switch (tested_shader_type)
7417                                 {
7418                                 case TestCaseBase<API>::VERTEX_SHADER_TYPE: /* Fall through */
7419                                 case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
7420                                         this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
7421                                         break;
7422
7423                                 case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
7424                                 case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
7425                                 case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
7426                                 case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
7427                                         this->execute_positive_test(vertex_shader_source, tess_ctrl_shader_source, tess_eval_shader_source,
7428                                                                                                 geometry_shader_source, fragment_shader_source, compute_shader_source,
7429                                                                                                 false, false);
7430                                         break;
7431
7432                                 default:
7433                                         TCU_FAIL("Invalid enum");
7434                                         break;
7435                                 }
7436                         }
7437                         else
7438                         {
7439                                 const std::string& fragment_shader_source =
7440                                         this->prepare_fragment_shader(tested_shader_type, uniform_definition, uniform_use);
7441                                 const std::string& vertex_shader_source =
7442                                         this->prepare_vertex_shader(tested_shader_type, uniform_definition, uniform_use);
7443
7444                                 this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
7445                         }
7446
7447                         glw::GLuint buffer_object_id       = 0;
7448                         glw::GLint  my_storage_block_index = GL_INVALID_INDEX;
7449
7450                         gl.useProgram(this->program_object_id);
7451                         GLU_EXPECT_NO_ERROR(gl.getError(), "glUseProgram() failed.");
7452
7453                         my_storage_block_index =
7454                                 gl.getProgramResourceIndex(this->program_object_id, GL_SHADER_STORAGE_BLOCK, "storage_block_name");
7455                         GLU_EXPECT_NO_ERROR(gl.getError(), "glGetProgramResourceIndex() failed.");
7456
7457                         if ((unsigned)my_storage_block_index == GL_INVALID_INDEX)
7458                         {
7459                                 TCU_FAIL("Uniform block not found or is considered as not active.");
7460                         }
7461
7462                         gl.genBuffers(1, &buffer_object_id);
7463                         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenBuffers() failed.");
7464
7465                         gl.bindBuffer(GL_SHADER_STORAGE_BUFFER, buffer_object_id);
7466                         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindBuffer() failed.");
7467
7468                         switch (var_type_index)
7469                         {
7470                         case 0: //float type of uniform is considered
7471                         {
7472                                 glw::GLfloat buffer_data[] = { 0.0f, 1.0f, 2.0f,  3.0f,  4.0f,  5.0f,  6.0f,  7.0f,
7473                                                                                            8.0f, 9.0f, 10.0f, 11.0f, 12.0f, 13.0f, 14.0f, 15.0f };
7474
7475                                 gl.bufferData(GL_SHADER_STORAGE_BUFFER, sizeof(buffer_data), buffer_data, GL_STATIC_DRAW);
7476                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glBufferData() failed.");
7477
7478                                 break;
7479                         }               /* float case */
7480                         case 1: //int type of uniform is considered
7481                         {
7482
7483                                 glw::GLint buffer_data[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 };
7484
7485                                 gl.bufferData(GL_SHADER_STORAGE_BUFFER, sizeof(buffer_data), buffer_data, GL_STATIC_DRAW);
7486                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glBufferData() failed.");
7487
7488                                 break;
7489                         }               /* int case */
7490                         case 2: //uint type of uniform is considered
7491                         {
7492                                 glw::GLuint buffer_data[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 };
7493
7494                                 gl.bufferData(GL_SHADER_STORAGE_BUFFER, sizeof(buffer_data), buffer_data, GL_STATIC_DRAW);
7495                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glBufferData() failed.");
7496
7497                                 break;
7498                         }               /* uint case */
7499                         case 3: //double type of uniform is considered
7500                         {
7501                                 glw::GLdouble buffer_data[] = { 0.0, 1.0, 2.0,  3.0,  4.0,  5.0,  6.0,  7.0,
7502                                                                                                 8.0, 9.0, 10.0, 11.0, 12.0, 13.0, 14.0, 15.0 };
7503
7504                                 gl.bufferData(GL_SHADER_STORAGE_BUFFER, sizeof(buffer_data), buffer_data, GL_STATIC_DRAW);
7505                                 GLU_EXPECT_NO_ERROR(gl.getError(), "glBufferData() failed.");
7506
7507                                 break;
7508                         } /* double case */
7509                         default:
7510                         {
7511                                 TCU_FAIL("Invalid variable-type index.");
7512
7513                                 break;
7514                         }
7515                         } /* switch (var_type_index) */
7516
7517                         gl.shaderStorageBlockBinding(this->program_object_id, my_storage_block_index, 0);
7518                         GLU_EXPECT_NO_ERROR(gl.getError(), "glUniformBlockBinding() failed.");
7519
7520                         gl.bindBufferBase(GL_SHADER_STORAGE_BUFFER, 0, buffer_object_id);
7521                         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindBufferBase() failed.");
7522
7523                         if (TestCaseBase<API>::COMPUTE_SHADER_TYPE != tested_shader_type)
7524                         {
7525                                 execute_draw_test(tested_shader_type);
7526                         }
7527                         else
7528                         {
7529                                 execute_dispatch_test();
7530                         }
7531
7532                         /* Deallocate any resources used. */
7533                         gl.deleteBuffers(1, &buffer_object_id);
7534                         this->delete_objects();
7535                 } /* if var_type iterator found */
7536                 else
7537                 {
7538                         TCU_FAIL("Type not found.");
7539                 }
7540         } /* for (int var_type_index = 0; ...) */
7541 }
7542
7543 /** Executes test for compute program
7544  *
7545  * @tparam API               Tested API descriptor
7546  **/
7547 template <class API>
7548 void InteractionStorageBuffers2<API>::execute_dispatch_test()
7549 {
7550         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
7551
7552         gl.dispatchCompute(1, 1, 1);
7553         GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
7554 }
7555
7556 /** Executes test for draw program
7557  *
7558  * @tparam API               Tested API descriptor
7559  *
7560  * @param tested_shader_type The type of shader that is being tested
7561  **/
7562 template <class API>
7563 void InteractionStorageBuffers2<API>::execute_draw_test(typename TestCaseBase<API>::TestShaderType tested_shader_type)
7564 {
7565         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
7566
7567         glw::GLuint vao_id = 0;
7568
7569         gl.genVertexArrays(1, &vao_id);
7570         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenVertexArrays() failed.");
7571
7572         gl.bindVertexArray(vao_id);
7573         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindVertexArray() failed.");
7574
7575         switch (tested_shader_type)
7576         {
7577         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
7578         case TestCaseBase<API>::VERTEX_SHADER_TYPE: /* Fall through */
7579         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
7580                 gl.drawArrays(GL_POINTS, 0, 1);
7581                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
7582                 break;
7583
7584         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
7585         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
7586                 /* Tesselation patch set up */
7587                 gl.patchParameteri(GL_PATCH_VERTICES, 1);
7588                 GLU_EXPECT_NO_ERROR(gl.getError(), "PatchParameteri");
7589
7590                 gl.drawArrays(GL_PATCHES, 0, 1);
7591                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
7592                 break;
7593
7594         default:
7595                 TCU_FAIL("Invalid enum");
7596                 break;
7597         }
7598
7599         gl.deleteVertexArrays(1, &vao_id);
7600         GLU_EXPECT_NO_ERROR(gl.getError(), "glDeleteVertexArrays() failed.");
7601 }
7602
7603 /* Generates the shader source code for the InteractionUniformBuffers3
7604  * array tests, and attempts to compile each test shader, for both
7605  * vertex and fragment shaders.
7606  *
7607  * @tparam API               Tested API descriptor
7608  *
7609  * @param tested_shader_type The type of shader that is being tested
7610  *                           (either TestCaseBase<API>::VERTEX_SHADER_TYPE or TestCaseBase<API>::FRAGMENT_SHADER_TYPE).
7611  */
7612 template <class API>
7613 void InteractionStorageBuffers3<API>::test_shader_compilation(
7614         typename TestCaseBase<API>::TestShaderType tested_shader_type)
7615 {
7616         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT };
7617         static const size_t                               num_var_types_es   = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
7618
7619         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_FLOAT, VAR_TYPE_INT, VAR_TYPE_UINT,
7620                                                                                                                          VAR_TYPE_DOUBLE };
7621         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
7622
7623         const std::string invalid_size_declarations[] = { "[2][2][2][]", "[2][2][][2]", "[2][][2][2]", "[][2][2][2]",
7624                                                                                                           "[2][2][][]",  "[2][][2][]",  "[][2][2][]",  "[2][][][2]",
7625                                                                                                           "[][2][][2]",  "[][][2][2]",  "[2][][][]",   "[][2][][]",
7626                                                                                                           "[][][2][]",   "[][][][2]",   "[][][][]" };
7627         const std::string array_initializers[] = { "float[2][2][2][2](float[2][2][2](float[2][2](float[2](1.0, 2.0),"
7628                                                                                            "float[2](3.0, 4.0)),"
7629                                                                                            "float[2][2](float[2](5.0, 6.0),"
7630                                                                                            "float[2](7.0, 8.0))),"
7631                                                                                            "float[2][2][2](float[2][2](float[2](1.1, 2.1),"
7632                                                                                            "float[2](3.1, 4.1)),"
7633                                                                                            "float[2][2](float[2](5.1, 6.1),"
7634                                                                                            "float[2](7.1, 8.1))));\n",
7635
7636                                                                                            "int[2][2][2][2](int[2][2][2](int[2][2](int[2]( 1,  2),"
7637                                                                                            "int[2]( 3,  4)),"
7638                                                                                            "int[2][2](int[2]( 5,  6),"
7639                                                                                            "int[2]( 7,  8))),"
7640                                                                                            "int[2][2][2](int[2][2](int[2](11, 12),"
7641                                                                                            "int[2](13, 14)),"
7642                                                                                            "int[2][2](int[2](15, 16),"
7643                                                                                            "int[2](17, 18))));\n",
7644
7645                                                                                            "uint[2][2][2][2](uint[2][2][2](uint[2][2](uint[2]( 1u,  2u),"
7646                                                                                            "uint[2]( 3u,  4u)),"
7647                                                                                            "uint[2][2](uint[2]( 5u,  6u),"
7648                                                                                            "uint[2]( 7u,  8u))),"
7649                                                                                            "uint[2][2][2](uint[2][2](uint[2](11u, 12u),"
7650                                                                                            "uint[2](13u, 14u)),"
7651                                                                                            "uint[2][2](uint[2](15u, 16u),"
7652                                                                                            "uint[2](17u, 18u))));\n",
7653
7654                                                                                            "double[2][2][2][2](double[2][2][2](double[2][2](double[2](1.0, 2.0),"
7655                                                                                            "double[2](3.0, 4.0)),"
7656                                                                                            "double[2][2](double[2](5.0, 6.0),"
7657                                                                                            "double[2](7.0, 8.0))),"
7658                                                                                            "double[2][2][2](double[2][2](double[2](1.1, 2.1),"
7659                                                                                            "double[2](3.1, 4.1)),"
7660                                                                                            "double[2][2](double[2](5.1, 6.1),"
7661                                                                                            "double[2](7.1, 8.1))));\n" };
7662         const glcts::test_var_type* var_types_set = var_types_set_es;
7663         size_t                                          num_var_types = num_var_types_es;
7664
7665         if (API::USE_DOUBLE)
7666         {
7667                 var_types_set = var_types_set_gl;
7668                 num_var_types = num_var_types_gl;
7669         }
7670
7671         /* Iterate through float/ int/ uint types.
7672          * Case: without initializer.
7673          */
7674         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
7675         {
7676                 _supported_variable_types_map_const_iterator var_iterator =
7677                         supported_variable_types_map.find(var_types_set[var_type_index]);
7678
7679                 if (var_iterator != supported_variable_types_map.end())
7680                 {
7681                         for (size_t invalid_size_declarations_index = 0;
7682                                  invalid_size_declarations_index <
7683                                  sizeof(invalid_size_declarations) / sizeof(invalid_size_declarations[0]);
7684                                  invalid_size_declarations_index++)
7685                         {
7686                                 std::string shader_source;
7687
7688                                 shader_source = "layout (std140) buffer MyStorage {\n";
7689                                 shader_source += "    " + var_iterator->second.type +
7690                                                                  invalid_size_declarations[invalid_size_declarations_index] + " my_variable;\n";
7691                                 shader_source += "};\n\n";
7692                                 shader_source += shader_start;
7693
7694                                 /* End main */
7695                                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
7696
7697                                 /* Execute test */
7698                                 EXECUTE_SHADER_TEST(API::ALLOW_UNSIZED_DECLARATION && invalid_size_declarations_index == 3,
7699                                                                         tested_shader_type, shader_source);
7700                         } /* for (int invalid_size_declarations_index = 0; ...) */
7701                 }
7702                 else
7703                 {
7704                         TCU_FAIL("Type not found.");
7705                 }
7706         } /* for (int var_type_index = 0; ...) */
7707
7708         /* Iterate through float/ int/ uint types.
7709          * Case: with initializer.
7710          */
7711         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
7712         {
7713                 _supported_variable_types_map_const_iterator var_iterator =
7714                         supported_variable_types_map.find(var_types_set[var_type_index]);
7715
7716                 if (var_iterator != supported_variable_types_map.end())
7717                 {
7718                         for (size_t invalid_size_declarations_index = 0;
7719                                  invalid_size_declarations_index <
7720                                  sizeof(invalid_size_declarations) / sizeof(invalid_size_declarations[0]);
7721                                  invalid_size_declarations_index++)
7722                         {
7723                                 std::string shader_source;
7724
7725                                 shader_source = "layout (std140) buffer MyStorage {\n";
7726                                 shader_source += "    " + var_iterator->second.type +
7727                                                                  invalid_size_declarations[invalid_size_declarations_index] +
7728                                                                  " my_variable = " + array_initializers[var_type_index];
7729
7730                                 var_iterator->second.type + invalid_size_declarations[invalid_size_declarations_index] +
7731                                         " my_variable = " + array_initializers[var_type_index];
7732                                 shader_source += "};\n\n";
7733                                 shader_source += shader_start;
7734
7735                                 /* End main */
7736                                 DEFAULT_MAIN_ENDING(tested_shader_type, shader_source);
7737
7738                                 /* Execute test */
7739                                 this->execute_negative_test(tested_shader_type, shader_source);
7740                         } /* for (int invalid_size_declarations_index = 0; ...) */
7741                 }        /* if var_type iterator found */
7742                 else
7743                 {
7744                         TCU_FAIL("Type not found.");
7745                 }
7746         } /* for (int var_type_index = 0; ...) */
7747 }
7748
7749 /* Generates the shader source code for the InteractionInterfaceArrays1
7750  * array test, and attempts to compile the test shader.
7751  *
7752  * @tparam API               Tested API descriptor
7753  *
7754  * @param tested_shader_type The type of shader that is being tested.
7755  */
7756 template <class API>
7757 void InteractionInterfaceArrays1<API>::test_shader_compilation(
7758         typename TestCaseBase<API>::TestShaderType tested_shader_type)
7759 {
7760         /* Shader source with invalid buffer (buffer cannot be of arrays of arrays type). */
7761         const std::string invalid_buffer_shader_source = "layout(std140) buffer MyBuffer\n"
7762                                                                                                          "{\n"
7763                                                                                                          "    float f;\n"
7764                                                                                                          "    int   i;\n"
7765                                                                                                          "    uint  ui;\n"
7766                                                                                                          "} myBuffers[2][2];\n\n"
7767                                                                                                          "void main()\n"
7768                                                                                                          "{\n";
7769
7770         /* Verify that buffer arrays of arrays type is rejected. */
7771         {
7772                 std::string source = invalid_buffer_shader_source;
7773
7774                 DEFAULT_MAIN_ENDING(tested_shader_type, source);
7775
7776                 EXECUTE_SHADER_TEST(API::ALLOW_A_OF_A_ON_INTERFACE_BLOCKS, tested_shader_type, source);
7777         }
7778 }
7779
7780 /* Generates the shader source code for the InteractionInterfaceArrays2
7781  * array test, and attempts to compile the test shader.
7782  *
7783  * @tparam API              Tested API descriptor
7784  *
7785  * @param input_shader_type The type of shader that is being tested.
7786  */
7787 template <class API>
7788 void InteractionInterfaceArrays2<API>::test_shader_compilation(
7789         typename TestCaseBase<API>::TestShaderType input_shader_type)
7790 {
7791         /* Shader source with invalid input (input cannot be of arrays of arrays type). */
7792         const std::string input_variable_shader_source[] = { "in  float inout_variable", "[2][2];\n"
7793                                                                                                                                                                          "out float result",
7794                                                                                                                  ";\n\n"
7795                                                                                                                  "void main()\n"
7796                                                                                                                  "{\n"
7797                                                                                                                  "    result",
7798                                                                                                                  " = inout_variable", "[0][0];\n" };
7799         /* Shader source with invalid output (output cannot be of arrays of arrays type). */
7800         const std::string output_variable_shader_source[] = { "out float inout_variable",
7801                                                                                                                   "[2][2];\n\n"
7802                                                                                                                   "void main()\n"
7803                                                                                                                   "{\n"
7804                                                                                                                   "    inout_variable",
7805                                                                                                                   "[0][0] = 0.0;\n"
7806                                                                                                                   "    inout_variable",
7807                                                                                                                   "[0][1] = 1.0;\n"
7808                                                                                                                   "    inout_variable",
7809                                                                                                                   "[1][0] = 2.0;\n"
7810                                                                                                                   "    inout_variable",
7811                                                                                                                   "[1][1] = 3.0;\n" };
7812
7813         const typename TestCaseBase<API>::TestShaderType& output_shader_type =
7814                 this->get_output_shader_type(input_shader_type);
7815         std::string input_source;
7816         std::string output_source;
7817
7818         this->prepare_sources(input_shader_type, output_shader_type, input_variable_shader_source,
7819                                                   output_variable_shader_source, input_source, output_source);
7820
7821         /* Verify that INPUTs and OUTPUTs arrays of arrays type is rejected. */
7822         if (TestCaseBase<API>::COMPUTE_SHADER_TYPE != input_shader_type)
7823         {
7824                 if (API::ALLOW_A_OF_A_ON_INTERFACE_BLOCKS)
7825                 {
7826
7827                         if (API::USE_ALL_SHADER_STAGES)
7828                         {
7829                                 const std::string& compute_shader_source = empty_string;
7830                                 const std::string& fragment_shader_source =
7831                                         this->prepare_fragment_shader(input_shader_type, input_source, output_source);
7832                                 const std::string& geometry_shader_source =
7833                                         this->prepare_geometry_shader(input_shader_type, input_source, output_source);
7834                                 const std::string& tess_ctrl_shader_source =
7835                                         this->prepare_tess_ctrl_shader_source(input_shader_type, input_source, output_source);
7836                                 const std::string& tess_eval_shader_source =
7837                                         this->prepare_tess_eval_shader_source(input_shader_type, input_source, output_source);
7838                                 const std::string& vertex_shader_source =
7839                                         this->prepare_vertex_shader(input_shader_type, input_source, output_source);
7840
7841                                 this->execute_positive_test(vertex_shader_source, tess_ctrl_shader_source, tess_eval_shader_source,
7842                                                                                         geometry_shader_source, fragment_shader_source, compute_shader_source, true,
7843                                                                                         false);
7844                         }
7845                         else
7846                         {
7847                                 const std::string& fragment_shader_source =
7848                                         this->prepare_fragment_shader(input_shader_type, input_source, output_source);
7849                                 const std::string& vertex_shader_source =
7850                                         this->prepare_vertex_shader(input_shader_type, input_source, output_source);
7851
7852                                 this->execute_positive_test(vertex_shader_source, fragment_shader_source, true, false);
7853                         }
7854                 }
7855                 else
7856                 {
7857                         this->execute_negative_test(input_shader_type, input_source);
7858                         this->execute_negative_test(output_shader_type, output_source);
7859                 }
7860         }
7861 }
7862
7863 /** Gets the shader type to test for the outputs
7864  *
7865  * @tparam API              Tested API descriptor
7866  *
7867  * @param input_shader_type The type of input shader that is being tested
7868  **/
7869 template <class API>
7870 const typename TestCaseBase<API>::TestShaderType InteractionInterfaceArrays2<API>::get_output_shader_type(
7871         const typename TestCaseBase<API>::TestShaderType& input_shader_type)
7872 {
7873         switch (input_shader_type)
7874         {
7875         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
7876                 return TestCaseBase<API>::FRAGMENT_SHADER_TYPE;
7877
7878         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
7879                 if (API::USE_ALL_SHADER_STAGES)
7880                 {
7881                         return TestCaseBase<API>::GEOMETRY_SHADER_TYPE;
7882                 }
7883                 else
7884                 {
7885                         return TestCaseBase<API>::VERTEX_SHADER_TYPE;
7886                 }
7887
7888         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
7889                 break;
7890
7891         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
7892                 return TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE;
7893
7894         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
7895                 return TestCaseBase<API>::VERTEX_SHADER_TYPE;
7896
7897         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
7898                 return TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE;
7899
7900         default:
7901                 TCU_FAIL("Unrecognized shader type.");
7902                 break;
7903         }
7904
7905         return input_shader_type;
7906 }
7907
7908 /** Prepare fragment shader
7909  *
7910  * @tparam API              Tested API descriptor
7911  *
7912  * @param input_shader_type The type of input shader that is being tested
7913  * @param input_source      Shader in case we want to test inputs for this shader
7914  * @param output_source     Shader in case we want to test outputs for this shader
7915  **/
7916 template <class API>
7917 const std::string InteractionInterfaceArrays2<API>::prepare_fragment_shader(
7918         const typename TestCaseBase<API>::TestShaderType& input_shader_type, const std::string& input_source,
7919         const std::string& output_source)
7920 {
7921         switch (input_shader_type)
7922         {
7923         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
7924                 return output_source;
7925
7926         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
7927                 return input_source;
7928
7929         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
7930         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
7931         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
7932         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
7933                 break;
7934
7935         default:
7936                 TCU_FAIL("Unrecognized shader type.");
7937                 break;
7938         }
7939
7940         return default_fragment_shader_source;
7941 }
7942
7943 /** Prepare geometry shader
7944  *
7945  * @tparam API              Tested API descriptor
7946  *
7947  * @param input_shader_type The type of input shader that is being tested
7948  * @param input_source      Shader in case we want to test inputs for this shader
7949  * @param output_source     Shader in case we want to test outputs for this shader
7950  **/
7951 template <class API>
7952 const std::string InteractionInterfaceArrays2<API>::prepare_geometry_shader(
7953         const typename TestCaseBase<API>::TestShaderType& input_shader_type, const std::string& input_source,
7954         const std::string& output_source)
7955 {
7956         switch (input_shader_type)
7957         {
7958         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
7959                 if (API::USE_ALL_SHADER_STAGES)
7960                 {
7961                         return output_source;
7962                 }
7963                 break;
7964
7965         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
7966                 return input_source;
7967
7968         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
7969         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
7970         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
7971         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
7972                 break;
7973
7974         default:
7975                 TCU_FAIL("Unrecognized shader type.");
7976                 break;
7977         }
7978
7979         return default_geometry_shader_source;
7980 }
7981
7982 /** Prepare tessellation control shader
7983  *
7984  * @tparam API              Tested API descriptor
7985  *
7986  * @param input_shader_type The type of input shader that is being tested
7987  * @param input_source      Shader in case we want to test inputs for this shader
7988  * @param output_source     Shader in case we want to test outputs for this shader
7989  **/
7990 template <class API>
7991 const std::string InteractionInterfaceArrays2<API>::prepare_tess_ctrl_shader_source(
7992         const typename TestCaseBase<API>::TestShaderType& input_shader_type, const std::string& input_source,
7993         const std::string& output_source)
7994 {
7995         switch (input_shader_type)
7996         {
7997         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
7998         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
7999         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
8000         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
8001                 break;
8002
8003         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
8004                 return input_source;
8005
8006         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
8007                 return output_source;
8008
8009         default:
8010                 TCU_FAIL("Unrecognized shader type.");
8011                 break;
8012         }
8013
8014         return default_tc_shader_source;
8015 }
8016
8017 /** Prepare tessellation evaluation shader
8018  *
8019  * @tparam API              Tested API descriptor
8020  *
8021  * @param input_shader_type The type of input shader that is being tested
8022  * @param input_source      Shader in case we want to test inputs for this shader
8023  * @param output_source     Shader in case we want to test outputs for this shader
8024  **/
8025 template <class API>
8026 const std::string InteractionInterfaceArrays2<API>::prepare_tess_eval_shader_source(
8027         const typename TestCaseBase<API>::TestShaderType& input_shader_type, const std::string& input_source,
8028         const std::string& output_source)
8029 {
8030         switch (input_shader_type)
8031         {
8032         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
8033         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
8034         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
8035         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
8036                 break;
8037
8038         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
8039                 return output_source;
8040
8041         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
8042                 return input_source;
8043
8044         default:
8045                 TCU_FAIL("Unrecognized shader type.");
8046                 break;
8047         }
8048
8049         return default_te_shader_source;
8050 }
8051
8052 /** Prepare vertex shader
8053  *
8054  * @tparam API              Tested API descriptor
8055  *
8056  * @param input_shader_type The type of input shader that is being tested
8057  * @param input_source      Shader in case we want to test inputs for this shader
8058  * @param output_source     Shader in case we want to test outputs for this shader
8059  **/
8060 template <class API>
8061 const std::string InteractionInterfaceArrays2<API>::prepare_vertex_shader(
8062         const typename TestCaseBase<API>::TestShaderType& input_shader_type, const std::string& input_source,
8063         const std::string& output_source)
8064 {
8065         switch (input_shader_type)
8066         {
8067         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
8068                 return input_source;
8069
8070         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
8071                 if (!API::USE_ALL_SHADER_STAGES)
8072                 {
8073                         return output_source;
8074                 }
8075                 break;
8076
8077         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
8078                 return output_source;
8079
8080         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
8081         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
8082         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
8083                 break;
8084
8085         default:
8086                 TCU_FAIL("Unrecognized shader type.");
8087                 break;
8088         }
8089
8090         return default_vertex_shader_source;
8091 }
8092
8093 /** Prepare the inputs and outputs shaders
8094  *
8095  * @tparam API                 Tested API descriptor
8096  *
8097  * @param input_shader_type    The type of input shader that is being tested
8098  * @param output_shader_type   The type of output shader that is being tested
8099  * @param input_shader_source  Snippet used to prepare the input shader
8100  * @param output_shader_source Snippet used to prepare the output shader
8101  * @param input_source         Resulting input shader
8102  * @param output_source        Resulting output shader
8103  **/
8104 template <class API>
8105 void InteractionInterfaceArrays2<API>::prepare_sources(
8106         const typename TestCaseBase<API>::TestShaderType& input_shader_type,
8107         const typename TestCaseBase<API>::TestShaderType& output_shader_type, const std::string* input_shader_source,
8108         const std::string* output_shader_source, std::string& input_source, std::string& output_source)
8109 {
8110         if (TestCaseBase<API>::COMPUTE_SHADER_TYPE != input_shader_type)
8111         {
8112                 input_source += input_shader_source[0];
8113                 output_source += output_shader_source[0];
8114
8115                 if ((TestCaseBase<API>::GEOMETRY_SHADER_TYPE == input_shader_type) ||
8116                         (TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE == input_shader_type) ||
8117                         (TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE == input_shader_type))
8118                 {
8119                         input_source += "[]";
8120                 }
8121
8122                 if (TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE == output_shader_type)
8123                 {
8124                         output_source += "[]";
8125                 }
8126
8127                 input_source += input_shader_source[1];
8128                 output_source += output_shader_source[1];
8129
8130                 if (TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE == input_shader_type)
8131                 {
8132                         input_source += "[]";
8133                 }
8134
8135                 if (TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE == output_shader_type)
8136                 {
8137                         output_source += "[gl_InvocationID]";
8138                 }
8139
8140                 input_source += input_shader_source[2];
8141                 output_source += output_shader_source[2];
8142
8143                 if (TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE == input_shader_type)
8144                 {
8145                         input_source += "[gl_InvocationID]";
8146                 }
8147
8148                 if (TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE == output_shader_type)
8149                 {
8150                         output_source += "[gl_InvocationID]";
8151                 }
8152
8153                 input_source += input_shader_source[3];
8154                 output_source += output_shader_source[3];
8155
8156                 if ((TestCaseBase<API>::GEOMETRY_SHADER_TYPE == input_shader_type) ||
8157                         (TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE == input_shader_type))
8158                 {
8159                         input_source += "[0]";
8160                 }
8161
8162                 if (TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE == input_shader_type)
8163                 {
8164                         input_source += "[gl_InvocationID]";
8165                 }
8166
8167                 if (TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE == output_shader_type)
8168                 {
8169                         output_source += "[gl_InvocationID]";
8170                 }
8171
8172                 input_source += input_shader_source[4];
8173                 output_source += output_shader_source[4];
8174
8175                 if (TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE == output_shader_type)
8176                 {
8177                         output_source += "[gl_InvocationID]";
8178                 }
8179
8180                 output_source += output_shader_source[5];
8181
8182                 DEFAULT_MAIN_ENDING(input_shader_type, input_source);
8183                 DEFAULT_MAIN_ENDING(output_shader_type, output_source);
8184         }
8185 }
8186
8187 /* Generates the shader source code for the InteractionInterfaceArrays3
8188  * array test, and attempts to compile the test shader.
8189  *
8190  * @tparam API               Tested API descriptor
8191  *
8192  * @param tested_shader_type The type of shader that is being tested.
8193  */
8194 template <class API>
8195 void InteractionInterfaceArrays3<API>::test_shader_compilation(
8196         typename TestCaseBase<API>::TestShaderType tested_shader_type)
8197 {
8198         /* Shader source with invalid uniform block (uniform block cannot be of arrays of arrays type). */
8199         const std::string invalid_uniform_block_shader_source = "layout(std140) uniform MyUniformBlock\n"
8200                                                                                                                         "{\n"
8201                                                                                                                         "    float f;\n"
8202                                                                                                                         "    int   i;\n"
8203                                                                                                                         "    uint  ui;\n"
8204                                                                                                                         "} myUniformBlocks[2][2];\n\n"
8205                                                                                                                         "void main()\n"
8206                                                                                                                         "{\n";
8207
8208         /* Verify that uniform block arrays of arrays type is rejected. */
8209         {
8210                 std::string source = invalid_uniform_block_shader_source;
8211
8212                 DEFAULT_MAIN_ENDING(tested_shader_type, source);
8213
8214                 EXECUTE_SHADER_TEST(API::ALLOW_A_OF_A_ON_INTERFACE_BLOCKS, tested_shader_type, source);
8215         }
8216 }
8217
8218 /* Generates the shader source code for the InteractionInterfaceArrays4
8219  * array test, and attempts to compile the test shader.
8220  *
8221  * @tparam API              Tested API descriptor
8222  *
8223  * @param input_shader_type The type of shader that is being tested.
8224  */
8225 template <class API>
8226 void InteractionInterfaceArrays4<API>::test_shader_compilation(
8227         typename TestCaseBase<API>::TestShaderType input_shader_type)
8228 {
8229         /* Shader source with invalid input (input cannot be of arrays of arrays type). */
8230         const std::string input_block_shader_source[] = { "in  InOutBlock {\n"
8231                                                                                                           "    float inout_variable;\n"
8232                                                                                                           "} inout_block",
8233                                                                                                           "[2][2];\n"
8234                                                                                                           "out float result",
8235                                                                                                           ";\n\n"
8236                                                                                                           "void main()\n"
8237                                                                                                           "{\n"
8238                                                                                                           "    result",
8239                                                                                                           " = inout_block", "[0][0].inout_variable;\n" };
8240         /* Shader source with invalid output (output cannot be of arrays of arrays type). */
8241         const std::string output_block_shader_source[] = { "out InOutBlock {\n"
8242                                                                                                            "    float inout_variable;\n"
8243                                                                                                            "} inout_block",
8244                                                                                                            "[2][2];\n"
8245                                                                                                            "\n"
8246                                                                                                            "void main()\n"
8247                                                                                                            "{\n"
8248                                                                                                            "    inout_block",
8249                                                                                                            "[0][0].inout_variable = 0.0;\n"
8250                                                                                                            "    inout_block",
8251                                                                                                            "[0][1].inout_variable = 1.0;\n"
8252                                                                                                            "    inout_block",
8253                                                                                                            "[1][0].inout_variable = 2.0;\n"
8254                                                                                                            "    inout_block",
8255                                                                                                            "[1][1].inout_variable = 3.0;\n" };
8256
8257         const typename TestCaseBase<API>::TestShaderType& output_shader_type =
8258                 this->get_output_shader_type(input_shader_type);
8259         std::string input_source;
8260         std::string output_source;
8261
8262         this->prepare_sources(input_shader_type, output_shader_type, input_block_shader_source, output_block_shader_source,
8263                                                   input_source, output_source);
8264
8265         /* Verify that INPUTs and OUTPUTs arrays of arrays type is rejected. */
8266         if ((TestCaseBase<API>::VERTEX_SHADER_TYPE != input_shader_type) &&
8267                 (TestCaseBase<API>::COMPUTE_SHADER_TYPE != input_shader_type))
8268         {
8269                 if (API::ALLOW_A_OF_A_ON_INTERFACE_BLOCKS && API::ALLOW_IN_OUT_INTERFACE_BLOCKS)
8270                 {
8271
8272                         if (API::USE_ALL_SHADER_STAGES)
8273                         {
8274                                 const std::string& compute_shader_source = empty_string;
8275                                 const std::string& fragment_shader_source =
8276                                         this->prepare_fragment_shader(input_shader_type, input_source, output_source);
8277                                 const std::string& geometry_shader_source =
8278                                         this->prepare_geometry_shader(input_shader_type, input_source, output_source);
8279                                 const std::string& tess_ctrl_shader_source =
8280                                         this->prepare_tess_ctrl_shader_source(input_shader_type, input_source, output_source);
8281                                 const std::string& tess_eval_shader_source =
8282                                         this->prepare_tess_eval_shader_source(input_shader_type, input_source, output_source);
8283                                 const std::string& vertex_shader_source =
8284                                         this->prepare_vertex_shader(input_shader_type, input_source, output_source);
8285
8286                                 this->execute_positive_test(vertex_shader_source, tess_ctrl_shader_source, tess_eval_shader_source,
8287                                                                                         geometry_shader_source, fragment_shader_source, compute_shader_source, true,
8288                                                                                         false);
8289                         }
8290                         else
8291                         {
8292                                 const std::string& fragment_shader_source =
8293                                         this->prepare_fragment_shader(input_shader_type, input_source, output_source);
8294                                 const std::string& vertex_shader_source =
8295                                         this->prepare_vertex_shader(input_shader_type, input_source, output_source);
8296
8297                                 this->execute_positive_test(vertex_shader_source, fragment_shader_source, true, false);
8298                         }
8299                 }
8300                 else
8301                 {
8302                         this->execute_negative_test(input_shader_type, input_source);
8303                         this->execute_negative_test(output_shader_type, output_source);
8304                 }
8305         }
8306 }
8307
8308 /** Calulate smallest denominator for values over 1
8309  *
8310  * @param value Value in question
8311  *
8312  * @return Smallest denominator
8313  **/
8314 size_t findSmallestDenominator(const size_t value)
8315 {
8316         /* Skip 0 and 1 */
8317         for (size_t i = 2; i < value; ++i)
8318         {
8319                 if (0 == value % i)
8320                 {
8321                         return i;
8322                 }
8323         }
8324
8325         return value;
8326 }
8327
8328 /** Check if left is bigger than right
8329  *
8330  * @tparam T Type of values
8331
8332  * @param l  Left value
8333  * @param r  Right value
8334  *
8335  * @return true if l > r, false otherwise
8336  **/
8337 template <class T>
8338 bool more(const T& l, const T& r)
8339 {
8340         return l > r;
8341 }
8342
8343 /** Prepare dimensions of array with given number of entries
8344  *
8345  * @tparam API       Tested API descriptor
8346  *
8347  * @param n_entries  Number of entries
8348  * @param dimensions Storage for dimesnions
8349  **/
8350 template <class API>
8351 void prepareDimensions(size_t n_entries, std::vector<size_t>& dimensions)
8352 {
8353         if (dimensions.empty())
8354                 return;
8355
8356         const size_t last = dimensions.size() - 1;
8357
8358         /* Calculate */
8359         for (size_t i = 0; i < last; ++i)
8360         {
8361                 const size_t denom = findSmallestDenominator(n_entries);
8362
8363                 n_entries /= denom;
8364
8365                 dimensions[i] = denom;
8366         }
8367
8368         dimensions[last] = n_entries;
8369
8370         /* Sort */
8371         std::sort(dimensions.begin(), dimensions.end(), more<size_t>);
8372 }
8373
8374 /* Generates the shader source code for the AtomicDeclarationTest
8375  * and attempts to compile each shader
8376  *
8377  * @tparam API               Tested API descriptor
8378  *
8379  * @param tested_shader_type The type of shader that is being tested
8380  */
8381 template <class API>
8382 void AtomicDeclarationTest<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
8383 {
8384         static const char* indent_step             = "    ";
8385         static const char* uniform_atomic_uint = "layout(binding = 0) uniform atomic_uint";
8386
8387         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
8388
8389         std::string                     comment;
8390         std::vector<size_t> dimensions;
8391         std::string                     indent;
8392         std::string                     indexing;
8393         std::string                     invalid_definition = uniform_atomic_uint;
8394         std::string                     invalid_iteration;
8395         std::string                     invalid_shader_source;
8396         std::string                     loop_end;
8397         glw::GLint                      max_atomics = 0;
8398         glw::GLenum                     pname           = 0;
8399         std::string                     valid_shader_source;
8400         std::string                     valid_definition = uniform_atomic_uint;
8401         std::string                     valid_iteration;
8402
8403         /* Select pname of max for stage */
8404         switch (tested_shader_type)
8405         {
8406         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
8407                 pname = GL_MAX_COMPUTE_ATOMIC_COUNTERS;
8408                 break;
8409         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
8410                 pname = GL_MAX_FRAGMENT_ATOMIC_COUNTERS;
8411                 break;
8412         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
8413                 pname = GL_MAX_GEOMETRY_ATOMIC_COUNTERS;
8414                 break;
8415         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
8416                 pname = GL_MAX_TESS_CONTROL_ATOMIC_COUNTERS;
8417                 break;
8418         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
8419                 pname = GL_MAX_TESS_EVALUATION_ATOMIC_COUNTERS;
8420                 break;
8421         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
8422                 pname = GL_MAX_VERTEX_ATOMIC_COUNTERS;
8423                 break;
8424         default:
8425                 TCU_FAIL("Invalid enum");
8426                 break;
8427         }
8428
8429         /* Get maximum */
8430         gl.getIntegerv(pname, &max_atomics);
8431         GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
8432
8433         if (0 == max_atomics)
8434         {
8435                 /* Not supported - skip */
8436                 return;
8437         }
8438         else
8439         {
8440                 dimensions.resize(API::MAX_ARRAY_DIMENSIONS);
8441                 prepareDimensions<API>(max_atomics, dimensions);
8442         }
8443
8444         /* Prepare parts of shader */
8445         for (size_t i = API::MAX_ARRAY_DIMENSIONS; i != 0; --i)
8446         {
8447                 char it[16];
8448                 char max[16];
8449
8450                 indent += indent_step;
8451
8452                 loop_end.insert(0, "}\n");
8453                 loop_end.insert(0, indent);
8454
8455                 sprintf(it, "i%u", (unsigned int)(API::MAX_ARRAY_DIMENSIONS - i));
8456
8457                 indexing += "[";
8458                 indexing += it;
8459                 indexing += "]";
8460
8461                 sprintf(max, "%u", (unsigned int)(dimensions[i - 1]));
8462
8463                 valid_definition += "[";
8464                 valid_definition += max;
8465                 valid_definition += "]";
8466
8467                 valid_iteration += indent;
8468                 valid_iteration += "for (uint ";
8469                 valid_iteration += it;
8470                 valid_iteration += " = 0; ";
8471                 valid_iteration += it;
8472                 valid_iteration += " < ";
8473                 valid_iteration += max;
8474                 valid_iteration += "; ++";
8475                 valid_iteration += it;
8476                 valid_iteration += ")\n";
8477                 valid_iteration += indent;
8478                 valid_iteration += "{\n";
8479
8480                 if (1 == i)
8481                 {
8482                         sprintf(max, "%u", (unsigned int)(dimensions[i - 1] + 1));
8483                 }
8484                 invalid_definition += "[";
8485                 invalid_definition += max;
8486                 invalid_definition += "]";
8487
8488                 invalid_iteration += indent;
8489                 invalid_iteration += "for (uint ";
8490                 invalid_iteration += it;
8491                 invalid_iteration += " = 0; ";
8492                 invalid_iteration += it;
8493                 invalid_iteration += " < ";
8494                 invalid_iteration += max;
8495                 invalid_iteration += "; ++";
8496                 invalid_iteration += it;
8497                 invalid_iteration += ")\n";
8498                 invalid_iteration += indent;
8499                 invalid_iteration += "{\n";
8500         }
8501
8502         {
8503                 char max[16];
8504
8505                 sprintf(max, "%u", (unsigned int)(max_atomics));
8506                 comment += "/* MAX_*_ATOMIC_COUNTERS = ";
8507                 comment += max;
8508                 comment += " */\n";
8509         }
8510
8511         /* Prepare invalid source */
8512         invalid_shader_source += comment;
8513         invalid_shader_source += invalid_definition;
8514         invalid_shader_source += " a;\n\nvoid main()\n{\n";
8515         invalid_shader_source += invalid_iteration;
8516         invalid_shader_source += indent;
8517         invalid_shader_source += indent_step;
8518         invalid_shader_source += "atomicCounterIncrement( a";
8519         invalid_shader_source += indexing;
8520         invalid_shader_source += " );\n";
8521         invalid_shader_source += loop_end;
8522
8523         /* Prepare valid source */
8524         valid_shader_source += comment;
8525         valid_shader_source += valid_definition;
8526         valid_shader_source += " a;\n\nvoid main()\n{\n";
8527         valid_shader_source += valid_iteration;
8528         valid_shader_source += indent;
8529         valid_shader_source += indent_step;
8530         valid_shader_source += "atomicCounterIncrement( a";
8531         valid_shader_source += indexing;
8532         valid_shader_source += " );\n";
8533         valid_shader_source += loop_end;
8534
8535         /* End main */
8536         DEFAULT_MAIN_ENDING(tested_shader_type, invalid_shader_source);
8537         DEFAULT_MAIN_ENDING(tested_shader_type, valid_shader_source);
8538
8539         /* Execute test */
8540         EXECUTE_POSITIVE_TEST(tested_shader_type, valid_shader_source, true, false);
8541
8542         /* Expect build failure for invalid shader source */
8543         {
8544                 bool negative_build_test_result = false;
8545
8546                 try
8547                 {
8548                         EXECUTE_POSITIVE_TEST(tested_shader_type, invalid_shader_source, true, false);
8549                 }
8550                 catch (...)
8551                 {
8552                         negative_build_test_result = true;
8553                 }
8554
8555                 if (false == negative_build_test_result)
8556                 {
8557                         TCU_FAIL("It was expected that build process will fail");
8558                 }
8559         }
8560 }
8561
8562 /* Generates the shader source code for the AtomicUsageTest
8563  * and attempts to compile each shader
8564  *
8565  * @tparam API               Tested API descriptor
8566  *
8567  * @param tested_shader_type The type of shader that is being tested
8568  */
8569 template <class API>
8570 void AtomicUsageTest<API>::test_shader_compilation(typename TestCaseBase<API>::TestShaderType tested_shader_type)
8571 {
8572         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
8573
8574         glw::GLint  max_atomics  = 0;
8575         glw::GLint  max_bindings = 0;
8576         glw::GLint  max_size     = 0;
8577         glw::GLenum pname                = 0;
8578
8579         /* Select pname of max for stage */
8580         switch (tested_shader_type)
8581         {
8582         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
8583                 pname = GL_MAX_COMPUTE_ATOMIC_COUNTERS;
8584                 break;
8585         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
8586                 pname = GL_MAX_FRAGMENT_ATOMIC_COUNTERS;
8587                 break;
8588         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
8589                 pname = GL_MAX_GEOMETRY_ATOMIC_COUNTERS;
8590                 break;
8591         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
8592                 pname = GL_MAX_TESS_CONTROL_ATOMIC_COUNTERS;
8593                 break;
8594         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
8595                 pname = GL_MAX_TESS_EVALUATION_ATOMIC_COUNTERS;
8596                 break;
8597         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
8598                 pname = GL_MAX_VERTEX_ATOMIC_COUNTERS;
8599                 break;
8600         default:
8601                 TCU_FAIL("Invalid enum");
8602                 break;
8603         }
8604
8605         /* Get limits */
8606         gl.getIntegerv(pname, &max_atomics);
8607         GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
8608
8609         gl.getIntegerv(GL_MAX_ATOMIC_COUNTER_BUFFER_BINDINGS, &max_bindings);
8610         GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
8611
8612         gl.getIntegerv(GL_MAX_ATOMIC_COUNTER_BUFFER_SIZE, &max_size);
8613         GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
8614
8615         if (0 == max_atomics)
8616         {
8617                 /* Not supported - skip */
8618                 return;
8619         }
8620
8621         const glw::GLuint last_binding = (glw::GLuint)max_bindings - 1;
8622         const glw::GLuint offset           = (glw::GLuint)max_size / 2;
8623         glw::GLuint               n_entries =
8624                 std::min((glw::GLuint)(max_size - offset) / (glw::GLuint)sizeof(glw::GLuint), (glw::GLuint)max_atomics);
8625
8626         if (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type)
8627         {
8628                 glw::GLint max_uniform_locations = 0;
8629
8630                 gl.getIntegerv(GL_MAX_UNIFORM_LOCATIONS, &max_uniform_locations);
8631                 GLU_EXPECT_NO_ERROR(gl.getError(), "GetIntegerv");
8632
8633                 max_atomics = std::min(max_atomics, (max_uniform_locations - 1));
8634                 n_entries   = (glw::GLuint)std::min((glw::GLint)n_entries, (max_uniform_locations - 1));
8635         }
8636
8637         execute(tested_shader_type, last_binding, 0 /* offset */, max_atomics);
8638         execute(tested_shader_type, last_binding, offset, n_entries);
8639 }
8640
8641 /* Generates the shader source code for the AtomicUsageTest
8642  * and attempts to compile each shader
8643  *
8644  * @tparam API               Tested API descriptor
8645  *
8646  * @param tested_shader_type The type of shader that is being tested
8647  * @param binding            Binding index
8648  * @param offset             Offset of data
8649  * @param n_entries          Number of entries in array
8650  */
8651 template <class API>
8652 void AtomicUsageTest<API>::execute(typename TestCaseBase<API>::TestShaderType tested_shader_type, glw::GLuint binding,
8653                                                                    glw::GLuint offset, glw::GLuint n_entries)
8654 {
8655         static const char* indent_step             = "    ";
8656         static const char* layout_binding         = "layout(binding = ";
8657         static const char* layout_offset           = ", offset = ";
8658         static const char* uniform_atomic_uint = ") uniform atomic_uint";
8659
8660         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
8661
8662         std::string                     comment;
8663         std::vector<size_t> dimensions;
8664         std::string                     indent;
8665         std::string                     indexing;
8666         std::string                     loop_end;
8667         std::string                     result;
8668         std::string                     valid_shader_source;
8669         std::string                     valid_definition = layout_binding;
8670         std::string                     valid_iteration;
8671         std::string                     varying_definition;
8672
8673         dimensions.resize(API::MAX_ARRAY_DIMENSIONS);
8674         prepareDimensions<API>(n_entries, dimensions);
8675
8676         /* Prepare parts of shader */
8677
8678         /* Append binding */
8679         {
8680                 char buffer[16];
8681                 sprintf(buffer, "%u", static_cast<unsigned int>(binding));
8682                 valid_definition += buffer;
8683                 valid_definition += layout_offset;
8684                 sprintf(buffer, "%u", static_cast<unsigned int>(offset));
8685                 valid_definition += buffer;
8686                 valid_definition += uniform_atomic_uint;
8687         }
8688
8689         for (size_t i = API::MAX_ARRAY_DIMENSIONS; i != 0; --i)
8690         {
8691                 char it[16];
8692                 char max[16];
8693
8694                 indent += indent_step;
8695
8696                 loop_end.insert(0, "}\n");
8697                 loop_end.insert(0, indent);
8698
8699                 sprintf(it, "i%u", (unsigned int)(API::MAX_ARRAY_DIMENSIONS - i));
8700
8701                 indexing += "[";
8702                 indexing += it;
8703                 indexing += "]";
8704
8705                 sprintf(max, "%u", (unsigned int)(dimensions[i - 1]));
8706                 valid_definition += "[";
8707                 valid_definition += max;
8708                 valid_definition += "]";
8709
8710                 valid_iteration += indent;
8711                 valid_iteration += "for (uint ";
8712                 valid_iteration += it;
8713                 valid_iteration += " = 0; ";
8714                 valid_iteration += it;
8715                 valid_iteration += " < ";
8716                 valid_iteration += max;
8717                 valid_iteration += "; ++";
8718                 valid_iteration += it;
8719                 valid_iteration += ")\n";
8720                 valid_iteration += indent;
8721                 valid_iteration += "{\n";
8722         }
8723
8724         {
8725                 char max[16];
8726
8727                 sprintf(max, "%u", (unsigned int)(n_entries));
8728                 comment += "/* Number of atomic counters = ";
8729                 comment += max;
8730                 comment += " */\n";
8731         }
8732
8733         /* Select varyings and result */
8734         switch (tested_shader_type)
8735         {
8736         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
8737                 result                     = "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), vec4(result, 0, 0, 0));\n";
8738                 varying_definition = "writeonly uniform image2D uni_image;\n"
8739                                                          "\n";
8740                 break;
8741
8742         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
8743                 result                     = "    color = vec4(result);\n";
8744                 varying_definition = "out vec4 color;\n"
8745                                                          "\n";
8746                 break;
8747
8748         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
8749                 result = "    gl_Position  = vec4(-1, -1, 0, 1);\n"
8750                                  "    fs_result = result;\n"
8751                                  "    EmitVertex();\n"
8752                                  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
8753                                  "    fs_result = result;\n"
8754                                  "    EmitVertex();\n"
8755                                  "    gl_Position  = vec4(1, -1, 0, 1);\n"
8756                                  "    fs_result = result;\n"
8757                                  "    EmitVertex();\n"
8758                                  "    gl_Position  = vec4(1, 1, 0, 1);\n"
8759                                  "    fs_result = result;\n"
8760                                  "    EmitVertex();\n";
8761                 varying_definition = "out float fs_result;\n"
8762                                                          "\n";
8763                 break;
8764
8765         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
8766                 result = "    tcs_result[gl_InvocationID] = result;\n"
8767                                  "\n"
8768                                  "    gl_TessLevelOuter[0] = 1.0;\n"
8769                                  "    gl_TessLevelOuter[1] = 1.0;\n"
8770                                  "    gl_TessLevelOuter[2] = 1.0;\n"
8771                                  "    gl_TessLevelOuter[3] = 1.0;\n"
8772                                  "    gl_TessLevelInner[0] = 1.0;\n"
8773                                  "    gl_TessLevelInner[1] = 1.0;\n";
8774                 varying_definition = "out float tcs_result[];\n"
8775                                                          "\n";
8776                 break;
8777
8778         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
8779                 result                     = "    fs_result = result;\n";
8780                 varying_definition = "out float fs_result;\n"
8781                                                          "\n";
8782                 break;
8783
8784         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
8785                 result                     = "    fs_result = result;\n";
8786                 varying_definition = "out float fs_result;\n"
8787                                                          "\n";
8788                 break;
8789
8790         default:
8791                 TCU_FAIL("Invalid enum");
8792                 break;
8793         };
8794
8795         /* Prepare valid source */
8796         valid_shader_source += varying_definition;
8797         valid_shader_source += comment;
8798         valid_shader_source += valid_definition;
8799         valid_shader_source += " a;\n\nvoid main()\n{\n    uint sum = 0u;\n";
8800         valid_shader_source += valid_iteration;
8801         valid_shader_source += indent;
8802         valid_shader_source += indent_step;
8803         valid_shader_source += "sum += atomicCounterIncrement( a";
8804         valid_shader_source += indexing;
8805         valid_shader_source += " );\n";
8806         valid_shader_source += loop_end;
8807         valid_shader_source += "\n"
8808                                                    "    float result = 0.0;\n"
8809                                                    "\n"
8810                                                    "    if (16u < sum)\n"
8811                                                    "    {\n"
8812                                                    "         result = 1.0;\n"
8813                                                    "    }\n";
8814         valid_shader_source += result;
8815         valid_shader_source += shader_end;
8816
8817         /* Build program */
8818         {
8819                 const std::string* cs  = &empty_string;
8820                 const std::string* vs  = &default_vertex_shader_source;
8821                 const std::string* tcs = &empty_string;
8822                 const std::string* tes = &empty_string;
8823                 const std::string* gs  = &empty_string;
8824                 const std::string* fs  = &pass_fragment_shader_source;
8825
8826                 switch (tested_shader_type)
8827                 {
8828                 case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
8829                         cs = &valid_shader_source;
8830                         vs = &empty_string;
8831                         fs = &empty_string;
8832                         break;
8833
8834                 case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
8835                         fs = &valid_shader_source;
8836                         break;
8837
8838                 case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
8839                         gs = &valid_shader_source;
8840                         break;
8841
8842                 case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
8843                         tcs = &valid_shader_source;
8844                         tes = &pass_te_shader_source;
8845                         break;
8846
8847                 case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
8848                         tcs = &default_tc_shader_source;
8849                         tes = &valid_shader_source;
8850                         break;
8851
8852                 case TestCaseBase<API>::VERTEX_SHADER_TYPE:
8853                         vs = &valid_shader_source;
8854                         break;
8855
8856                 default:
8857                         TCU_FAIL("Invalid enum");
8858                         break;
8859                 };
8860
8861                 if (API::USE_ALL_SHADER_STAGES)
8862                 {
8863                         this->execute_positive_test(*vs, *tcs, *tes, *gs, *fs, *cs, false, false);
8864                 }
8865                 else
8866                 {
8867                         this->execute_positive_test(*vs, *fs, false, false);
8868                 }
8869         }
8870
8871         gl.useProgram(this->program_object_id);
8872         GLU_EXPECT_NO_ERROR(gl.getError(), "glUseProgram() failed.");
8873
8874         /* Prepare buffer */
8875         glw::GLuint                              buffer_object_id = 0;
8876         std::vector<glw::GLuint> buffer_data;
8877         const size_t                     start_pos                = offset / 4;
8878         const size_t                     last_pos                 = start_pos + n_entries;
8879         const size_t                     buffer_data_size = last_pos * sizeof(glw::GLuint);
8880
8881         gl.genBuffers(1, &buffer_object_id);
8882         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenBuffers() failed.");
8883
8884         gl.bindBuffer(GL_ATOMIC_COUNTER_BUFFER, buffer_object_id);
8885         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindBuffer() failed.");
8886
8887         buffer_data.resize(start_pos + n_entries);
8888         for (size_t i = 0; i < n_entries; ++i)
8889         {
8890                 buffer_data[start_pos + i] = (glw::GLuint)i;
8891         }
8892
8893         gl.bufferData(GL_ATOMIC_COUNTER_BUFFER, buffer_data_size, &buffer_data[0], GL_STATIC_DRAW);
8894         GLU_EXPECT_NO_ERROR(gl.getError(), "glBufferData() failed.");
8895
8896         gl.bindBufferBase(GL_ATOMIC_COUNTER_BUFFER, binding, buffer_object_id);
8897         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindBufferBase() failed.");
8898
8899         /* Run program */
8900         if (TestCaseBase<API>::COMPUTE_SHADER_TYPE != tested_shader_type)
8901         {
8902                 glw::GLuint framebuffer_object_id = 0;
8903                 glw::GLuint texture_object_id    = 0;
8904                 glw::GLuint vao_id                                = 0;
8905
8906                 gl.genTextures(1, &texture_object_id);
8907                 GLU_EXPECT_NO_ERROR(gl.getError(), "glGenTextures() failed.");
8908
8909                 gl.bindTexture(GL_TEXTURE_2D, texture_object_id);
8910                 GLU_EXPECT_NO_ERROR(gl.getError(), "glBindTexture() failed.");
8911
8912                 gl.texStorage2D(GL_TEXTURE_2D, 1, GL_RGBA8, 1, 1);
8913                 GLU_EXPECT_NO_ERROR(gl.getError(), "glTexStorage2D() failed.");
8914
8915                 gl.genFramebuffers(1, &framebuffer_object_id);
8916                 GLU_EXPECT_NO_ERROR(gl.getError(), "glGenFramebuffers() failed.");
8917
8918                 gl.bindFramebuffer(GL_FRAMEBUFFER, framebuffer_object_id);
8919                 GLU_EXPECT_NO_ERROR(gl.getError(), "glBindFramebuffer() failed.");
8920
8921                 gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texture_object_id, 0);
8922                 GLU_EXPECT_NO_ERROR(gl.getError(), "glFramebufferTexture2D() failed.");
8923
8924                 gl.viewport(0, 0, 1, 1);
8925                 GLU_EXPECT_NO_ERROR(gl.getError(), "glViewport() failed.");
8926
8927                 gl.genVertexArrays(1, &vao_id);
8928                 GLU_EXPECT_NO_ERROR(gl.getError(), "glGenVertexArrays() failed.");
8929
8930                 gl.bindVertexArray(vao_id);
8931                 GLU_EXPECT_NO_ERROR(gl.getError(), "glBindVertexArray() failed.");
8932
8933                 switch (tested_shader_type)
8934                 {
8935                 case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
8936                 case TestCaseBase<API>::VERTEX_SHADER_TYPE: /* Fall through */
8937                 case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
8938                         gl.drawArrays(GL_POINTS, 0, 1);
8939                         GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
8940                         break;
8941
8942                 case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
8943                 case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
8944                         /* Tesselation patch set up */
8945                         gl.patchParameteri(GL_PATCH_VERTICES, 1);
8946                         GLU_EXPECT_NO_ERROR(gl.getError(), "PatchParameteri");
8947
8948                         gl.drawArrays(GL_PATCHES, 0, 1);
8949                         GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
8950                         break;
8951
8952                 default:
8953                         TCU_FAIL("Invalid enum");
8954                         break;
8955                 }
8956
8957                 gl.memoryBarrier(GL_ALL_BARRIER_BITS);
8958                 GLU_EXPECT_NO_ERROR(gl.getError(), "MemoryBarrier.");
8959
8960                 gl.bindTexture(GL_TEXTURE_2D, 0);
8961                 gl.bindFramebuffer(GL_FRAMEBUFFER, 0);
8962                 gl.bindVertexArray(0);
8963                 gl.deleteTextures(1, &texture_object_id);
8964                 gl.deleteFramebuffers(1, &framebuffer_object_id);
8965                 gl.deleteVertexArrays(1, &vao_id);
8966                 GLU_EXPECT_NO_ERROR(gl.getError(), "An error ocurred while deleting generated objects.");
8967         }
8968         else
8969         {
8970                 gl.dispatchCompute(1, 1, 1);
8971                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
8972
8973                 gl.memoryBarrier(GL_ALL_BARRIER_BITS);
8974                 GLU_EXPECT_NO_ERROR(gl.getError(), "MemoryBarrier.");
8975         }
8976
8977         /* Verify results */
8978         bool test_result = true;
8979
8980         const glw::GLuint* results =
8981                 (glw::GLuint*)gl.mapBufferRange(GL_ATOMIC_COUNTER_BUFFER, 0 /* offset */, buffer_data_size, GL_MAP_READ_BIT);
8982         GLU_EXPECT_NO_ERROR(gl.getError(), "MapBufferRange");
8983
8984         /* Anything before start position should be 0 */
8985         for (size_t i = 0; i < start_pos; ++i)
8986         {
8987                 if (0 != results[i])
8988                 {
8989                         test_result = false;
8990                         break;
8991                 }
8992         }
8993
8994         /* Anything from start_pos should be incremented by 1 */
8995         int diff = 0;
8996         for (size_t i = 0; i < n_entries; ++i)
8997         {
8998                 /* Tesselation evaluation can be called several times
8999                  In here, check the increment is consistent over all results.
9000                  */
9001                 if (tested_shader_type == TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE)
9002                 {
9003                         if (i == 0)
9004                         {
9005                                 diff = static_cast<int>(results[i + start_pos]) - static_cast<int>(i);
9006                                 if (diff <= 0)
9007                                 {
9008                                         test_result = false;
9009                                         break;
9010                                 }
9011                         }
9012                         else if ((static_cast<int>(results[i + start_pos]) - static_cast<int>(i)) != diff)
9013                         {
9014                                 test_result = false;
9015                                 break;
9016                         }
9017                 }
9018                 else
9019                 {
9020                         if (i + 1 != results[i + start_pos])
9021                         {
9022                                 test_result = false;
9023                                 break;
9024                         }
9025                 }
9026         }
9027
9028         gl.unmapBuffer(GL_ATOMIC_COUNTER_BUFFER);
9029         GLU_EXPECT_NO_ERROR(gl.getError(), "UnmapBuffer");
9030
9031         /* Deallocate any resources used. */
9032         gl.deleteBuffers(1, &buffer_object_id);
9033         this->delete_objects();
9034
9035         if (false == test_result)
9036         {
9037                 TCU_FAIL("Invalid results.");
9038         }
9039 }
9040
9041 /* Generates the shader source code for the SubroutineFunctionCalls1
9042  * array tests, attempts to build and execute test program
9043  *
9044  * @tparam API               Tested API descriptor
9045  *
9046  * @param tested_shader_type The type of shader that is being tested
9047  */
9048 template <class API>
9049 void SubroutineFunctionCalls1<API>::test_shader_compilation(
9050         typename TestCaseBase<API>::TestShaderType tested_shader_type)
9051 {
9052         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
9053                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
9054                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
9055                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4 };
9056         static const size_t num_var_types_es = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
9057
9058         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
9059                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
9060                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
9061                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4,  VAR_TYPE_DOUBLE,
9062                                                                                                                          VAR_TYPE_DMAT2, VAR_TYPE_DMAT3, VAR_TYPE_DMAT4 };
9063         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
9064
9065         const std::string iteration_loop_end = "                               }\n"
9066                                                                                    "                           }\n"
9067                                                                                    "                        }\n"
9068                                                                                    "                    }\n"
9069                                                                                    "                }\n"
9070                                                                                    "            }\n"
9071                                                                                    "        }\n"
9072                                                                                    "    }\n";
9073         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
9074                                                                                          "    {\n"
9075                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
9076                                                                                          "        {\n"
9077                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
9078                                                                                          "            {\n"
9079                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
9080                                                                                          "                {\n"
9081                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
9082                                                                                          "                    {\n"
9083                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
9084                                                                                          "                        {\n"
9085                                                                                          "                           for (uint g = 0u; g < 2u; g++)\n"
9086                                                                                          "                           {\n"
9087                                                                                          "                               for (uint h = 0u; h < 2u; h++)\n"
9088                                                                                          "                               {\n";
9089         const glcts::test_var_type* var_types_set = var_types_set_es;
9090         size_t                                          num_var_types = num_var_types_es;
9091         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
9092
9093         if (API::USE_DOUBLE)
9094         {
9095                 var_types_set = var_types_set_gl;
9096                 num_var_types = num_var_types_gl;
9097         }
9098
9099         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
9100         {
9101                 _supported_variable_types_map_const_iterator var_iterator =
9102                         supported_variable_types_map.find(var_types_set[var_type_index]);
9103
9104                 if (var_iterator != supported_variable_types_map.end())
9105                 {
9106                         std::string iterator_declaration = "    " + var_iterator->second.iterator_type +
9107                                                                                            " iterator = " + var_iterator->second.iterator_initialization + ";\n";
9108
9109                         std::string function_definition;
9110                         std::string function_use;
9111                         std::string verification;
9112
9113                         function_definition += "// Subroutine types\n"
9114                                                                    "subroutine void out_routine_type(out ";
9115                         function_definition += var_iterator->second.type;
9116                         function_definition += " output_array[2][2][2][2][2][2][2][2]);\n\n"
9117                                                                    "// Subroutine definitions\n"
9118                                                                    "subroutine(out_routine_type) void original_routine(out ";
9119                         function_definition += var_iterator->second.type;
9120                         function_definition += " output_array[2][2][2][2][2][2][2][2]) {\n";
9121                         function_definition += iterator_declaration;
9122                         function_definition += iteration_loop_start;
9123                         function_definition += "                                   output_array[a][b][c][d][e][f][g][h] = " +
9124                                                                    var_iterator->second.variable_type_initializer1 + ";\n";
9125                         function_definition +=
9126                                 "                                   iterator += " + var_iterator->second.iterator_type + "(1);\n";
9127                         function_definition += iteration_loop_end;
9128                         function_definition += "}\n\n";
9129                         function_definition += "subroutine(out_routine_type) void new_routine(out ";
9130                         function_definition += var_iterator->second.type;
9131                         function_definition += " output_array[2][2][2][2][2][2][2][2]) {\n";
9132                         function_definition += iterator_declaration;
9133                         function_definition += iteration_loop_start;
9134                         function_definition += "                                   output_array[a][b][c][d][e][f][g][h] = " +
9135                                                                    var_iterator->second.variable_type_initializer1 + ";\n";
9136                         function_definition +=
9137                                 "                                   iterator -= " + var_iterator->second.iterator_type + "(1);\n";
9138                         function_definition += iteration_loop_end;
9139                         function_definition += "}\n\n"
9140                                                                    "// Subroutine uniform\n"
9141                                                                    "subroutine uniform out_routine_type routine;\n";
9142
9143                         function_use = "    " + var_iterator->second.type + " my_array[2][2][2][2][2][2][2][2];\n";
9144                         function_use += "    routine(my_array);";
9145
9146                         verification = iterator_declaration;
9147                         verification += "    float result = 1.0;\n";
9148                         verification += iteration_loop_start;
9149                         verification += "                                   if (my_array[a][b][c][d][e][f][g][h] " +
9150                                                         var_iterator->second.specific_element +
9151                                                         " != iterator)\n"
9152                                                         "                                   {\n"
9153                                                         "                                       result = 0.0;\n"
9154                                                         "                                   }\n"
9155                                                         "                                   iterator += " +
9156                                                         var_iterator->second.iterator_type + "(1);\n";
9157                         verification += iteration_loop_end;
9158
9159                         if (false == test_compute)
9160                         {
9161                                 execute_draw_test(tested_shader_type, function_definition, function_use, verification, false, true);
9162                                 execute_draw_test(tested_shader_type, function_definition, function_use, verification, true, false);
9163                         }
9164                         else
9165                         {
9166                                 execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, false, true);
9167                                 execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, true, false);
9168                         }
9169
9170                         /* Deallocate any resources used. */
9171                         this->delete_objects();
9172                 } /* if var_type iterator found */
9173                 else
9174                 {
9175                         TCU_FAIL("Type not found.");
9176                 }
9177         } /* for (int var_type_index = 0; ...) */
9178 }
9179
9180 /** Executes test for compute program
9181  *
9182  * @tparam API                  Tested API descriptor
9183  *
9184  * @param tested_shader_type    The type of shader that is being tested
9185  * @param function_definition   Definition used to prepare shader
9186  * @param function_use          Use of definition
9187  * @param verification          Result verification
9188  * @param use_original          Selects if "original_routine" - true or "new_routine" is choosen
9189  * @param expect_invalid_result Does test expects invalid results
9190  **/
9191 template <class API>
9192 void SubroutineFunctionCalls1<API>::execute_dispatch_test(typename TestCaseBase<API>::TestShaderType tested_shader_type,
9193                                                                                                                   const std::string& function_definition,
9194                                                                                                                   const std::string& function_use,
9195                                                                                                                   const std::string& verification, bool use_original,
9196                                                                                                                   bool expect_invalid_result)
9197 {
9198         const std::string& compute_shader_source =
9199                 prepare_compute_shader(tested_shader_type, function_definition, function_use, verification);
9200         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
9201
9202         this->execute_positive_test(empty_string, empty_string, empty_string, empty_string, empty_string,
9203                                                                 compute_shader_source, false, false);
9204
9205         /* We are now ready to verify whether the returned size is correct. */
9206         unsigned char     buffer[4]                      = { 0 };
9207         glw::GLuint                framebuffer_object_id = 0;
9208         glw::GLint                 location                              = -1;
9209         glw::GLuint                routine_index                 = -1;
9210         glw::GLuint                routine_location              = -1;
9211         const glw::GLchar* routine_name                  = "original_routine";
9212         const glw::GLenum  shader_type                   = GL_COMPUTE_SHADER;
9213         glw::GLuint                texture_object_id     = 0;
9214
9215         if (false == use_original)
9216         {
9217                 routine_name = "new_routine";
9218         }
9219
9220         gl.useProgram(this->program_object_id);
9221         GLU_EXPECT_NO_ERROR(gl.getError(), "glUseProgram() failed.");
9222
9223         /* Select subroutine */
9224         routine_index = gl.getSubroutineIndex(this->program_object_id, shader_type, routine_name);
9225         GLU_EXPECT_NO_ERROR(gl.getError(), "glGetSubroutineIndex() failed.");
9226
9227         routine_location = gl.getSubroutineUniformLocation(this->program_object_id, shader_type, "routine");
9228         GLU_EXPECT_NO_ERROR(gl.getError(), "glGetSubroutineUniformLocation() failed.");
9229
9230         if (0 != routine_location)
9231         {
9232                 TCU_FAIL("Subroutine location is invalid");
9233         }
9234
9235         gl.uniformSubroutinesuiv(shader_type, 1, &routine_index);
9236         GLU_EXPECT_NO_ERROR(gl.getError(), "glUniformSubroutinesuiv() failed.");
9237
9238         /* Prepare texture */
9239         gl.genTextures(1, &texture_object_id);
9240         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenTextures() failed.");
9241
9242         gl.bindTexture(GL_TEXTURE_2D, texture_object_id);
9243         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindTexture() failed.");
9244
9245         gl.texStorage2D(GL_TEXTURE_2D, 1, GL_RGBA8, 1, 1);
9246         GLU_EXPECT_NO_ERROR(gl.getError(), "glTexStorage2D() failed.");
9247
9248         gl.bindImageTexture(0 /* image unit */, texture_object_id, 0 /* level */, GL_FALSE /* layered */, 0 /* layer */,
9249                                                 GL_WRITE_ONLY, GL_RGBA8);
9250         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindImageTexture() failed.");
9251
9252         location = gl.getUniformLocation(this->program_object_id, "uni_image");
9253         GLU_EXPECT_NO_ERROR(gl.getError(), "glGetUniformLocation() failed.");
9254
9255         if (-1 == location)
9256         {
9257                 TCU_FAIL("Uniform is inactive");
9258         }
9259
9260         gl.uniform1i(location, 0 /* image unit */);
9261         GLU_EXPECT_NO_ERROR(gl.getError(), "glUniform1i() failed.");
9262
9263         /* Execute */
9264         gl.dispatchCompute(1, 1, 1);
9265         GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
9266
9267         /* Verify */
9268         gl.genFramebuffers(1, &framebuffer_object_id);
9269         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenFramebuffers() failed.");
9270
9271         gl.bindFramebuffer(GL_FRAMEBUFFER, framebuffer_object_id);
9272         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindFramebuffer() failed.");
9273
9274         gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texture_object_id, 0);
9275         GLU_EXPECT_NO_ERROR(gl.getError(), "glFramebufferTexture2D() failed.");
9276
9277         gl.viewport(0, 0, 1, 1);
9278         GLU_EXPECT_NO_ERROR(gl.getError(), "glViewport() failed.");
9279
9280         gl.readBuffer(GL_COLOR_ATTACHMENT0);
9281         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadBuffer() failed.");
9282
9283         gl.readPixels(0, 0, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
9284         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadPixels() failed.");
9285
9286         if ((buffer[0] != 255) != expect_invalid_result)
9287         {
9288                 TCU_FAIL("Invalid result was returned.");
9289         }
9290
9291         /* Delete generated objects. */
9292         gl.deleteTextures(1, &texture_object_id);
9293         gl.deleteFramebuffers(1, &framebuffer_object_id);
9294         GLU_EXPECT_NO_ERROR(gl.getError(), "An error ocurred while deleting generated objects.");
9295 }
9296
9297 /** Executes test for draw program
9298  *
9299  * @tparam API                  Tested API descriptor
9300  *
9301  * @param tested_shader_type    The type of shader that is being tested
9302  * @param function_definition   Definition used to prepare shader
9303  * @param function_use          Use of definition
9304  * @param verification          Result verification
9305  * @param use_original          Selects if "original_routine" - true or "new_routine" is choosen
9306  * @param expect_invalid_result Does test expects invalid results
9307  **/
9308 template <class API>
9309 void SubroutineFunctionCalls1<API>::execute_draw_test(typename TestCaseBase<API>::TestShaderType tested_shader_type,
9310                                                                                                           const std::string&                                             function_definition,
9311                                                                                                           const std::string& function_use, const std::string& verification,
9312                                                                                                           bool use_original, bool expect_invalid_result)
9313 {
9314         const glw::Functions& gl = this->context_id.getRenderContext().getFunctions();
9315
9316         if (API::USE_ALL_SHADER_STAGES)
9317         {
9318                 const std::string& compute_shader_source = empty_string;
9319                 const std::string& fragment_shader_source =
9320                         this->prepare_fragment_shader(tested_shader_type, function_definition, function_use, verification);
9321                 const std::string& geometry_shader_source =
9322                         this->prepare_geometry_shader(tested_shader_type, function_definition, function_use, verification);
9323                 const std::string& tess_ctrl_shader_source =
9324                         this->prepare_tess_ctrl_shader(tested_shader_type, function_definition, function_use, verification);
9325                 const std::string& tess_eval_shader_source =
9326                         this->prepare_tess_eval_shader(tested_shader_type, function_definition, function_use, verification);
9327                 const std::string& vertex_shader_source =
9328                         this->prepare_vertex_shader(tested_shader_type, function_definition, function_use, verification);
9329
9330                 switch (tested_shader_type)
9331                 {
9332                 case TestCaseBase<API>::VERTEX_SHADER_TYPE: /* Fall through */
9333                 case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
9334                         this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
9335                         break;
9336
9337                 case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
9338                 case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
9339                 case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
9340                 case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
9341                         this->execute_positive_test(vertex_shader_source, tess_ctrl_shader_source, tess_eval_shader_source,
9342                                                                                 geometry_shader_source, fragment_shader_source, compute_shader_source, false,
9343                                                                                 false);
9344                         break;
9345
9346                 default:
9347                         TCU_FAIL("Invalid enum");
9348                         break;
9349                 }
9350         }
9351         else
9352         {
9353                 const std::string& fragment_shader_source =
9354                         this->prepare_fragment_shader(tested_shader_type, function_definition, function_use, verification);
9355                 const std::string& vertex_shader_source =
9356                         this->prepare_vertex_shader(tested_shader_type, function_definition, function_use, verification);
9357
9358                 this->execute_positive_test(vertex_shader_source, fragment_shader_source, false, false);
9359         }
9360
9361         /* We are now ready to verify whether the returned size is correct. */
9362         unsigned char     buffer[4]                      = { 0 };
9363         glw::GLuint                framebuffer_object_id = 0;
9364         glw::GLuint                routine_index                 = -1;
9365         glw::GLuint                routine_location              = -1;
9366         const glw::GLchar* routine_name                  = "original_routine";
9367         glw::GLenum                shader_type                   = 0;
9368         glw::GLuint                texture_object_id     = 0;
9369         glw::GLuint                vao_id                                = 0;
9370
9371         switch (tested_shader_type)
9372         {
9373         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
9374                 shader_type = GL_FRAGMENT_SHADER;
9375                 break;
9376         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
9377                 shader_type = GL_VERTEX_SHADER;
9378                 break;
9379         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
9380                 shader_type = GL_COMPUTE_SHADER;
9381                 break;
9382         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
9383                 shader_type = GL_GEOMETRY_SHADER;
9384                 break;
9385         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
9386                 shader_type = GL_TESS_CONTROL_SHADER;
9387                 break;
9388         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
9389                 shader_type = GL_TESS_EVALUATION_SHADER;
9390                 break;
9391         default:
9392                 TCU_FAIL("Invalid shader type");
9393                 break;
9394         }
9395
9396         if (false == use_original)
9397         {
9398                 routine_name = "new_routine";
9399         }
9400
9401         gl.useProgram(this->program_object_id);
9402         GLU_EXPECT_NO_ERROR(gl.getError(), "glUseProgram() failed.");
9403
9404         /* Select subroutine */
9405         routine_index = gl.getSubroutineIndex(this->program_object_id, shader_type, routine_name);
9406         GLU_EXPECT_NO_ERROR(gl.getError(), "glGetSubroutineIndex() failed.");
9407
9408         routine_location = gl.getSubroutineUniformLocation(this->program_object_id, shader_type, "routine");
9409         GLU_EXPECT_NO_ERROR(gl.getError(), "glGetSubroutineUniformLocation() failed.");
9410
9411         if (0 != routine_location)
9412         {
9413                 TCU_FAIL("Subroutine location is invalid");
9414         }
9415
9416         gl.uniformSubroutinesuiv(shader_type, 1, &routine_index);
9417         GLU_EXPECT_NO_ERROR(gl.getError(), "glUniformSubroutinesuiv() failed.");
9418
9419         /* Prepre texture */
9420         assert(0 == texture_object_id);
9421         gl.genTextures(1, &texture_object_id);
9422         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenTextures() failed.");
9423
9424         gl.bindTexture(GL_TEXTURE_2D, texture_object_id);
9425         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindTexture() failed.");
9426
9427         gl.texStorage2D(GL_TEXTURE_2D, 1, GL_RGBA8, 1, 1);
9428         GLU_EXPECT_NO_ERROR(gl.getError(), "glTexStorage2D() failed.");
9429
9430         /* Prepare framebuffer */
9431         assert(0 == framebuffer_object_id);
9432         gl.genFramebuffers(1, &framebuffer_object_id);
9433         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenFramebuffers() failed.");
9434
9435         gl.bindFramebuffer(GL_FRAMEBUFFER, framebuffer_object_id);
9436         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindFramebuffer() failed.");
9437
9438         gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texture_object_id, 0);
9439         GLU_EXPECT_NO_ERROR(gl.getError(), "glFramebufferTexture2D() failed.");
9440
9441         gl.viewport(0, 0, 1, 1);
9442         GLU_EXPECT_NO_ERROR(gl.getError(), "glViewport() failed.");
9443
9444         /* Set VAO */
9445         assert(0 == vao_id);
9446         gl.genVertexArrays(1, &vao_id);
9447         GLU_EXPECT_NO_ERROR(gl.getError(), "glGenVertexArrays() failed.");
9448
9449         gl.bindVertexArray(vao_id);
9450         GLU_EXPECT_NO_ERROR(gl.getError(), "glBindVertexArray() failed.");
9451
9452         switch (tested_shader_type)
9453         {
9454         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE: /* Fall through */
9455         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
9456                 gl.drawArrays(GL_TRIANGLE_FAN, 0, 4);
9457                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
9458                 break;
9459
9460         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
9461         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
9462                 /* Tesselation patch set up */
9463                 gl.patchParameteri(GL_PATCH_VERTICES, 1);
9464                 GLU_EXPECT_NO_ERROR(gl.getError(), "PatchParameteri");
9465
9466                 gl.drawArrays(GL_PATCHES, 0, 1);
9467                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
9468                 break;
9469
9470         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
9471                 gl.drawArrays(GL_POINTS, 0, 1);
9472                 GLU_EXPECT_NO_ERROR(gl.getError(), "glDrawArrays() failed.");
9473                 break;
9474
9475         default:
9476                 TCU_FAIL("Invalid enum");
9477                 break;
9478         }
9479
9480         /* Verify */
9481         gl.readBuffer(GL_COLOR_ATTACHMENT0);
9482         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadBuffer() failed.");
9483
9484         gl.readPixels(0, 0, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
9485         GLU_EXPECT_NO_ERROR(gl.getError(), "glReadPixels() failed.");
9486
9487         const bool result = ((buffer[0] != 255) == expect_invalid_result);
9488
9489         /* Delete generated objects. */
9490         gl.useProgram(0);
9491         gl.bindTexture(GL_TEXTURE_2D, 0);
9492         gl.bindFramebuffer(GL_FRAMEBUFFER, 0);
9493         gl.bindVertexArray(0);
9494
9495         gl.deleteProgram(this->program_object_id);
9496         this->program_object_id = 0;
9497
9498         gl.deleteTextures(1, &texture_object_id);
9499         texture_object_id = 0;
9500
9501         gl.deleteFramebuffers(1, &framebuffer_object_id);
9502         framebuffer_object_id = 0;
9503
9504         gl.deleteVertexArrays(1, &vao_id);
9505         vao_id = 0;
9506
9507         GLU_EXPECT_NO_ERROR(gl.getError(), "An error ocurred while deleting generated objects.");
9508
9509         if (!result)
9510         {
9511                 TCU_FAIL("Invalid result was returned.");
9512         }
9513 }
9514
9515 /** Prepare shader
9516  *
9517  * @tparam API               Tested API descriptor
9518  *
9519  * @param tested_shader_type    The type of shader that is being tested
9520  * @param function_definition   Definition used to prepare shader
9521  * @param function_use          Use of definition
9522  * @param verification          Result verification
9523  **/
9524 template <class API>
9525 std::string SubroutineFunctionCalls1<API>::prepare_compute_shader(
9526         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
9527         const std::string& function_use, const std::string& verification)
9528 {
9529         std::string compute_shader_source;
9530
9531         if (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type)
9532         {
9533                 compute_shader_source = "writeonly uniform image2D uni_image;\n"
9534                                                                 "\n";
9535
9536                 /* User-defined function definition. */
9537                 compute_shader_source += function_definition;
9538                 compute_shader_source += "\n\n";
9539
9540                 /* Main function definition. */
9541                 compute_shader_source += shader_start;
9542                 compute_shader_source += function_use;
9543                 compute_shader_source += "\n\n";
9544                 compute_shader_source += verification;
9545                 compute_shader_source += "\n\n";
9546                 compute_shader_source += "\n"
9547                                                                  "    imageStore(uni_image, ivec2(gl_GlobalInvocationID.xy), vec4(result, 0, 0, 0));\n"
9548                                                                  "}\n"
9549                                                                  "\n";
9550         }
9551
9552         return compute_shader_source;
9553 }
9554
9555 /** Prepare shader
9556  *
9557  * @tparam API               Tested API descriptor
9558  *
9559  * @param tested_shader_type    The type of shader that is being tested
9560  * @param function_definition   Definition used to prepare shader
9561  * @param function_use          Use of definition
9562  * @param verification          Result verification
9563  **/
9564 template <class API>
9565 std::string SubroutineFunctionCalls1<API>::prepare_fragment_shader(
9566         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
9567         const std::string& function_use, const std::string& verification)
9568 {
9569         std::string fragment_shader_source;
9570
9571         switch (tested_shader_type)
9572         {
9573         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
9574                 break;
9575
9576         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
9577                 fragment_shader_source = "out vec4 colour;\n\n";
9578
9579                 /* User-defined function definition. */
9580                 fragment_shader_source += function_definition;
9581                 fragment_shader_source += "\n\n";
9582
9583                 /* Main function definition. */
9584                 fragment_shader_source += shader_start;
9585                 fragment_shader_source += function_use;
9586                 fragment_shader_source += "\n\n";
9587                 fragment_shader_source += verification;
9588                 fragment_shader_source += "\n\n";
9589                 fragment_shader_source += "    colour = vec4(result);\n";
9590                 fragment_shader_source += shader_end;
9591                 break;
9592
9593         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
9594         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
9595         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE: /* Fall through */
9596         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
9597                 fragment_shader_source = "in float fs_result;\n\n"
9598                                                                  "out vec4 colour;\n\n"
9599                                                                  "void main()\n"
9600                                                                  "{\n"
9601                                                                  "    colour =  vec4(fs_result);\n"
9602                                                                  "}\n"
9603                                                                  "\n";
9604                 break;
9605
9606         default:
9607                 TCU_FAIL("Unrecognized shader object type.");
9608                 break;
9609         }
9610
9611         return fragment_shader_source;
9612 }
9613
9614 /** Prepare shader
9615  *
9616  * @tparam API               Tested API descriptor
9617  *
9618  * @param tested_shader_type    The type of shader that is being tested
9619  * @param function_definition   Definition used to prepare shader
9620  * @param function_use          Use of definition
9621  * @param verification          Result verification
9622  **/
9623 template <class API>
9624 std::string SubroutineFunctionCalls1<API>::prepare_geometry_shader(
9625         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
9626         const std::string& function_use, const std::string& verification)
9627 {
9628         std::string geometry_shader_source;
9629
9630         switch (tested_shader_type)
9631         {
9632         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
9633         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE: /* Fall through */
9634         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
9635                 break;
9636
9637         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE: /* Fall through */
9638         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
9639                 geometry_shader_source = "layout(points)                           in;\n"
9640                                                                  "layout(triangle_strip, max_vertices = 4) out;\n"
9641                                                                  "\n"
9642                                                                  "in  float tes_result[];\n"
9643                                                                  "out float fs_result;\n"
9644                                                                  "\n"
9645                                                                  "void main()\n"
9646                                                                  "{\n"
9647                                                                  "    gl_Position  = vec4(-1, -1, 0, 1);\n"
9648                                                                  "    fs_result    = tes_result[0];\n"
9649                                                                  "    EmitVertex();\n"
9650                                                                  "    gl_Position  = vec4(-1, 1, 0, 1);\n"
9651                                                                  "    fs_result    = tes_result[0];\n"
9652                                                                  "    EmitVertex();\n"
9653                                                                  "    gl_Position  = vec4(1, -1, 0, 1);\n"
9654                                                                  "    fs_result    = tes_result[0];\n"
9655                                                                  "    EmitVertex();\n"
9656                                                                  "    gl_Position  = vec4(1, 1, 0, 1);\n"
9657                                                                  "    fs_result    = tes_result[0];\n"
9658                                                                  "    EmitVertex();\n"
9659                                                                  "}\n";
9660                 break;
9661
9662         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
9663                 geometry_shader_source = "layout(points)                           in;\n"
9664                                                                  "layout(triangle_strip, max_vertices = 4) out;\n"
9665                                                                  "\n"
9666                                                                  "out float fs_result;\n"
9667                                                                  "\n";
9668
9669                 /* User-defined function definition. */
9670                 geometry_shader_source += function_definition;
9671                 geometry_shader_source += "\n\n";
9672
9673                 /* Main function definition. */
9674                 geometry_shader_source += shader_start;
9675                 geometry_shader_source += function_use;
9676                 geometry_shader_source += "\n\n";
9677                 geometry_shader_source += verification;
9678                 geometry_shader_source += "\n\n";
9679                 geometry_shader_source += "\n    gl_Position  = vec4(-1, -1, 0, 1);\n"
9680                                                                   "    fs_result    = result;\n"
9681                                                                   "    EmitVertex();\n"
9682                                                                   "    gl_Position  = vec4(-1, 1, 0, 1);\n"
9683                                                                   "    fs_result    = result;\n"
9684                                                                   "    EmitVertex();\n"
9685                                                                   "    gl_Position  = vec4(1, -1, 0, 1);\n"
9686                                                                   "    fs_result    = result;\n"
9687                                                                   "    EmitVertex();\n"
9688                                                                   "    gl_Position  = vec4(1, 1, 0, 1);\n"
9689                                                                   "    fs_result    = result;\n"
9690                                                                   "    EmitVertex();\n"
9691                                                                   "}\n";
9692                 break;
9693
9694         default:
9695                 TCU_FAIL("Unrecognized shader object type.");
9696                 break;
9697         }
9698
9699         return geometry_shader_source;
9700 }
9701
9702 /** Prepare shader
9703  *
9704  * @tparam API               Tested API descriptor
9705  *
9706  * @param tested_shader_type    The type of shader that is being tested
9707  * @param function_definition   Definition used to prepare shader
9708  * @param function_use          Use of definition
9709  * @param verification          Result verification
9710  **/
9711 template <class API>
9712 std::string SubroutineFunctionCalls1<API>::prepare_tess_ctrl_shader(
9713         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
9714         const std::string& function_use, const std::string& verification)
9715 {
9716         std::string tess_ctrl_shader_source;
9717
9718         switch (tested_shader_type)
9719         {
9720         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
9721         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
9722         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
9723         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
9724                 break;
9725
9726         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
9727                 tess_ctrl_shader_source = "layout(vertices = 1) out;\n"
9728                                                                   "\n"
9729                                                                   "out float tcs_result[];\n"
9730                                                                   "\n";
9731
9732                 /* User-defined function definition. */
9733                 tess_ctrl_shader_source += function_definition;
9734                 tess_ctrl_shader_source += "\n\n";
9735
9736                 /* Main function definition. */
9737                 tess_ctrl_shader_source += shader_start;
9738                 tess_ctrl_shader_source += function_use;
9739                 tess_ctrl_shader_source += "\n\n";
9740                 tess_ctrl_shader_source += verification;
9741                 tess_ctrl_shader_source += "\n\n";
9742                 tess_ctrl_shader_source += "    tcs_result[gl_InvocationID] = result;\n"
9743                                                                    "\n"
9744                                                                    "    gl_TessLevelOuter[0] = 1.0;\n"
9745                                                                    "    gl_TessLevelOuter[1] = 1.0;\n"
9746                                                                    "    gl_TessLevelOuter[2] = 1.0;\n"
9747                                                                    "    gl_TessLevelOuter[3] = 1.0;\n"
9748                                                                    "    gl_TessLevelInner[0] = 1.0;\n"
9749                                                                    "    gl_TessLevelInner[1] = 1.0;\n"
9750                                                                    "}\n";
9751                 break;
9752
9753         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
9754                 tess_ctrl_shader_source = default_tc_shader_source;
9755                 break;
9756
9757         default:
9758                 TCU_FAIL("Unrecognized shader object type.");
9759                 break;
9760         }
9761
9762         return tess_ctrl_shader_source;
9763 }
9764
9765 /** Prepare shader
9766  *
9767  * @tparam API               Tested API descriptor
9768  *
9769  * @param tested_shader_type    The type of shader that is being tested
9770  * @param function_definition   Definition used to prepare shader
9771  * @param function_use          Use of definition
9772  * @param verification          Result verification
9773  **/
9774 template <class API>
9775 std::string SubroutineFunctionCalls1<API>::prepare_tess_eval_shader(
9776         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
9777         const std::string& function_use, const std::string& verification)
9778 {
9779         std::string tess_eval_shader_source;
9780
9781         switch (tested_shader_type)
9782         {
9783         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
9784         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
9785         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
9786         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
9787                 break;
9788
9789         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
9790                 tess_eval_shader_source = "layout(isolines, point_mode) in;\n"
9791                                                                   "\n"
9792                                                                   "in  float tcs_result[];\n"
9793                                                                   "out float tes_result;\n"
9794                                                                   "\n"
9795                                                                   "void main()\n"
9796                                                                   "{\n"
9797                                                                   "    tes_result = tcs_result[0];\n"
9798                                                                   "}\n";
9799                 break;
9800
9801         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
9802                 tess_eval_shader_source = "layout(isolines, point_mode) in;\n"
9803                                                                   "\n"
9804                                                                   "out float tes_result;\n"
9805                                                                   "\n";
9806
9807                 /* User-defined function definition. */
9808                 tess_eval_shader_source += function_definition;
9809                 tess_eval_shader_source += "\n\n";
9810
9811                 /* Main function definition. */
9812                 tess_eval_shader_source += shader_start;
9813                 tess_eval_shader_source += function_use;
9814                 tess_eval_shader_source += "\n\n";
9815                 tess_eval_shader_source += verification;
9816                 tess_eval_shader_source += "\n\n";
9817                 tess_eval_shader_source += "    tes_result = result;\n"
9818                                                                    "}\n";
9819                 break;
9820
9821         default:
9822                 TCU_FAIL("Unrecognized shader object type.");
9823                 break;
9824         }
9825
9826         return tess_eval_shader_source;
9827 }
9828
9829 /** Prepare shader
9830  *
9831  * @tparam API               Tested API descriptor
9832  *
9833  * @param tested_shader_type    The type of shader that is being tested
9834  * @param function_definition   Definition used to prepare shader
9835  * @param function_use          Use of definition
9836  * @param verification          Result verification
9837  **/
9838 template <class API>
9839 std::string SubroutineFunctionCalls1<API>::prepare_vertex_shader(
9840         typename TestCaseBase<API>::TestShaderType tested_shader_type, const std::string& function_definition,
9841         const std::string& function_use, const std::string& verification)
9842 {
9843         std::string vertex_shader_source;
9844
9845         switch (tested_shader_type)
9846         {
9847         case TestCaseBase<API>::COMPUTE_SHADER_TYPE:
9848                 break;
9849
9850         case TestCaseBase<API>::FRAGMENT_SHADER_TYPE:
9851                 vertex_shader_source = "/** GL_TRIANGLE_FAN-type quad vertex data. */\n"
9852                                                            "const vec4 vertex_positions[4] = vec4[4](vec4( 1.0, -1.0, 0.0, 1.0),\n"
9853                                                            "                                         vec4(-1.0, -1.0, 0.0, 1.0),\n"
9854                                                            "                                         vec4(-1.0,  1.0, 0.0, 1.0),\n"
9855                                                            "                                         vec4( 1.0,  1.0, 0.0, 1.0) );\n"
9856                                                            "\n"
9857                                                            "void main()\n"
9858                                                            "{\n"
9859                                                            "    gl_Position = vertex_positions[gl_VertexID];"
9860                                                            "}\n\n";
9861                 break;
9862
9863         case TestCaseBase<API>::GEOMETRY_SHADER_TYPE:
9864         case TestCaseBase<API>::TESSELATION_CONTROL_SHADER_TYPE:
9865         case TestCaseBase<API>::TESSELATION_EVALUATION_SHADER_TYPE:
9866                 vertex_shader_source = default_vertex_shader_source;
9867                 break;
9868
9869         case TestCaseBase<API>::VERTEX_SHADER_TYPE:
9870                 /* Vertex shader source. */
9871                 vertex_shader_source = "out float fs_result;\n\n";
9872                 vertex_shader_source += "/** GL_TRIANGLE_FAN-type quad vertex data. */\n"
9873                                                                 "const vec4 vertex_positions[4] = vec4[4](vec4( 1.0, -1.0, 0.0, 1.0),\n"
9874                                                                 "                                         vec4(-1.0, -1.0, 0.0, 1.0),\n"
9875                                                                 "                                         vec4(-1.0,  1.0, 0.0, 1.0),\n"
9876                                                                 "                                         vec4( 1.0,  1.0, 0.0, 1.0) );\n\n";
9877
9878                 /* User-defined function definition. */
9879                 vertex_shader_source += function_definition;
9880                 vertex_shader_source += "\n\n";
9881
9882                 /* Main function definition. */
9883                 vertex_shader_source += shader_start;
9884                 vertex_shader_source += function_use;
9885                 vertex_shader_source += "\n\n";
9886                 vertex_shader_source += verification;
9887                 vertex_shader_source += "\n\n";
9888                 vertex_shader_source += "    fs_result   = result;\n"
9889                                                                 "    gl_Position = vertex_positions[gl_VertexID];\n";
9890                 vertex_shader_source += shader_end;
9891                 break;
9892
9893         default:
9894                 TCU_FAIL("Unrecognized shader object type.");
9895                 break;
9896         }
9897
9898         return vertex_shader_source;
9899 }
9900
9901 /* Generates the shader source code for the InteractionFunctionCalls2
9902  * array tests, and attempts to build and execute test program.
9903  *
9904  * @tparam API               Tested API descriptor
9905  *
9906  * @param tested_shader_type The type of shader that is being tested
9907  */
9908 template <class API>
9909 void SubroutineFunctionCalls2<API>::test_shader_compilation(
9910         typename TestCaseBase<API>::TestShaderType tested_shader_type)
9911 {
9912         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
9913                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
9914                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
9915                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4 };
9916         static const size_t num_var_types_es = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
9917
9918         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
9919                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
9920                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
9921                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4,  VAR_TYPE_DOUBLE,
9922                                                                                                                          VAR_TYPE_DMAT2, VAR_TYPE_DMAT3, VAR_TYPE_DMAT4 };
9923         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
9924
9925         const std::string iteration_loop_end = "                               }\n"
9926                                                                                    "                           }\n"
9927                                                                                    "                        }\n"
9928                                                                                    "                    }\n"
9929                                                                                    "                }\n"
9930                                                                                    "            }\n"
9931                                                                                    "        }\n"
9932                                                                                    "    }\n";
9933         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
9934                                                                                          "    {\n"
9935                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
9936                                                                                          "        {\n"
9937                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
9938                                                                                          "            {\n"
9939                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
9940                                                                                          "                {\n"
9941                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
9942                                                                                          "                    {\n"
9943                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
9944                                                                                          "                        {\n"
9945                                                                                          "                           for (uint g = 0u; g < 2u; g++)\n"
9946                                                                                          "                           {\n"
9947                                                                                          "                               for (uint h = 0u; h < 2u; h++)\n"
9948                                                                                          "                               {\n";
9949         const std::string multiplier_array = "const int[] multiplier_array = int[]( 1,  2,  3,  4,  5,  6,  7,  8,\n"
9950                                                                                  "                                     11, 12, 13, 14, 15, 16, 17, 18,\n"
9951                                                                                  "                                     21, 22, 23, 24, 25, 26, 27, 28,\n"
9952                                                                                  "                                     31, 32, 33, 34, 35, 36, 37, 38,\n"
9953                                                                                  "                                     41, 42, 43, 44, 45, 46, 47, 48,\n"
9954                                                                                  "                                     51, 52, 53, 54, 55, 56, 57, 58,\n"
9955                                                                                  "                                     61, 62, 63, 64, 65, 66, 67, 68,\n"
9956                                                                                  "                                     71, 72, 73, 74, 75, 76, 77, 78,\n"
9957                                                                                  "                                     81, 82, 83, 84, 85, 86, 87, 88);\n";
9958         const glcts::test_var_type* var_types_set = var_types_set_es;
9959         size_t                                          num_var_types = num_var_types_es;
9960         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
9961
9962         if (API::USE_DOUBLE)
9963         {
9964                 var_types_set = var_types_set_gl;
9965                 num_var_types = num_var_types_gl;
9966         }
9967
9968         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
9969         {
9970                 _supported_variable_types_map_const_iterator var_iterator =
9971                         supported_variable_types_map.find(var_types_set[var_type_index]);
9972
9973                 if (var_iterator != supported_variable_types_map.end())
9974                 {
9975                         std::string function_definition;
9976                         std::string function_use;
9977                         std::string verification;
9978
9979                         function_definition += multiplier_array;
9980
9981                         function_definition += "// Subroutine types\n"
9982                                                                    "subroutine void inout_routine_type(inout ";
9983                         function_definition += var_iterator->second.type;
9984                         function_definition += " inout_array[2][2][2][2][2][2][2][2]);\n\n"
9985                                                                    "// Subroutine definitions\n"
9986                                                                    "subroutine(inout_routine_type) void original_routine(inout ";
9987                         function_definition += var_iterator->second.type;
9988                         function_definition += " inout_array[2][2][2][2][2][2][2][2]) {\n"
9989                                                                    "    uint i = 0u;\n";
9990                         function_definition += iteration_loop_start;
9991                         function_definition += "                                   inout_array[a][b][c][d][e][f][g][h] *= " +
9992                                                                    var_iterator->second.iterator_type + "(multiplier_array[i % 64u]);\n";
9993                         function_definition += "                                   i+= 1u;\n";
9994                         function_definition += iteration_loop_end;
9995                         function_definition += "}\n\n"
9996                                                                    "subroutine(inout_routine_type) void new_routine(inout ";
9997                         function_definition += var_iterator->second.type;
9998                         function_definition += " inout_array[2][2][2][2][2][2][2][2]) {\n"
9999                                                                    "    uint i = 0u;\n";
10000                         function_definition += iteration_loop_start;
10001                         function_definition += "                                   inout_array[a][b][c][d][e][f][g][h] /= " +
10002                                                                    var_iterator->second.iterator_type + "(multiplier_array[i % 64u]);\n";
10003                         function_definition += "                                   i+= 1u;\n";
10004                         function_definition += iteration_loop_end;
10005                         function_definition += "}\n\n"
10006                                                                    "// Subroutine uniform\n"
10007                                                                    "subroutine uniform inout_routine_type routine;\n";
10008
10009                         function_use += "    float result = 1.0;\n";
10010                         function_use += "    uint iterator = 0u;\n";
10011                         function_use += "    " + var_iterator->second.type + " my_array[2][2][2][2][2][2][2][2];\n";
10012                         function_use += iteration_loop_start;
10013                         function_use += "                                   my_array[a][b][c][d][e][f][g][h] = " +
10014                                                         var_iterator->second.variable_type_initializer2 + ";\n";
10015                         function_use += iteration_loop_end;
10016                         function_use += "    routine(my_array);";
10017
10018                         verification += iteration_loop_start;
10019                         verification += "                                   if (my_array[a][b][c][d][e][f][g][h] " +
10020                                                         var_iterator->second.specific_element + "!= " + var_iterator->second.iterator_type +
10021                                                         "(multiplier_array[iterator % 64u]))\n"
10022                                                         "                                   {\n"
10023                                                         "                                       result = 0.0;\n"
10024                                                         "                                   }\n"
10025                                                         "                                   iterator += 1u;\n";
10026                         verification += iteration_loop_end;
10027
10028                         if (false == test_compute)
10029                         {
10030                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification, false,
10031                                                                                 true);
10032                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification, true,
10033                                                                                 false);
10034                         }
10035                         else
10036                         {
10037                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, false,
10038                                                                                         true);
10039                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, true,
10040                                                                                         false);
10041                         }
10042
10043                         /* Deallocate any resources used. */
10044                         this->delete_objects();
10045                 } /* if var_type iterator found */
10046                 else
10047                 {
10048                         TCU_FAIL("Type not found.");
10049                 }
10050         } /* for (int var_type_index = 0; ...) */
10051 }
10052
10053 /* Generates the shader source code for the SubroutineArgumentAliasing1
10054  * array tests, attempts to build and execute test program
10055  *
10056  * @tparam API               Tested API descriptor
10057  *
10058  * @param tested_shader_type The type of shader that is being tested
10059  */
10060 template <class API>
10061 void SubroutineArgumentAliasing1<API>::test_shader_compilation(
10062         typename TestCaseBase<API>::TestShaderType tested_shader_type)
10063 {
10064         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
10065                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
10066                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
10067                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4 };
10068         static const size_t num_var_types_es = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
10069
10070         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
10071                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
10072                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
10073                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4,  VAR_TYPE_DOUBLE,
10074                                                                                                                          VAR_TYPE_DMAT2, VAR_TYPE_DMAT3, VAR_TYPE_DMAT4 };
10075         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
10076
10077         const std::string iteration_loop_end = "                        }\n"
10078                                                                                    "                    }\n"
10079                                                                                    "                }\n"
10080                                                                                    "            }\n"
10081                                                                                    "        }\n"
10082                                                                                    "    }\n";
10083         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
10084                                                                                          "    {\n"
10085                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
10086                                                                                          "        {\n"
10087                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
10088                                                                                          "            {\n"
10089                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
10090                                                                                          "                {\n"
10091                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
10092                                                                                          "                    {\n"
10093                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
10094                                                                                          "                        {\n";
10095         const glcts::test_var_type* var_types_set = var_types_set_es;
10096         size_t                                          num_var_types = num_var_types_es;
10097         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
10098
10099         if (API::USE_DOUBLE)
10100         {
10101                 var_types_set = var_types_set_gl;
10102                 num_var_types = num_var_types_gl;
10103         }
10104
10105         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
10106         {
10107                 _supported_variable_types_map_const_iterator var_iterator =
10108                         supported_variable_types_map.find(var_types_set[var_type_index]);
10109
10110                 if (var_iterator != supported_variable_types_map.end())
10111                 {
10112                         std::string function_definition;
10113                         std::string function_use;
10114                         std::string verification;
10115
10116                         function_definition += "// Subroutine types\n"
10117                                                                    "subroutine bool in_routine_type(";
10118                         function_definition += var_iterator->second.type;
10119                         function_definition += " x[2][2][2][2][2][2], ";
10120                         function_definition += var_iterator->second.type;
10121                         function_definition += " y[2][2][2][2][2][2]);\n\n"
10122                                                                    "// Subroutine definitions\n"
10123                                                                    "subroutine(in_routine_type) bool original_routine(";
10124                         function_definition += var_iterator->second.type;
10125                         function_definition += " x[2][2][2][2][2][2], ";
10126                         function_definition += var_iterator->second.type;
10127                         function_definition += " y[2][2][2][2][2][2])\n{\n";
10128                         function_definition += iteration_loop_start;
10129                         function_definition +=
10130                                 "                                   x[a][b][c][d][e][f] = " + var_iterator->second.type + "(123);\n";
10131                         function_definition += iteration_loop_end;
10132                         function_definition += "\n";
10133                         function_definition += iteration_loop_start;
10134                         function_definition += "                                   if(y[a][b][c][d][e][f]";
10135                         if (var_iterator->second.type == "mat4") // mat4 comparison
10136                         {
10137                                 function_definition += "[0][0]";
10138                                 function_definition += " != float";
10139                         }
10140                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
10141                         {
10142                                 function_definition += "[0][0]";
10143                                 function_definition += " != double";
10144                         }
10145                         else
10146                         {
10147                                 function_definition += " != ";
10148                                 function_definition += var_iterator->second.type;
10149                         }
10150                         function_definition += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f))) {return false;}\n";
10151                         function_definition += iteration_loop_end;
10152                         function_definition += "\n    return true;\n";
10153                         function_definition += "}\n\n"
10154                                                                    "subroutine(in_routine_type) bool new_routine(";
10155                         function_definition += var_iterator->second.type;
10156                         function_definition += " x[2][2][2][2][2][2], ";
10157                         function_definition += var_iterator->second.type;
10158                         function_definition += " y[2][2][2][2][2][2])\n{\n";
10159                         function_definition += iteration_loop_start;
10160                         function_definition +=
10161                                 "                                   y[a][b][c][d][e][f] = " + var_iterator->second.type + "(123);\n";
10162                         function_definition += iteration_loop_end;
10163                         function_definition += "\n";
10164                         function_definition += iteration_loop_start;
10165                         function_definition += "                                   if(x[a][b][c][d][e][f]";
10166                         if (var_iterator->second.type == "mat4") // mat4 comparison
10167                         {
10168                                 function_definition += "[0][0]";
10169                                 function_definition += " != float";
10170                         }
10171                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
10172                         {
10173                                 function_definition += "[0][0]";
10174                                 function_definition += " != double";
10175                         }
10176                         else
10177                         {
10178                                 function_definition += " != ";
10179                                 function_definition += var_iterator->second.type;
10180                         }
10181                         function_definition += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f))) {return false;}\n";
10182                         function_definition += iteration_loop_end;
10183                         function_definition += "\n    return true;\n";
10184                         function_definition += "}\n\n"
10185                                                                    "// Subroutine uniform\n"
10186                                                                    "subroutine uniform in_routine_type routine;\n";
10187
10188                         function_use += "    " + var_iterator->second.type + " z[2][2][2][2][2][2];\n";
10189                         function_use += iteration_loop_start;
10190                         function_use += "                                   z[a][b][c][d][e][f] = ";
10191                         function_use += var_iterator->second.type;
10192                         function_use += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f));\n";
10193                         function_use += iteration_loop_end;
10194
10195                         verification = "    float result = 0.0;\n"
10196                                                    "    if(routine(z, z) == true)\n"
10197                                                    "    {\n"
10198                                                    "        result = 1.0;\n"
10199                                                    "    }\n"
10200                                                    "    else\n"
10201                                                    "    {\n"
10202                                                    "        result = 0.5;\n"
10203                                                    "    }\n";
10204
10205                         if (false == test_compute)
10206                         {
10207                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification, false,
10208                                                                                 false);
10209                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification, true,
10210                                                                                 false);
10211                         }
10212                         else
10213                         {
10214                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, false,
10215                                                                                         false);
10216                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, true,
10217                                                                                         false);
10218                         }
10219
10220                         /* Deallocate any resources used. */
10221                         this->delete_objects();
10222                 } /* if var_type iterator found */
10223                 else
10224                 {
10225                         TCU_FAIL("Type not found.");
10226                 }
10227         } /* for (int var_type_index = 0; ...) */
10228 }
10229
10230 /* Generates the shader source code for the SubroutineArgumentAliasing1
10231  * array tests, attempts to build and execute test program
10232  *
10233  * @tparam API               Tested API descriptor
10234  *
10235  * @param tested_shader_type The type of shader that is being tested
10236  */
10237 template <class API>
10238 void SubroutineArgumentAliasing2<API>::test_shader_compilation(
10239         typename TestCaseBase<API>::TestShaderType tested_shader_type)
10240 {
10241         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
10242                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
10243                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
10244                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4 };
10245         static const size_t num_var_types_es = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
10246
10247         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
10248                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
10249                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
10250                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4,  VAR_TYPE_DOUBLE,
10251                                                                                                                          VAR_TYPE_DMAT2, VAR_TYPE_DMAT3, VAR_TYPE_DMAT4 };
10252         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
10253
10254         const std::string iteration_loop_end = "                        }\n"
10255                                                                                    "                    }\n"
10256                                                                                    "                }\n"
10257                                                                                    "            }\n"
10258                                                                                    "        }\n"
10259                                                                                    "    }\n";
10260         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
10261                                                                                          "    {\n"
10262                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
10263                                                                                          "        {\n"
10264                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
10265                                                                                          "            {\n"
10266                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
10267                                                                                          "                {\n"
10268                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
10269                                                                                          "                    {\n"
10270                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
10271                                                                                          "                        {\n";
10272         const glcts::test_var_type* var_types_set = var_types_set_es;
10273         size_t                                          num_var_types = num_var_types_es;
10274         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
10275
10276         if (API::USE_DOUBLE)
10277         {
10278                 var_types_set = var_types_set_gl;
10279                 num_var_types = num_var_types_gl;
10280         }
10281
10282         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
10283         {
10284                 _supported_variable_types_map_const_iterator var_iterator =
10285                         supported_variable_types_map.find(var_types_set[var_type_index]);
10286
10287                 if (var_iterator != supported_variable_types_map.end())
10288                 {
10289                         std::string function_definition;
10290                         std::string function_use;
10291                         std::string verification;
10292
10293                         function_definition += "// Subroutine types\n"
10294                                                                    "subroutine bool inout_routine_type(inout ";
10295                         function_definition += var_iterator->second.type;
10296                         function_definition += " x[2][2][2][2][2][2], inout ";
10297                         function_definition += var_iterator->second.type;
10298                         function_definition += " y[2][2][2][2][2][2]);\n\n"
10299                                                                    "// Subroutine definitions\n"
10300                                                                    "subroutine(inout_routine_type) bool original_routine(inout ";
10301                         function_definition += var_iterator->second.type;
10302                         function_definition += " x[2][2][2][2][2][2], inout ";
10303                         function_definition += var_iterator->second.type;
10304                         function_definition += " y[2][2][2][2][2][2])\n{\n";
10305                         function_definition += iteration_loop_start;
10306                         function_definition +=
10307                                 "                                   x[a][b][c][d][e][f] = " + var_iterator->second.type + "(123);\n";
10308                         function_definition += iteration_loop_end;
10309                         function_definition += "\n";
10310                         function_definition += iteration_loop_start;
10311                         function_definition += "                                   if(y[a][b][c][d][e][f]";
10312                         if (var_iterator->second.type == "mat4") // mat4 comparison
10313                         {
10314                                 function_definition += "[0][0]";
10315                                 function_definition += " != float";
10316                         }
10317                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
10318                         {
10319                                 function_definition += "[0][0]";
10320                                 function_definition += " != double";
10321                         }
10322                         else
10323                         {
10324                                 function_definition += " != ";
10325                                 function_definition += var_iterator->second.type;
10326                         }
10327                         function_definition += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f))) {return false;}\n";
10328                         function_definition += iteration_loop_end;
10329                         function_definition += "\n    return true;\n";
10330                         function_definition += "}\n\n"
10331                                                                    "subroutine(inout_routine_type) bool new_routine(inout ";
10332                         function_definition += var_iterator->second.type;
10333                         function_definition += " x[2][2][2][2][2][2], inout ";
10334                         function_definition += var_iterator->second.type;
10335                         function_definition += " y[2][2][2][2][2][2])\n{\n";
10336                         function_definition += iteration_loop_start;
10337                         function_definition +=
10338                                 "                                   y[a][b][c][d][e][f] = " + var_iterator->second.type + "(123);\n";
10339                         function_definition += iteration_loop_end;
10340                         function_definition += "\n";
10341                         function_definition += iteration_loop_start;
10342                         function_definition += "                                   if(x[a][b][c][d][e][f]";
10343                         if (var_iterator->second.type == "mat4") // mat4 comparison
10344                         {
10345                                 function_definition += "[0][0]";
10346                                 function_definition += " != float";
10347                         }
10348                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
10349                         {
10350                                 function_definition += "[0][0]";
10351                                 function_definition += " != double";
10352                         }
10353                         else
10354                         {
10355                                 function_definition += " != ";
10356                                 function_definition += var_iterator->second.type;
10357                         }
10358                         function_definition += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f))) {return false;}\n";
10359                         function_definition += iteration_loop_end;
10360                         function_definition += "\n    return true;\n";
10361                         function_definition += "}\n\n"
10362                                                                    "// Subroutine uniform\n"
10363                                                                    "subroutine uniform inout_routine_type routine;\n";
10364
10365                         function_use += "    " + var_iterator->second.type + " z[2][2][2][2][2][2];\n";
10366                         function_use += iteration_loop_start;
10367                         function_use += "                                   z[a][b][c][d][e][f] = ";
10368                         function_use += var_iterator->second.type;
10369                         function_use += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f));\n";
10370                         function_use += iteration_loop_end;
10371
10372                         verification = "    float result = 0.0;\n"
10373                                                    "    if(routine(z, z) == true)\n"
10374                                                    "    {\n"
10375                                                    "        result = 1.0;\n"
10376                                                    "    }\n"
10377                                                    "    else\n"
10378                                                    "    {\n"
10379                                                    "        result = 0.5;\n"
10380                                                    "    }\n";
10381
10382                         if (false == test_compute)
10383                         {
10384                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification, false,
10385                                                                                 false);
10386                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification, true,
10387                                                                                 false);
10388                         }
10389                         else
10390                         {
10391                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, false,
10392                                                                                         false);
10393                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, true,
10394                                                                                         false);
10395                         }
10396
10397                         /* Deallocate any resources used. */
10398                         this->delete_objects();
10399                 } /* if var_type iterator found */
10400                 else
10401                 {
10402                         TCU_FAIL("Type not found.");
10403                 }
10404         } /* for (int var_type_index = 0; ...) */
10405 }
10406
10407 /* Generates the shader source code for the SubroutineArgumentAliasing1
10408  * array tests, attempts to build and execute test program
10409  *
10410  * @tparam API               Tested API descriptor
10411  *
10412  * @param tested_shader_type The type of shader that is being tested
10413  */
10414 template <class API>
10415 void SubroutineArgumentAliasing3<API>::test_shader_compilation(
10416         typename TestCaseBase<API>::TestShaderType tested_shader_type)
10417 {
10418         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
10419                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
10420                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
10421                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4 };
10422         static const size_t num_var_types_es = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
10423
10424         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
10425                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
10426                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
10427                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4,  VAR_TYPE_DOUBLE,
10428                                                                                                                          VAR_TYPE_DMAT2, VAR_TYPE_DMAT3, VAR_TYPE_DMAT4 };
10429         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
10430
10431         const std::string iteration_loop_end = "                        }\n"
10432                                                                                    "                    }\n"
10433                                                                                    "                }\n"
10434                                                                                    "            }\n"
10435                                                                                    "        }\n"
10436                                                                                    "    }\n";
10437         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
10438                                                                                          "    {\n"
10439                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
10440                                                                                          "        {\n"
10441                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
10442                                                                                          "            {\n"
10443                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
10444                                                                                          "                {\n"
10445                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
10446                                                                                          "                    {\n"
10447                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
10448                                                                                          "                        {\n";
10449         const glcts::test_var_type* var_types_set = var_types_set_es;
10450         size_t                                          num_var_types = num_var_types_es;
10451         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
10452
10453         if (API::USE_DOUBLE)
10454         {
10455                 var_types_set = var_types_set_gl;
10456                 num_var_types = num_var_types_gl;
10457         }
10458
10459         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
10460         {
10461                 _supported_variable_types_map_const_iterator var_iterator =
10462                         supported_variable_types_map.find(var_types_set[var_type_index]);
10463
10464                 if (var_iterator != supported_variable_types_map.end())
10465                 {
10466                         std::string function_definition;
10467                         std::string function_use;
10468                         std::string verification;
10469
10470                         function_definition += "// Subroutine types\n"
10471                                                                    "subroutine bool out_routine_type(out ";
10472                         function_definition += var_iterator->second.type;
10473                         function_definition += " x[2][2][2][2][2][2], ";
10474                         function_definition += var_iterator->second.type;
10475                         function_definition += " y[2][2][2][2][2][2]);\n\n"
10476                                                                    "// Subroutine definitions\n"
10477                                                                    "subroutine(out_routine_type) bool original_routine(out ";
10478                         function_definition += var_iterator->second.type;
10479                         function_definition += " x[2][2][2][2][2][2], ";
10480                         function_definition += var_iterator->second.type;
10481                         function_definition += " y[2][2][2][2][2][2])\n{\n";
10482                         function_definition += iteration_loop_start;
10483                         function_definition +=
10484                                 "                                   x[a][b][c][d][e][f] = " + var_iterator->second.type + "(123);\n";
10485                         function_definition += iteration_loop_end;
10486                         function_definition += "\n";
10487                         function_definition += iteration_loop_start;
10488                         function_definition += "                                   if(y[a][b][c][d][e][f]";
10489                         if (var_iterator->second.type == "mat4") // mat4 comparison
10490                         {
10491                                 function_definition += "[0][0]";
10492                                 function_definition += " != float";
10493                         }
10494                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
10495                         {
10496                                 function_definition += "[0][0]";
10497                                 function_definition += " != double";
10498                         }
10499                         else
10500                         {
10501                                 function_definition += " != ";
10502                                 function_definition += var_iterator->second.type;
10503                         }
10504                         function_definition += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f))) {return false;}\n";
10505                         function_definition += iteration_loop_end;
10506                         function_definition += "\n    return true;\n";
10507                         function_definition += "}\n\n"
10508                                                                    "subroutine(out_routine_type) bool new_routine(out ";
10509                         function_definition += var_iterator->second.type;
10510                         function_definition += " x[2][2][2][2][2][2], ";
10511                         function_definition += var_iterator->second.type;
10512                         function_definition += " y[2][2][2][2][2][2])\n{\n";
10513                         function_definition += iteration_loop_start;
10514                         function_definition +=
10515                                 "                                   x[a][b][c][d][e][f] = " + var_iterator->second.type + "(321);\n";
10516                         function_definition += iteration_loop_end;
10517                         function_definition += "\n";
10518                         function_definition += iteration_loop_start;
10519                         function_definition += "                                   if(y[a][b][c][d][e][f]";
10520                         if (var_iterator->second.type == "mat4") // mat4 comparison
10521                         {
10522                                 function_definition += "[0][0]";
10523                                 function_definition += " != float";
10524                         }
10525                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
10526                         {
10527                                 function_definition += "[0][0]";
10528                                 function_definition += " != double";
10529                         }
10530                         else
10531                         {
10532                                 function_definition += " != ";
10533                                 function_definition += var_iterator->second.type;
10534                         }
10535                         function_definition += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f))) {return false;}\n";
10536                         function_definition += iteration_loop_end;
10537                         function_definition += "\n    return true;\n";
10538                         function_definition += "}\n\n"
10539                                                                    "// Subroutine uniform\n"
10540                                                                    "subroutine uniform out_routine_type routine;\n";
10541
10542                         function_use += "    " + var_iterator->second.type + " z[2][2][2][2][2][2];\n";
10543                         function_use += iteration_loop_start;
10544                         function_use += "                                   z[a][b][c][d][e][f] = ";
10545                         function_use += var_iterator->second.type;
10546                         function_use += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f));\n";
10547                         function_use += iteration_loop_end;
10548
10549                         verification = "    float result = 0.0;\n"
10550                                                    "    if(routine(z, z) == true)\n"
10551                                                    "    {\n"
10552                                                    "        result = 1.0;\n"
10553                                                    "    }\n"
10554                                                    "    else\n"
10555                                                    "    {\n"
10556                                                    "        result = 0.5;\n"
10557                                                    "    }\n";
10558
10559                         if (false == test_compute)
10560                         {
10561                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification, false,
10562                                                                                 false);
10563                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification, true,
10564                                                                                 false);
10565                         }
10566                         else
10567                         {
10568                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, false,
10569                                                                                         false);
10570                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, true,
10571                                                                                         false);
10572                         }
10573
10574                         /* Deallocate any resources used. */
10575                         this->delete_objects();
10576                 } /* if var_type iterator found */
10577                 else
10578                 {
10579                         TCU_FAIL("Type not found.");
10580                 }
10581         } /* for (int var_type_index = 0; ...) */
10582 }
10583
10584 /* Generates the shader source code for the SubroutineArgumentAliasing1
10585  * array tests, attempts to build and execute test program
10586  *
10587  * @tparam API               Tested API descriptor
10588  *
10589  * @param tested_shader_type The type of shader that is being tested
10590  */
10591 template <class API>
10592 void SubroutineArgumentAliasing4<API>::test_shader_compilation(
10593         typename TestCaseBase<API>::TestShaderType tested_shader_type)
10594 {
10595         static const glcts::test_var_type var_types_set_es[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
10596                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
10597                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
10598                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4 };
10599         static const size_t num_var_types_es = sizeof(var_types_set_es) / sizeof(var_types_set_es[0]);
10600
10601         static const glcts::test_var_type var_types_set_gl[] = { VAR_TYPE_INT,   VAR_TYPE_FLOAT, VAR_TYPE_IVEC2,
10602                                                                                                                          VAR_TYPE_IVEC3, VAR_TYPE_IVEC4, VAR_TYPE_VEC2,
10603                                                                                                                          VAR_TYPE_VEC3,  VAR_TYPE_VEC4,  VAR_TYPE_MAT2,
10604                                                                                                                          VAR_TYPE_MAT3,  VAR_TYPE_MAT4,  VAR_TYPE_DOUBLE,
10605                                                                                                                          VAR_TYPE_DMAT2, VAR_TYPE_DMAT3, VAR_TYPE_DMAT4 };
10606         static const size_t num_var_types_gl = sizeof(var_types_set_gl) / sizeof(var_types_set_gl[0]);
10607
10608         const std::string iteration_loop_end = "                        }\n"
10609                                                                                    "                    }\n"
10610                                                                                    "                }\n"
10611                                                                                    "            }\n"
10612                                                                                    "        }\n"
10613                                                                                    "    }\n";
10614         const std::string iteration_loop_start = "    for (uint a = 0u; a < 2u; a++)\n"
10615                                                                                          "    {\n"
10616                                                                                          "        for (uint b = 0u; b < 2u; b++)\n"
10617                                                                                          "        {\n"
10618                                                                                          "            for (uint c = 0u; c < 2u; c++)\n"
10619                                                                                          "            {\n"
10620                                                                                          "                for (uint d = 0u; d < 2u; d++)\n"
10621                                                                                          "                {\n"
10622                                                                                          "                    for (uint e = 0u; e < 2u; e++)\n"
10623                                                                                          "                    {\n"
10624                                                                                          "                        for (uint f = 0u; f < 2u; f++)\n"
10625                                                                                          "                        {\n";
10626         const glcts::test_var_type* var_types_set = var_types_set_es;
10627         size_t                                          num_var_types = num_var_types_es;
10628         const bool                                      test_compute  = (TestCaseBase<API>::COMPUTE_SHADER_TYPE == tested_shader_type);
10629
10630         if (API::USE_DOUBLE)
10631         {
10632                 var_types_set = var_types_set_gl;
10633                 num_var_types = num_var_types_gl;
10634         }
10635
10636         for (size_t var_type_index = 0; var_type_index < num_var_types; var_type_index++)
10637         {
10638                 _supported_variable_types_map_const_iterator var_iterator =
10639                         supported_variable_types_map.find(var_types_set[var_type_index]);
10640
10641                 if (var_iterator != supported_variable_types_map.end())
10642                 {
10643                         std::string function_definition;
10644                         std::string function_use;
10645                         std::string verification;
10646
10647                         function_definition += "// Subroutine types\n"
10648                                                                    "subroutine bool out_routine_type(";
10649                         function_definition += var_iterator->second.type;
10650                         function_definition += " x[2][2][2][2][2][2], out ";
10651                         function_definition += var_iterator->second.type;
10652                         function_definition += " y[2][2][2][2][2][2]);\n\n"
10653                                                                    "// Subroutine definitions\n"
10654                                                                    "subroutine(out_routine_type) bool original_routine(";
10655                         function_definition += var_iterator->second.type;
10656                         function_definition += " x[2][2][2][2][2][2], out ";
10657                         function_definition += var_iterator->second.type;
10658                         function_definition += " y[2][2][2][2][2][2])\n{\n";
10659                         function_definition += iteration_loop_start;
10660                         function_definition +=
10661                                 "                                   y[a][b][c][d][e][f] = " + var_iterator->second.type + "(123);\n";
10662                         function_definition += iteration_loop_end;
10663                         function_definition += "\n";
10664                         function_definition += iteration_loop_start;
10665                         function_definition += "                                   if(x[a][b][c][d][e][f]";
10666                         if (var_iterator->second.type == "mat4") // mat4 comparison
10667                         {
10668                                 function_definition += "[0][0]";
10669                                 function_definition += " != float";
10670                         }
10671                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
10672                         {
10673                                 function_definition += "[0][0]";
10674                                 function_definition += " != double";
10675                         }
10676                         else
10677                         {
10678                                 function_definition += " != ";
10679                                 function_definition += var_iterator->second.type;
10680                         }
10681                         function_definition += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f))) {return false;}\n";
10682                         function_definition += iteration_loop_end;
10683                         function_definition += "\n    return true;\n";
10684                         function_definition += "}\n\n"
10685                                                                    "subroutine(out_routine_type) bool new_routine(";
10686                         function_definition += var_iterator->second.type;
10687                         function_definition += " x[2][2][2][2][2][2], out ";
10688                         function_definition += var_iterator->second.type;
10689                         function_definition += " y[2][2][2][2][2][2])\n{\n";
10690                         function_definition += iteration_loop_start;
10691                         function_definition +=
10692                                 "                                   y[a][b][c][d][e][f] = " + var_iterator->second.type + "(321);\n";
10693                         function_definition += iteration_loop_end;
10694                         function_definition += "\n";
10695                         function_definition += iteration_loop_start;
10696                         function_definition += "                                   if(x[a][b][c][d][e][f]";
10697                         if (var_iterator->second.type == "mat4") // mat4 comparison
10698                         {
10699                                 function_definition += "[0][0]";
10700                                 function_definition += " != float";
10701                         }
10702                         else if (var_iterator->second.type == "dmat4") // dmat4 comparison
10703                         {
10704                                 function_definition += "[0][0]";
10705                                 function_definition += " != double";
10706                         }
10707                         else
10708                         {
10709                                 function_definition += " != ";
10710                                 function_definition += var_iterator->second.type;
10711                         }
10712                         function_definition += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f))) {return false;}\n";
10713                         function_definition += iteration_loop_end;
10714                         function_definition += "\n    return true;\n";
10715                         function_definition += "}\n\n"
10716                                                                    "// Subroutine uniform\n"
10717                                                                    "subroutine uniform out_routine_type routine;\n";
10718
10719                         function_use += "    " + var_iterator->second.type + " z[2][2][2][2][2][2];\n";
10720                         function_use += iteration_loop_start;
10721                         function_use += "                                   z[a][b][c][d][e][f] = ";
10722                         function_use += var_iterator->second.type;
10723                         function_use += "(((a*32u)+(b*16u)+(c*8u)+(d*4u)+(e*2u)+f));\n";
10724                         function_use += iteration_loop_end;
10725
10726                         verification = "    float result = 0.0;\n"
10727                                                    "    if(routine(z, z) == true)\n"
10728                                                    "    {\n"
10729                                                    "        result = 1.0;\n"
10730                                                    "    }\n"
10731                                                    "    else\n"
10732                                                    "    {\n"
10733                                                    "        result = 0.5;\n"
10734                                                    "    }\n";
10735
10736                         if (false == test_compute)
10737                         {
10738                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification, false,
10739                                                                                 false);
10740                                 this->execute_draw_test(tested_shader_type, function_definition, function_use, verification, true,
10741                                                                                 false);
10742                         }
10743                         else
10744                         {
10745                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, false,
10746                                                                                         false);
10747                                 this->execute_dispatch_test(tested_shader_type, function_definition, function_use, verification, true,
10748                                                                                         false);
10749                         }
10750
10751                         /* Deallocate any resources used. */
10752                         this->delete_objects();
10753                 } /* if var_type iterator found */
10754                 else
10755                 {
10756                         TCU_FAIL("Type not found.");
10757                 }
10758         } /* for (int var_type_index = 0; ...) */
10759 }
10760
10761 /** Instantiates all tests and adds them as children to the node
10762  *
10763  * @tparam API    Tested API descriptor
10764  *
10765  * @param context CTS context
10766  **/
10767 template <class API>
10768 void initTests(TestCaseGroup& group, glcts::Context& context)
10769 {
10770         // Set up the map
10771         ArraysOfArrays::initializeMap<API>();
10772
10773         group.addChild(new glcts::ArraysOfArrays::SizedDeclarationsPrimitive<API>(context));
10774         group.addChild(new glcts::ArraysOfArrays::SizedDeclarationsStructTypes1<API>(context));
10775         group.addChild(new glcts::ArraysOfArrays::SizedDeclarationsStructTypes2<API>(context));
10776         group.addChild(new glcts::ArraysOfArrays::SizedDeclarationsStructTypes3<API>(context));
10777         group.addChild(new glcts::ArraysOfArrays::SizedDeclarationsStructTypes4<API>(context));
10778         group.addChild(new glcts::ArraysOfArrays::SizedDeclarationsTypenameStyle1<API>(context));
10779         group.addChild(new glcts::ArraysOfArrays::SizedDeclarationsTypenameStyle2<API>(context));
10780         group.addChild(new glcts::ArraysOfArrays::SizedDeclarationsTypenameStyle3<API>(context));
10781         group.addChild(new glcts::ArraysOfArrays::SizedDeclarationsTypenameStyle4<API>(context));
10782         group.addChild(new glcts::ArraysOfArrays::SizedDeclarationsTypenameStyle5<API>(context));
10783         group.addChild(new glcts::ArraysOfArrays::SizedDeclarationsFunctionParams<API>(context));
10784         group.addChild(new glcts::ArraysOfArrays::sized_declarations_invalid_sizes1<API>(context));
10785         group.addChild(new glcts::ArraysOfArrays::sized_declarations_invalid_sizes2<API>(context));
10786         group.addChild(new glcts::ArraysOfArrays::sized_declarations_invalid_sizes3<API>(context));
10787         group.addChild(new glcts::ArraysOfArrays::sized_declarations_invalid_sizes4<API>(context));
10788         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclConstructors1<API>(context));
10789         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclConstructors2<API>(context));
10790         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclUnsizedConstructors<API>(context));
10791         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclConst<API>(context));
10792
10793         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclInvalidConstructors1<API>(context));
10794         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclInvalidConstructors2<API>(context));
10795         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclInvalidConstructors3<API>(context));
10796         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclInvalidConstructors4<API>(context));
10797         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclConstructorSizing1<API>(context));
10798         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclConstructorSizing2<API>(context));
10799         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclStructConstructors<API>(context));
10800         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclUnsizedArrays1<API>(context));
10801         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclUnsizedArrays2<API>(context));
10802         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclUnsizedArrays3<API>(context));
10803         group.addChild(new glcts::ArraysOfArrays::ConstructorsAndUnsizedDeclUnsizedArrays4<API>(context));
10804         group.addChild(new glcts::ArraysOfArrays::ExpressionsAssignment1<API>(context));
10805         group.addChild(new glcts::ArraysOfArrays::ExpressionsAssignment2<API>(context));
10806         group.addChild(new glcts::ArraysOfArrays::ExpressionsAssignment3<API>(context));
10807         group.addChild(new glcts::ArraysOfArrays::ExpressionsTypeRestrictions1<API>(context));
10808         group.addChild(new glcts::ArraysOfArrays::ExpressionsTypeRestrictions2<API>(context));
10809         group.addChild(new glcts::ArraysOfArrays::ExpressionsIndexingScalar1<API>(context));
10810         group.addChild(new glcts::ArraysOfArrays::ExpressionsIndexingScalar2<API>(context));
10811         group.addChild(new glcts::ArraysOfArrays::ExpressionsIndexingScalar3<API>(context));
10812         group.addChild(new glcts::ArraysOfArrays::ExpressionsIndexingScalar4<API>(context));
10813         group.addChild(new glcts::ArraysOfArrays::ExpressionsIndexingArray1<API>(context));
10814         group.addChild(new glcts::ArraysOfArrays::ExpressionsIndexingArray2<API>(context));
10815         group.addChild(new glcts::ArraysOfArrays::ExpressionsIndexingArray3<API>(context));
10816         group.addChild(new glcts::ArraysOfArrays::ExpressionsDynamicIndexing1<API>(context));
10817         group.addChild(new glcts::ArraysOfArrays::ExpressionsDynamicIndexing2<API>(context));
10818         group.addChild(new glcts::ArraysOfArrays::ExpressionsEquality1<API>(context));
10819         group.addChild(new glcts::ArraysOfArrays::ExpressionsEquality2<API>(context));
10820         group.addChild(new glcts::ArraysOfArrays::ExpressionsLength1<API>(context));
10821         group.addChild(new glcts::ArraysOfArrays::ExpressionsLength2<API>(context));
10822         group.addChild(new glcts::ArraysOfArrays::ExpressionsLength3<API>(context));
10823         group.addChild(new glcts::ArraysOfArrays::ExpressionsInvalid1<API>(context));
10824         group.addChild(new glcts::ArraysOfArrays::ExpressionsInvalid2<API>(context));
10825
10826         group.addChild(new glcts::ArraysOfArrays::InteractionFunctionCalls1<API>(context));
10827         group.addChild(new glcts::ArraysOfArrays::InteractionFunctionCalls2<API>(context));
10828         group.addChild(new glcts::ArraysOfArrays::InteractionArgumentAliasing1<API>(context));
10829         group.addChild(new glcts::ArraysOfArrays::InteractionArgumentAliasing2<API>(context));
10830         group.addChild(new glcts::ArraysOfArrays::InteractionArgumentAliasing3<API>(context));
10831         group.addChild(new glcts::ArraysOfArrays::InteractionArgumentAliasing4<API>(context));
10832         group.addChild(new glcts::ArraysOfArrays::InteractionArgumentAliasing5<API>(context));
10833         group.addChild(new glcts::ArraysOfArrays::InteractionArgumentAliasing6<API>(context));
10834
10835         group.addChild(new glcts::ArraysOfArrays::InteractionUniforms1<API>(context));
10836         group.addChild(new glcts::ArraysOfArrays::InteractionUniforms2<API>(context));
10837         group.addChild(new glcts::ArraysOfArrays::InteractionUniformBuffers1<API>(context));
10838         group.addChild(new glcts::ArraysOfArrays::InteractionUniformBuffers2<API>(context));
10839         group.addChild(new glcts::ArraysOfArrays::InteractionUniformBuffers3<API>(context));
10840         group.addChild(new glcts::ArraysOfArrays::InteractionInterfaceArrays1<API>(context));
10841         group.addChild(new glcts::ArraysOfArrays::InteractionInterfaceArrays2<API>(context));
10842         group.addChild(new glcts::ArraysOfArrays::InteractionInterfaceArrays3<API>(context));
10843         group.addChild(new glcts::ArraysOfArrays::InteractionInterfaceArrays4<API>(context));
10844
10845         if (API::USE_STORAGE_BLOCK)
10846         {
10847                 group.addChild(new glcts::ArraysOfArrays::InteractionStorageBuffers1<API>(context));
10848                 group.addChild(new glcts::ArraysOfArrays::InteractionStorageBuffers2<API>(context));
10849                 group.addChild(new glcts::ArraysOfArrays::InteractionStorageBuffers3<API>(context));
10850         }
10851
10852         if (API::USE_ATOMIC)
10853         {
10854                 group.addChild(new glcts::ArraysOfArrays::AtomicDeclarationTest<API>(context));
10855                 group.addChild(new glcts::ArraysOfArrays::AtomicUsageTest<API>(context));
10856         }
10857
10858         if (API::USE_SUBROUTINE)
10859         {
10860                 group.addChild(new glcts::ArraysOfArrays::SubroutineFunctionCalls1<API>(context));
10861                 group.addChild(new glcts::ArraysOfArrays::SubroutineFunctionCalls2<API>(context));
10862                 group.addChild(new glcts::ArraysOfArrays::SubroutineArgumentAliasing1<API>(context));
10863                 group.addChild(new glcts::ArraysOfArrays::SubroutineArgumentAliasing2<API>(context));
10864                 group.addChild(new glcts::ArraysOfArrays::SubroutineArgumentAliasing3<API>(context));
10865                 group.addChild(new glcts::ArraysOfArrays::SubroutineArgumentAliasing4<API>(context));
10866         }
10867 }
10868 } /* namespace ArraysOfArrays */
10869
10870 /** Constructor
10871  *
10872  * @param context CTS context
10873  **/
10874 ArrayOfArraysTestGroup::ArrayOfArraysTestGroup(Context& context)
10875         : TestCaseGroup(context, "arrays_of_arrays", "Groups all tests that verify 'arrays of arrays' functionality.")
10876 {
10877         /* Left blank on purpose */
10878 }
10879
10880 /* Instantiates all tests and adds them as children to the node */
10881 void ArrayOfArraysTestGroup::init(void)
10882 {
10883         ArraysOfArrays::initTests<ArraysOfArrays::Interface::ES>(*this, m_context);
10884 }
10885
10886 /** Constructor
10887  *
10888  * @param context CTS context
10889  **/
10890 ArrayOfArraysTestGroupGL::ArrayOfArraysTestGroupGL(Context& context)
10891         : TestCaseGroup(context, "arrays_of_arrays_gl", "Groups all tests that verify 'arrays of arrays' functionality.")
10892 {
10893         /* Left blank on purpose */
10894 }
10895
10896 /* Instantiates all tests and adds them as children to the node */
10897 void ArrayOfArraysTestGroupGL::init(void)
10898 {
10899         ArraysOfArrays::initTests<ArraysOfArrays::Interface::GL>(*this, m_context);
10900 }
10901 } /* namespace glcts */