Home | History | Annotate | Download | only in functional
      1 /*-------------------------------------------------------------------------
      2  * drawElements Quality Program OpenGL ES 3.0 Module
      3  * -------------------------------------------------
      4  *
      5  * Copyright 2014 The Android Open Source Project
      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 Occlusion query tests.
     22  *//*--------------------------------------------------------------------*/
     23 
     24 #include "es3fOcclusionQueryTests.hpp"
     25 
     26 #include "tcuTestLog.hpp"
     27 #include "tcuVector.hpp"
     28 #include "tcuSurface.hpp"
     29 #include "tcuRenderTarget.hpp"
     30 #include "gluShaderProgram.hpp"
     31 #include "gluPixelTransfer.hpp"
     32 #include "deRandom.hpp"
     33 #include "deString.h"
     34 
     35 #include "glw.h"
     36 
     37 namespace deqp
     38 {
     39 namespace gles3
     40 {
     41 namespace Functional
     42 {
     43 
     44 static const tcu::Vec4	DEPTH_WRITE_COLOR	= tcu::Vec4(0.0f, 0.0f, 1.0f, 1.0f);
     45 static const tcu::Vec4	DEPTH_CLEAR_COLOR	= tcu::Vec4(0.0f, 0.5f, 0.8f, 1.0f);
     46 static const tcu::Vec4	STENCIL_WRITE_COLOR	= tcu::Vec4(0.0f, 1.0f, 0.0f, 1.0f);
     47 static const tcu::Vec4	STENCIL_CLEAR_COLOR	= tcu::Vec4(0.0f, 0.8f, 0.5f, 1.0f);
     48 static const tcu::Vec4	TARGET_COLOR		= tcu::Vec4(1.0f, 0.0f, 0.0f, 1.0f);
     49 static const int		ELEMENTS_PER_VERTEX = 4;
     50 static const int		NUM_CASE_ITERATIONS = 10;
     51 
     52 // Constants to tweak visible/invisible case probability balance.
     53 
     54 static const int		DEPTH_CLEAR_OFFSET		= 100;
     55 static const int		STENCIL_CLEAR_OFFSET	= 100;
     56 static const int		SCISSOR_OFFSET			= 100;
     57 static const int		SCISSOR_MINSIZE			= 250;
     58 
     59 enum OccluderType
     60 {
     61 	OCCLUDER_SCISSOR		= (1 << 0),
     62 	OCCLUDER_DEPTH_WRITE	= (1 << 1),
     63 	OCCLUDER_DEPTH_CLEAR	= (1 << 2),
     64 	OCCLUDER_STENCIL_WRITE	= (1 << 3),
     65 	OCCLUDER_STENCIL_CLEAR	= (1 << 4)
     66 };
     67 
     68 class OcclusionQueryCase : public TestCase
     69 {
     70 public:
     71 								OcclusionQueryCase		(Context& context, const char* name, const char* description,int numOccluderDraws, int numOccludersPerDraw, float occluderSize, int numTargetDraws, int numTargetsPerDraw, float targetSize, deUint32 queryMode, deUint32 occluderTypes);
     72 								~OcclusionQueryCase		(void);
     73 
     74 	void						init					(void);
     75 	void						deinit					(void);
     76 	IterateResult				iterate					(void);
     77 
     78 private:
     79 								OcclusionQueryCase		(const OcclusionQueryCase& other);
     80 	OcclusionQueryCase&			operator=				(const OcclusionQueryCase& other);
     81 
     82 	int							m_numOccluderDraws;
     83 	int							m_numOccludersPerDraw;
     84 	float						m_occluderSize;
     85 	int							m_numTargetDraws;
     86 	int							m_numTargetsPerDraw;
     87 	float						m_targetSize;
     88 	deUint32					m_queryMode;
     89 	deUint32					m_occluderTypes;
     90 
     91 	glu::RenderContext&			m_renderCtx;
     92 	glu::ShaderProgram*			m_program;
     93 	int							m_iterNdx;
     94 	de::Random					m_rnd;
     95 };
     96 
     97 OcclusionQueryCase::OcclusionQueryCase (Context& context, const char* name, const char* description, int numOccluderDraws, int numOccludersPerDraw, float occluderSize, int numTargetDraws, int numTargetsPerDraw, float targetSize, deUint32 queryMode, deUint32 occluderTypes)
     98 	: TestCase				(context, name, description)
     99 	, m_numOccluderDraws	(numOccluderDraws)
    100 	, m_numOccludersPerDraw	(numOccludersPerDraw)
    101 	, m_occluderSize		(occluderSize)
    102 	, m_numTargetDraws		(numTargetDraws)
    103 	, m_numTargetsPerDraw	(numTargetsPerDraw)
    104 	, m_targetSize			(targetSize)
    105 	, m_queryMode			(queryMode)
    106 	, m_occluderTypes		(occluderTypes)
    107 	, m_renderCtx			(context.getRenderContext())
    108 	, m_program				(DE_NULL)
    109 	, m_iterNdx				(0)
    110 	, m_rnd					(deStringHash(name))
    111 {
    112 }
    113 
    114 OcclusionQueryCase::~OcclusionQueryCase (void)
    115 {
    116 	OcclusionQueryCase::deinit();
    117 }
    118 
    119 static void generateVertices (std::vector<float>& dst, float width, float height, int primitiveCount, int verticesPerPrimitive, de::Random rnd, float primitiveSize, float minZ, float maxZ)
    120 {
    121 	float w = width/2.0f;
    122 	float h = height/2.0f;
    123 	float s = primitiveSize/2.0f;
    124 
    125 	int vertexCount = verticesPerPrimitive * primitiveCount;
    126 	dst.resize(vertexCount * ELEMENTS_PER_VERTEX);
    127 
    128 	for (int i = 0; i < vertexCount; i += 3)			// First loop gets a random point inside unit square
    129 	{
    130 		float rndX = rnd.getFloat(-w, w);
    131 		float rndY = rnd.getFloat(-h, h);
    132 
    133 		for (int j = 0; j < verticesPerPrimitive; j++)	// Second loop gets 3 random points within given distance s from (rndX, rndY)
    134 		{
    135 			dst[(i+j)*ELEMENTS_PER_VERTEX    ] = rndX + rnd.getFloat(-s,s);	// x
    136 			dst[(i+j)*ELEMENTS_PER_VERTEX + 1] = rndY + rnd.getFloat(-s,s);	// y
    137 			dst[(i+j)*ELEMENTS_PER_VERTEX + 2] = rnd.getFloat(minZ, maxZ);	// z
    138 			dst[(i+j)*ELEMENTS_PER_VERTEX + 3] = 1.0f;						// w
    139 		}
    140 	}
    141 }
    142 
    143 void OcclusionQueryCase::init (void)
    144 {
    145 	const char*	vertShaderSource =
    146 				"#version 300 es\n"
    147 				"layout(location = 0) in mediump vec4 a_position;\n"
    148 				"\n"
    149 				"void main (void)\n"
    150 				"{\n"
    151 				"	gl_Position = a_position;\n"
    152 				"}\n";
    153 
    154 	const char* fragShaderSource =
    155 				"#version 300 es\n"
    156 				"layout(location = 0) out mediump vec4 dEQP_FragColor;\n"
    157 				"uniform mediump vec4 u_color;\n"
    158 				"\n"
    159 				"void main (void)\n"
    160 				"{\n"
    161 				"	mediump float depth_gradient = gl_FragCoord.z;\n"
    162 				"	mediump float bias = 0.1;\n"
    163 				"	dEQP_FragColor = vec4(u_color.xyz * (depth_gradient + bias), 1.0);\n"
    164 				"}\n";
    165 
    166 	DE_ASSERT(!m_program);
    167 	m_program = new glu::ShaderProgram(m_context.getRenderContext(), glu::makeVtxFragSources(vertShaderSource, fragShaderSource));
    168 
    169 	if (!m_program->isOk())
    170 	{
    171 		m_testCtx.getLog() << *m_program;
    172 		delete m_program;
    173 		m_program = DE_NULL;
    174 		TCU_FAIL("Failed to compile shader program");
    175 	}
    176 
    177 	m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass"); // Initialize test result to pass.
    178 	GLU_CHECK_MSG ("Case initialization finished");
    179 }
    180 
    181 void OcclusionQueryCase::deinit (void)
    182 {
    183 	delete m_program;
    184 	m_program = DE_NULL;
    185 }
    186 
    187 OcclusionQueryCase::IterateResult OcclusionQueryCase::iterate (void)
    188 {
    189 	tcu::TestLog&				log					= m_testCtx.getLog();
    190 	const tcu::RenderTarget&	renderTarget		= m_context.getRenderTarget();
    191 	deUint32					colorUnif			= glGetUniformLocation(m_program->getProgram(), "u_color");
    192 
    193 	std::vector<float>			occluderVertices;
    194 	std::vector<float>			targetVertices;
    195 	std::vector<deUint32>		queryIds(1, 0);
    196 	bool						queryResult			= false;
    197 	bool						colorReadResult		= false;
    198 	int							targetW				= renderTarget.getWidth();
    199 	int							targetH				= renderTarget.getHeight();
    200 
    201 	log << tcu::TestLog::Message << "Case iteration " << m_iterNdx+1 << " / " << NUM_CASE_ITERATIONS << tcu::TestLog::EndMessage;
    202 	log << tcu::TestLog::Message << "Parameters:\n"
    203 								 << "- " << m_numOccluderDraws	<< " occluder draws, "	<< m_numOccludersPerDraw	<< " primitive writes per draw,\n"
    204 								 << "- " << m_numTargetDraws	<< " target draws, "	<< m_numTargetsPerDraw		<< " targets per draw\n"
    205 		<< tcu::TestLog::EndMessage;
    206 
    207 	DE_ASSERT(m_program);
    208 
    209 	glClearColor				(0.0f, 0.0f, 0.0f, 1.0f);
    210 	glClearDepthf				(1.0f);
    211 	glClearStencil				(0);
    212 	glClear						(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
    213 	glUseProgram				(m_program->getProgram());
    214 	glEnableVertexAttribArray	(0);
    215 
    216 	// Draw occluders
    217 
    218 	std::vector<OccluderType> occOptions(0);
    219 	if (m_occluderTypes & OCCLUDER_DEPTH_WRITE)		occOptions.push_back(OCCLUDER_DEPTH_WRITE);
    220 	if (m_occluderTypes & OCCLUDER_DEPTH_CLEAR)		occOptions.push_back(OCCLUDER_DEPTH_CLEAR);
    221 	if (m_occluderTypes & OCCLUDER_STENCIL_WRITE)	occOptions.push_back(OCCLUDER_STENCIL_WRITE);
    222 	if (m_occluderTypes & OCCLUDER_STENCIL_CLEAR)	occOptions.push_back(OCCLUDER_STENCIL_CLEAR);
    223 
    224 	for (int i = 0; i < m_numOccluderDraws; i++)
    225 	{
    226 		if (occOptions.empty())
    227 			break;
    228 
    229 		OccluderType type = occOptions[m_rnd.getInt(0, (int)occOptions.size()-1)];	// Choosing a random occluder type from available options
    230 
    231 		switch (type)
    232 		{
    233 			case OCCLUDER_DEPTH_WRITE:
    234 				log << tcu::TestLog::Message	<< "Occluder draw "	<< i+1 << " / " << m_numOccluderDraws << " : "
    235 												<< "Depth write"	<< tcu::TestLog::EndMessage;
    236 
    237 				generateVertices(occluderVertices, 2.0f, 2.0f, m_numOccludersPerDraw, 3, m_rnd, m_occluderSize, 0.0f, 0.6f);	// Generate vertices for occluding primitives
    238 
    239 				DE_ASSERT(!occluderVertices.empty());
    240 
    241 				glEnable				(GL_DEPTH_TEST);
    242 				glUniform4f				(colorUnif, DEPTH_WRITE_COLOR.x(), DEPTH_WRITE_COLOR.y(), DEPTH_WRITE_COLOR.z(), DEPTH_WRITE_COLOR.w());
    243 				glVertexAttribPointer	(0, ELEMENTS_PER_VERTEX, GL_FLOAT, GL_FALSE, 0, &occluderVertices[0]);
    244 				glDrawArrays			(GL_TRIANGLES, 0, 3*m_numOccludersPerDraw);
    245 				glDisable				(GL_DEPTH_TEST);
    246 
    247 				break;
    248 
    249 			case OCCLUDER_DEPTH_CLEAR:
    250 			{
    251 				int scissorBoxX = m_rnd.getInt(-DEPTH_CLEAR_OFFSET,	targetW);
    252 				int scissorBoxY = m_rnd.getInt(-DEPTH_CLEAR_OFFSET,	targetH);
    253 				int scissorBoxW = m_rnd.getInt( DEPTH_CLEAR_OFFSET,	targetW+DEPTH_CLEAR_OFFSET);
    254 				int scissorBoxH = m_rnd.getInt( DEPTH_CLEAR_OFFSET,	targetH+DEPTH_CLEAR_OFFSET);
    255 
    256 				log << tcu::TestLog::Message	<< "Occluder draw "	<< i+1 << " / " << m_numOccluderDraws << " : "	<< "Depth clear"
    257 					<< tcu::TestLog::EndMessage;
    258 				log << tcu::TestLog::Message	<< "Depth-clearing box drawn at "
    259 												<< "("			<< scissorBoxX << ", "			<< scissorBoxY << ")"
    260 												<< ", width = "	<< scissorBoxW << ", height = " << scissorBoxH << "."
    261 					<< tcu::TestLog::EndMessage;
    262 
    263 				glEnable		(GL_SCISSOR_TEST);
    264 				glScissor		(scissorBoxX, scissorBoxY, scissorBoxW, scissorBoxH);
    265 				glClearDepthf	(0.0f);
    266 				glClearColor	(DEPTH_CLEAR_COLOR.x(), DEPTH_CLEAR_COLOR.y(), DEPTH_CLEAR_COLOR.z(), DEPTH_CLEAR_COLOR.w());
    267 				glClear			(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    268 				glDisable		(GL_SCISSOR_TEST);
    269 
    270 				break;
    271 			}
    272 
    273 			case OCCLUDER_STENCIL_WRITE:
    274 				log << tcu::TestLog::Message	<< "Occluder draw "	<< i+1 << " / " << m_numOccluderDraws << " : "
    275 												<< "Stencil write"	<< tcu::TestLog::EndMessage;
    276 
    277 				generateVertices(occluderVertices, 2.0f, 2.0f, m_numOccludersPerDraw, 3, m_rnd, m_occluderSize, 0.0f, 0.6f);
    278 
    279 				glStencilFunc	(GL_ALWAYS, 1, 0xFF);
    280 				glStencilOp		(GL_KEEP, GL_KEEP, GL_REPLACE);
    281 
    282 				DE_ASSERT(!occluderVertices.empty());
    283 
    284 				glEnable				(GL_STENCIL_TEST);
    285 				glUniform4f				(colorUnif, STENCIL_WRITE_COLOR.x(), STENCIL_WRITE_COLOR.y(), STENCIL_WRITE_COLOR.z(), STENCIL_WRITE_COLOR.w());
    286 				glVertexAttribPointer	(0, ELEMENTS_PER_VERTEX, GL_FLOAT, GL_FALSE, 0, &occluderVertices[0]);
    287 				glDrawArrays			(GL_TRIANGLES, 0, 3*m_numOccludersPerDraw);
    288 				glDisable				(GL_STENCIL_TEST);
    289 
    290 				break;
    291 
    292 			case OCCLUDER_STENCIL_CLEAR:
    293 			{
    294 				int scissorBoxX = m_rnd.getInt(-STENCIL_CLEAR_OFFSET,	targetW);
    295 				int scissorBoxY = m_rnd.getInt(-STENCIL_CLEAR_OFFSET,	targetH);
    296 				int scissorBoxW = m_rnd.getInt(	STENCIL_CLEAR_OFFSET,	targetW+STENCIL_CLEAR_OFFSET);
    297 				int scissorBoxH = m_rnd.getInt(	STENCIL_CLEAR_OFFSET,	targetH+STENCIL_CLEAR_OFFSET);
    298 
    299 				log << tcu::TestLog::Message	<< "Occluder draw "	<< i+1 << " / " << m_numOccluderDraws << " : "	<< "Stencil clear"
    300 					<< tcu::TestLog::EndMessage;
    301 				log << tcu::TestLog::Message	<< "Stencil-clearing box drawn at "
    302 												<< "("			<< scissorBoxX << ", "			<< scissorBoxY << ")"
    303 												<< ", width = "	<< scissorBoxW << ", height = " << scissorBoxH << "."
    304 					<< tcu::TestLog::EndMessage;
    305 
    306 				glEnable		(GL_SCISSOR_TEST);
    307 				glScissor		(scissorBoxX, scissorBoxY, scissorBoxW, scissorBoxH);
    308 				glClearStencil	(1);
    309 				glClearColor	(STENCIL_CLEAR_COLOR.x(), STENCIL_CLEAR_COLOR.y(), STENCIL_CLEAR_COLOR.z(), STENCIL_CLEAR_COLOR.w());
    310 				glClear			(GL_COLOR_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
    311 				glDisable		(GL_SCISSOR_TEST);
    312 
    313 				break;
    314 			}
    315 
    316 			default:
    317 				DE_ASSERT(false);
    318 				break;
    319 		}
    320 	}
    321 
    322 	if (m_occluderTypes & OCCLUDER_SCISSOR)
    323 	{
    324 		int scissorBoxX = m_rnd.getInt(-SCISSOR_OFFSET,	targetW-SCISSOR_OFFSET);
    325 		int scissorBoxY = m_rnd.getInt(-SCISSOR_OFFSET,	targetH-SCISSOR_OFFSET);
    326 		int scissorBoxW = m_rnd.getInt(SCISSOR_MINSIZE,	targetW+SCISSOR_OFFSET);
    327 		int scissorBoxH = m_rnd.getInt(SCISSOR_MINSIZE,	targetH+SCISSOR_OFFSET);
    328 
    329 		log << tcu::TestLog::Message	<< "Scissor box drawn at "
    330 										<< "("			<< scissorBoxX << ", "			<< scissorBoxY << ")"
    331 										<< ", width = "	<< scissorBoxW << ", height = " << scissorBoxH << "."
    332 			<< tcu::TestLog::EndMessage;
    333 
    334 		glEnable	(GL_SCISSOR_TEST);
    335 		glScissor	(scissorBoxX, scissorBoxY, scissorBoxW, scissorBoxH);
    336 	}
    337 
    338 	glGenQueries	(1, &queryIds[0]);
    339 	glBeginQuery	(m_queryMode, queryIds[0]);
    340 	GLU_CHECK_MSG	("Occlusion query started");
    341 
    342 	// Draw target primitives
    343 
    344 	glEnable		(GL_DEPTH_TEST);
    345 	glEnable		(GL_STENCIL_TEST);
    346 	glStencilFunc	(GL_EQUAL, 0, 0xFF);
    347 
    348 	for (int i = 0; i < m_numTargetDraws; i++)
    349 	{
    350 		generateVertices(targetVertices, 2.0f, 2.0f, m_numTargetsPerDraw, 3,  m_rnd, m_targetSize, 0.4f, 1.0f);		// Generate vertices for target primitives
    351 
    352 		if (!targetVertices.empty())
    353 		{
    354 			glUniform4f				(colorUnif, TARGET_COLOR.x(), TARGET_COLOR.y(), TARGET_COLOR.z(), TARGET_COLOR.w());
    355 			glVertexAttribPointer	(0, ELEMENTS_PER_VERTEX, GL_FLOAT, GL_FALSE, 0, &targetVertices[0]);
    356 			glDrawArrays			(GL_TRIANGLES, 0, 3*m_numTargetsPerDraw);
    357 		}
    358 	}
    359 
    360 	glEndQuery		(m_queryMode);
    361 	glFinish		();
    362 	glDisable		(GL_SCISSOR_TEST);
    363 	glDisable		(GL_STENCIL_TEST);
    364 	glDisable		(GL_DEPTH_TEST);
    365 
    366 	// Check that query result is available.
    367 	{
    368 		deUint32 resultAvailable = GL_FALSE;
    369 		glGetQueryObjectuiv(queryIds[0], GL_QUERY_RESULT_AVAILABLE, &resultAvailable);
    370 
    371 		if (resultAvailable == GL_FALSE)
    372 			TCU_FAIL("Occlusion query failed to return a result after glFinish()");
    373 	}
    374 
    375 	// Read query result.
    376 	{
    377 		deUint32 result = 0;
    378 		glGetQueryObjectuiv(queryIds[0], GL_QUERY_RESULT, &result);
    379 		queryResult = (result != GL_FALSE);
    380 	}
    381 
    382 	glDeleteQueries	(1, &queryIds[0]);
    383 	GLU_CHECK_MSG	("Occlusion query finished");
    384 
    385 	// Read pixel data
    386 
    387 	tcu::Surface pixels(renderTarget.getWidth(), renderTarget.getHeight());
    388 	glu::readPixels(m_context.getRenderContext(), 0, 0, pixels.getAccess());
    389 
    390 	{
    391 		int width = pixels.getWidth();
    392 		int height = pixels.getHeight();
    393 
    394 		for (int y = 0; y < height; y++)
    395 		{
    396 			for (int x = 0; x < width; x++)
    397 			{
    398 				if (pixels.getPixel(x,y).getRed() != 0)
    399 				{
    400 					colorReadResult = true;
    401 					break;
    402 				}
    403 			}
    404 			if (colorReadResult) break;
    405 		}
    406 	}
    407 
    408 	log << tcu::TestLog::Message << "Occlusion query result:  Target " << (queryResult		? "visible" : "invisible") << "\n"
    409 								 << "Framebuffer read result: Target " << (colorReadResult	? "visible" : "invisible") << tcu::TestLog::EndMessage;
    410 
    411 	bool testOk = false;
    412 	if (m_queryMode == GL_ANY_SAMPLES_PASSED_CONSERVATIVE)
    413 	{
    414 		if (queryResult || colorReadResult)
    415 			testOk = queryResult;	// Allow conservative occlusion query to return false positives.
    416 		else
    417 			testOk = queryResult == colorReadResult;
    418 	}
    419 	else
    420 		testOk = (queryResult == colorReadResult);
    421 
    422 	if (!testOk)
    423 	{
    424 		log << tcu::TestLog::Image("Result image", "Result image", pixels);
    425 		log << tcu::TestLog::Message << "Case FAILED!" << tcu::TestLog::EndMessage;
    426 
    427 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
    428 		return STOP;
    429 	}
    430 
    431 	log << tcu::TestLog::Message << "Case passed!" << tcu::TestLog::EndMessage;
    432 
    433 	return (++m_iterNdx < NUM_CASE_ITERATIONS) ? CONTINUE : STOP;
    434 }
    435 
    436 OcclusionQueryTests::OcclusionQueryTests (Context& context)
    437 	: TestCaseGroup(context, "occlusion_query", "Occlusion Query Tests")
    438 {
    439 }
    440 
    441 OcclusionQueryTests::~OcclusionQueryTests (void)
    442 {
    443 }
    444 
    445 void OcclusionQueryTests::init (void)
    446 {
    447 	// Strict occlusion query cases
    448 
    449 	addChild(new OcclusionQueryCase(m_context, "scissor",												"scissor",												1,	10, 1.6f, 1, 1, 0.3f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR));
    450 	addChild(new OcclusionQueryCase(m_context, "depth_write",											"depth_write",											8,	10, 1.6f, 1, 7, 0.3f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_WRITE));
    451 	addChild(new OcclusionQueryCase(m_context, "depth_clear",											"depth_clear",											5,	10, 1.6f, 1, 5, 0.2f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_CLEAR));
    452 	addChild(new OcclusionQueryCase(m_context, "stencil_write",											"stencil_write",										8,	10, 2.0f, 1, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_STENCIL_WRITE));
    453 	addChild(new OcclusionQueryCase(m_context, "stencil_clear",											"stencil_clear",										5,	10, 2.0f, 1, 3, 0.3f, GL_ANY_SAMPLES_PASSED, OCCLUDER_STENCIL_CLEAR));
    454 
    455 	addChild(new OcclusionQueryCase(m_context, "scissor_depth_write",									"scissor_depth_write",									5,	10, 1.6f, 2, 5, 0.3f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE));
    456 	addChild(new OcclusionQueryCase(m_context, "scissor_depth_clear",									"scissor_depth_clear",									7,	10, 1.6f, 2, 5, 1.0f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_CLEAR));
    457 	addChild(new OcclusionQueryCase(m_context, "scissor_stencil_write",									"scissor_stencil_write",								4,	10, 1.6f, 2, 5, 0.3f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_STENCIL_WRITE));
    458 	addChild(new OcclusionQueryCase(m_context, "scissor_stencil_clear",									"scissor_stencil_clear",								4,	10, 1.6f, 2, 5, 1.0f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_STENCIL_CLEAR));
    459 	addChild(new OcclusionQueryCase(m_context, "depth_write_depth_clear",								"depth_write_depth_clear",								7,	10, 1.6f, 1, 5, 0.2f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR));
    460 	addChild(new OcclusionQueryCase(m_context, "depth_write_stencil_write",								"depth_write_stencil_write",							8,	10, 1.6f, 1, 5, 0.3f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_WRITE));
    461 	addChild(new OcclusionQueryCase(m_context, "depth_write_stencil_clear",								"depth_write_stencil_clear",							8,	10, 1.6f, 1, 5, 0.3f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_CLEAR));
    462 	addChild(new OcclusionQueryCase(m_context, "depth_clear_stencil_write",								"depth_clear_stencil_write",							8,	10, 1.6f, 1, 5, 0.3f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE));
    463 	addChild(new OcclusionQueryCase(m_context, "depth_clear_stencil_clear",								"depth_clear_stencil_clear",							12,	10, 1.6f, 1, 5, 0.2f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_CLEAR));
    464 	addChild(new OcclusionQueryCase(m_context, "stencil_write_stencil_clear",							"stencil_write_stencil_clear",							5,	10, 2.0f, 1, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    465 
    466 	addChild(new OcclusionQueryCase(m_context, "scissor_depth_write_depth_clear",						"scissor_depth_write_depth_clear",						5,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR));
    467 	addChild(new OcclusionQueryCase(m_context, "scissor_depth_write_stencil_write",						"scissor_depth_write_stencil_write",					4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_WRITE));
    468 	addChild(new OcclusionQueryCase(m_context, "scissor_depth_write_stencil_clear",						"scissor_depth_write_stencil_clear",					6,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_CLEAR));
    469 	addChild(new OcclusionQueryCase(m_context, "scissor_depth_clear_stencil_write",						"scissor_depth_clear_stencil_write",					4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE));
    470 	addChild(new OcclusionQueryCase(m_context, "scissor_depth_clear_stencil_clear",						"scissor_depth_clear_stencil_clear",					5,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_CLEAR));
    471 	addChild(new OcclusionQueryCase(m_context, "scissor_stencil_write_stencil_clear",					"scissor_stencil_write_stencil_clear",					4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    472 	addChild(new OcclusionQueryCase(m_context, "depth_write_depth_clear_stencil_write",					"depth_write_depth_clear_stencil_write",				7,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE));
    473 	addChild(new OcclusionQueryCase(m_context, "depth_write_depth_clear_stencil_clear",					"depth_write_depth_clear_stencil_clear",				7,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_CLEAR));
    474 	addChild(new OcclusionQueryCase(m_context, "depth_write_stencil_write_stencil_clear",				"depth_write_stencil_write_stencil_clear",				7,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    475 	addChild(new OcclusionQueryCase(m_context, "depth_clear_stencil_write_stencil_clear",				"depth_clear_stencil_write_stencil_clear",				7,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    476 
    477 	addChild(new OcclusionQueryCase(m_context, "scissor_depth_write_depth_clear_stencil_write",			"scissor_depth_write_depth_clear_stencil_write",		4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE));
    478 	addChild(new OcclusionQueryCase(m_context, "scissor_depth_write_depth_clear_stencil_clear",			"scissor_depth_write_depth_clear_stencil_clear",		4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_CLEAR));
    479 	addChild(new OcclusionQueryCase(m_context, "scissor_depth_write_stencil_write_stencil_clear",		"scissor_depth_write_stencil_write_stencil_clear",		5,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    480 	addChild(new OcclusionQueryCase(m_context, "scissor_depth_clear_stencil_write_stencil_clear",		"scissor_depth_clear_stencil_write_stencil_clear",		4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    481 	addChild(new OcclusionQueryCase(m_context, "depth_write_depth_clear_stencil_write_stencil_clear",	"depth_write_depth_clear_stencil_write_stencil_clear",	7,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED, OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    482 
    483 	addChild(new OcclusionQueryCase(m_context, "all_occluders",											"all_occluders",										7,	10, 1.6f, 3, 5, 0.6f, GL_ANY_SAMPLES_PASSED, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    484 
    485 	// Conservative occlusion query cases
    486 
    487 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor",												"conservative_scissor",												1,	10, 1.6f, 1, 1, 0.3f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR));
    488 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_write",											"conservative_depth_write",											8,	10, 1.6f, 1, 7, 0.3f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_WRITE));
    489 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_clear",											"conservative_depth_clear",											5,	10, 1.6f, 1, 5, 0.2f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_CLEAR));
    490 	addChild(new OcclusionQueryCase(m_context, "conservative_stencil_write",										"conservative_stencil_write",										8,	10, 2.0f, 1, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_STENCIL_WRITE));
    491 	addChild(new OcclusionQueryCase(m_context, "conservative_stencil_clear",										"conservative_stencil_clear",										5,	10, 2.0f, 1, 3, 0.3f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_STENCIL_CLEAR));
    492 
    493 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_depth_write",									"conservative_scissor_depth_write",									5,	10, 1.6f, 2, 5, 0.3f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE));
    494 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_depth_clear",									"conservative_scissor_depth_clear",									7,	10, 1.6f, 2, 5, 1.0f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_CLEAR));
    495 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_stencil_write",								"conservative_scissor_stencil_write",								4,	10, 1.6f, 2, 5, 0.3f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_STENCIL_WRITE));
    496 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_stencil_clear",								"conservative_scissor_stencil_clear",								4,	10, 1.6f, 2, 5, 1.0f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_STENCIL_CLEAR));
    497 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_write_depth_clear",								"conservative_depth_write_depth_clear",								7,	10, 1.6f, 1, 5, 0.2f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR));
    498 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_write_stencil_write",							"conservative_depth_write_stencil_write",							8,	10, 1.6f, 1, 5, 0.3f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_WRITE));
    499 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_write_stencil_clear",							"conservative_depth_write_stencil_clear",							8,	10, 1.6f, 1, 5, 0.3f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_CLEAR));
    500 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_clear_stencil_write",							"conservative_depth_clear_stencil_write",							8,	10, 1.6f, 1, 5, 0.3f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE));
    501 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_clear_stencil_clear",							"conservative_depth_clear_stencil_clear",							12,	10, 1.6f, 1, 5, 0.2f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_CLEAR));
    502 	addChild(new OcclusionQueryCase(m_context, "conservative_stencil_write_stencil_clear",							"conservative_stencil_write_stencil_clear",							5,	10, 2.0f, 1, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    503 
    504 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_depth_write_depth_clear",						"conservative_scissor_depth_write_depth_clear",						5,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR));
    505 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_depth_write_stencil_write",					"conservative_scissor_depth_write_stencil_write",					4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_WRITE));
    506 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_depth_write_stencil_clear",					"conservative_scissor_depth_write_stencil_clear",					6,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_CLEAR));
    507 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_depth_clear_stencil_write",					"conservative_scissor_depth_clear_stencil_write",					4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE));
    508 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_depth_clear_stencil_clear",					"conservative_scissor_depth_clear_stencil_clear",					5,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_CLEAR));
    509 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_stencil_write_stencil_clear",					"conservative_scissor_stencil_write_stencil_clear",					4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    510 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_write_depth_clear_stencil_write",				"conservative_depth_write_depth_clear_stencil_write",				7,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE));
    511 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_write_depth_clear_stencil_clear",				"conservative_depth_write_depth_clear_stencil_clear",				7,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_CLEAR));
    512 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_write_stencil_write_stencil_clear",				"conservative_depth_write_stencil_write_stencil_clear",				7,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    513 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_clear_stencil_write_stencil_clear",				"conservative_depth_clear_stencil_write_stencil_clear",				7,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    514 
    515 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_depth_write_depth_clear_stencil_write",		"conservative_scissor_depth_write_depth_clear_stencil_write",		4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE));
    516 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_depth_write_depth_clear_stencil_clear",		"conservative_scissor_depth_write_depth_clear_stencil_clear",		4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_CLEAR));
    517 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_depth_write_stencil_write_stencil_clear",		"conservative_scissor_depth_write_stencil_write_stencil_clear",		5,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    518 	addChild(new OcclusionQueryCase(m_context, "conservative_scissor_depth_clear_stencil_write_stencil_clear",		"conservative_scissor_depth_clear_stencil_write_stencil_clear",		4,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    519 	addChild(new OcclusionQueryCase(m_context, "conservative_depth_write_depth_clear_stencil_write_stencil_clear",	"conservative_depth_write_depth_clear_stencil_write_stencil_clear",	7,	10, 1.6f, 2, 5, 0.4f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    520 
    521 	addChild(new OcclusionQueryCase(m_context, "conservative_all_occluders",										"conservative_all_occluders",										7,	10, 1.6f, 3, 5, 0.6f, GL_ANY_SAMPLES_PASSED_CONSERVATIVE, OCCLUDER_SCISSOR | OCCLUDER_DEPTH_WRITE | OCCLUDER_DEPTH_CLEAR | OCCLUDER_STENCIL_WRITE | OCCLUDER_STENCIL_CLEAR));
    522 }
    523 
    524 } // Functional
    525 } // gles3
    526 } // deqp
    527