1 /*------------------------------------------------------------------------
2 * Vulkan Conformance Tests
3 * ------------------------
4 *
5 * Copyright (c) 2015 The Khronos Group Inc.
6 * Copyright (c) 2015 Samsung Electronics Co., Ltd.
7 * Copyright (c) 2016 The Android Open Source Project
8 *
9 * Licensed under the Apache License, Version 2.0 (the "License");
10 * you may not use this file except in compliance with the License.
11 * You may obtain a copy of the License at
12 *
13 * http://www.apache.org/licenses/LICENSE-2.0
14 *
15 * Unless required by applicable law or agreed to in writing, software
16 * distributed under the License is distributed on an "AS IS" BASIS,
17 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18 * See the License for the specific language governing permissions and
19 * limitations under the License.
20 *
21 *//*!
22 * \file
23 * \brief Uniform block tests.
24 *//*--------------------------------------------------------------------*/
25
26 #include "vktUniformBlockTests.hpp"
27
28 #include "vktUniformBlockCase.hpp"
29 #include "vktRandomUniformBlockCase.hpp"
30
31 #include "tcuCommandLine.hpp"
32 #include "deStringUtil.hpp"
33
34 namespace vkt
35 {
36 namespace ubo
37 {
38
39 namespace
40 {
41
42 class BlockBasicTypeCase : public UniformBlockCase
43 {
44 public:
BlockBasicTypeCase(tcu::TestContext & testCtx,const std::string & name,const std::string & description,const VarType & type,deUint32 layoutFlags,int numInstances)45 BlockBasicTypeCase (tcu::TestContext& testCtx, const std::string& name, const std::string& description, const VarType& type, deUint32 layoutFlags, int numInstances)
46 : UniformBlockCase(testCtx, name, description, BUFFERMODE_PER_BLOCK)
47 {
48 UniformBlock& block = m_interface.allocBlock("Block");
49 block.addUniform(Uniform("var", type, 0));
50 block.setFlags(layoutFlags);
51
52 if (numInstances > 0)
53 {
54 block.setArraySize(numInstances);
55 block.setInstanceName("block");
56 }
57
58 init();
59 }
60 };
61
createBlockBasicTypeCases(tcu::TestCaseGroup * group,tcu::TestContext & testCtx,const std::string & name,const VarType & type,deUint32 layoutFlags,int numInstances=0)62 static void createBlockBasicTypeCases (tcu::TestCaseGroup* group, tcu::TestContext& testCtx, const std::string& name, const VarType& type, deUint32 layoutFlags, int numInstances = 0)
63 {
64 group->addChild(new BlockBasicTypeCase(testCtx, name + "_vertex", "", type, layoutFlags|DECLARE_VERTEX, numInstances));
65 group->addChild(new BlockBasicTypeCase(testCtx, name + "_fragment", "", type, layoutFlags|DECLARE_FRAGMENT, numInstances));
66 group->addChild(new BlockBasicTypeCase(testCtx, name + "_both", "", type, layoutFlags|DECLARE_VERTEX|DECLARE_FRAGMENT, numInstances));
67 }
68
69 class BlockSingleStructCase : public UniformBlockCase
70 {
71 public:
BlockSingleStructCase(tcu::TestContext & testCtx,const std::string & name,const std::string & description,deUint32 layoutFlags,BufferMode bufferMode,int numInstances)72 BlockSingleStructCase (tcu::TestContext& testCtx, const std::string& name, const std::string& description, deUint32 layoutFlags, BufferMode bufferMode, int numInstances)
73 : UniformBlockCase (testCtx, name, description, bufferMode)
74 {
75 StructType& typeS = m_interface.allocStruct("S");
76 typeS.addMember("a", VarType(glu::TYPE_INT_VEC3, PRECISION_HIGH), UNUSED_BOTH); // First member is unused.
77 typeS.addMember("b", VarType(VarType(glu::TYPE_FLOAT_MAT3, PRECISION_MEDIUM), 4));
78 typeS.addMember("c", VarType(glu::TYPE_FLOAT_VEC4, PRECISION_HIGH));
79
80 UniformBlock& block = m_interface.allocBlock("Block");
81 block.addUniform(Uniform("s", VarType(&typeS), 0));
82 block.setFlags(layoutFlags);
83
84 if (numInstances > 0)
85 {
86 block.setInstanceName("block");
87 block.setArraySize(numInstances);
88 }
89
90 init();
91 }
92 };
93
94 class BlockSingleStructArrayCase : public UniformBlockCase
95 {
96 public:
BlockSingleStructArrayCase(tcu::TestContext & testCtx,const std::string & name,const std::string & description,deUint32 layoutFlags,BufferMode bufferMode,int numInstances)97 BlockSingleStructArrayCase (tcu::TestContext& testCtx, const std::string& name, const std::string& description, deUint32 layoutFlags, BufferMode bufferMode, int numInstances)
98 : UniformBlockCase (testCtx, name, description, bufferMode)
99 {
100 StructType& typeS = m_interface.allocStruct("S");
101 typeS.addMember("a", VarType(glu::TYPE_INT_VEC3, PRECISION_HIGH), UNUSED_BOTH);
102 typeS.addMember("b", VarType(VarType(glu::TYPE_FLOAT_MAT3, PRECISION_MEDIUM), 4));
103 typeS.addMember("c", VarType(glu::TYPE_FLOAT_VEC4, PRECISION_HIGH));
104
105 UniformBlock& block = m_interface.allocBlock("Block");
106 block.addUniform(Uniform("u", VarType(glu::TYPE_UINT, PRECISION_LOW)));
107 block.addUniform(Uniform("s", VarType(VarType(&typeS), 3)));
108 block.addUniform(Uniform("v", VarType(glu::TYPE_FLOAT_VEC4, PRECISION_MEDIUM)));
109 block.setFlags(layoutFlags);
110
111 if (numInstances > 0)
112 {
113 block.setInstanceName("block");
114 block.setArraySize(numInstances);
115 }
116
117 init();
118 }
119 };
120
121 class BlockSingleNestedStructCase : public UniformBlockCase
122 {
123 public:
BlockSingleNestedStructCase(tcu::TestContext & testCtx,const std::string & name,const std::string & description,deUint32 layoutFlags,BufferMode bufferMode,int numInstances)124 BlockSingleNestedStructCase (tcu::TestContext& testCtx, const std::string& name, const std::string& description, deUint32 layoutFlags, BufferMode bufferMode, int numInstances)
125 : UniformBlockCase (testCtx, name, description, bufferMode)
126 {
127 StructType& typeS = m_interface.allocStruct("S");
128 typeS.addMember("a", VarType(glu::TYPE_INT_VEC3, PRECISION_HIGH));
129 typeS.addMember("b", VarType(VarType(glu::TYPE_FLOAT_MAT3, PRECISION_MEDIUM), 4));
130 typeS.addMember("c", VarType(glu::TYPE_FLOAT_VEC4, PRECISION_HIGH), UNUSED_BOTH);
131
132 StructType& typeT = m_interface.allocStruct("T");
133 typeT.addMember("a", VarType(glu::TYPE_FLOAT_MAT3, PRECISION_MEDIUM));
134 typeT.addMember("b", VarType(&typeS));
135
136 UniformBlock& block = m_interface.allocBlock("Block");
137 block.addUniform(Uniform("s", VarType(&typeS), 0));
138 block.addUniform(Uniform("v", VarType(glu::TYPE_FLOAT_VEC2, PRECISION_LOW), UNUSED_BOTH));
139 block.addUniform(Uniform("t", VarType(&typeT), 0));
140 block.addUniform(Uniform("u", VarType(glu::TYPE_UINT, PRECISION_HIGH), 0));
141 block.setFlags(layoutFlags);
142
143 if (numInstances > 0)
144 {
145 block.setInstanceName("block");
146 block.setArraySize(numInstances);
147 }
148
149 init();
150 }
151 };
152
153 class BlockSingleNestedStructArrayCase : public UniformBlockCase
154 {
155 public:
BlockSingleNestedStructArrayCase(tcu::TestContext & testCtx,const std::string & name,const std::string & description,deUint32 layoutFlags,BufferMode bufferMode,int numInstances)156 BlockSingleNestedStructArrayCase (tcu::TestContext& testCtx, const std::string& name, const std::string& description, deUint32 layoutFlags, BufferMode bufferMode, int numInstances)
157 : UniformBlockCase (testCtx, name, description, bufferMode)
158 {
159 StructType& typeS = m_interface.allocStruct("S");
160 typeS.addMember("a", VarType(glu::TYPE_INT_VEC3, PRECISION_HIGH));
161 typeS.addMember("b", VarType(VarType(glu::TYPE_INT_VEC2, PRECISION_MEDIUM), 4));
162 typeS.addMember("c", VarType(glu::TYPE_FLOAT_VEC4, PRECISION_HIGH), UNUSED_BOTH);
163
164 StructType& typeT = m_interface.allocStruct("T");
165 typeT.addMember("a", VarType(glu::TYPE_FLOAT_MAT3, PRECISION_MEDIUM));
166 typeT.addMember("b", VarType(VarType(&typeS), 3));
167
168 UniformBlock& block = m_interface.allocBlock("Block");
169 block.addUniform(Uniform("s", VarType(&typeS), 0));
170 block.addUniform(Uniform("v", VarType(glu::TYPE_FLOAT_VEC2, PRECISION_LOW), UNUSED_BOTH));
171 block.addUniform(Uniform("t", VarType(VarType(&typeT), 2), 0));
172 block.addUniform(Uniform("u", VarType(glu::TYPE_UINT, PRECISION_HIGH), 0));
173 block.setFlags(layoutFlags);
174
175 if (numInstances > 0)
176 {
177 block.setInstanceName("block");
178 block.setArraySize(numInstances);
179 }
180
181 init();
182 }
183 };
184
185 class BlockMultiBasicTypesCase : public UniformBlockCase
186 {
187 public:
BlockMultiBasicTypesCase(tcu::TestContext & testCtx,const std::string & name,const std::string & description,deUint32 flagsA,deUint32 flagsB,BufferMode bufferMode,int numInstances)188 BlockMultiBasicTypesCase (tcu::TestContext& testCtx, const std::string& name, const std::string& description, deUint32 flagsA, deUint32 flagsB, BufferMode bufferMode, int numInstances)
189 : UniformBlockCase (testCtx, name, description, bufferMode)
190 {
191 UniformBlock& blockA = m_interface.allocBlock("BlockA");
192 blockA.addUniform(Uniform("a", VarType(glu::TYPE_FLOAT, PRECISION_HIGH)));
193 blockA.addUniform(Uniform("b", VarType(glu::TYPE_UINT_VEC3, PRECISION_LOW), UNUSED_BOTH));
194 blockA.addUniform(Uniform("c", VarType(glu::TYPE_FLOAT_MAT2, PRECISION_MEDIUM)));
195 blockA.setInstanceName("blockA");
196 blockA.setFlags(flagsA);
197
198 UniformBlock& blockB = m_interface.allocBlock("BlockB");
199 blockB.addUniform(Uniform("a", VarType(glu::TYPE_FLOAT_MAT3, PRECISION_MEDIUM)));
200 blockB.addUniform(Uniform("b", VarType(glu::TYPE_INT_VEC2, PRECISION_LOW)));
201 blockB.addUniform(Uniform("c", VarType(glu::TYPE_FLOAT_VEC4, PRECISION_HIGH), UNUSED_BOTH));
202 blockB.addUniform(Uniform("d", VarType(glu::TYPE_BOOL, 0)));
203 blockB.setInstanceName("blockB");
204 blockB.setFlags(flagsB);
205
206 if (numInstances > 0)
207 {
208 blockA.setArraySize(numInstances);
209 blockB.setArraySize(numInstances);
210 }
211
212 init();
213 }
214 };
215
216 class BlockMultiNestedStructCase : public UniformBlockCase
217 {
218 public:
BlockMultiNestedStructCase(tcu::TestContext & testCtx,const std::string & name,const std::string & description,deUint32 flagsA,deUint32 flagsB,BufferMode bufferMode,int numInstances)219 BlockMultiNestedStructCase (tcu::TestContext& testCtx, const std::string& name, const std::string& description, deUint32 flagsA, deUint32 flagsB, BufferMode bufferMode, int numInstances)
220 : UniformBlockCase (testCtx, name, description, bufferMode)
221 {
222 StructType& typeS = m_interface.allocStruct("S");
223 typeS.addMember("a", VarType(glu::TYPE_FLOAT_MAT3, PRECISION_LOW));
224 typeS.addMember("b", VarType(VarType(glu::TYPE_INT_VEC2, PRECISION_MEDIUM), 4));
225 typeS.addMember("c", VarType(glu::TYPE_FLOAT_VEC4, PRECISION_HIGH));
226
227 StructType& typeT = m_interface.allocStruct("T");
228 typeT.addMember("a", VarType(glu::TYPE_UINT, PRECISION_MEDIUM), UNUSED_BOTH);
229 typeT.addMember("b", VarType(&typeS));
230 typeT.addMember("c", VarType(glu::TYPE_BOOL_VEC4, 0));
231
232 UniformBlock& blockA = m_interface.allocBlock("BlockA");
233 blockA.addUniform(Uniform("a", VarType(glu::TYPE_FLOAT, PRECISION_HIGH)));
234 blockA.addUniform(Uniform("b", VarType(&typeS)));
235 blockA.addUniform(Uniform("c", VarType(glu::TYPE_UINT_VEC3, PRECISION_LOW), UNUSED_BOTH));
236 blockA.setInstanceName("blockA");
237 blockA.setFlags(flagsA);
238
239 UniformBlock& blockB = m_interface.allocBlock("BlockB");
240 blockB.addUniform(Uniform("a", VarType(glu::TYPE_FLOAT_MAT2, PRECISION_MEDIUM)));
241 blockB.addUniform(Uniform("b", VarType(&typeT)));
242 blockB.addUniform(Uniform("c", VarType(glu::TYPE_BOOL_VEC4, 0), UNUSED_BOTH));
243 blockB.addUniform(Uniform("d", VarType(glu::TYPE_BOOL, 0)));
244 blockB.setInstanceName("blockB");
245 blockB.setFlags(flagsB);
246
247 if (numInstances > 0)
248 {
249 blockA.setArraySize(numInstances);
250 blockB.setArraySize(numInstances);
251 }
252
253 init();
254 }
255 };
256
257 class Block2LevelStructArrayCase : public UniformBlockCase
258 {
259 public:
Block2LevelStructArrayCase(tcu::TestContext & testCtx,const std::string & name,const std::string & description,deUint32 layoutFlags,BufferMode bufferMode,int numInstances)260 Block2LevelStructArrayCase (tcu::TestContext& testCtx, const std::string& name, const std::string& description, deUint32 layoutFlags, BufferMode bufferMode, int numInstances)
261 : UniformBlockCase (testCtx, name, description, bufferMode)
262 , m_layoutFlags (layoutFlags)
263 , m_numInstances (numInstances)
264 {
265 StructType& typeS = m_interface.allocStruct("S");
266 typeS.addMember("a", VarType(glu::TYPE_UINT_VEC3, PRECISION_HIGH), UNUSED_BOTH);
267 typeS.addMember("b", VarType(VarType(glu::TYPE_FLOAT_MAT2, PRECISION_MEDIUM), 4));
268 typeS.addMember("c", VarType(glu::TYPE_UINT, PRECISION_LOW));
269
270 UniformBlock& block = m_interface.allocBlock("Block");
271 block.addUniform(Uniform("u", VarType(glu::TYPE_INT, PRECISION_MEDIUM)));
272 block.addUniform(Uniform("s", VarType(VarType(VarType(&typeS), 3), 2)));
273 block.addUniform(Uniform("v", VarType(glu::TYPE_FLOAT_VEC2, PRECISION_MEDIUM)));
274 block.setFlags(m_layoutFlags);
275
276 if (m_numInstances > 0)
277 {
278 block.setInstanceName("block");
279 block.setArraySize(m_numInstances);
280 }
281
282 init();
283 }
284
285 private:
286 deUint32 m_layoutFlags;
287 int m_numInstances;
288 };
289
290 class LinkByBindingCase : public UniformBlockCase
291 {
292 public:
LinkByBindingCase(tcu::TestContext & testCtx,const std::string & name,const std::string & description,BufferMode bufferMode,int numInstances)293 LinkByBindingCase (tcu::TestContext& testCtx, const std::string& name, const std::string& description, BufferMode bufferMode, int numInstances)
294 : UniformBlockCase (testCtx, name, description, bufferMode)
295 {
296 UniformBlock& blockA = m_interface.allocBlock("TestBlock");
297 blockA.addUniform(Uniform("a", VarType(glu::TYPE_FLOAT, PRECISION_HIGH)));
298 blockA.addUniform(Uniform("b", VarType(glu::TYPE_UINT_VEC3, PRECISION_LOW), UNUSED_BOTH));
299 blockA.addUniform(Uniform("c", VarType(glu::TYPE_FLOAT_MAT2, PRECISION_MEDIUM)));
300 blockA.setFlags(LAYOUT_STD140|DECLARE_VERTEX);
301
302 UniformBlock& blockB = m_interface.allocBlock("TestBlock");
303 blockB.addUniform(Uniform("a", VarType(glu::TYPE_FLOAT_MAT3, PRECISION_MEDIUM)));
304 blockB.addUniform(Uniform("b", VarType(glu::TYPE_INT_VEC2, PRECISION_LOW)));
305 blockB.addUniform(Uniform("c", VarType(glu::TYPE_FLOAT_VEC4, PRECISION_HIGH), UNUSED_BOTH));
306 blockB.addUniform(Uniform("d", VarType(glu::TYPE_BOOL, 0)));
307 blockB.setFlags(LAYOUT_STD140|DECLARE_FRAGMENT);
308
309 if (numInstances > 0)
310 {
311 blockA.setInstanceName("testBlock");
312 blockA.setArraySize(numInstances);
313 blockB.setInstanceName("testBlock");
314 blockB.setArraySize(numInstances);
315 }
316
317 init();
318 }
319 };
320
createRandomCaseGroup(tcu::TestCaseGroup * parentGroup,tcu::TestContext & testCtx,const char * groupName,const char * description,UniformBlockCase::BufferMode bufferMode,deUint32 features,int numCases,deUint32 baseSeed)321 void createRandomCaseGroup (tcu::TestCaseGroup* parentGroup, tcu::TestContext& testCtx, const char* groupName, const char* description, UniformBlockCase::BufferMode bufferMode, deUint32 features, int numCases, deUint32 baseSeed)
322 {
323 tcu::TestCaseGroup* group = new tcu::TestCaseGroup(testCtx, groupName, description);
324 parentGroup->addChild(group);
325
326 baseSeed += (deUint32)testCtx.getCommandLine().getBaseSeed();
327
328 for (int ndx = 0; ndx < numCases; ndx++)
329 group->addChild(new RandomUniformBlockCase(testCtx, de::toString(ndx), "", bufferMode, features, (deUint32)ndx + baseSeed));
330 }
331
332 // UniformBlockTests
333
334 class UniformBlockTests : public tcu::TestCaseGroup
335 {
336 public:
337 UniformBlockTests (tcu::TestContext& testCtx);
338 ~UniformBlockTests (void);
339
340 void init (void);
341
342 private:
343 UniformBlockTests (const UniformBlockTests& other);
344 UniformBlockTests& operator= (const UniformBlockTests& other);
345 };
346
UniformBlockTests(tcu::TestContext & testCtx)347 UniformBlockTests::UniformBlockTests (tcu::TestContext& testCtx)
348 : TestCaseGroup(testCtx, "ubo", "Uniform Block tests")
349 {
350 }
351
~UniformBlockTests(void)352 UniformBlockTests::~UniformBlockTests (void)
353 {
354 }
355
init(void)356 void UniformBlockTests::init (void)
357 {
358 static const glu::DataType basicTypes[] =
359 {
360 glu::TYPE_FLOAT,
361 glu::TYPE_FLOAT_VEC2,
362 glu::TYPE_FLOAT_VEC3,
363 glu::TYPE_FLOAT_VEC4,
364 glu::TYPE_INT,
365 glu::TYPE_INT_VEC2,
366 glu::TYPE_INT_VEC3,
367 glu::TYPE_INT_VEC4,
368 glu::TYPE_UINT,
369 glu::TYPE_UINT_VEC2,
370 glu::TYPE_UINT_VEC3,
371 glu::TYPE_UINT_VEC4,
372 glu::TYPE_BOOL,
373 glu::TYPE_BOOL_VEC2,
374 glu::TYPE_BOOL_VEC3,
375 glu::TYPE_BOOL_VEC4,
376 glu::TYPE_FLOAT_MAT2,
377 glu::TYPE_FLOAT_MAT3,
378 glu::TYPE_FLOAT_MAT4,
379 glu::TYPE_FLOAT_MAT2X3,
380 glu::TYPE_FLOAT_MAT2X4,
381 glu::TYPE_FLOAT_MAT3X2,
382 glu::TYPE_FLOAT_MAT3X4,
383 glu::TYPE_FLOAT_MAT4X2,
384 glu::TYPE_FLOAT_MAT4X3
385 };
386
387 static const struct
388 {
389 const std::string name;
390 deUint32 flags;
391 } precisionFlags[] =
392 {
393 // TODO remove PRECISION_LOW because both PRECISION_LOW and PRECISION_MEDIUM means relaxed precision?
394 { "lowp", PRECISION_LOW },
395 { "mediump", PRECISION_MEDIUM },
396 { "highp", PRECISION_HIGH }
397 };
398
399 static const struct
400 {
401 const char* name;
402 deUint32 flags;
403 } layoutFlags[] =
404 {
405 { "std140", LAYOUT_STD140 }
406 };
407
408 static const struct
409 {
410 const std::string name;
411 deUint32 flags;
412 } matrixFlags[] =
413 {
414 { "row_major", LAYOUT_ROW_MAJOR },
415 { "column_major", LAYOUT_COLUMN_MAJOR }
416 };
417
418 static const struct
419 {
420 const char* name;
421 UniformBlockCase::BufferMode mode;
422 } bufferModes[] =
423 {
424 { "per_block_buffer", UniformBlockCase::BUFFERMODE_PER_BLOCK },
425 { "single_buffer", UniformBlockCase::BUFFERMODE_SINGLE }
426 };
427
428 // ubo.2_level_array
429 {
430 tcu::TestCaseGroup* nestedArrayGroup = new tcu::TestCaseGroup(m_testCtx, "2_level_array", "2-level basic array variable in single buffer");
431 addChild(nestedArrayGroup);
432
433 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
434 {
435 tcu::TestCaseGroup* layoutGroup = new tcu::TestCaseGroup(m_testCtx, layoutFlags[layoutFlagNdx].name, "");
436 nestedArrayGroup->addChild(layoutGroup);
437
438 for (int basicTypeNdx = 0; basicTypeNdx < DE_LENGTH_OF_ARRAY(basicTypes); basicTypeNdx++)
439 {
440 const glu::DataType type = basicTypes[basicTypeNdx];
441 const char* typeName = glu::getDataTypeName(type);
442 const int childSize = 4;
443 const int parentSize = 3;
444 const VarType childType (VarType(type, glu::isDataTypeBoolOrBVec(type) ? 0 : PRECISION_HIGH), childSize);
445 const VarType parentType (childType, parentSize);
446
447 createBlockBasicTypeCases(layoutGroup, m_testCtx, typeName, parentType, layoutFlags[layoutFlagNdx].flags);
448
449 if (glu::isDataTypeMatrix(type))
450 {
451 for (int matFlagNdx = 0; matFlagNdx < DE_LENGTH_OF_ARRAY(matrixFlags); matFlagNdx++)
452 createBlockBasicTypeCases(layoutGroup, m_testCtx, (std::string(matrixFlags[matFlagNdx].name) + "_" + typeName),
453 parentType, layoutFlags[layoutFlagNdx].flags|matrixFlags[matFlagNdx].flags);
454 }
455 }
456 }
457 }
458
459 // ubo.3_level_array
460 {
461 tcu::TestCaseGroup* nestedArrayGroup = new tcu::TestCaseGroup(m_testCtx, "3_level_array", "3-level basic array variable in single buffer");
462 addChild(nestedArrayGroup);
463
464 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
465 {
466 tcu::TestCaseGroup* layoutGroup = new tcu::TestCaseGroup(m_testCtx, layoutFlags[layoutFlagNdx].name, "");
467 nestedArrayGroup->addChild(layoutGroup);
468
469 for (int basicTypeNdx = 0; basicTypeNdx < DE_LENGTH_OF_ARRAY(basicTypes); basicTypeNdx++)
470 {
471 const glu::DataType type = basicTypes[basicTypeNdx];
472 const char* typeName = glu::getDataTypeName(type);
473 const int childSize0 = 2;
474 const int childSize1 = 4;
475 const int parentSize = 3;
476 const VarType childType0 (VarType(type, glu::isDataTypeBoolOrBVec(type) ? 0 : PRECISION_HIGH), childSize0);
477 const VarType childType1 (childType0, childSize1);
478 const VarType parentType (childType1, parentSize);
479
480 createBlockBasicTypeCases(layoutGroup, m_testCtx, typeName, parentType, layoutFlags[layoutFlagNdx].flags);
481
482 if (glu::isDataTypeMatrix(type))
483 {
484 for (int matFlagNdx = 0; matFlagNdx < DE_LENGTH_OF_ARRAY(matrixFlags); matFlagNdx++)
485 createBlockBasicTypeCases(layoutGroup, m_testCtx, (std::string(matrixFlags[matFlagNdx].name) + "_" + typeName),
486 parentType, layoutFlags[layoutFlagNdx].flags|matrixFlags[matFlagNdx].flags);
487 }
488 }
489 }
490 }
491
492 // ubo.2_level_struct_array
493 {
494 tcu::TestCaseGroup* structArrayArrayGroup = new tcu::TestCaseGroup(m_testCtx, "2_level_struct_array", "Struct array in one uniform block");
495 addChild(structArrayArrayGroup);
496
497 for (int modeNdx = 0; modeNdx < DE_LENGTH_OF_ARRAY(bufferModes); modeNdx++)
498 {
499 tcu::TestCaseGroup* modeGroup = new tcu::TestCaseGroup(m_testCtx, bufferModes[modeNdx].name, "");
500 structArrayArrayGroup->addChild(modeGroup);
501
502 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
503 {
504 for (int isArray = 0; isArray < 2; isArray++)
505 {
506 std::string baseName = layoutFlags[layoutFlagNdx].name;
507 deUint32 baseFlags = layoutFlags[layoutFlagNdx].flags;
508
509 if (bufferModes[modeNdx].mode == UniformBlockCase::BUFFERMODE_SINGLE && isArray == 0)
510 continue; // Doesn't make sense to add this variant.
511
512 if (isArray)
513 baseName += "_instance_array";
514
515 modeGroup->addChild(new Block2LevelStructArrayCase(m_testCtx, (baseName + "_vertex"), "", baseFlags|DECLARE_VERTEX, bufferModes[modeNdx].mode, isArray ? 3 : 0));
516 modeGroup->addChild(new Block2LevelStructArrayCase(m_testCtx, (baseName + "_fragment"), "", baseFlags|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
517 modeGroup->addChild(new Block2LevelStructArrayCase(m_testCtx, (baseName + "_both"), "", baseFlags|DECLARE_VERTEX|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
518 }
519 }
520 }
521 }
522
523 // ubo.single_basic_type
524 {
525 tcu::TestCaseGroup* singleBasicTypeGroup = new tcu::TestCaseGroup(m_testCtx, "single_basic_type", "Single basic variable in single buffer");
526 addChild(singleBasicTypeGroup);
527
528 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
529 {
530 tcu::TestCaseGroup* layoutGroup = new tcu::TestCaseGroup(m_testCtx, layoutFlags[layoutFlagNdx].name, "");
531 singleBasicTypeGroup->addChild(layoutGroup);
532
533 for (int basicTypeNdx = 0; basicTypeNdx < DE_LENGTH_OF_ARRAY(basicTypes); basicTypeNdx++)
534 {
535 glu::DataType type = basicTypes[basicTypeNdx];
536 const char* typeName = glu::getDataTypeName(type);
537
538 if (glu::isDataTypeBoolOrBVec(type))
539 createBlockBasicTypeCases(layoutGroup, m_testCtx, typeName, VarType(type, 0), layoutFlags[layoutFlagNdx].flags);
540 else
541 {
542 for (int precNdx = 0; precNdx < DE_LENGTH_OF_ARRAY(precisionFlags); precNdx++)
543 createBlockBasicTypeCases(layoutGroup, m_testCtx, precisionFlags[precNdx].name + "_" + typeName,
544 VarType(type, precisionFlags[precNdx].flags), layoutFlags[layoutFlagNdx].flags);
545 }
546
547 if (glu::isDataTypeMatrix(type))
548 {
549 for (int matFlagNdx = 0; matFlagNdx < DE_LENGTH_OF_ARRAY(matrixFlags); matFlagNdx++)
550 {
551 for (int precNdx = 0; precNdx < DE_LENGTH_OF_ARRAY(precisionFlags); precNdx++)
552 createBlockBasicTypeCases(layoutGroup, m_testCtx, matrixFlags[matFlagNdx].name + "_" + precisionFlags[precNdx].name + "_" + typeName,
553 VarType(type, precisionFlags[precNdx].flags), layoutFlags[layoutFlagNdx].flags|matrixFlags[matFlagNdx].flags);
554 }
555 }
556 }
557 }
558 }
559
560 // ubo.single_basic_array
561 {
562 tcu::TestCaseGroup* singleBasicArrayGroup = new tcu::TestCaseGroup(m_testCtx, "single_basic_array", "Single basic array variable in single buffer");
563 addChild(singleBasicArrayGroup);
564
565 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
566 {
567 tcu::TestCaseGroup* layoutGroup = new tcu::TestCaseGroup(m_testCtx, layoutFlags[layoutFlagNdx].name, "");
568 singleBasicArrayGroup->addChild(layoutGroup);
569
570 for (int basicTypeNdx = 0; basicTypeNdx < DE_LENGTH_OF_ARRAY(basicTypes); basicTypeNdx++)
571 {
572 glu::DataType type = basicTypes[basicTypeNdx];
573 const char* typeName = glu::getDataTypeName(type);
574 const int arraySize = 3;
575
576 createBlockBasicTypeCases(layoutGroup, m_testCtx, typeName,
577 VarType(VarType(type, glu::isDataTypeBoolOrBVec(type) ? 0 : PRECISION_HIGH), arraySize),
578 layoutFlags[layoutFlagNdx].flags);
579
580 if (glu::isDataTypeMatrix(type))
581 {
582 for (int matFlagNdx = 0; matFlagNdx < DE_LENGTH_OF_ARRAY(matrixFlags); matFlagNdx++)
583 createBlockBasicTypeCases(layoutGroup, m_testCtx, matrixFlags[matFlagNdx].name + "_" + typeName,
584 VarType(VarType(type, PRECISION_HIGH), arraySize),
585 layoutFlags[layoutFlagNdx].flags|matrixFlags[matFlagNdx].flags);
586 }
587 }
588 }
589 }
590
591 // ubo.single_struct
592 {
593 tcu::TestCaseGroup* singleStructGroup = new tcu::TestCaseGroup(m_testCtx, "single_struct", "Single struct in uniform block");
594 addChild(singleStructGroup);
595
596 for (int modeNdx = 0; modeNdx < DE_LENGTH_OF_ARRAY(bufferModes); modeNdx++)
597 {
598 tcu::TestCaseGroup* modeGroup = new tcu::TestCaseGroup(m_testCtx, bufferModes[modeNdx].name, "");
599 singleStructGroup->addChild(modeGroup);
600
601 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
602 {
603 for (int isArray = 0; isArray < 2; isArray++)
604 {
605 std::string baseName = layoutFlags[layoutFlagNdx].name;
606 deUint32 baseFlags = layoutFlags[layoutFlagNdx].flags;
607
608 if (bufferModes[modeNdx].mode == UniformBlockCase::BUFFERMODE_SINGLE && isArray == 0)
609 continue; // Doesn't make sense to add this variant.
610
611 if (isArray)
612 baseName += "_instance_array";
613
614 modeGroup->addChild(new BlockSingleStructCase(m_testCtx, baseName + "_vertex", "", baseFlags|DECLARE_VERTEX, bufferModes[modeNdx].mode, isArray ? 3 : 0));
615 modeGroup->addChild(new BlockSingleStructCase(m_testCtx, baseName + "_fragment", "", baseFlags|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
616 modeGroup->addChild(new BlockSingleStructCase(m_testCtx, baseName + "_both", "", baseFlags|DECLARE_VERTEX|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
617 }
618 }
619 }
620 }
621
622 // ubo.single_struct_array
623 {
624 tcu::TestCaseGroup* singleStructArrayGroup = new tcu::TestCaseGroup(m_testCtx, "single_struct_array", "Struct array in one uniform block");
625 addChild(singleStructArrayGroup);
626
627 for (int modeNdx = 0; modeNdx < DE_LENGTH_OF_ARRAY(bufferModes); modeNdx++)
628 {
629 tcu::TestCaseGroup* modeGroup = new tcu::TestCaseGroup(m_testCtx, bufferModes[modeNdx].name, "");
630 singleStructArrayGroup->addChild(modeGroup);
631
632 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
633 {
634 for (int isArray = 0; isArray < 2; isArray++)
635 {
636 std::string baseName = layoutFlags[layoutFlagNdx].name;
637 deUint32 baseFlags = layoutFlags[layoutFlagNdx].flags;
638
639 if (bufferModes[modeNdx].mode == UniformBlockCase::BUFFERMODE_SINGLE && isArray == 0)
640 continue; // Doesn't make sense to add this variant.
641
642 if (isArray)
643 baseName += "_instance_array";
644
645 modeGroup->addChild(new BlockSingleStructArrayCase(m_testCtx, baseName + "_vertex", "", baseFlags|DECLARE_VERTEX, bufferModes[modeNdx].mode, isArray ? 3 : 0));
646 modeGroup->addChild(new BlockSingleStructArrayCase(m_testCtx, baseName + "_fragment", "", baseFlags|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
647 modeGroup->addChild(new BlockSingleStructArrayCase(m_testCtx, baseName + "_both", "", baseFlags|DECLARE_VERTEX|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
648 }
649 }
650 }
651 }
652
653 // ubo.single_nested_struct
654 {
655 tcu::TestCaseGroup* singleNestedStructGroup = new tcu::TestCaseGroup(m_testCtx, "single_nested_struct", "Nested struct in one uniform block");
656 addChild(singleNestedStructGroup);
657
658 for (int modeNdx = 0; modeNdx < DE_LENGTH_OF_ARRAY(bufferModes); modeNdx++)
659 {
660 tcu::TestCaseGroup* modeGroup = new tcu::TestCaseGroup(m_testCtx, bufferModes[modeNdx].name, "");
661 singleNestedStructGroup->addChild(modeGroup);
662
663 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
664 {
665 for (int isArray = 0; isArray < 2; isArray++)
666 {
667 std::string baseName = layoutFlags[layoutFlagNdx].name;
668 deUint32 baseFlags = layoutFlags[layoutFlagNdx].flags;
669
670 if (bufferModes[modeNdx].mode == UniformBlockCase::BUFFERMODE_SINGLE && isArray == 0)
671 continue; // Doesn't make sense to add this variant.
672
673 if (isArray)
674 baseName += "_instance_array";
675
676 modeGroup->addChild(new BlockSingleNestedStructCase(m_testCtx, baseName + "_vertex", "", baseFlags|DECLARE_VERTEX, bufferModes[modeNdx].mode, isArray ? 3 : 0));
677 modeGroup->addChild(new BlockSingleNestedStructCase(m_testCtx, baseName + "_fragment", "", baseFlags|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
678 modeGroup->addChild(new BlockSingleNestedStructCase(m_testCtx, baseName + "_both", "", baseFlags|DECLARE_VERTEX|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
679 }
680 }
681 }
682 }
683
684 // ubo.single_nested_struct_array
685 {
686 tcu::TestCaseGroup* singleNestedStructArrayGroup = new tcu::TestCaseGroup(m_testCtx, "single_nested_struct_array", "Nested struct array in one uniform block");
687 addChild(singleNestedStructArrayGroup);
688
689 for (int modeNdx = 0; modeNdx < DE_LENGTH_OF_ARRAY(bufferModes); modeNdx++)
690 {
691 tcu::TestCaseGroup* modeGroup = new tcu::TestCaseGroup(m_testCtx, bufferModes[modeNdx].name, "");
692 singleNestedStructArrayGroup->addChild(modeGroup);
693
694 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
695 {
696 for (int isArray = 0; isArray < 2; isArray++)
697 {
698 std::string baseName = layoutFlags[layoutFlagNdx].name;
699 deUint32 baseFlags = layoutFlags[layoutFlagNdx].flags;
700
701 if (bufferModes[modeNdx].mode == UniformBlockCase::BUFFERMODE_SINGLE && isArray == 0)
702 continue; // Doesn't make sense to add this variant.
703
704 if (isArray)
705 baseName += "_instance_array";
706
707 modeGroup->addChild(new BlockSingleNestedStructArrayCase(m_testCtx, baseName + "_vertex", "", baseFlags|DECLARE_VERTEX, bufferModes[modeNdx].mode, isArray ? 3 : 0));
708 modeGroup->addChild(new BlockSingleNestedStructArrayCase(m_testCtx, baseName + "_fragment", "", baseFlags|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
709 modeGroup->addChild(new BlockSingleNestedStructArrayCase(m_testCtx, baseName + "_both", "", baseFlags|DECLARE_VERTEX|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
710 }
711 }
712 }
713 }
714
715 // ubo.instance_array_basic_type
716 {
717 tcu::TestCaseGroup* instanceArrayBasicTypeGroup = new tcu::TestCaseGroup(m_testCtx, "instance_array_basic_type", "Single basic variable in instance array");
718 addChild(instanceArrayBasicTypeGroup);
719
720 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
721 {
722 tcu::TestCaseGroup* layoutGroup = new tcu::TestCaseGroup(m_testCtx, layoutFlags[layoutFlagNdx].name, "");
723 instanceArrayBasicTypeGroup->addChild(layoutGroup);
724
725 for (int basicTypeNdx = 0; basicTypeNdx < DE_LENGTH_OF_ARRAY(basicTypes); basicTypeNdx++)
726 {
727 glu::DataType type = basicTypes[basicTypeNdx];
728 const char* typeName = glu::getDataTypeName(type);
729 const int numInstances = 3;
730
731 createBlockBasicTypeCases(layoutGroup, m_testCtx, typeName,
732 VarType(type, glu::isDataTypeBoolOrBVec(type) ? 0 : PRECISION_HIGH),
733 layoutFlags[layoutFlagNdx].flags, numInstances);
734
735 if (glu::isDataTypeMatrix(type))
736 {
737 for (int matFlagNdx = 0; matFlagNdx < DE_LENGTH_OF_ARRAY(matrixFlags); matFlagNdx++)
738 createBlockBasicTypeCases(layoutGroup, m_testCtx, matrixFlags[matFlagNdx].name + "_" + typeName,
739 VarType(type, PRECISION_HIGH), layoutFlags[layoutFlagNdx].flags|matrixFlags[matFlagNdx].flags,
740 numInstances);
741 }
742 }
743 }
744 }
745
746 // ubo.multi_basic_types
747 {
748 tcu::TestCaseGroup* multiBasicTypesGroup = new tcu::TestCaseGroup(m_testCtx, "multi_basic_types", "Multiple buffers with basic types");
749 addChild(multiBasicTypesGroup);
750
751 for (int modeNdx = 0; modeNdx < DE_LENGTH_OF_ARRAY(bufferModes); modeNdx++)
752 {
753 tcu::TestCaseGroup* modeGroup = new tcu::TestCaseGroup(m_testCtx, bufferModes[modeNdx].name, "");
754 multiBasicTypesGroup->addChild(modeGroup);
755
756 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
757 {
758 for (int isArray = 0; isArray < 2; isArray++)
759 {
760 std::string baseName = layoutFlags[layoutFlagNdx].name;
761 deUint32 baseFlags = layoutFlags[layoutFlagNdx].flags;
762
763 if (isArray)
764 baseName += "_instance_array";
765
766 modeGroup->addChild(new BlockMultiBasicTypesCase(m_testCtx, baseName + "_vertex", "", baseFlags|DECLARE_VERTEX, baseFlags|DECLARE_VERTEX, bufferModes[modeNdx].mode, isArray ? 3 : 0));
767 modeGroup->addChild(new BlockMultiBasicTypesCase(m_testCtx, baseName + "_fragment", "", baseFlags|DECLARE_FRAGMENT, baseFlags|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
768 modeGroup->addChild(new BlockMultiBasicTypesCase(m_testCtx, baseName + "_both", "", baseFlags|DECLARE_VERTEX|DECLARE_FRAGMENT, baseFlags|DECLARE_VERTEX|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
769 modeGroup->addChild(new BlockMultiBasicTypesCase(m_testCtx, baseName + "_mixed", "", baseFlags|DECLARE_VERTEX, baseFlags|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
770 }
771 }
772 }
773 }
774
775 // ubo.multi_nested_struct
776 {
777 tcu::TestCaseGroup* multiNestedStructGroup = new tcu::TestCaseGroup(m_testCtx, "multi_nested_struct", "Multiple buffers with nested structs");
778 addChild(multiNestedStructGroup);
779
780 for (int modeNdx = 0; modeNdx < DE_LENGTH_OF_ARRAY(bufferModes); modeNdx++)
781 {
782 tcu::TestCaseGroup* modeGroup = new tcu::TestCaseGroup(m_testCtx, bufferModes[modeNdx].name, "");
783 multiNestedStructGroup->addChild(modeGroup);
784
785 for (int layoutFlagNdx = 0; layoutFlagNdx < DE_LENGTH_OF_ARRAY(layoutFlags); layoutFlagNdx++)
786 {
787 for (int isArray = 0; isArray < 2; isArray++)
788 {
789 std::string baseName = layoutFlags[layoutFlagNdx].name;
790 deUint32 baseFlags = layoutFlags[layoutFlagNdx].flags;
791
792 if (isArray)
793 baseName += "_instance_array";
794
795 modeGroup->addChild(new BlockMultiNestedStructCase(m_testCtx, baseName + "_vertex", "", baseFlags|DECLARE_VERTEX, baseFlags|DECLARE_VERTEX, bufferModes[modeNdx].mode, isArray ? 3 : 0));
796 modeGroup->addChild(new BlockMultiNestedStructCase(m_testCtx, baseName + "_fragment", "", baseFlags|DECLARE_FRAGMENT, baseFlags|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
797 modeGroup->addChild(new BlockMultiNestedStructCase(m_testCtx, baseName + "_both", "", baseFlags|DECLARE_VERTEX|DECLARE_FRAGMENT, baseFlags|DECLARE_VERTEX|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
798 modeGroup->addChild(new BlockMultiNestedStructCase(m_testCtx, baseName + "_mixed", "", baseFlags|DECLARE_VERTEX, baseFlags|DECLARE_FRAGMENT, bufferModes[modeNdx].mode, isArray ? 3 : 0));
799 }
800 }
801 }
802 }
803
804 // .link_by_binding
805 {
806 tcu::TestCaseGroup* linkByBindingGroup = new tcu::TestCaseGroup(m_testCtx, "link_by_binding", "Blocks with same name but different binding");
807 addChild(linkByBindingGroup);
808
809 linkByBindingGroup->addChild(new LinkByBindingCase(m_testCtx, "single_buf_single_instance", "", UniformBlockCase::BUFFERMODE_SINGLE, 0));
810 linkByBindingGroup->addChild(new LinkByBindingCase(m_testCtx, "single_buf_instance_array", "", UniformBlockCase::BUFFERMODE_SINGLE, 2));
811 linkByBindingGroup->addChild(new LinkByBindingCase(m_testCtx, "per_block_buf_single_instance", "", UniformBlockCase::BUFFERMODE_PER_BLOCK, 0));
812 linkByBindingGroup->addChild(new LinkByBindingCase(m_testCtx, "per_block_buf_instance_array", "", UniformBlockCase::BUFFERMODE_PER_BLOCK, 2));
813 }
814
815 // ubo.random
816 {
817 const deUint32 allShaders = FEATURE_VERTEX_BLOCKS|FEATURE_FRAGMENT_BLOCKS|FEATURE_SHARED_BLOCKS;
818 const deUint32 allLayouts = FEATURE_STD140_LAYOUT;
819 const deUint32 allBasicTypes = FEATURE_VECTORS|FEATURE_MATRICES;
820 const deUint32 unused = FEATURE_UNUSED_MEMBERS|FEATURE_UNUSED_UNIFORMS;
821 const deUint32 matFlags = FEATURE_MATRIX_LAYOUT;
822 const deUint32 allFeatures = ~FEATURE_ARRAYS_OF_ARRAYS;
823
824 tcu::TestCaseGroup* randomGroup = new tcu::TestCaseGroup(m_testCtx, "random", "Random Uniform Block cases");
825 addChild(randomGroup);
826
827 // Basic types.
828 createRandomCaseGroup(randomGroup, m_testCtx, "scalar_types", "Scalar types only, per-block buffers", UniformBlockCase::BUFFERMODE_PER_BLOCK, allShaders|allLayouts|unused, 25, 0);
829 createRandomCaseGroup(randomGroup, m_testCtx, "vector_types", "Scalar and vector types only, per-block buffers", UniformBlockCase::BUFFERMODE_PER_BLOCK, allShaders|allLayouts|unused|FEATURE_VECTORS, 25, 25);
830 createRandomCaseGroup(randomGroup, m_testCtx, "basic_types", "All basic types, per-block buffers", UniformBlockCase::BUFFERMODE_PER_BLOCK, allShaders|allLayouts|unused|allBasicTypes|matFlags, 25, 50);
831 createRandomCaseGroup(randomGroup, m_testCtx, "basic_arrays", "Arrays, per-block buffers", UniformBlockCase::BUFFERMODE_PER_BLOCK, allShaders|allLayouts|unused|allBasicTypes|matFlags|FEATURE_ARRAYS, 25, 50);
832
833 createRandomCaseGroup(randomGroup, m_testCtx, "basic_instance_arrays", "Basic instance arrays, per-block buffers", UniformBlockCase::BUFFERMODE_PER_BLOCK, allShaders|allLayouts|unused|allBasicTypes|matFlags|FEATURE_INSTANCE_ARRAYS, 25, 75);
834 createRandomCaseGroup(randomGroup, m_testCtx, "nested_structs", "Nested structs, per-block buffers", UniformBlockCase::BUFFERMODE_PER_BLOCK, allShaders|allLayouts|unused|allBasicTypes|matFlags|FEATURE_STRUCTS, 25, 100);
835 createRandomCaseGroup(randomGroup, m_testCtx, "nested_structs_arrays", "Nested structs, arrays, per-block buffers", UniformBlockCase::BUFFERMODE_PER_BLOCK, allShaders|allLayouts|unused|allBasicTypes|matFlags|FEATURE_STRUCTS|FEATURE_ARRAYS, 25, 150);
836 createRandomCaseGroup(randomGroup, m_testCtx, "nested_structs_instance_arrays", "Nested structs, instance arrays, per-block buffers", UniformBlockCase::BUFFERMODE_PER_BLOCK, allShaders|allLayouts|unused|allBasicTypes|matFlags|FEATURE_STRUCTS|FEATURE_INSTANCE_ARRAYS, 25, 125);
837 createRandomCaseGroup(randomGroup, m_testCtx, "nested_structs_arrays_instance_arrays", "Nested structs, instance arrays, per-block buffers", UniformBlockCase::BUFFERMODE_PER_BLOCK, allShaders|allLayouts|unused|allBasicTypes|matFlags|FEATURE_STRUCTS|FEATURE_ARRAYS|FEATURE_INSTANCE_ARRAYS, 25, 175);
838
839 createRandomCaseGroup(randomGroup, m_testCtx, "all_per_block_buffers", "All random features, per-block buffers", UniformBlockCase::BUFFERMODE_PER_BLOCK, allFeatures, 50, 200);
840 createRandomCaseGroup(randomGroup, m_testCtx, "all_shared_buffer", "All random features, shared buffer", UniformBlockCase::BUFFERMODE_SINGLE, allFeatures, 50, 250);
841 }
842 }
843
844 } // anonymous
845
createTests(tcu::TestContext & testCtx)846 tcu::TestCaseGroup* createTests (tcu::TestContext& testCtx)
847 {
848 return new UniformBlockTests(testCtx);
849 }
850
851 } // ubo
852 } // vkt
853