1 #ifndef _GLSUNIFORMBLOCKCASE_HPP
2 #define _GLSUNIFORMBLOCKCASE_HPP
3 /*-------------------------------------------------------------------------
4 * drawElements Quality Program OpenGL (ES) Module
5 * -----------------------------------------------
7 * Copyright 2014 The Android Open Source Project
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
13 * http://www.apache.org/licenses/LICENSE-2.0
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.
23 * \brief Uniform block tests.
24 *//*--------------------------------------------------------------------*/
26 #include "tcuDefs.hpp"
27 #include "tcuTestCase.hpp"
28 #include "gluShaderUtil.hpp"
40 // Uniform block details.
46 PRECISION_LOW = (1<<0),
47 PRECISION_MEDIUM = (1<<1),
48 PRECISION_HIGH = (1<<2),
49 PRECISION_MASK = PRECISION_LOW|PRECISION_MEDIUM|PRECISION_HIGH,
51 LAYOUT_SHARED = (1<<3),
52 LAYOUT_PACKED = (1<<4),
53 LAYOUT_STD140 = (1<<5),
54 LAYOUT_ROW_MAJOR = (1<<6),
55 LAYOUT_COLUMN_MAJOR = (1<<7), //!< \note Lack of both flags means column-major matrix.
56 LAYOUT_MASK = LAYOUT_SHARED|LAYOUT_PACKED|LAYOUT_STD140|LAYOUT_ROW_MAJOR|LAYOUT_COLUMN_MAJOR,
58 DECLARE_VERTEX = (1<<8),
59 DECLARE_FRAGMENT = (1<<9),
60 DECLARE_BOTH = DECLARE_VERTEX|DECLARE_FRAGMENT,
62 UNUSED_VERTEX = (1<<10), //!< Uniform or struct member is not read in vertex shader.
63 UNUSED_FRAGMENT = (1<<11), //!< Uniform or struct member is not read in fragment shader.
64 UNUSED_BOTH = UNUSED_VERTEX|UNUSED_FRAGMENT
67 // \todo [2012-07-25 pyry] Use glu::VarType.
75 VarType (const VarType& other);
76 VarType (glu::DataType basicType, deUint32 flags);
77 VarType (const VarType& elementType, int arraySize);
78 explicit VarType (const StructType* structPtr);
81 bool isBasicType (void) const { return m_type == TYPE_BASIC; }
82 bool isArrayType (void) const { return m_type == TYPE_ARRAY; }
83 bool isStructType (void) const { return m_type == TYPE_STRUCT; }
85 deUint32 getFlags (void) const { return m_flags; }
86 glu::DataType getBasicType (void) const { return m_data.basicType; }
88 const VarType& getElementType (void) const { return *m_data.array.elementType; }
89 int getArraySize (void) const { return m_data.array.size; }
91 const StructType& getStruct (void) const { return *m_data.structPtr; }
93 VarType& operator= (const VarType& other);
109 glu::DataType basicType;
112 VarType* elementType;
115 const StructType* structPtr;
119 array.elementType = DE_NULL;
128 StructMember (const char* name, const VarType& type, deUint32 flags) : m_name(name), m_type(type), m_flags(flags) {}
129 StructMember (void) : m_flags(0) {}
131 const char* getName (void) const { return m_name.c_str(); }
132 const VarType& getType (void) const { return m_type; }
133 deUint32 getFlags (void) const { return m_flags; }
144 typedef std::vector<StructMember>::iterator Iterator;
145 typedef std::vector<StructMember>::const_iterator ConstIterator;
147 StructType (const char* typeName) : m_typeName(typeName) {}
148 ~StructType (void) {}
150 const char* getTypeName (void) const { return m_typeName.empty() ? DE_NULL : m_typeName.c_str(); }
152 inline Iterator begin (void) { return m_members.begin(); }
153 inline ConstIterator begin (void) const { return m_members.begin(); }
154 inline Iterator end (void) { return m_members.end(); }
155 inline ConstIterator end (void) const { return m_members.end(); }
157 void addMember (const char* name, const VarType& type, deUint32 flags = 0);
160 std::string m_typeName;
161 std::vector<StructMember> m_members;
167 Uniform (const char* name, const VarType& type, deUint32 flags = 0);
169 const char* getName (void) const { return m_name.c_str(); }
170 const VarType& getType (void) const { return m_type; }
171 deUint32 getFlags (void) const { return m_flags; }
182 typedef std::vector<Uniform>::iterator Iterator;
183 typedef std::vector<Uniform>::const_iterator ConstIterator;
185 UniformBlock (const char* blockName);
187 const char* getBlockName (void) const { return m_blockName.c_str(); }
188 const char* getInstanceName (void) const { return m_instanceName.empty() ? DE_NULL : m_instanceName.c_str(); }
189 bool isArray (void) const { return m_arraySize > 0; }
190 int getArraySize (void) const { return m_arraySize; }
191 deUint32 getFlags (void) const { return m_flags; }
193 void setInstanceName (const char* name) { m_instanceName = name; }
194 void setFlags (deUint32 flags) { m_flags = flags; }
195 void setArraySize (int arraySize) { m_arraySize = arraySize; }
196 void addUniform (const Uniform& uniform) { m_uniforms.push_back(uniform); }
198 inline Iterator begin (void) { return m_uniforms.begin(); }
199 inline ConstIterator begin (void) const { return m_uniforms.begin(); }
200 inline Iterator end (void) { return m_uniforms.end(); }
201 inline ConstIterator end (void) const { return m_uniforms.end(); }
204 std::string m_blockName;
205 std::string m_instanceName;
206 std::vector<Uniform> m_uniforms;
207 int m_arraySize; //!< Array size or 0 if not interface block array.
211 class ShaderInterface
214 ShaderInterface (void);
215 ~ShaderInterface (void);
217 StructType& allocStruct (const char* name);
218 const StructType* findStruct (const char* name) const;
219 void getNamedStructs (std::vector<const StructType*>& structs) const;
221 UniformBlock& allocBlock (const char* name);
223 int getNumUniformBlocks (void) const { return (int)m_uniformBlocks.size(); }
224 const UniformBlock& getUniformBlock (int ndx) const { return *m_uniformBlocks[ndx]; }
227 std::vector<StructType*> m_structs;
228 std::vector<UniformBlock*> m_uniformBlocks;
235 class UniformBlockCase : public tcu::TestCase
240 BUFFERMODE_SINGLE = 0, //!< Single buffer shared between uniform blocks.
241 BUFFERMODE_PER_BLOCK, //!< Per-block buffers
246 UniformBlockCase (tcu::TestContext& testCtx, glu::RenderContext& renderCtx, const char* name, const char* description, glu::GLSLVersion glslVersion, BufferMode bufferMode);
247 ~UniformBlockCase (void);
249 IterateResult iterate (void);
252 bool compareStd140Blocks (const ub::UniformLayout& refLayout, const ub::UniformLayout& cmpLayout) const;
253 bool compareSharedBlocks (const ub::UniformLayout& refLayout, const ub::UniformLayout& cmpLayout) const;
254 bool compareTypes (const ub::UniformLayout& refLayout, const ub::UniformLayout& cmpLayout) const;
255 bool checkLayoutIndices (const ub::UniformLayout& layout) const;
256 bool checkLayoutBounds (const ub::UniformLayout& layout) const;
257 bool checkIndexQueries (deUint32 program, const ub::UniformLayout& layout) const;
259 bool render (deUint32 program) const;
261 glu::RenderContext& m_renderCtx;
262 glu::GLSLVersion m_glslVersion;
263 BufferMode m_bufferMode;
264 ub::ShaderInterface m_interface;
270 #endif // _GLSUNIFORMBLOCKCASE_HPP