• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*-------------------------------------------------------------------------
2  * OpenGL Conformance Test Suite
3  * -----------------------------
4  *
5  * Copyright (c) 2017 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  glcPackedDepthStencilTests.cpp
21  * \brief
22  */ /*-------------------------------------------------------------------*/
23 
24 #include "glcPackedDepthStencilTests.hpp"
25 #include "deMath.h"
26 #include "gluContextInfo.hpp"
27 #include "gluDrawUtil.hpp"
28 #include "gluRenderContext.hpp"
29 #include "gluShaderProgram.hpp"
30 #include "gluStrUtil.hpp"
31 #include "glwEnums.hpp"
32 #include "glwFunctions.hpp"
33 #include "tcuRenderTarget.hpp"
34 #include "tcuTestLog.hpp"
35 #include <algorithm>
36 #include <cstring>
37 #include <stdio.h>
38 
39 using namespace glw;
40 using namespace glu;
41 
42 namespace glcts
43 {
44 
45 #define TEX_SIZE 256
46 #define TOLERANCE_LOW 0.48
47 #define TOLERANCE_HIGH 0.52
48 #define EPSILON 0.01
49 
50 enum DrawMode
51 {
52 	DEFAULT,
53 	DEPTH_SPAN1,
54 	DEPTH_SPAN2,
55 };
56 
57 struct D32F_S8
58 {
59 	GLfloat d;
60 	GLuint  s;
61 };
62 
63 // Reference texture names for the described 5 textures and framebuffers
64 // and also for identifying other cases' reference textures
65 enum TextureNames
66 {
67 	packedTexImage,
68 	packedTexRender,
69 	packedTexRenderInitStencil,
70 	packedTexRenderDepthStep,
71 	packedTexRenderStencilStep,
72 	NUM_TEXTURES,
73 	verifyCopyTexImage,
74 	verifyPartialAttachments,
75 	verifyMixedAttachments,
76 	verifyClearBufferDepth,
77 	verifyClearBufferStencil,
78 	verifyClearBufferDepthStencil,
79 	verifyBlit,
80 };
81 
82 struct TypeFormat
83 {
84 	GLenum		type;
85 	GLenum		format;
86 	const char* formatName;
87 	int			size;
88 	int			d;
89 	int			s;
90 };
91 
92 #define NUM_TEXTURE_TYPES 2
93 
94 static const TypeFormat TextureTypes[NUM_TEXTURE_TYPES] = {
95 	{ GL_UNSIGNED_INT_24_8, GL_DEPTH24_STENCIL8, "depth24_stencil8", sizeof(GLuint), 24, 8 },
96 	{ GL_FLOAT_32_UNSIGNED_INT_24_8_REV, GL_DEPTH32F_STENCIL8, "depth32f_stencil8", sizeof(GLuint) + sizeof(GLfloat),
97 	  32, 8 },
98 };
99 
100 // Texture targets for initial state checking
101 static const GLenum coreTexTargets[] = {
102 	GL_TEXTURE_2D,
103 	GL_TEXTURE_3D,
104 	GL_TEXTURE_2D_ARRAY,
105 	GL_TEXTURE_CUBE_MAP_POSITIVE_X,
106 	GL_TEXTURE_CUBE_MAP_NEGATIVE_X,
107 	GL_TEXTURE_CUBE_MAP_POSITIVE_Y,
108 	GL_TEXTURE_CUBE_MAP_NEGATIVE_Y,
109 	GL_TEXTURE_CUBE_MAP_POSITIVE_Z,
110 	GL_TEXTURE_CUBE_MAP_NEGATIVE_Z,
111 	GL_TEXTURE_1D,
112 	GL_TEXTURE_1D_ARRAY,
113 	GL_TEXTURE_CUBE_MAP_ARRAY,
114 	GL_TEXTURE_RECTANGLE,
115 	GL_TEXTURE_2D_MULTISAMPLE,
116 	GL_TEXTURE_2D_MULTISAMPLE_ARRAY,
117 	GL_PROXY_TEXTURE_1D,
118 	GL_PROXY_TEXTURE_2D,
119 	GL_PROXY_TEXTURE_3D,
120 	GL_PROXY_TEXTURE_1D_ARRAY,
121 	GL_PROXY_TEXTURE_2D_ARRAY,
122 	GL_PROXY_TEXTURE_CUBE_MAP_ARRAY,
123 	GL_PROXY_TEXTURE_RECTANGLE,
124 	GL_PROXY_TEXTURE_CUBE_MAP,
125 	GL_PROXY_TEXTURE_2D_MULTISAMPLE,
126 	GL_PROXY_TEXTURE_2D_MULTISAMPLE_ARRAY,
127 };
128 static const GLenum esTexTargets[] = {
129 	GL_TEXTURE_2D,
130 	GL_TEXTURE_3D,
131 	GL_TEXTURE_2D_ARRAY,
132 	GL_TEXTURE_CUBE_MAP_POSITIVE_X,
133 	GL_TEXTURE_CUBE_MAP_NEGATIVE_X,
134 	GL_TEXTURE_CUBE_MAP_POSITIVE_Y,
135 	GL_TEXTURE_CUBE_MAP_NEGATIVE_Y,
136 	GL_TEXTURE_CUBE_MAP_POSITIVE_Z,
137 	GL_TEXTURE_CUBE_MAP_NEGATIVE_Z,
138 };
139 
140 // Listing of non-depth_stencil types for error tests
141 static const GLenum coreNonDepthStencilTypes[] = {
142 	GL_UNSIGNED_BYTE,
143 	GL_BYTE,
144 	GL_UNSIGNED_SHORT,
145 	GL_SHORT,
146 	GL_UNSIGNED_INT,
147 	GL_INT,
148 	GL_HALF_FLOAT,
149 	GL_FLOAT,
150 	GL_UNSIGNED_SHORT_5_6_5,
151 	GL_UNSIGNED_SHORT_4_4_4_4,
152 	GL_UNSIGNED_SHORT_5_5_5_1,
153 	GL_UNSIGNED_INT_2_10_10_10_REV,
154 	GL_UNSIGNED_INT_10F_11F_11F_REV,
155 	GL_UNSIGNED_INT_5_9_9_9_REV,
156 	GL_UNSIGNED_BYTE_3_3_2,
157 	GL_UNSIGNED_BYTE_2_3_3_REV,
158 	GL_UNSIGNED_SHORT_5_6_5_REV,
159 	GL_UNSIGNED_SHORT_4_4_4_4_REV,
160 	GL_UNSIGNED_SHORT_1_5_5_5_REV,
161 	GL_UNSIGNED_INT_8_8_8_8,
162 	GL_UNSIGNED_INT_8_8_8_8_REV,
163 	GL_UNSIGNED_INT_10_10_10_2,
164 };
165 static const GLenum esNonDepthStencilTypes[] = {
166 	GL_UNSIGNED_BYTE,
167 	GL_BYTE,
168 	GL_UNSIGNED_SHORT,
169 	GL_SHORT,
170 	GL_UNSIGNED_INT,
171 	GL_INT,
172 	GL_HALF_FLOAT,
173 	GL_FLOAT,
174 	GL_UNSIGNED_SHORT_5_6_5,
175 	GL_UNSIGNED_SHORT_4_4_4_4,
176 	GL_UNSIGNED_SHORT_5_5_5_1,
177 	GL_UNSIGNED_INT_2_10_10_10_REV,
178 	GL_UNSIGNED_INT_10F_11F_11F_REV,
179 	GL_UNSIGNED_INT_5_9_9_9_REV,
180 };
181 
182 // Listing of non-depth_stencil formats for error tests
183 static const GLenum coreNonDepthStencilFormats[] = {
184 	GL_STENCIL_INDEX, GL_RED,		  GL_GREEN,		   GL_BLUE,			 GL_RG,			  GL_RGB,		 GL_RGBA,
185 	GL_BGR,			  GL_BGRA,		  GL_RED_INTEGER,  GL_GREEN_INTEGER, GL_BLUE_INTEGER, GL_RG_INTEGER, GL_RGB_INTEGER,
186 	GL_RGBA_INTEGER,  GL_BGR_INTEGER, GL_BGRA_INTEGER,
187 };
188 static const GLenum esNonDepthStencilFormats[] = {
189 	GL_RED,
190 	GL_RG,
191 	GL_RGB,
192 	GL_RGBA,
193 	GL_LUMINANCE,		// for es3+
194 	GL_ALPHA,			// for es3+
195 	GL_LUMINANCE_ALPHA, // for es3+
196 	GL_RED_INTEGER,
197 	GL_RG_INTEGER,
198 	GL_RGB_INTEGER,
199 	GL_RGBA_INTEGER,
200 };
201 
202 // Listing of non-depth_stencil base formats for error tests
203 static const GLenum coreOtherBaseFormats[] = {
204 	GL_RED, GL_RG, GL_RGB, GL_RGBA,
205 };
206 static const GLenum esOtherBaseFormats[] = {
207 	GL_RED, GL_RG, GL_RGB, GL_RGBA, GL_LUMINANCE, GL_ALPHA, GL_LUMINANCE_ALPHA,
208 };
209 
210 struct AttachmentParam
211 {
212 	GLenum pname;
213 	GLint  value;
214 };
215 
216 #define NUM_ATTACHMENT_PARAMS_CORE 13
217 #define NUM_ATTACHMENT_PARAMS_ES 12
218 
219 static const AttachmentParam coreAttachmentParams[NUM_TEXTURE_TYPES][NUM_ATTACHMENT_PARAMS_CORE] = {
220 	{
221 		{ GL_FRAMEBUFFER_ATTACHMENT_RED_SIZE, 0 },
222 		{ GL_FRAMEBUFFER_ATTACHMENT_GREEN_SIZE, 0 },
223 		{ GL_FRAMEBUFFER_ATTACHMENT_BLUE_SIZE, 0 },
224 		{ GL_FRAMEBUFFER_ATTACHMENT_ALPHA_SIZE, 0 },
225 		{ GL_FRAMEBUFFER_ATTACHMENT_DEPTH_SIZE, 24 },
226 		{ GL_FRAMEBUFFER_ATTACHMENT_STENCIL_SIZE, 8 },
227 		{ GL_FRAMEBUFFER_ATTACHMENT_COMPONENT_TYPE, GL_UNSIGNED_NORMALIZED },
228 		{ GL_FRAMEBUFFER_ATTACHMENT_COLOR_ENCODING, GL_LINEAR },
229 		{ GL_FRAMEBUFFER_ATTACHMENT_OBJECT_NAME, -1 },
230 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LEVEL, 0 },
231 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_CUBE_MAP_FACE, 0 },
232 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LAYER, 0 },
233 		{ GL_FRAMEBUFFER_ATTACHMENT_LAYERED, 0 },
234 	},
235 	{
236 		{ GL_FRAMEBUFFER_ATTACHMENT_RED_SIZE, 0 },
237 		{ GL_FRAMEBUFFER_ATTACHMENT_GREEN_SIZE, 0 },
238 		{ GL_FRAMEBUFFER_ATTACHMENT_BLUE_SIZE, 0 },
239 		{ GL_FRAMEBUFFER_ATTACHMENT_ALPHA_SIZE, 0 },
240 		{ GL_FRAMEBUFFER_ATTACHMENT_DEPTH_SIZE, 32 },
241 		{ GL_FRAMEBUFFER_ATTACHMENT_STENCIL_SIZE, 8 },
242 		{ GL_FRAMEBUFFER_ATTACHMENT_COMPONENT_TYPE, GL_FLOAT },
243 		{ GL_FRAMEBUFFER_ATTACHMENT_COLOR_ENCODING, GL_LINEAR },
244 		{ GL_FRAMEBUFFER_ATTACHMENT_OBJECT_NAME, -1 },
245 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LEVEL, 0 },
246 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_CUBE_MAP_FACE, 0 },
247 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LAYER, 0 },
248 		{ GL_FRAMEBUFFER_ATTACHMENT_LAYERED, 0 },
249 	},
250 };
251 static const AttachmentParam esAttachmentParams[NUM_TEXTURE_TYPES][NUM_ATTACHMENT_PARAMS_ES] = {
252 	{
253 		{ GL_FRAMEBUFFER_ATTACHMENT_RED_SIZE, 0 },
254 		{ GL_FRAMEBUFFER_ATTACHMENT_GREEN_SIZE, 0 },
255 		{ GL_FRAMEBUFFER_ATTACHMENT_BLUE_SIZE, 0 },
256 		{ GL_FRAMEBUFFER_ATTACHMENT_ALPHA_SIZE, 0 },
257 		{ GL_FRAMEBUFFER_ATTACHMENT_DEPTH_SIZE, 24 },
258 		{ GL_FRAMEBUFFER_ATTACHMENT_STENCIL_SIZE, 8 },
259 		{ GL_FRAMEBUFFER_ATTACHMENT_COMPONENT_TYPE, GL_UNSIGNED_NORMALIZED },
260 		{ GL_FRAMEBUFFER_ATTACHMENT_COLOR_ENCODING, GL_LINEAR },
261 		{ GL_FRAMEBUFFER_ATTACHMENT_OBJECT_NAME, -1 },
262 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LEVEL, 0 },
263 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_CUBE_MAP_FACE, 0 },
264 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LAYER, 0 },
265 	},
266 	{
267 		{ GL_FRAMEBUFFER_ATTACHMENT_RED_SIZE, 0 },
268 		{ GL_FRAMEBUFFER_ATTACHMENT_GREEN_SIZE, 0 },
269 		{ GL_FRAMEBUFFER_ATTACHMENT_BLUE_SIZE, 0 },
270 		{ GL_FRAMEBUFFER_ATTACHMENT_ALPHA_SIZE, 0 },
271 		{ GL_FRAMEBUFFER_ATTACHMENT_DEPTH_SIZE, 32 },
272 		{ GL_FRAMEBUFFER_ATTACHMENT_STENCIL_SIZE, 8 },
273 		{ GL_FRAMEBUFFER_ATTACHMENT_COMPONENT_TYPE, GL_FLOAT },
274 		{ GL_FRAMEBUFFER_ATTACHMENT_COLOR_ENCODING, GL_LINEAR },
275 		{ GL_FRAMEBUFFER_ATTACHMENT_OBJECT_NAME, -1 },
276 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LEVEL, 0 },
277 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_CUBE_MAP_FACE, 0 },
278 		{ GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LAYER, 0 },
279 	},
280 };
281 
282 enum ColorFunction
283 {
284 	COLOR_CHECK_DEFAULT,
285 	COLOR_CHECK_DEPTH,
286 	COLOR_CHECK_STENCIL,
287 };
288 
289 class BaseTest : public deqp::TestCase
290 {
291 public:
292 	BaseTest(deqp::Context& context, const TypeFormat& tf);
293 	virtual ~BaseTest();
294 
295 	void								 init(void);
296 	virtual tcu::TestNode::IterateResult iterate(void);
297 
298 	const AttachmentParam* getAttachmentParams() const;
299 	void createGradient(std::vector<GLbyte>& data);
300 
301 	void setDrawReadBuffer(GLenum draw, GLenum read);
302 	void restoreDrawReadBuffer();
303 
304 	void createTextures();
305 	void setupTexture();
306 	void destroyTextures();
307 
308 	GLuint createProgram(const char* vsCode, const char* fsCode);
309 	void setupColorProgram(GLint& uColor);
310 	bool setupTextureProgram();
311 	bool setupStencilProgram();
312 	bool setTextureUniform(GLuint programId);
313 
314 	void drawQuad(DrawMode drawMode, GLuint program);
315 	void renderToTextures();
316 	bool verifyDepthStencilGradient(GLvoid* data, unsigned int texIndex, int width, int height);
317 	bool verifyColorGradient(GLvoid* data, unsigned int texIndex, int function, int width, int height);
318 	bool doReadPixels(GLuint texture, int function);
319 
320 protected:
321 	GLuint m_defaultFBO;
322 	GLuint m_drawBuffer;
323 	GLuint m_readBuffer;
324 
325 	const GLenum* m_textureTargets;
326 	GLuint		  m_textureTargetsCount;
327 	const GLenum* m_nonDepthStencilTypes;
328 	GLuint		  m_nonDepthStencilTypesCount;
329 	const GLenum* m_nonDepthStencilFormats;
330 	GLuint		  m_nonDepthStencilFormatsCount;
331 	const GLenum* m_otherBaseFormats;
332 	GLuint		  m_otherBaseFormatsCount;
333 
334 	const AttachmentParam* m_attachmentParams[NUM_TEXTURE_TYPES];
335 	GLuint				   m_attachmentParamsCount;
336 
337 	const TypeFormat& m_typeFormat;
338 
339 	GLuint m_textureProgram;
340 	GLuint m_colorProgram;
341 	GLuint m_stencilProgram;
342 
343 	GLuint m_textures[NUM_TEXTURES];
344 	GLuint m_framebuffers[NUM_TEXTURES];
345 };
346 
BaseTest(deqp::Context & context,const TypeFormat & tf)347 BaseTest::BaseTest(deqp::Context& context, const TypeFormat& tf)
348 	: deqp::TestCase(context, tf.formatName, "")
349 	, m_defaultFBO(0)
350 	, m_drawBuffer(GL_COLOR_ATTACHMENT0)
351 	, m_readBuffer(GL_COLOR_ATTACHMENT0)
352 	, m_textureTargets(coreTexTargets)
353 	, m_textureTargetsCount(DE_LENGTH_OF_ARRAY(coreTexTargets))
354 	, m_nonDepthStencilTypes(coreNonDepthStencilTypes)
355 	, m_nonDepthStencilTypesCount(DE_LENGTH_OF_ARRAY(coreNonDepthStencilTypes))
356 	, m_nonDepthStencilFormats(coreNonDepthStencilFormats)
357 	, m_nonDepthStencilFormatsCount(DE_LENGTH_OF_ARRAY(coreNonDepthStencilFormats))
358 	, m_otherBaseFormats(coreOtherBaseFormats)
359 	, m_otherBaseFormatsCount(DE_LENGTH_OF_ARRAY(coreOtherBaseFormats))
360 	, m_typeFormat(tf)
361 	, m_textureProgram(0)
362 	, m_colorProgram(0)
363 	, m_stencilProgram(0)
364 
365 {
366 }
367 
~BaseTest()368 BaseTest::~BaseTest()
369 {
370 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
371 	if (m_textureProgram)
372 		gl.deleteProgram(m_textureProgram);
373 	if (m_colorProgram)
374 		gl.deleteProgram(m_colorProgram);
375 	if (m_stencilProgram)
376 		gl.deleteProgram(m_stencilProgram);
377 }
378 
init(void)379 void BaseTest::init(void)
380 {
381 	if (glu::isContextTypeES(m_context.getRenderContext().getType()))
382 	{
383 		m_textureTargets			  = esTexTargets;
384 		m_textureTargetsCount		  = DE_LENGTH_OF_ARRAY(esTexTargets);
385 		m_nonDepthStencilTypes		  = esNonDepthStencilTypes;
386 		m_nonDepthStencilTypesCount   = DE_LENGTH_OF_ARRAY(esNonDepthStencilTypes);
387 		m_nonDepthStencilFormats	  = esNonDepthStencilFormats;
388 		m_nonDepthStencilFormatsCount = DE_LENGTH_OF_ARRAY(esNonDepthStencilFormats);
389 		m_otherBaseFormats			  = esOtherBaseFormats;
390 		m_otherBaseFormatsCount		  = DE_LENGTH_OF_ARRAY(esOtherBaseFormats);
391 
392 		for (int i				  = 0; i < NUM_TEXTURE_TYPES; i++)
393 			m_attachmentParams[i] = esAttachmentParams[i];
394 		m_attachmentParamsCount   = NUM_ATTACHMENT_PARAMS_ES;
395 	}
396 	else
397 	{
398 		for (int i				  = 0; i < NUM_TEXTURE_TYPES; i++)
399 			m_attachmentParams[i] = coreAttachmentParams[i];
400 		m_attachmentParamsCount   = NUM_ATTACHMENT_PARAMS_CORE;
401 	}
402 }
403 
iterate(void)404 tcu::TestNode::IterateResult BaseTest::iterate(void)
405 {
406 	m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
407 	return STOP;
408 }
409 
getAttachmentParams() const410 const AttachmentParam* BaseTest::getAttachmentParams() const
411 {
412 	// find type index
413 	int index = 0;
414 	for (; index < NUM_TEXTURE_TYPES; index++)
415 	{
416 		if (TextureTypes[index].format == m_typeFormat.format)
417 			break;
418 	}
419 
420 	if (index >= NUM_TEXTURE_TYPES)
421 		TCU_FAIL("Missing attachment definition");
422 
423 	return m_attachmentParams[index];
424 }
425 
426 // Creates a gradient texture data in the given type parameter format
createGradient(std::vector<GLbyte> & data)427 void BaseTest::createGradient(std::vector<GLbyte>& data)
428 {
429 	switch (m_typeFormat.type)
430 	{
431 	case GL_UNSIGNED_INT_24_8:
432 	{
433 		data.resize(TEX_SIZE * TEX_SIZE * sizeof(GLuint));
434 		GLuint* dataPtr = reinterpret_cast<GLuint*>(&data[0]);
435 		for (int j = 0; j < TEX_SIZE; j++)
436 		{
437 			for (int i = 0; i < TEX_SIZE; i++)
438 			{
439 				GLuint  d = static_cast<GLuint>(static_cast<float>(i) / (TEX_SIZE - 1) * 0x00ffffff);
440 				GLubyte s = i & 0xff;
441 
442 				dataPtr[TEX_SIZE * j + i] = (d << 8) + s;
443 			}
444 		}
445 		return;
446 	}
447 	case GL_FLOAT_32_UNSIGNED_INT_24_8_REV:
448 	{
449 		data.resize(TEX_SIZE * TEX_SIZE * sizeof(D32F_S8));
450 		D32F_S8* dataPtr = reinterpret_cast<D32F_S8*>(&data[0]);
451 		for (int j = 0; j < TEX_SIZE; j++)
452 		{
453 			for (int i = 0; i < TEX_SIZE; i++)
454 			{
455 				D32F_S8 v				  = { static_cast<float>(i) / (TEX_SIZE - 1), static_cast<GLuint>(i & 0xff) };
456 				dataPtr[TEX_SIZE * j + i] = v;
457 			}
458 		}
459 		return;
460 	}
461 	default:
462 		TCU_FAIL("Unsuported type");
463 	}
464 }
465 
setDrawReadBuffer(GLenum draw,GLenum read)466 void BaseTest::setDrawReadBuffer(GLenum draw, GLenum read)
467 {
468 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
469 
470 	GLint drawBuffer;
471 	gl.getIntegerv(GL_DRAW_BUFFER0, &drawBuffer);
472 	m_drawBuffer = static_cast<GLuint>(drawBuffer);
473 
474 	GLint readBuffer;
475 	gl.getIntegerv(GL_READ_BUFFER, &readBuffer);
476 	m_readBuffer = static_cast<GLuint>(readBuffer);
477 
478 	gl.drawBuffers(1, &draw);
479 	gl.readBuffer(read);
480 	GLU_EXPECT_NO_ERROR(gl.getError(), "glReadBuffer");
481 }
482 
restoreDrawReadBuffer()483 void BaseTest::restoreDrawReadBuffer()
484 {
485 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
486 	gl.drawBuffers(1, &m_drawBuffer);
487 	gl.readBuffer(m_readBuffer);
488 	GLU_EXPECT_NO_ERROR(gl.getError(), "glReadBuffer");
489 }
490 
createTextures()491 void BaseTest::createTextures()
492 {
493 	// Creates all the textures and framebuffers
494 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
495 
496 	gl.genTextures(NUM_TEXTURES, m_textures);
497 	gl.genFramebuffers(NUM_TEXTURES, m_framebuffers);
498 
499 	// packedTexImage
500 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexImage]);
501 	gl.bindTexture(GL_TEXTURE_2D, m_textures[packedTexImage]);
502 	setupTexture();
503 	std::vector<GLbyte> data;
504 	createGradient(data);
505 	gl.texImage2D(GL_TEXTURE_2D, 0, m_typeFormat.format, TEX_SIZE, TEX_SIZE, 0, GL_DEPTH_STENCIL, m_typeFormat.type,
506 				  &data[0]);
507 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, m_textures[packedTexImage], 0);
508 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_TEXTURE_2D, m_textures[packedTexImage], 0);
509 
510 	// packedTexRender
511 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexRender]);
512 	gl.bindTexture(GL_TEXTURE_2D, m_textures[packedTexRender]);
513 	setupTexture();
514 	gl.texImage2D(GL_TEXTURE_2D, 0, m_typeFormat.format, TEX_SIZE, TEX_SIZE, 0, GL_DEPTH_STENCIL, m_typeFormat.type,
515 				  NULL);
516 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, m_textures[packedTexRender], 0);
517 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_TEXTURE_2D, m_textures[packedTexRender], 0);
518 
519 	// packedTexRenderInitStencil
520 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexRenderInitStencil]);
521 	gl.bindTexture(GL_TEXTURE_2D, m_textures[packedTexRenderInitStencil]);
522 	setupTexture();
523 	createGradient(data);
524 	gl.texImage2D(GL_TEXTURE_2D, 0, m_typeFormat.format, TEX_SIZE, TEX_SIZE, 0, GL_DEPTH_STENCIL, m_typeFormat.type,
525 				  &data[0]);
526 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, m_textures[packedTexRenderInitStencil],
527 							0);
528 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_TEXTURE_2D,
529 							m_textures[packedTexRenderInitStencil], 0);
530 
531 	// packedTexRenderDepthStep
532 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexRenderDepthStep]);
533 	gl.bindTexture(GL_TEXTURE_2D, m_textures[packedTexRenderDepthStep]);
534 	setupTexture();
535 	gl.texImage2D(GL_TEXTURE_2D, 0, m_typeFormat.format, TEX_SIZE, TEX_SIZE, 0, GL_DEPTH_STENCIL, m_typeFormat.type,
536 				  NULL);
537 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, m_textures[packedTexRenderDepthStep],
538 							0);
539 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_TEXTURE_2D, m_textures[packedTexRenderDepthStep],
540 							0);
541 
542 	// packedTexRenderStencilStep
543 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexRenderStencilStep]);
544 	gl.bindTexture(GL_TEXTURE_2D, m_textures[packedTexRenderStencilStep]);
545 	setupTexture();
546 	gl.texImage2D(GL_TEXTURE_2D, 0, m_typeFormat.format, TEX_SIZE, TEX_SIZE, 0, GL_DEPTH_STENCIL, m_typeFormat.type,
547 				  NULL);
548 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, m_textures[packedTexRenderStencilStep],
549 							0);
550 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_TEXTURE_2D,
551 							m_textures[packedTexRenderStencilStep], 0);
552 
553 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_defaultFBO);
554 	GLU_EXPECT_NO_ERROR(gl.getError(), "glBindFramebuffer");
555 }
556 
setupTexture()557 void BaseTest::setupTexture()
558 {
559 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
560 	gl.texParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
561 	gl.texParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
562 	gl.texParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
563 	gl.texParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
564 	GLU_EXPECT_NO_ERROR(gl.getError(), "glTexParameteri");
565 }
566 
567 // Destroys all the textures and framebuffers
destroyTextures()568 void BaseTest::destroyTextures()
569 {
570 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
571 	gl.deleteFramebuffers(NUM_TEXTURES, m_framebuffers);
572 	gl.deleteTextures(NUM_TEXTURES, m_textures);
573 }
574 
createProgram(const char * vsCode,const char * fsCode)575 GLuint BaseTest::createProgram(const char* vsCode, const char* fsCode)
576 {
577 	glu::RenderContext&   renderContext = m_context.getRenderContext();
578 	glu::ContextType	  contextType   = renderContext.getType();
579 	const glw::Functions& gl			= m_context.getRenderContext().getFunctions();
580 	glu::GLSLVersion	  glslVersion   = glu::getContextTypeGLSLVersion(contextType);
581 	const char*			  version		= glu::getGLSLVersionDeclaration(glslVersion);
582 
583 	glu::Shader vs(gl, glu::SHADERTYPE_VERTEX);
584 	const char* vSources[] = { version, vsCode };
585 	const int   vLengths[] = { int(strlen(version)), int(strlen(vsCode)) };
586 	vs.setSources(2, vSources, vLengths);
587 	vs.compile();
588 	if (!vs.getCompileStatus())
589 		TCU_FAIL("Vertex shader compilation failed");
590 
591 	glu::Shader fs(gl, glu::SHADERTYPE_FRAGMENT);
592 	const char* fSources[] = { version, fsCode };
593 	const int   fLengths[] = { int(strlen(version)), int(strlen(fsCode)) };
594 	fs.setSources(2, fSources, fLengths);
595 	fs.compile();
596 	if (!fs.getCompileStatus())
597 		TCU_FAIL("Fragment shader compilation failed");
598 
599 	GLuint p = gl.createProgram();
600 	gl.attachShader(p, vs.getShader());
601 	gl.attachShader(p, fs.getShader());
602 	gl.linkProgram(p);
603 	return p;
604 }
605 
setupColorProgram(GLint & uColor)606 void BaseTest::setupColorProgram(GLint& uColor)
607 {
608 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
609 
610 	const char* vs = "\n"
611 					 "precision highp float;\n"
612 					 "in vec4 pos;\n"
613 					 "void main() {\n"
614 					 "  gl_Position = pos;\n"
615 					 "}\n";
616 
617 	const char* fs = "\n"
618 					 "precision highp float;\n"
619 					 "out vec4 color;\n"
620 					 "uniform vec4 uColor;\n"
621 					 "void main() {\n"
622 					 "  color = uColor;\n"
623 					 "}\n";
624 
625 	// setup shader program
626 	if (!m_colorProgram)
627 		m_colorProgram = createProgram(vs, fs);
628 	if (!m_colorProgram)
629 		TCU_FAIL("Error while loading shader program");
630 
631 	gl.useProgram(m_colorProgram);
632 
633 	// Setup program uniforms
634 	uColor = gl.getUniformLocation(m_colorProgram, "uColor");
635 	GLU_EXPECT_NO_ERROR(gl.getError(), "glGetUniformLocation");
636 
637 	if (uColor == -1)
638 		TCU_FAIL("Error getting uniform uColor");
639 
640 	gl.uniform4f(uColor, 1.0f, 1.0f, 1.0f, 1.0f);
641 }
642 
643 // Common code for default and stencil texture rendering shaders
setTextureUniform(GLuint programId)644 bool BaseTest::setTextureUniform(GLuint programId)
645 {
646 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
647 
648 	gl.useProgram(programId);
649 
650 	GLint uniformTex = gl.getUniformLocation(programId, "tex");
651 	GLU_EXPECT_NO_ERROR(gl.getError(), "glGetUniformLocation");
652 
653 	if (uniformTex == -1)
654 	{
655 		m_testCtx.getLog() << tcu::TestLog::Message << "Error getting uniform tex" << tcu::TestLog::EndMessage;
656 		return false;
657 	}
658 
659 	gl.uniform1i(uniformTex, 0);
660 	return true;
661 }
662 
663 // Loads texture rendering shader
setupTextureProgram()664 bool BaseTest::setupTextureProgram()
665 {
666 	const char* vs = "\n"
667 					 "precision highp float;\n"
668 					 "in vec4 pos;\n"
669 					 "in vec2 UV;\n"
670 					 "out vec2 vUV;\n"
671 					 "void main() {\n"
672 					 "  gl_Position = pos;\n"
673 					 "  vUV = UV;\n"
674 					 "}\n";
675 
676 	const char* fs = "\n"
677 					 "precision highp float;\n"
678 					 "in vec2 vUV;\n"
679 					 "out vec4 color;\n"
680 					 "uniform sampler2D tex;\n"
681 					 "void main() {\n"
682 					 "  color = texture(tex, vUV).rrra;\n"
683 					 "}\n";
684 
685 	if (!m_textureProgram)
686 		m_textureProgram = createProgram(vs, fs);
687 	if (!m_textureProgram)
688 		return false;
689 
690 	return setTextureUniform(m_textureProgram);
691 }
692 
693 // Loads texture stencil rendering shader
setupStencilProgram()694 bool BaseTest::setupStencilProgram()
695 {
696 	const char* vs = "\n"
697 					 "precision highp float;\n"
698 					 "in vec4 pos;\n"
699 					 "in vec2 UV;\n"
700 					 "out vec2 vUV;\n"
701 					 "void main() {\n"
702 					 "  gl_Position = pos;\n"
703 					 "  vUV = UV;\n"
704 					 "}\n";
705 
706 	const char* fs = "\n"
707 					 "precision highp float;\n"
708 					 "in vec2 vUV;\n"
709 					 "out vec4 color;\n"
710 					 "uniform highp usampler2D tex;\n"
711 					 "void main() {\n"
712 					 "  float s = float(texture(tex, vUV).r);\n"
713 					 "  s /= 255.0;\n"
714 					 "  color = vec4(s, s, s, 1);\n"
715 					 "}\n";
716 
717 	if (!m_stencilProgram)
718 		m_stencilProgram = createProgram(vs, fs);
719 	if (!m_stencilProgram)
720 		return false;
721 
722 	return setTextureUniform(m_stencilProgram);
723 }
724 
drawQuad(DrawMode drawMode,GLuint program)725 void BaseTest::drawQuad(DrawMode drawMode, GLuint program)
726 {
727 	static const GLfloat verticesDefault[] = {
728 		-1.0f, -1.0f, 0.0f, 1.0f, 1.0f, -1.0f, 0.0f, 1.0f, -1.0f, 1.0f, 0.0f, 1.0f, 1.0f, 1.0f, 0.0f, 1.0f,
729 	};
730 
731 	static const GLfloat verticesDepthSpan1[] = {
732 		-1.0f, -1.0f, -1.0f, 1.0f, 1.0f, -1.0f, -1.0f, 1.0f, -1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f,
733 	};
734 
735 	static const GLfloat verticesDepthSpan2[] = {
736 		-1.0f, -1.0f, 1.0f, 1.0f, 1.0f, -1.0f, 1.0f, 1.0f, -1.0f, 1.0f, -1.0f, 1.0f, 1.0f, 1.0f, -1.0f, 1.0f,
737 	};
738 
739 	static const GLfloat texCoords[] = {
740 		0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 1.0f,
741 	};
742 
743 	static const deUint16 quadIndices[] = { 0, 1, 2, 2, 1, 3 };
744 	static PrimitiveList  quadPrimitive = glu::pr::TriangleStrip(DE_LENGTH_OF_ARRAY(quadIndices), quadIndices);
745 
746 	static const glu::VertexArrayBinding depthSpanVA1[] = { glu::va::Float("pos", 4, 4, 0, verticesDepthSpan1) };
747 	static const glu::VertexArrayBinding depthSpanVA2[] = { glu::va::Float("pos", 4, 4, 0, verticesDepthSpan2) };
748 	static const glu::VertexArrayBinding defaultVA[]	= { glu::va::Float("pos", 4, 4, 0, verticesDefault),
749 														 glu::va::Float("UV", 2, 4, 0, texCoords) };
750 
751 	const glu::RenderContext& renderContext = m_context.getRenderContext();
752 	if (drawMode == DEPTH_SPAN1)
753 		glu::draw(renderContext, program, 1, depthSpanVA1, quadPrimitive);
754 	else if (drawMode == DEPTH_SPAN2)
755 		glu::draw(renderContext, program, 1, depthSpanVA2, quadPrimitive);
756 	else
757 		glu::draw(renderContext, program, 2, defaultVA, quadPrimitive);
758 }
759 
760 // Renders all non-trivial startup textures
renderToTextures()761 void BaseTest::renderToTextures()
762 {
763 	const glu::RenderContext& renderContext = m_context.getRenderContext();
764 	const glw::Functions&	 gl			= renderContext.getFunctions();
765 
766 	GLint uColor;
767 	setupColorProgram(uColor);
768 
769 	gl.enable(GL_DEPTH_TEST);
770 	// depth writing must be enabled as it is disabled in places like doReadPixels
771 	gl.depthMask(GL_TRUE);
772 
773 	if (glu::isContextTypeES(renderContext.getType()))
774 		gl.clearDepthf(1.0f);
775 	else
776 		gl.clearDepth(1.0);
777 
778 	gl.depthFunc(GL_LEQUAL);
779 	gl.viewport(0, 0, TEX_SIZE, TEX_SIZE);
780 
781 	drawQuad(DEPTH_SPAN1, m_colorProgram);
782 
783 	// packedTexRender
784 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexRender]);
785 
786 	setDrawReadBuffer(GL_NONE, GL_NONE);
787 
788 	gl.enable(GL_STENCIL_TEST);
789 	gl.stencilFunc(GL_ALWAYS, 0x0, 0xFF);
790 	gl.stencilOp(GL_ZERO, GL_INCR, GL_INCR);
791 
792 	gl.clear(GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
793 	drawQuad(DEPTH_SPAN1, m_colorProgram);
794 
795 	gl.disable(GL_STENCIL_TEST);
796 
797 	restoreDrawReadBuffer();
798 
799 	// packedTexRenderInitStencil
800 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexRenderInitStencil]);
801 
802 	setDrawReadBuffer(GL_NONE, GL_NONE);
803 
804 	gl.clear(GL_DEPTH_BUFFER_BIT);
805 	drawQuad(DEPTH_SPAN1, m_colorProgram);
806 
807 	restoreDrawReadBuffer();
808 
809 	// packedTexRenderDepthStep
810 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexRenderDepthStep]);
811 
812 	setDrawReadBuffer(GL_NONE, GL_NONE);
813 
814 	gl.clear(GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
815 	drawQuad(DEPTH_SPAN2, m_colorProgram);
816 	drawQuad(DEPTH_SPAN1, m_colorProgram);
817 
818 	restoreDrawReadBuffer();
819 
820 	// packedTexRenderStencilStep
821 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexRenderStencilStep]);
822 
823 	setDrawReadBuffer(GL_NONE, GL_NONE);
824 
825 	gl.clear(GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
826 	gl.enable(GL_SCISSOR_TEST);
827 	gl.scissor(0, 0, TEX_SIZE, TEX_SIZE / 2);
828 
829 	gl.enable(GL_STENCIL_TEST);
830 	gl.stencilFunc(GL_ALWAYS, 0x0, 0xFF);
831 	gl.stencilOp(GL_ZERO, GL_INCR, GL_INCR);
832 	for (int i = 0; i < 256; i++)
833 		drawQuad(DEPTH_SPAN2, m_colorProgram);
834 	gl.disable(GL_SCISSOR_TEST);
835 
836 	gl.stencilFunc(GL_EQUAL, 0xFF, 0xFF);
837 	gl.clear(GL_DEPTH_BUFFER_BIT);
838 	drawQuad(DEPTH_SPAN1, m_colorProgram);
839 	gl.disable(GL_STENCIL_TEST);
840 	GLU_EXPECT_NO_ERROR(gl.getError(), "glDisable");
841 
842 	restoreDrawReadBuffer();
843 
844 	// end
845 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_defaultFBO);
846 	GLU_EXPECT_NO_ERROR(gl.getError(), "glBindFramebuffer");
847 }
848 
849 // Verifies DepthStencil buffer data against reference values
verifyDepthStencilGradient(GLvoid * data,unsigned int texIndex,int width,int height)850 bool BaseTest::verifyDepthStencilGradient(GLvoid* data, unsigned int texIndex, int width, int height)
851 {
852 	bool result = true;
853 
854 	int index, skip;
855 	int countD, countS;
856 
857 	index  = 0;
858 	countD = 0;
859 	countS = 0;
860 
861 	for (int j = 0; j < height; j++)
862 	{
863 		for (int i = 0; i < width; i++)
864 		{
865 			float d, dref = 0.0;
866 			int   s, sref = 0;
867 
868 			skip = 0;
869 
870 			switch (m_typeFormat.type)
871 			{
872 			case GL_UNSIGNED_INT_24_8:
873 			{
874 				GLuint v = ((GLuint*)data)[index];
875 				d		 = ((float)(v >> 8)) / 0xffffff;
876 				s		 = v & 0xff;
877 				break;
878 			}
879 			case GL_FLOAT_32_UNSIGNED_INT_24_8_REV:
880 			{
881 				D32F_S8 v = ((D32F_S8*)data)[index];
882 				d		  = v.d;
883 				s		  = v.s & 0xff;
884 				break;
885 			}
886 			default:
887 				d = -1;
888 				s = -1;
889 				break;
890 			}
891 
892 			switch (texIndex)
893 			{
894 			case packedTexImage:
895 				dref = ((float)i) / (width - 1);
896 				sref = (int)(dref * 255);
897 				break;
898 			case packedTexRender:
899 				dref = ((float)j) / (height - 1);
900 				sref = 1;
901 				break;
902 			case packedTexRenderInitStencil:
903 				dref = ((float)j) / (height - 1);
904 				sref = (int)(((float)i) / (width - 1) * 255);
905 				break;
906 			case packedTexRenderDepthStep:
907 				if (j < height * TOLERANCE_LOW)
908 				{
909 					dref = ((float)j) / (height - 1);
910 					sref = 0;
911 				}
912 				else if (j > height * TOLERANCE_HIGH)
913 				{
914 					dref = 1.0f - ((float)j) / (height - 1);
915 					sref = 0;
916 				}
917 				else
918 				{
919 					skip = 1; // give some tolerance to pixels in the middle
920 				}
921 				break;
922 			case packedTexRenderStencilStep:
923 				if (j < height * TOLERANCE_LOW)
924 				{
925 					dref = ((float)j) / (height - 1);
926 					sref = 255;
927 				}
928 				else if (j > height * TOLERANCE_HIGH)
929 				{
930 					dref = 1;
931 					sref = 0;
932 				}
933 				else
934 				{
935 					skip = 1; // give some tolerance to pixels in the middle
936 				}
937 				break;
938 			case verifyCopyTexImage:
939 				if (j < height * TOLERANCE_LOW)
940 				{
941 					dref = ((float)j) / (height - 1);
942 					sref = 1;
943 				}
944 				else if (j > height * TOLERANCE_HIGH)
945 				{
946 					dref = 0.5;
947 					sref = 1;
948 				}
949 				else
950 				{
951 					skip = 1; // give some tolerance to pixels in the middle
952 				}
953 				break;
954 			default:
955 				dref = -2;
956 				sref = -2;
957 				break;
958 			}
959 
960 			if (!skip)
961 			{
962 				if (deFloatAbs(d - dref) > EPSILON)
963 				{
964 					result = false;
965 					countD++;
966 				}
967 
968 				if (s != sref)
969 				{
970 					result = false;
971 					countS++;
972 				}
973 			}
974 			else
975 			{
976 				skip = 0;
977 			}
978 
979 			index++;
980 		}
981 	}
982 
983 	if (countD || countS)
984 	{
985 		m_testCtx.getLog() << tcu::TestLog::Message << "DEPTH_STENCIL comparison failed" << tcu::TestLog::EndMessage;
986 	}
987 	return result;
988 }
989 
990 // Verifies Color buffer data against reference values
verifyColorGradient(GLvoid * data,unsigned int texIndex,int function,int width,int height)991 bool BaseTest::verifyColorGradient(GLvoid* data, unsigned int texIndex, int function, int width, int height)
992 {
993 	bool result = true;
994 
995 	int index   = 0, skip;
996 	int channel = 0;
997 	int count   = 0;
998 
999 	for (int j = 0; j < height; j++)
1000 	{
1001 		for (int i = 0; i < width; i++)
1002 		{
1003 			skip			= 0;
1004 			GLuint color	= ((GLuint*)data)[index];
1005 			GLuint colorref = 0;
1006 
1007 			switch (texIndex)
1008 			{
1009 			case packedTexImage:
1010 				channel  = (int)(((float)i) / (width - 1) * 255);
1011 				colorref = 0xff000000 + channel * 0x00010101;
1012 				break;
1013 			case packedTexRender:
1014 				if (function == COLOR_CHECK_DEPTH)
1015 					channel = (int)(((float)j) / (height - 1) * 255);
1016 				else
1017 					channel = 1;
1018 				colorref	= 0xff000000 + channel * 0x00010101;
1019 				break;
1020 			case packedTexRenderInitStencil:
1021 				if (function == COLOR_CHECK_DEPTH)
1022 					channel = (int)(((float)j) / (height - 1) * 255);
1023 				else
1024 					channel = (int)(((float)i) / (width - 1) * 255);
1025 				colorref	= 0xff000000 + channel * 0x00010101;
1026 				break;
1027 			case packedTexRenderDepthStep:
1028 				if (function == COLOR_CHECK_DEPTH)
1029 				{
1030 					if (j < height * TOLERANCE_LOW)
1031 						channel = (int)(((float)j) / (height - 1) * 255);
1032 					else if (j > height * TOLERANCE_HIGH)
1033 						channel = 255 - (int)(((float)j) / (height - 1) * 255);
1034 					else
1035 						skip = 1; // give some tolerance to pixels in the middle
1036 				}
1037 				else
1038 					channel = 0;
1039 				colorref	= 0xff000000 + channel * 0x00010101;
1040 				break;
1041 			case packedTexRenderStencilStep:
1042 				if (j < height * TOLERANCE_LOW)
1043 				{
1044 					if (function == COLOR_CHECK_DEPTH)
1045 						channel = (int)(((float)j) / (height - 1) * 255);
1046 					else
1047 						channel = 255;
1048 				}
1049 				else if (j > height * TOLERANCE_HIGH)
1050 					channel = (function == COLOR_CHECK_DEPTH) ? 255 : 0;
1051 				else
1052 					skip = 1; // give some tolerance to pixels in the middle
1053 				colorref = 0xff000000 + channel * 0x00010101;
1054 				break;
1055 			case verifyCopyTexImage:
1056 				if (j < height * TOLERANCE_LOW)
1057 				{
1058 					if (function == COLOR_CHECK_DEPTH)
1059 						channel = (int)(((float)j) / (height - 1) * 255);
1060 					else
1061 						channel = 1;
1062 				}
1063 				else if (j > height * TOLERANCE_HIGH)
1064 				{
1065 					channel = (function == COLOR_CHECK_DEPTH) ? 127 : 1;
1066 				}
1067 				else
1068 				{
1069 					skip = 1; // give some tolerance to pixels in the middle
1070 				}
1071 				colorref = 0xff000000 + channel * 0x00010101;
1072 				break;
1073 			case verifyPartialAttachments:
1074 				colorref = 0xffffffff;
1075 				break;
1076 			case verifyMixedAttachments:
1077 				if (j > height * TOLERANCE_HIGH)
1078 					colorref = 0xffffffff;
1079 				else if (j < height * TOLERANCE_LOW)
1080 					colorref = 0xcccccccc;
1081 				else
1082 					skip = 1;
1083 				break;
1084 			case verifyClearBufferDepth:
1085 				if ((i & 0xff) == 0xff)
1086 					colorref = 0xffffffff;
1087 				else
1088 					colorref = 0xcccccccc;
1089 				break;
1090 			case verifyClearBufferStencil:
1091 				if (i > width * TOLERANCE_HIGH)
1092 					colorref = 0xffffffff;
1093 				else if (i < width * TOLERANCE_LOW)
1094 					colorref = 0xcccccccc;
1095 				else
1096 					skip = 1;
1097 				break;
1098 			case verifyClearBufferDepthStencil:
1099 				colorref = 0xffffffff;
1100 				break;
1101 			case verifyBlit:
1102 				if (j > height * TOLERANCE_HIGH)
1103 					colorref = 0xffffffff;
1104 				else if (j < height * TOLERANCE_LOW)
1105 					colorref = 0xcccccccc;
1106 				else
1107 					skip = 1;
1108 				break;
1109 			default:
1110 				colorref = 0xdeadbeef;
1111 				break;
1112 			}
1113 
1114 			if (skip)
1115 				skip = 0;
1116 			else if (color != colorref)
1117 			{
1118 				float d	= (float)(color & 0xff) / 0xff;
1119 				float dref = (float)(colorref & 0xff) / 0xff;
1120 				if (!((function == COLOR_CHECK_DEPTH) && (deFloatAbs(d - dref) < EPSILON)))
1121 				{
1122 					result = false;
1123 					count++;
1124 				}
1125 			}
1126 
1127 			index++;
1128 		}
1129 	}
1130 
1131 	if (count)
1132 	{
1133 		m_testCtx.getLog() << tcu::TestLog::Message << "*** Color comparison failed" << tcu::TestLog::EndMessage;
1134 		result = false;
1135 	}
1136 	return result;
1137 }
1138 
1139 // Verify DepthStencil texture by replicating it to color channels
1140 // so it can be read using ReadPixels in Halti.
doReadPixels(GLuint texture,int function)1141 bool BaseTest::doReadPixels(GLuint texture, int function)
1142 {
1143 	bool				  result = true;
1144 	const glw::Functions& gl	 = m_context.getRenderContext().getFunctions();
1145 
1146 	GLuint fbo;
1147 	gl.genFramebuffers(1, &fbo);
1148 	gl.bindFramebuffer(GL_FRAMEBUFFER, fbo);
1149 
1150 	GLuint texColor;
1151 	gl.genTextures(1, &texColor);
1152 	gl.bindTexture(GL_TEXTURE_2D, texColor);
1153 	setupTexture();
1154 	gl.texImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, TEX_SIZE, TEX_SIZE, 0, GL_RGBA, GL_UNSIGNED_BYTE, 0);
1155 
1156 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texColor, 0);
1157 	setDrawReadBuffer(GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT0);
1158 
1159 	// Step 1: Verify depth values
1160 	GLenum status = gl.checkFramebufferStatus(GL_FRAMEBUFFER);
1161 	if (status != GL_FRAMEBUFFER_COMPLETE)
1162 	{
1163 		m_testCtx.getLog() << tcu::TestLog::Message << "Framebuffer is incomplete: " << status
1164 						   << tcu::TestLog::EndMessage;
1165 		result = false;
1166 	}
1167 	else
1168 	{
1169 		setupTextureProgram();
1170 
1171 		gl.bindTexture(GL_TEXTURE_2D, texture);
1172 
1173 		gl.disable(GL_DEPTH_TEST);
1174 		gl.depthMask(GL_FALSE);
1175 		gl.disable(GL_STENCIL_TEST);
1176 		gl.viewport(0, 0, TEX_SIZE, TEX_SIZE);
1177 		gl.clearColor(0.8f, 0.8f, 0.8f, 0.8f);
1178 		gl.clear(GL_COLOR_BUFFER_BIT);
1179 		drawQuad(DEFAULT, m_textureProgram);
1180 
1181 		std::vector<GLuint> dataColor(TEX_SIZE * TEX_SIZE, 0);
1182 		gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_RGBA, GL_UNSIGNED_BYTE, &dataColor[0]);
1183 		result &= verifyColorGradient(&dataColor[0], function, COLOR_CHECK_DEPTH, TEX_SIZE, TEX_SIZE);
1184 
1185 		// Step 2: Verify stencil values
1186 		gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT, GL_TEXTURE_2D, texture, 0);
1187 
1188 		status = gl.checkFramebufferStatus(GL_FRAMEBUFFER);
1189 		if (status != GL_FRAMEBUFFER_COMPLETE)
1190 		{
1191 			m_testCtx.getLog() << tcu::TestLog::Message << "Framebuffer is incomplete: " << status
1192 							   << tcu::TestLog::EndMessage;
1193 			result = false;
1194 		}
1195 		else
1196 		{
1197 			GLint uColor;
1198 			setupColorProgram(uColor);
1199 
1200 			gl.clearColor(0.8f, 0.8f, 0.8f, 0.8f);
1201 			gl.clear(GL_COLOR_BUFFER_BIT);
1202 
1203 			gl.enable(GL_STENCIL_TEST);
1204 			for (int i = 0; i < 256; i++)
1205 			{
1206 				float v = i / 255.0f;
1207 				gl.uniform4f(uColor, v, v, v, 1.0f);
1208 				gl.stencilFunc(GL_EQUAL, i, 0xFF);
1209 				gl.stencilOp(GL_KEEP, GL_KEEP, GL_KEEP);
1210 				drawQuad(DEFAULT, m_colorProgram);
1211 			}
1212 
1213 			gl.disable(GL_STENCIL_TEST);
1214 			dataColor.assign(dataColor.size(), 0);
1215 			gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_RGBA, GL_UNSIGNED_BYTE, &dataColor[0]);
1216 			result &= verifyColorGradient(&dataColor[0], function, COLOR_CHECK_STENCIL, TEX_SIZE, TEX_SIZE);
1217 		}
1218 	}
1219 
1220 	// clean up
1221 	restoreDrawReadBuffer();
1222 	gl.deleteFramebuffers(1, &fbo);
1223 	gl.deleteTextures(1, &texColor);
1224 
1225 	return result;
1226 }
1227 
1228 class InitialStateTest : public deqp::TestCase
1229 {
1230 public:
1231 	InitialStateTest(deqp::Context& context);
1232 	virtual ~InitialStateTest();
1233 
1234 	virtual tcu::TestNode::IterateResult iterate(void);
1235 };
1236 
InitialStateTest(deqp::Context & context)1237 InitialStateTest::InitialStateTest(deqp::Context& context)
1238 	: deqp::TestCase(context, "initial_state", "TEXTURE_STENCIL_SIZE for the default texture objects should be 0")
1239 {
1240 }
1241 
~InitialStateTest()1242 InitialStateTest::~InitialStateTest()
1243 {
1244 }
1245 
iterate(void)1246 tcu::TestNode::IterateResult InitialStateTest::iterate(void)
1247 {
1248 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
1249 
1250 	m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
1251 	for (int i = 0; i < DE_LENGTH_OF_ARRAY(coreTexTargets); i++)
1252 	{
1253 		GLenum target = coreTexTargets[i];
1254 
1255 		GLfloat fp;
1256 		gl.getTexLevelParameterfv(target, 0, GL_TEXTURE_STENCIL_SIZE, &fp);
1257 		if (deFloatCmpNE(fp, 0.0f))
1258 		{
1259 			m_testCtx.getLog() << tcu::TestLog::Message << "gl.getTexLevelParameterfv: Parameter is not 0"
1260 							   << tcu::TestLog::EndMessage;
1261 			m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
1262 		}
1263 
1264 		GLint ip;
1265 		gl.getTexLevelParameteriv(target, 0, GL_TEXTURE_STENCIL_SIZE, &ip);
1266 		if (deFloatCmpNE((float)ip, 0.0f))
1267 		{
1268 			m_testCtx.getLog() << tcu::TestLog::Message << "gl.getTexLevelParameteriv: Parameter is not 0"
1269 							   << tcu::TestLog::EndMessage;
1270 			m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
1271 		}
1272 	}
1273 
1274 	return STOP;
1275 }
1276 
1277 class ValidateErrorsTest : public BaseTest
1278 {
1279 public:
1280 	ValidateErrorsTest(deqp::Context& context, const TypeFormat& tf);
1281 	virtual ~ValidateErrorsTest();
1282 
1283 	virtual tcu::TestNode::IterateResult iterate(void);
1284 
1285 protected:
1286 	bool checkErrors();
1287 };
1288 
ValidateErrorsTest(deqp::Context & context,const TypeFormat & tf)1289 ValidateErrorsTest::ValidateErrorsTest(deqp::Context& context, const TypeFormat& tf) : BaseTest(context, tf)
1290 {
1291 }
1292 
~ValidateErrorsTest()1293 ValidateErrorsTest::~ValidateErrorsTest()
1294 {
1295 }
1296 
iterate(void)1297 tcu::TestNode::IterateResult ValidateErrorsTest::iterate(void)
1298 {
1299 	createTextures();
1300 	if (checkErrors())
1301 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
1302 	else
1303 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
1304 
1305 	destroyTextures();
1306 	return STOP;
1307 }
1308 
1309 //  Error tests [desktop only]:
1310 
1311 //  - The error INVALID_ENUM is generated if ReadPixels is
1312 //	called where format is DEPTH_STENCIL and type is not
1313 //	UNSIGNED_INT_24_8, or FLOAT_32_UNSIGNED_INT_24_8_REV.
1314 
1315 //  - The error INVALID_OPERATION is generated if ReadPixels
1316 //	is called where type is UNSIGNED_INT_24_8 or
1317 //	FLOAT_32_UNSIGNED_INT_24_8_REV and format is not DEPTH_STENCIL.
1318 
1319 //  - The error INVALID_OPERATION is generated if ReadPixels
1320 //	is called where format is DEPTH_STENCIL and there is not both a
1321 //	depth buffer and a stencil buffer.
1322 
1323 //  - Calling GetTexImage with a <format> of DEPTH_COMPONENT when the
1324 //	base internal format of the texture image is not DEPTH_COMPONENT
1325 //	or DEPTH_STENCIL causes the error INVALID_OPERATION.
1326 
1327 //  - Calling GetTexImage with a <format> of DEPTH_STENCIL when
1328 //	the base internal format of the texture image is not
1329 //	DEPTH_STENCIL causes the error INVALID_OPERATION.
1330 
1331 //  Error tests [Halti only]:
1332 
1333 //  - The error INVALID_ENUM is generated if ReadPixels is
1334 //	called where format is DEPTH_STENCIL.
1335 
1336 //  Error tests [desktop and Halti]:
1337 
1338 //  - TexImage generates INVALID_OPERATION if one of the base internal format
1339 //	and format is DEPTH_COMPONENT or DEPTH_STENCIL, and the other is neither
1340 //	of these values.
1341 
1342 //  - The error INVALID_OPERATION is generated if CopyTexImage
1343 //	is called where format is DEPTH_STENCIL and there is not both a
1344 //	depth buffer and a stencil buffer.
checkErrors()1345 bool ValidateErrorsTest::checkErrors()
1346 {
1347 	bool					  result = true;
1348 	GLuint					  fbo, fbo2;
1349 	GLuint					  texColor;
1350 	std::vector<GLfloat>	  data(4 * TEX_SIZE * TEX_SIZE, 0.0f);
1351 	const glu::RenderContext& renderContext = m_context.getRenderContext();
1352 	const glw::Functions&	 gl			= renderContext.getFunctions();
1353 	bool					  isContextES   = glu::isContextTypeES(renderContext.getType());
1354 
1355 	if (isContextES)
1356 	{
1357 		gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexImage]);
1358 		setDrawReadBuffer(GL_NONE, GL_NONE);
1359 		gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_DEPTH_STENCIL, m_typeFormat.type, &data[0]);
1360 
1361 		GLenum error = gl.getError();
1362 		if (((GL_INVALID_OPERATION != error) && (GL_INVALID_ENUM != error)) &&
1363 			!((GL_NO_ERROR == error) && m_context.getContextInfo().isExtensionSupported("GL_NV_read_depth_stencil")))
1364 		{
1365 			gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_DEPTH_STENCIL, m_typeFormat.type, &data[0]);
1366 			if (gl.getError() != GL_INVALID_OPERATION)
1367 				result = false;
1368 		}
1369 
1370 		restoreDrawReadBuffer();
1371 		gl.bindFramebuffer(GL_FRAMEBUFFER, m_defaultFBO);
1372 	}
1373 	else
1374 	{
1375 		gl.bindTexture(GL_TEXTURE_2D, m_textures[packedTexImage]);
1376 		gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexImage]);
1377 		setDrawReadBuffer(GL_NONE, GL_NONE);
1378 
1379 		for (unsigned int i = 0; i < m_nonDepthStencilTypesCount; i++)
1380 		{
1381 			gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_DEPTH_STENCIL, m_nonDepthStencilTypes[i], &data[0]);
1382 			if (gl.getError() != GL_INVALID_ENUM)
1383 				result = false;
1384 		}
1385 
1386 		for (unsigned int i = 0; i < m_nonDepthStencilFormatsCount; i++)
1387 		{
1388 			gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, m_nonDepthStencilFormats[i], m_typeFormat.type, &data[0]);
1389 
1390 			if (gl.getError() != GL_INVALID_OPERATION)
1391 				result = false;
1392 		}
1393 
1394 		for (int i = 0; i < 2; i++)
1395 		{
1396 			// setup texture/fbo
1397 			gl.genTextures(1, &texColor);
1398 			gl.genFramebuffers(1, &fbo);
1399 			gl.bindFramebuffer(GL_FRAMEBUFFER, fbo);
1400 
1401 			GLenum attachmentType = (i == 0) ? GL_DEPTH_ATTACHMENT : GL_STENCIL_ATTACHMENT;
1402 			gl.framebufferTexture2D(GL_FRAMEBUFFER, attachmentType, GL_TEXTURE_2D, m_textures[packedTexImage], 0);
1403 
1404 			gl.bindTexture(GL_TEXTURE_2D, texColor);
1405 			setupTexture();
1406 			gl.texImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, TEX_SIZE, TEX_SIZE, 0, GL_RGBA, GL_UNSIGNED_BYTE, 0);
1407 			gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texColor, 0);
1408 
1409 			gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_DEPTH_STENCIL, m_typeFormat.type, &data[0]);
1410 			if (gl.getError() != GL_INVALID_OPERATION)
1411 				result = false;
1412 
1413 			gl.bindFramebuffer(GL_FRAMEBUFFER, m_defaultFBO);
1414 			gl.bindTexture(GL_TEXTURE_2D, 0);
1415 			gl.deleteFramebuffers(1, &fbo);
1416 			gl.deleteTextures(1, &texColor);
1417 		}
1418 
1419 		for (unsigned int i = 0; i < m_otherBaseFormatsCount; i++)
1420 		{
1421 			GLenum format = m_otherBaseFormats[i];
1422 			gl.genTextures(1, &texColor);
1423 			gl.bindTexture(GL_TEXTURE_2D, texColor);
1424 			setupTexture();
1425 			gl.texImage2D(GL_TEXTURE_2D, 0, format, TEX_SIZE, TEX_SIZE, 0, format, GL_UNSIGNED_BYTE, 0);
1426 
1427 			if (format != GL_DEPTH_COMPONENT)
1428 			{
1429 				gl.getTexImage(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT, GL_UNSIGNED_SHORT, &data[0]);
1430 
1431 				if (gl.getError() != GL_INVALID_OPERATION)
1432 					result = false;
1433 			}
1434 
1435 			gl.getTexImage(GL_TEXTURE_2D, 0, GL_DEPTH_STENCIL, GL_UNSIGNED_INT_24_8, &data[0]);
1436 			if (gl.getError() != GL_INVALID_OPERATION)
1437 				result = false;
1438 
1439 			gl.deleteTextures(1, &texColor);
1440 		}
1441 	}
1442 
1443 	bool coreGL = !glu::isContextTypeES(m_context.getRenderContext().getType());
1444 	for (int i = 0; i < 4; i++)
1445 	{
1446 		int limit;
1447 		if (i < 2)
1448 			limit = m_nonDepthStencilFormatsCount;
1449 		else
1450 			limit = m_otherBaseFormatsCount;
1451 
1452 		for (int j = 0; j < limit; j++)
1453 		{
1454 			GLint internalFormat = 0;
1455 			GLint format		 = 0;
1456 
1457 			gl.genTextures(1, &texColor);
1458 			gl.bindTexture(GL_TEXTURE_2D, texColor);
1459 			setupTexture();
1460 
1461 			switch (i)
1462 			{
1463 			case 0:
1464 				internalFormat = GL_DEPTH_COMPONENT;
1465 				format		   = m_nonDepthStencilFormats[j];
1466 				break;
1467 			case 1:
1468 				internalFormat = GL_DEPTH_STENCIL;
1469 				format		   = m_nonDepthStencilFormats[j];
1470 				break;
1471 			case 2:
1472 				internalFormat = m_otherBaseFormats[j];
1473 				format		   = GL_DEPTH_COMPONENT;
1474 				break;
1475 			case 3:
1476 				internalFormat = m_otherBaseFormats[j];
1477 				format		   = GL_DEPTH_STENCIL;
1478 				break;
1479 			}
1480 
1481 			gl.texImage2D(GL_TEXTURE_2D, 0, internalFormat, TEX_SIZE, TEX_SIZE, 0, format,
1482 						  (format == GL_DEPTH_STENCIL) ? GL_UNSIGNED_INT_24_8 : GL_UNSIGNED_BYTE, 0);
1483 
1484 			GLenum expectedError = GL_INVALID_OPERATION;
1485 			if (coreGL && (format == GL_STENCIL_INDEX))
1486 			{
1487 				// The OpenGL 4.3 spec is imprecise about what error this should generate
1488 				// see Bugzilla 10134: TexImage with a <format> of STENCIL_INDEX
1489 				//	 4.3 core (Feb 14 2013) p. 174:
1490 				//	 (describing TexImage3D)
1491 				//		 The format STENCIL_INDEX is not allowed.
1492 				// The new OpenGL 4.4 feature ARB_texture_stencil8 removes this error. So
1493 				// the best we can do for OpenGL is to just allow any error, or no error,
1494 				// for this specific case.
1495 				gl.getError();
1496 			}
1497 			else if (gl.getError() != expectedError)
1498 				result = false;
1499 
1500 			gl.bindTexture(GL_TEXTURE_2D, 0);
1501 			gl.deleteTextures(1, &texColor);
1502 		}
1503 	}
1504 
1505 	gl.genFramebuffers(1, &fbo);
1506 	gl.bindFramebuffer(GL_FRAMEBUFFER, fbo);
1507 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, m_textures[packedTexImage], 0);
1508 
1509 	gl.genFramebuffers(1, &fbo2);
1510 	gl.bindFramebuffer(GL_FRAMEBUFFER, fbo2);
1511 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_TEXTURE_2D, m_textures[packedTexImage], 0);
1512 
1513 	GLuint tex;
1514 	gl.genTextures(1, &tex);
1515 	gl.bindTexture(GL_TEXTURE_2D, tex);
1516 	setupTexture();
1517 	gl.texImage2D(GL_TEXTURE_2D, 0, m_typeFormat.format, TEX_SIZE, TEX_SIZE, 0, GL_DEPTH_STENCIL, m_typeFormat.type, 0);
1518 
1519 	for (int i = 0; i < 2; i++)
1520 	{
1521 		switch (i)
1522 		{
1523 		case 0:
1524 			gl.bindFramebuffer(GL_FRAMEBUFFER, fbo);
1525 			gl.bindTexture(GL_TEXTURE_2D, tex);
1526 			break;
1527 		case 1:
1528 			gl.bindFramebuffer(GL_FRAMEBUFFER, fbo2);
1529 			gl.bindTexture(GL_TEXTURE_2D, tex);
1530 			break;
1531 		}
1532 
1533 		setDrawReadBuffer(GL_NONE, GL_NONE);
1534 
1535 		gl.copyTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_STENCIL, 0, 0, TEX_SIZE, TEX_SIZE, 0);
1536 
1537 		GLenum error = gl.getError();
1538 		if ((GL_INVALID_OPERATION != error) && (GL_INVALID_ENUM != error))
1539 		{
1540 			gl.copyTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_STENCIL, 0, 0, TEX_SIZE, TEX_SIZE, 0);
1541 			if (gl.getError() != GL_INVALID_OPERATION)
1542 				result = false;
1543 		}
1544 
1545 		restoreDrawReadBuffer();
1546 		gl.bindFramebuffer(GL_FRAMEBUFFER, m_defaultFBO);
1547 	}
1548 
1549 	gl.bindTexture(GL_TEXTURE_2D, 0);
1550 	gl.deleteTextures(1, &tex);
1551 
1552 	gl.deleteFramebuffers(1, &fbo);
1553 	gl.deleteFramebuffers(1, &fbo2);
1554 
1555 	return result;
1556 }
1557 
1558 class VerifyReadPixelsTest : public BaseTest
1559 {
1560 public:
1561 	VerifyReadPixelsTest(deqp::Context& context, const TypeFormat& tf);
1562 	virtual ~VerifyReadPixelsTest();
1563 
1564 	virtual tcu::TestNode::IterateResult iterate(void);
1565 };
1566 
VerifyReadPixelsTest(deqp::Context & context,const TypeFormat & tf)1567 VerifyReadPixelsTest::VerifyReadPixelsTest(deqp::Context& context, const TypeFormat& tf) : BaseTest(context, tf)
1568 {
1569 }
1570 
~VerifyReadPixelsTest()1571 VerifyReadPixelsTest::~VerifyReadPixelsTest()
1572 {
1573 }
1574 
iterate(void)1575 tcu::TestNode::IterateResult VerifyReadPixelsTest::iterate(void)
1576 {
1577 	//  Use readpixels to verify the results for the 5 textures above are correct.
1578 	//	Note that in ES you can only use gl.readpixels on color buffers.
1579 	//  Test method:
1580 	//  - on desktop: ReadPixel DEPTH_STENCIL value to buffer. Verify gradient.
1581 	//  - on desktop/Halti: Create FBO with color/depth/stencil attachment.
1582 	//	Draw a quad with depth texture bound. Verify gradient.
1583 	//	Draw 256 times using stencil test and gradient color. Verify gradient.
1584 
1585 	const glu::RenderContext& renderContext = m_context.getRenderContext();
1586 	const glw::Functions&	 gl			= renderContext.getFunctions();
1587 	std::size_t				  dataSize		= static_cast<std::size_t>(TEX_SIZE * TEX_SIZE * m_typeFormat.size);
1588 	std::vector<GLubyte>	  data(dataSize);
1589 
1590 	createTextures();
1591 	renderToTextures();
1592 
1593 	bool result = true;
1594 	for (int i = 0; i < NUM_TEXTURES; i++)
1595 	{
1596 		// Read DEPTH_STENCIL value, applies only to desktop
1597 		if (!glu::isContextTypeES(renderContext.getType()))
1598 		{
1599 			gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[i]);
1600 
1601 			setDrawReadBuffer(GL_NONE, GL_NONE);
1602 
1603 			data.assign(TEX_SIZE * TEX_SIZE * m_typeFormat.size, 0);
1604 			gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_DEPTH_STENCIL, m_typeFormat.type, &data[0]);
1605 			result &= verifyDepthStencilGradient(&data[0], i, TEX_SIZE, TEX_SIZE);
1606 
1607 			restoreDrawReadBuffer();
1608 		}
1609 
1610 		// On ES3.2 we have to render to color buffer to verify.
1611 		// We can run this also on desktop.
1612 		result &= doReadPixels(m_textures[i], i);
1613 	}
1614 
1615 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_defaultFBO);
1616 
1617 	destroyTextures();
1618 	if (result)
1619 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
1620 	else
1621 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
1622 
1623 	return STOP;
1624 }
1625 
1626 class VerifyGetTexImageTest : public BaseTest
1627 {
1628 public:
1629 	VerifyGetTexImageTest(deqp::Context& context, const TypeFormat& tf);
1630 	virtual ~VerifyGetTexImageTest();
1631 
1632 	virtual tcu::TestNode::IterateResult iterate(void);
1633 };
1634 
VerifyGetTexImageTest(deqp::Context & context,const TypeFormat & tf)1635 VerifyGetTexImageTest::VerifyGetTexImageTest(deqp::Context& context, const TypeFormat& tf) : BaseTest(context, tf)
1636 {
1637 }
1638 
~VerifyGetTexImageTest()1639 VerifyGetTexImageTest::~VerifyGetTexImageTest()
1640 {
1641 }
1642 
iterate(void)1643 tcu::TestNode::IterateResult VerifyGetTexImageTest::iterate(void)
1644 {
1645 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
1646 	std::vector<GLubyte>  data(TEX_SIZE * TEX_SIZE * m_typeFormat.size);
1647 
1648 	createTextures();
1649 	renderToTextures();
1650 
1651 	bool result = true;
1652 	for (int i = 0; i < NUM_TEXTURES; i++)
1653 	{
1654 		data.assign(TEX_SIZE * TEX_SIZE * m_typeFormat.size, 0);
1655 		gl.bindTexture(GL_TEXTURE_2D, m_textures[i]);
1656 		gl.getTexImage(GL_TEXTURE_2D, 0, GL_DEPTH_STENCIL, m_typeFormat.type, &data[0]);
1657 		result &= verifyDepthStencilGradient(&data[0], i, TEX_SIZE, TEX_SIZE);
1658 	}
1659 
1660 	destroyTextures();
1661 	if (result)
1662 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
1663 	else
1664 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
1665 
1666 	return STOP;
1667 }
1668 
1669 class VerifyCopyTexImageTest : public BaseTest
1670 {
1671 public:
1672 	VerifyCopyTexImageTest(deqp::Context& context, const TypeFormat& tf);
1673 	virtual ~VerifyCopyTexImageTest();
1674 
1675 	virtual tcu::TestNode::IterateResult iterate(void);
1676 };
1677 
VerifyCopyTexImageTest(deqp::Context & context,const TypeFormat & tf)1678 VerifyCopyTexImageTest::VerifyCopyTexImageTest(deqp::Context& context, const TypeFormat& tf) : BaseTest(context, tf)
1679 {
1680 }
1681 
~VerifyCopyTexImageTest()1682 VerifyCopyTexImageTest::~VerifyCopyTexImageTest()
1683 {
1684 }
1685 
iterate(void)1686 tcu::TestNode::IterateResult VerifyCopyTexImageTest::iterate(void)
1687 {
1688 	// After rendering to depth and stencil, CopyTexImage the results to a new
1689 	// DEPTH_STENCIL texture. Attach this texture to a new FBO. Verify that
1690 	// depth and stencil tests work with the copied data.
1691 
1692 	createTextures();
1693 	renderToTextures();
1694 
1695 	bool				  result = true;
1696 	const glw::Functions& gl	 = m_context.getRenderContext().getFunctions();
1697 
1698 	// setup shader
1699 	GLint uColor;
1700 	setupColorProgram(uColor);
1701 
1702 	// setup and copy texture/fbo
1703 	GLuint tex;
1704 	gl.genTextures(1, &tex);
1705 	GLuint fbo;
1706 	gl.genFramebuffers(1, &fbo);
1707 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexRender]);
1708 	gl.bindTexture(GL_TEXTURE_2D, tex);
1709 	setupTexture();
1710 
1711 	setDrawReadBuffer(GL_NONE, GL_NONE);
1712 
1713 	gl.texImage2D(GL_TEXTURE_2D, 0, m_typeFormat.format, TEX_SIZE, TEX_SIZE, 0, GL_DEPTH_STENCIL, m_typeFormat.type,
1714 				  NULL);
1715 	gl.copyTexImage2D(GL_TEXTURE_2D, 0, m_typeFormat.format, 0, 0, TEX_SIZE, TEX_SIZE, 0);
1716 
1717 	restoreDrawReadBuffer();
1718 
1719 	gl.bindFramebuffer(GL_FRAMEBUFFER, fbo);
1720 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, tex, 0);
1721 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_TEXTURE_2D, tex, 0);
1722 	setDrawReadBuffer(GL_NONE, GL_NONE);
1723 
1724 	int status = gl.checkFramebufferStatus(GL_FRAMEBUFFER);
1725 	if (status != GL_FRAMEBUFFER_COMPLETE)
1726 	{
1727 		m_testCtx.getLog() << tcu::TestLog::Message << "Framebuffer is incomplete: " << status
1728 						   << tcu::TestLog::EndMessage;
1729 		result = false;
1730 		restoreDrawReadBuffer();
1731 	}
1732 	else
1733 	{
1734 		// render
1735 		gl.enable(GL_DEPTH_TEST);
1736 		gl.depthFunc(GL_LEQUAL);
1737 		gl.viewport(0, 0, TEX_SIZE, TEX_SIZE);
1738 		gl.enable(GL_STENCIL_TEST);
1739 		gl.stencilFunc(GL_EQUAL, 0x1, 0xFF);
1740 		gl.stencilOp(GL_KEEP, GL_KEEP, GL_KEEP);
1741 		drawQuad(DEFAULT, m_colorProgram);
1742 		gl.disable(GL_STENCIL_TEST);
1743 
1744 		// verify
1745 		std::vector<GLubyte> data(TEX_SIZE * TEX_SIZE * m_typeFormat.size, 0);
1746 		gl.getTexImage(GL_TEXTURE_2D, 0, GL_DEPTH_STENCIL, m_typeFormat.type, &data[0]);
1747 		result &= verifyDepthStencilGradient(&data[0], verifyCopyTexImage, TEX_SIZE, TEX_SIZE);
1748 
1749 		restoreDrawReadBuffer();
1750 
1751 		result &= doReadPixels(tex, verifyCopyTexImage);
1752 	}
1753 
1754 	// clean up
1755 	gl.deleteFramebuffers(1, &fbo);
1756 	gl.deleteTextures(1, &tex);
1757 
1758 	destroyTextures();
1759 	if (result)
1760 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
1761 	else
1762 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
1763 
1764 	return STOP;
1765 }
1766 
1767 class VerifyPartialAttachmentsTest : public BaseTest
1768 {
1769 public:
1770 	VerifyPartialAttachmentsTest(deqp::Context& context, const TypeFormat& tf);
1771 	virtual ~VerifyPartialAttachmentsTest();
1772 
1773 	virtual tcu::TestNode::IterateResult iterate(void);
1774 };
1775 
VerifyPartialAttachmentsTest(deqp::Context & context,const TypeFormat & tf)1776 VerifyPartialAttachmentsTest::VerifyPartialAttachmentsTest(deqp::Context& context, const TypeFormat& tf)
1777 	: BaseTest(context, tf)
1778 {
1779 }
1780 
~VerifyPartialAttachmentsTest()1781 VerifyPartialAttachmentsTest::~VerifyPartialAttachmentsTest()
1782 {
1783 }
1784 
iterate(void)1785 tcu::TestNode::IterateResult VerifyPartialAttachmentsTest::iterate(void)
1786 {
1787 	createTextures();
1788 	renderToTextures();
1789 
1790 	bool result = true;
1791 
1792 	//  - Create an FBO with a packed depth stencil renderbuffer attached to
1793 	//	DEPTH_ATTACHMENT only. If this FBO is complete, stencil test must act as
1794 	//	if there is no stencil buffer (always pass.)
1795 
1796 	//  - Create an FBO with a packed depth stencil renderbuffer attached to
1797 	//	STENCIL_ATTACHMENT only. If this FBO is complete, depth test must act as
1798 	//	if there is no depth buffer (always pass.)
1799 
1800 	//  - Create an FBO with a packed depth stencil renderbuffer attached to
1801 	//	STENCIL_ATTACHMENT only. If this FBO is complete, occlusion query must
1802 	//	act as if there is no depth buffer (always pass.)
1803 
1804 	const glu::RenderContext& renderContext = m_context.getRenderContext();
1805 	const glw::Functions&	 gl			= renderContext.getFunctions();
1806 	bool					  isContextES   = glu::isContextTypeES(renderContext.getType());
1807 
1808 	// setup shader
1809 	GLint uColor;
1810 	setupColorProgram(uColor);
1811 
1812 	GLuint occ;
1813 	gl.genQueries(1, &occ);
1814 
1815 	for (int i = 0; i < 3; i++)
1816 	{
1817 		// setup fbo
1818 		GLuint fbo;
1819 		gl.genFramebuffers(1, &fbo);
1820 		gl.bindFramebuffer(GL_FRAMEBUFFER, fbo);
1821 
1822 		GLuint rbo[2]; // color, D/S
1823 		gl.genRenderbuffers(2, rbo);
1824 		gl.bindRenderbuffer(GL_RENDERBUFFER, rbo[0]);
1825 		gl.renderbufferStorage(GL_RENDERBUFFER, GL_RGBA8, TEX_SIZE, TEX_SIZE);
1826 		gl.bindRenderbuffer(GL_RENDERBUFFER, rbo[1]);
1827 		gl.renderbufferStorage(GL_RENDERBUFFER, m_typeFormat.format, TEX_SIZE, TEX_SIZE);
1828 
1829 		gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, rbo[0]);
1830 		setDrawReadBuffer(GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT0);
1831 
1832 		switch (i)
1833 		{
1834 		case 0:
1835 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rbo[1]);
1836 			break;
1837 		case 1:
1838 		case 2:
1839 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, rbo[1]);
1840 			break;
1841 		default:
1842 			result = false;
1843 		}
1844 
1845 		if (!result)
1846 			break;
1847 
1848 		int status = gl.checkFramebufferStatus(GL_FRAMEBUFFER);
1849 		if (status != GL_FRAMEBUFFER_COMPLETE)
1850 		{
1851 			m_testCtx.getLog() << tcu::TestLog::Message << "Framebuffer is incomplete: " << status
1852 							   << tcu::TestLog::EndMessage;
1853 			result = false;
1854 		}
1855 		else
1856 		{
1857 			// render
1858 			gl.viewport(0, 0, TEX_SIZE, TEX_SIZE);
1859 			if (isContextES)
1860 				gl.clearDepthf(1.0f);
1861 			else
1862 				gl.clearDepth(1.0);
1863 
1864 			gl.clearStencil(0);
1865 			gl.clearColor(0.8f, 0.8f, 0.8f, 0.8f);
1866 			gl.clear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
1867 
1868 			switch (i)
1869 			{
1870 			case 0:
1871 				gl.disable(GL_DEPTH_TEST);
1872 				gl.enable(GL_STENCIL_TEST);
1873 				gl.stencilFunc(GL_NEVER, 0xFF, 0xFF);
1874 				gl.stencilOp(GL_KEEP, GL_KEEP, GL_KEEP);
1875 				break;
1876 			case 1:
1877 				gl.enable(GL_DEPTH_TEST);
1878 				gl.depthFunc(GL_NEVER);
1879 				gl.disable(GL_STENCIL_TEST);
1880 				break;
1881 			case 2:
1882 				gl.enable(GL_DEPTH_TEST);
1883 				gl.depthFunc(GL_NEVER);
1884 				gl.disable(GL_STENCIL_TEST);
1885 				gl.beginQuery(GL_ANY_SAMPLES_PASSED, occ);
1886 				break;
1887 			default:
1888 				break;
1889 			}
1890 
1891 			drawQuad(DEFAULT, m_colorProgram);
1892 
1893 			if (i == 2)
1894 			{
1895 				GLuint n;
1896 
1897 				gl.endQuery(GL_ANY_SAMPLES_PASSED);
1898 				gl.getQueryObjectuiv(occ, GL_QUERY_RESULT, &n);
1899 
1900 				if (n > 0)
1901 				{
1902 					drawQuad(DEFAULT, m_colorProgram);
1903 				}
1904 			}
1905 
1906 			std::vector<GLuint> data(TEX_SIZE * TEX_SIZE, 0);
1907 			gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_RGBA, GL_UNSIGNED_BYTE, &data[0]);
1908 			result &= verifyColorGradient(&data[0], verifyPartialAttachments, COLOR_CHECK_DEFAULT, TEX_SIZE, TEX_SIZE);
1909 		}
1910 
1911 		restoreDrawReadBuffer();
1912 
1913 		gl.bindFramebuffer(GL_FRAMEBUFFER, m_defaultFBO);
1914 
1915 		// clean up
1916 		gl.deleteFramebuffers(1, &fbo);
1917 		gl.deleteRenderbuffers(2, rbo);
1918 	}
1919 
1920 	gl.deleteQueries(1, &occ);
1921 
1922 	destroyTextures();
1923 	if (result)
1924 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
1925 	else
1926 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
1927 
1928 	return STOP;
1929 }
1930 
1931 class VerifyMixedAttachmentsTest : public BaseTest
1932 {
1933 public:
1934 	VerifyMixedAttachmentsTest(deqp::Context& context, const TypeFormat& tf);
1935 	virtual ~VerifyMixedAttachmentsTest();
1936 
1937 	virtual tcu::TestNode::IterateResult iterate(void);
1938 };
1939 
VerifyMixedAttachmentsTest(deqp::Context & context,const TypeFormat & tf)1940 VerifyMixedAttachmentsTest::VerifyMixedAttachmentsTest(deqp::Context& context, const TypeFormat& tf)
1941 	: BaseTest(context, tf)
1942 {
1943 }
1944 
~VerifyMixedAttachmentsTest()1945 VerifyMixedAttachmentsTest::~VerifyMixedAttachmentsTest()
1946 {
1947 }
1948 
iterate(void)1949 tcu::TestNode::IterateResult VerifyMixedAttachmentsTest::iterate(void)
1950 {
1951 	// Create FBOs that mix DEPTH_STENCIL renderbuffers with DEPTH or STENCIL
1952 	// renderbuffers. If these FBOs are complete, depth and stencil test
1953 	// must work properly.
1954 
1955 	// Create an FBO with two different packed depth stencil renderbuffers, one
1956 	// attached to DEPTH_ATTACHMENT and the other attached to STENCIL_ATTACHMENT.
1957 	// Querying DEPTH_STENCIL_ATTACHMENT must fail with INVALID_OPERATION. If
1958 	// this FBO is complete, depth and stencil tests must work properly.
1959 
1960 	createTextures();
1961 	renderToTextures();
1962 
1963 	bool result = true;
1964 
1965 	const glu::RenderContext& renderContext = m_context.getRenderContext();
1966 	const glw::Functions&	 gl			= renderContext.getFunctions();
1967 	bool					  isContextES   = glu::isContextTypeES(renderContext.getType());
1968 
1969 	GLint uColor;
1970 	setupColorProgram(uColor);
1971 
1972 	for (int i = 0; i < 3; i++)
1973 	{
1974 		// set up FBO/RBOs
1975 		GLuint fbo;
1976 		gl.genFramebuffers(1, &fbo);
1977 		gl.bindFramebuffer(GL_FRAMEBUFFER, fbo);
1978 
1979 		GLuint rbo[3]; // color, DEPTH_STENCIL, DEPTH/STENCIL
1980 		gl.genRenderbuffers(3, rbo);
1981 
1982 		gl.bindRenderbuffer(GL_RENDERBUFFER, rbo[0]);
1983 		gl.renderbufferStorage(GL_RENDERBUFFER, GL_RGBA8, TEX_SIZE, TEX_SIZE);
1984 		gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, rbo[0]);
1985 
1986 		gl.bindRenderbuffer(GL_RENDERBUFFER, rbo[1]);
1987 		gl.renderbufferStorage(GL_RENDERBUFFER, m_typeFormat.format, TEX_SIZE, TEX_SIZE);
1988 
1989 		gl.bindRenderbuffer(GL_RENDERBUFFER, rbo[2]);
1990 		switch (i)
1991 		{
1992 		case 0:
1993 			gl.renderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT16, TEX_SIZE, TEX_SIZE);
1994 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, rbo[1]);
1995 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rbo[2]);
1996 			break;
1997 		case 1:
1998 			gl.renderbufferStorage(GL_RENDERBUFFER, GL_STENCIL_INDEX8, TEX_SIZE, TEX_SIZE);
1999 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rbo[1]);
2000 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, rbo[2]);
2001 			break;
2002 		case 2:
2003 			gl.renderbufferStorage(GL_RENDERBUFFER, m_typeFormat.format, TEX_SIZE, TEX_SIZE);
2004 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rbo[1]);
2005 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, rbo[2]);
2006 
2007 			GLint param;
2008 			gl.getFramebufferAttachmentParameteriv(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT,
2009 												   GL_FRAMEBUFFER_ATTACHMENT_OBJECT_TYPE, &param);
2010 			if (gl.getError() != GL_INVALID_OPERATION)
2011 			{
2012 				m_testCtx.getLog() << tcu::TestLog::Message
2013 								   << "Expected INVALID_OPERATION for DEPTH_STENCIL_ATTACHMENT query"
2014 								   << tcu::TestLog::EndMessage;
2015 				result = false;
2016 			}
2017 
2018 			break;
2019 		}
2020 
2021 		GLenum status = gl.checkFramebufferStatus(GL_FRAMEBUFFER);
2022 		if (status != GL_FRAMEBUFFER_COMPLETE)
2023 		{
2024 			if (status == GL_FRAMEBUFFER_UNSUPPORTED)
2025 			{
2026 				/* The spec only requires
2027 
2028 					 "when both depth and stencil attachments are present, implementations are only
2029 					  required to support framebuffer objects where both attachments refer to the same image."
2030 
2031 				   Thus, it is accepatable for an implementation returning GL_FRAMEBUFFER_UNSUPPORTED.  And the
2032 				   test can NOT be marked as fail.
2033 				 */
2034 			}
2035 			else
2036 			{
2037 				m_testCtx.getLog() << tcu::TestLog::Message << "Framebuffer is incomplete" << tcu::TestLog::EndMessage;
2038 				result = false;
2039 			}
2040 		}
2041 		else
2042 		{
2043 
2044 			// render
2045 			// step 1
2046 			gl.viewport(0, 0, TEX_SIZE, TEX_SIZE);
2047 			gl.enable(GL_DEPTH_TEST);
2048 			gl.depthFunc(GL_LEQUAL);
2049 
2050 			if (isContextES)
2051 				gl.clearDepthf(1.0f);
2052 			else
2053 				gl.clearDepth(1.0);
2054 
2055 			gl.enable(GL_STENCIL_TEST);
2056 			gl.stencilFunc(GL_ALWAYS, 0x1, 0xFF);
2057 			gl.stencilOp(GL_REPLACE, GL_REPLACE, GL_REPLACE);
2058 			gl.clearStencil(0);
2059 			gl.clearColor(0.8f, 0.8f, 0.8f, 0.8f);
2060 			gl.clear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
2061 			drawQuad(DEPTH_SPAN1, m_colorProgram);
2062 
2063 			// step 2
2064 			gl.stencilFunc(GL_EQUAL, 0x1, 0xFF);
2065 			gl.stencilOp(GL_REPLACE, GL_REPLACE, GL_REPLACE);
2066 			gl.clearColor(0.8f, 0.8f, 0.8f, 0.8f);
2067 			gl.clear(GL_COLOR_BUFFER_BIT);
2068 			drawQuad(DEFAULT, m_colorProgram);
2069 
2070 			std::vector<GLuint> data(TEX_SIZE * TEX_SIZE, 0);
2071 			gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_RGBA, GL_UNSIGNED_BYTE, &data[0]);
2072 			result &= verifyColorGradient(&data[0], verifyMixedAttachments, COLOR_CHECK_DEFAULT, TEX_SIZE, TEX_SIZE);
2073 		}
2074 
2075 		// clean up
2076 		gl.deleteRenderbuffers(3, rbo);
2077 		gl.deleteFramebuffers(1, &fbo);
2078 	}
2079 
2080 	destroyTextures();
2081 	if (result)
2082 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
2083 	else
2084 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
2085 
2086 	return STOP;
2087 }
2088 
2089 class VerifyParametersTest : public BaseTest
2090 {
2091 public:
2092 	VerifyParametersTest(deqp::Context& context, const TypeFormat& tf);
2093 	virtual ~VerifyParametersTest();
2094 
2095 	virtual tcu::TestNode::IterateResult iterate(void);
2096 };
2097 
VerifyParametersTest(deqp::Context & context,const TypeFormat & tf)2098 VerifyParametersTest::VerifyParametersTest(deqp::Context& context, const TypeFormat& tf) : BaseTest(context, tf)
2099 {
2100 }
2101 
~VerifyParametersTest()2102 VerifyParametersTest::~VerifyParametersTest()
2103 {
2104 }
2105 
iterate(void)2106 tcu::TestNode::IterateResult VerifyParametersTest::iterate(void)
2107 {
2108 	//  Verify GetFramebufferAttachmentParameter queries of each <pname> on
2109 	//	DEPTH_STENCIL_ATTACHMENT work correctly if both attachments are populated
2110 	//	with the same object.
2111 
2112 	createTextures();
2113 	renderToTextures();
2114 
2115 	bool result = true;
2116 
2117 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
2118 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexImage]);
2119 
2120 	GLint param;
2121 	gl.getFramebufferAttachmentParameteriv(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT,
2122 										   GL_FRAMEBUFFER_ATTACHMENT_OBJECT_TYPE, &param);
2123 	if (param != GL_TEXTURE)
2124 	{
2125 		m_testCtx.getLog() << tcu::TestLog::Message
2126 						   << "Invalid value for GL_FRAMEBUFFER_ATTACHMENT_OBJECT_TYPE: " << param
2127 						   << tcu::TestLog::EndMessage;
2128 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
2129 		return STOP;
2130 	}
2131 
2132 	const AttachmentParam* attachmentParams = getAttachmentParams();
2133 	for (GLuint i = 0; i < m_attachmentParamsCount; i++)
2134 	{
2135 		int	ref;
2136 		GLenum pname = attachmentParams[i].pname;
2137 		if (GL_FRAMEBUFFER_ATTACHMENT_COMPONENT_TYPE == pname)
2138 		{
2139 			gl.getFramebufferAttachmentParameteriv(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT, pname, &param);
2140 			if (gl.getError() != GL_INVALID_OPERATION)
2141 				result = false;
2142 			continue;
2143 		}
2144 
2145 		gl.getFramebufferAttachmentParameteriv(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT, pname, &param);
2146 
2147 		ref = attachmentParams[i].value;
2148 		if (pname == GL_FRAMEBUFFER_ATTACHMENT_OBJECT_NAME)
2149 			ref = m_textures[packedTexImage];
2150 
2151 		if (param != ref)
2152 		{
2153 			m_testCtx.getLog() << tcu::TestLog::Message << "Invalid value for pname " << attachmentParams[i].pname
2154 							   << ": " << param << " ( expected " << ref << ")" << tcu::TestLog::EndMessage;
2155 			result = false;
2156 		}
2157 	}
2158 
2159 	destroyTextures();
2160 	if (result)
2161 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
2162 	else
2163 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
2164 
2165 	return STOP;
2166 }
2167 
2168 class RenderbuffersTest : public BaseTest
2169 {
2170 public:
2171 	RenderbuffersTest(deqp::Context& context, const TypeFormat& tf);
2172 	virtual ~RenderbuffersTest();
2173 
2174 	virtual tcu::TestNode::IterateResult iterate(void);
2175 };
2176 
RenderbuffersTest(deqp::Context & context,const TypeFormat & tf)2177 RenderbuffersTest::RenderbuffersTest(deqp::Context& context, const TypeFormat& tf) : BaseTest(context, tf)
2178 {
2179 }
2180 
~RenderbuffersTest()2181 RenderbuffersTest::~RenderbuffersTest()
2182 {
2183 }
2184 
iterate(void)2185 tcu::TestNode::IterateResult RenderbuffersTest::iterate(void)
2186 {
2187 	createTextures();
2188 	renderToTextures();
2189 
2190 	bool result = true;
2191 
2192 	// Verify RENDERBUFFER_DEPTH_SIZE and RENDERBUFFER_STENCIL_SIZE report
2193 	// appropriate values for for DEPTH_STENCIL renderbuffers.
2194 
2195 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
2196 
2197 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_framebuffers[packedTexImage]);
2198 
2199 	GLuint rbo;
2200 	gl.genRenderbuffers(1, &rbo);
2201 	gl.bindRenderbuffer(GL_RENDERBUFFER, rbo);
2202 	gl.renderbufferStorage(GL_RENDERBUFFER, m_typeFormat.format, TEX_SIZE, TEX_SIZE);
2203 	gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT, GL_RENDERBUFFER, rbo);
2204 
2205 	GLint param;
2206 	gl.getRenderbufferParameteriv(GL_RENDERBUFFER, GL_RENDERBUFFER_DEPTH_SIZE, &param);
2207 	if (param != m_typeFormat.d)
2208 	{
2209 		m_testCtx.getLog() << tcu::TestLog::Message << "Invalid depth: " << param << ", expected: " << m_typeFormat.d
2210 						   << tcu::TestLog::EndMessage;
2211 		result = false;
2212 	}
2213 
2214 	gl.getRenderbufferParameteriv(GL_RENDERBUFFER, GL_RENDERBUFFER_STENCIL_SIZE, &param);
2215 	if (param != m_typeFormat.s)
2216 	{
2217 		m_testCtx.getLog() << tcu::TestLog::Message << "Invalid stencil: " << param << ", expected: " << m_typeFormat.s
2218 						   << tcu::TestLog::EndMessage;
2219 		result = false;
2220 	}
2221 
2222 	gl.bindRenderbuffer(GL_RENDERBUFFER, 0);
2223 	gl.deleteRenderbuffers(1, &rbo);
2224 	gl.bindFramebuffer(GL_FRAMEBUFFER, m_defaultFBO);
2225 
2226 	destroyTextures();
2227 	if (result)
2228 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
2229 	else
2230 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
2231 
2232 	return STOP;
2233 }
2234 
2235 class StencilSizeTest : public BaseTest
2236 {
2237 public:
2238 	StencilSizeTest(deqp::Context& context, const TypeFormat& tf);
2239 	virtual ~StencilSizeTest();
2240 
2241 	virtual tcu::TestNode::IterateResult iterate(void);
2242 };
2243 
StencilSizeTest(deqp::Context & context,const TypeFormat & tf)2244 StencilSizeTest::StencilSizeTest(deqp::Context& context, const TypeFormat& tf) : BaseTest(context, tf)
2245 {
2246 }
2247 
~StencilSizeTest()2248 StencilSizeTest::~StencilSizeTest()
2249 {
2250 }
2251 
iterate(void)2252 tcu::TestNode::IterateResult StencilSizeTest::iterate(void)
2253 {
2254 	// [desktop only] Verify TEXTURE_STENCIL_SIZE reports 8 for DEPTH_STENCIL
2255 	// textures, and 0 for RGBA and DEPTH_COMPONENT textures.
2256 
2257 	createTextures();
2258 	renderToTextures();
2259 
2260 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
2261 
2262 	bool  result = true;
2263 	GLint param;
2264 	gl.bindTexture(GL_TEXTURE_2D, m_textures[packedTexImage]);
2265 	gl.getTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_STENCIL_SIZE, &param);
2266 	if (param != 8)
2267 	{
2268 		m_testCtx.getLog() << tcu::TestLog::Message << "Invalid value for DEPTH_STENCIL stencil size: " << param
2269 						   << tcu::TestLog::EndMessage;
2270 		result = false;
2271 	}
2272 
2273 	GLuint texRGBA;
2274 	gl.genTextures(1, &texRGBA);
2275 	gl.bindTexture(GL_TEXTURE_2D, texRGBA);
2276 	setupTexture();
2277 	gl.texImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, TEX_SIZE, TEX_SIZE, 0, GL_RGBA, GL_UNSIGNED_BYTE, 0);
2278 	gl.getTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_STENCIL_SIZE, &param);
2279 	if (param != 0)
2280 	{
2281 		m_testCtx.getLog() << tcu::TestLog::Message << "Invalid value for RGBA stencil size: " << param
2282 						   << tcu::TestLog::EndMessage;
2283 		result = false;
2284 	}
2285 	gl.deleteTextures(1, &texRGBA);
2286 
2287 	GLuint texDepth;
2288 	gl.genTextures(1, &texDepth);
2289 	gl.bindTexture(GL_TEXTURE_2D, texDepth);
2290 	setupTexture();
2291 	gl.texImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT16, TEX_SIZE, TEX_SIZE, 0, GL_DEPTH_COMPONENT, GL_UNSIGNED_SHORT,
2292 				  0);
2293 	gl.getTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_STENCIL_SIZE, &param);
2294 	if (param != 0)
2295 	{
2296 		m_testCtx.getLog() << tcu::TestLog::Message << "Invalid value for DEPTH_COMPONENT stencil size: " << param
2297 						   << tcu::TestLog::EndMessage;
2298 		result = false;
2299 	}
2300 	gl.deleteTextures(1, &texDepth);
2301 
2302 	destroyTextures();
2303 	if (result)
2304 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
2305 	else
2306 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
2307 
2308 	return STOP;
2309 }
2310 
2311 class ClearBufferTest : public BaseTest
2312 {
2313 public:
2314 	ClearBufferTest(deqp::Context& context, const TypeFormat& tf);
2315 	virtual ~ClearBufferTest();
2316 
2317 	virtual tcu::TestNode::IterateResult iterate(void);
2318 };
2319 
ClearBufferTest(deqp::Context & context,const TypeFormat & tf)2320 ClearBufferTest::ClearBufferTest(deqp::Context& context, const TypeFormat& tf) : BaseTest(context, tf)
2321 {
2322 }
2323 
~ClearBufferTest()2324 ClearBufferTest::~ClearBufferTest()
2325 {
2326 }
2327 
iterate(void)2328 tcu::TestNode::IterateResult ClearBufferTest::iterate(void)
2329 {
2330 	// Verify ClearBufferfv correctly clears the depth channel of a DEPTH_STENCIL
2331 	// FBO attachment (and does not touch the stencil channel.)
2332 	// Verify ClearBufferiv correctly clears the stencil channel of a
2333 	// DEPTH_STENCIL FBO attachment (and does not touch the depth channel.)
2334 	// Verify ClearBufferfi correctly clears the depth and stencil channels of a
2335 	// DEPTH_STENCIL FBO attachment.
2336 
2337 	createTextures();
2338 	renderToTextures();
2339 
2340 	bool	result = true;
2341 	GLfloat valuef;
2342 	GLint   valuei;
2343 	GLenum  status;
2344 
2345 	const glw::Functions& gl = m_context.getRenderContext().getFunctions();
2346 
2347 	// setup shader
2348 	GLint uColor;
2349 	setupColorProgram(uColor);
2350 
2351 	for (int i = 0; i < 3; i++)
2352 	{
2353 		// setup texture/fbo
2354 		GLuint tex;
2355 		GLuint texColor;
2356 		GLuint fbo;
2357 		gl.genTextures(1, &tex);
2358 		gl.genTextures(1, &texColor);
2359 		gl.genFramebuffers(1, &fbo);
2360 		gl.bindFramebuffer(GL_FRAMEBUFFER, fbo);
2361 
2362 		gl.bindTexture(GL_TEXTURE_2D, tex);
2363 		setupTexture();
2364 		std::vector<GLbyte> data;
2365 		createGradient(data);
2366 		gl.texImage2D(GL_TEXTURE_2D, 0, m_typeFormat.format, TEX_SIZE, TEX_SIZE, 0, GL_DEPTH_STENCIL, m_typeFormat.type,
2367 					  &data[0]);
2368 		gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT, GL_TEXTURE_2D, tex, 0);
2369 
2370 		gl.bindTexture(GL_TEXTURE_2D, texColor);
2371 		setupTexture();
2372 		gl.texImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, TEX_SIZE, TEX_SIZE, 0, GL_RGBA, GL_UNSIGNED_BYTE, 0);
2373 		gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texColor, 0);
2374 
2375 		setDrawReadBuffer(GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT0);
2376 
2377 		status = gl.checkFramebufferStatus(GL_FRAMEBUFFER);
2378 		if (status != GL_FRAMEBUFFER_COMPLETE)
2379 		{
2380 			m_testCtx.getLog() << tcu::TestLog::Message << "Framebuffer is incomplete: " << status
2381 							   << tcu::TestLog::EndMessage;
2382 			result = false;
2383 		}
2384 		else
2385 		{
2386 			// clear relevant buffers
2387 			switch (i)
2388 			{
2389 			case 0:
2390 				valuef = 1.0f;
2391 				gl.clearBufferfv(GL_DEPTH, 0, &valuef);
2392 				break;
2393 			case 1:
2394 				valuei = 0xff;
2395 				gl.clearBufferiv(GL_STENCIL, 0, &valuei);
2396 				break;
2397 			case 2:
2398 				valuef = 1.0f;
2399 				valuei = 0xff;
2400 				gl.clearBufferfi(GL_DEPTH_STENCIL, 0, valuef, valuei);
2401 				break;
2402 			}
2403 
2404 			// render reference image
2405 			gl.viewport(0, 0, TEX_SIZE, TEX_SIZE);
2406 			gl.enable(GL_DEPTH_TEST);
2407 			gl.depthFunc(GL_LEQUAL);
2408 			gl.enable(GL_STENCIL_TEST);
2409 			gl.stencilFunc(GL_EQUAL, 0xFF, 0xFF);
2410 			gl.stencilOp(GL_KEEP, GL_KEEP, GL_KEEP);
2411 			gl.clearColor(0.8f, 0.8f, 0.8f, 0.8f);
2412 			gl.clear(GL_COLOR_BUFFER_BIT);
2413 			drawQuad(DEFAULT, m_colorProgram);
2414 
2415 			// verify
2416 			std::vector<GLubyte> readData(TEX_SIZE * TEX_SIZE * 4, 0);
2417 			gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_RGBA, GL_UNSIGNED_BYTE, &readData[0]);
2418 			result &=
2419 				verifyColorGradient(&readData[0], verifyClearBufferDepth + i, COLOR_CHECK_DEFAULT, TEX_SIZE, TEX_SIZE);
2420 		}
2421 
2422 		// destroy texture/fbo
2423 		restoreDrawReadBuffer();
2424 
2425 		gl.bindFramebuffer(GL_FRAMEBUFFER, m_defaultFBO);
2426 		gl.bindTexture(GL_TEXTURE_2D, 0);
2427 		gl.deleteFramebuffers(1, &fbo);
2428 		gl.deleteTextures(1, &tex);
2429 		gl.deleteTextures(1, &texColor);
2430 	}
2431 
2432 	destroyTextures();
2433 	if (result)
2434 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
2435 	else
2436 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
2437 
2438 	return STOP;
2439 }
2440 
2441 class BlitTest : public BaseTest
2442 {
2443 public:
2444 	BlitTest(deqp::Context& context, const TypeFormat& tf);
2445 	virtual ~BlitTest();
2446 
2447 	virtual tcu::TestNode::IterateResult iterate(void);
2448 };
2449 
BlitTest(deqp::Context & context,const TypeFormat & tf)2450 BlitTest::BlitTest(deqp::Context& context, const TypeFormat& tf) : BaseTest(context, tf)
2451 {
2452 }
2453 
~BlitTest()2454 BlitTest::~BlitTest()
2455 {
2456 }
2457 
iterate(void)2458 tcu::TestNode::IterateResult BlitTest::iterate(void)
2459 {
2460 	// Verify that NEAREST filtered blits of DEPTH and/or STENCIL between two
2461 	// FBOs with the same format packed depth stencil attachment work. Test
2462 	// non-multisample [1->1], multisample resolve [N->1], and multisample
2463 	// replicate [1->N] blits, for each supported value of N up to MAX_SAMPLES.
2464 
2465 	createTextures();
2466 	renderToTextures();
2467 
2468 	GLuint fbo[3]; // Framebuffers: source, dest, downsample
2469 	GLuint rbo[4]; // Renderbuffers: source D/S, dest D/S, dest color, downsample color
2470 	GLint  maxSamples;
2471 	int	srcSamples, destSamples;
2472 	bool   result = true;
2473 
2474 	const glu::RenderContext& renderContext = m_context.getRenderContext();
2475 	const glw::Functions&	 gl			= renderContext.getFunctions();
2476 	bool					  isContextES   = glu::isContextTypeES(renderContext.getType());
2477 
2478 	std::vector<GLuint> data(TEX_SIZE * TEX_SIZE);
2479 
2480 	GLint uColor;
2481 	setupColorProgram(uColor);
2482 
2483 	gl.getIntegerv(GL_MAX_SAMPLES, &maxSamples);
2484 
2485 	// ES does not allow SAMPLE_BUFFERS for the draw frame
2486 	// buffer is greater than zero when doing a blit.
2487 	int loopCount = isContextES ? 1 : 2;
2488 
2489 	for (int j = 0; j < loopCount; j++)
2490 	{
2491 		for (int i = 0; i <= maxSamples; i++)
2492 		{
2493 			// Create FBO/RBO
2494 			gl.genFramebuffers(3, fbo);
2495 			gl.genRenderbuffers(4, rbo);
2496 
2497 			if (j == 0)
2498 			{
2499 				srcSamples  = i;
2500 				destSamples = 0;
2501 			}
2502 			else
2503 			{
2504 				srcSamples  = 0;
2505 				destSamples = i;
2506 			}
2507 
2508 			gl.bindFramebuffer(GL_FRAMEBUFFER, fbo[0]);
2509 			gl.bindRenderbuffer(GL_RENDERBUFFER, rbo[0]);
2510 			gl.renderbufferStorageMultisample(GL_RENDERBUFFER, srcSamples, m_typeFormat.format, TEX_SIZE, TEX_SIZE);
2511 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT, GL_RENDERBUFFER, rbo[0]);
2512 
2513 			gl.bindFramebuffer(GL_FRAMEBUFFER, fbo[1]);
2514 			gl.bindRenderbuffer(GL_RENDERBUFFER, rbo[1]);
2515 			gl.renderbufferStorageMultisample(GL_RENDERBUFFER, destSamples, m_typeFormat.format, TEX_SIZE, TEX_SIZE);
2516 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT, GL_RENDERBUFFER, rbo[1]);
2517 
2518 			gl.bindRenderbuffer(GL_RENDERBUFFER, rbo[2]);
2519 			gl.renderbufferStorageMultisample(GL_RENDERBUFFER, destSamples, GL_RGBA8, TEX_SIZE, TEX_SIZE);
2520 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, rbo[2]);
2521 
2522 			gl.bindFramebuffer(GL_FRAMEBUFFER, fbo[2]);
2523 			gl.bindRenderbuffer(GL_RENDERBUFFER, rbo[3]);
2524 			gl.renderbufferStorageMultisample(GL_RENDERBUFFER, 0, GL_RGBA8, TEX_SIZE, TEX_SIZE);
2525 			gl.framebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, rbo[3]);
2526 
2527 			// Render
2528 			gl.bindFramebuffer(GL_FRAMEBUFFER, fbo[0]);
2529 			setDrawReadBuffer(GL_NONE, GL_NONE);
2530 
2531 			gl.viewport(0, 0, TEX_SIZE, TEX_SIZE);
2532 			gl.enable(GL_DEPTH_TEST);
2533 			gl.depthFunc(GL_LEQUAL);
2534 
2535 			if (isContextES)
2536 				gl.clearDepthf(1.0f);
2537 			else
2538 				gl.clearDepth(1.0);
2539 
2540 			gl.enable(GL_STENCIL_TEST);
2541 			gl.stencilFunc(GL_ALWAYS, 0x1, 0xFF);
2542 			gl.stencilOp(GL_REPLACE, GL_REPLACE, GL_REPLACE);
2543 			gl.clearStencil(0);
2544 			gl.clearColor(0.8f, 0.8f, 0.8f, 0.8f);
2545 			gl.clear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
2546 			drawQuad(DEPTH_SPAN1, m_colorProgram);
2547 
2548 			restoreDrawReadBuffer();
2549 
2550 			// Blit
2551 			gl.bindFramebuffer(GL_READ_FRAMEBUFFER, fbo[0]);
2552 			gl.bindFramebuffer(GL_DRAW_FRAMEBUFFER, fbo[1]);
2553 			setDrawReadBuffer(GL_NONE, GL_NONE);
2554 			gl.blitFramebuffer(0, 0, TEX_SIZE, TEX_SIZE, 0, 0, TEX_SIZE, TEX_SIZE,
2555 							   GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT, GL_NEAREST);
2556 			restoreDrawReadBuffer();
2557 
2558 			// Verify
2559 			gl.bindFramebuffer(GL_FRAMEBUFFER, fbo[1]);
2560 			setDrawReadBuffer(GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT0);
2561 
2562 			gl.stencilFunc(GL_EQUAL, 0x1, 0xFF);
2563 			gl.stencilOp(GL_KEEP, GL_KEEP, GL_KEEP);
2564 			gl.clear(GL_COLOR_BUFFER_BIT);
2565 			drawQuad(DEFAULT, m_colorProgram);
2566 
2567 			restoreDrawReadBuffer();
2568 
2569 			// Downsample blit
2570 			gl.bindFramebuffer(GL_READ_FRAMEBUFFER, fbo[1]);
2571 			gl.bindFramebuffer(GL_DRAW_FRAMEBUFFER, fbo[2]);
2572 			setDrawReadBuffer(GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT0);
2573 			gl.blitFramebuffer(0, 0, TEX_SIZE, TEX_SIZE, 0, 0, TEX_SIZE, TEX_SIZE, GL_COLOR_BUFFER_BIT, GL_NEAREST);
2574 			restoreDrawReadBuffer();
2575 
2576 			gl.bindFramebuffer(GL_FRAMEBUFFER, fbo[2]);
2577 
2578 			gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_RGBA, GL_UNSIGNED_BYTE, &data[0]);
2579 
2580 			result &= verifyColorGradient(&data[0], verifyBlit, COLOR_CHECK_DEFAULT, TEX_SIZE, TEX_SIZE);
2581 
2582 			// Clean up
2583 			gl.bindFramebuffer(GL_FRAMEBUFFER, m_defaultFBO);
2584 			gl.bindRenderbuffer(GL_RENDERBUFFER, 0);
2585 
2586 			gl.deleteRenderbuffers(4, rbo);
2587 			gl.deleteFramebuffers(3, fbo);
2588 		}
2589 	}
2590 
2591 	destroyTextures();
2592 	if (result)
2593 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
2594 	else
2595 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
2596 
2597 	return STOP;
2598 }
2599 
2600 class StencilTexturingTest : public BaseTest
2601 {
2602 public:
2603 	StencilTexturingTest(deqp::Context& context, const TypeFormat& tf);
2604 	virtual ~StencilTexturingTest();
2605 
2606 	virtual tcu::TestNode::IterateResult iterate(void);
2607 };
2608 
StencilTexturingTest(deqp::Context & context,const TypeFormat & tf)2609 StencilTexturingTest::StencilTexturingTest(deqp::Context& context, const TypeFormat& tf) : BaseTest(context, tf)
2610 {
2611 }
2612 
~StencilTexturingTest()2613 StencilTexturingTest::~StencilTexturingTest()
2614 {
2615 }
2616 
iterate(void)2617 tcu::TestNode::IterateResult StencilTexturingTest::iterate(void)
2618 {
2619 	// Verifies that either depth or stencil can be sampled depending on
2620 	// GL_DEPTH_STENCIL_TEXTURE_MODE
2621 
2622 	const glu::RenderContext& renderContext = m_context.getRenderContext();
2623 	glu::ContextType		  contextType   = renderContext.getType();
2624 	const glw::Functions&	 gl			= renderContext.getFunctions();
2625 
2626 	bool notSupported = false;
2627 	if (glu::isContextTypeES(contextType))
2628 		notSupported = !glu::contextSupports(contextType, glu::ApiType::es(3, 1));
2629 	else
2630 		notSupported = !glu::contextSupports(contextType, glu::ApiType::core(4, 3));
2631 
2632 	if (notSupported)
2633 	{
2634 		m_testCtx.setTestResult(QP_TEST_RESULT_NOT_SUPPORTED, "stencil_texturing extension is not supported");
2635 		return STOP;
2636 	}
2637 
2638 	createTextures();
2639 	renderToTextures();
2640 
2641 	bool   result = true;
2642 	GLuint fbo;
2643 	gl.genFramebuffers(1, &fbo);
2644 	gl.bindFramebuffer(GL_FRAMEBUFFER, fbo);
2645 
2646 	GLuint texColor;
2647 	gl.genTextures(1, &texColor);
2648 	gl.bindTexture(GL_TEXTURE_2D, texColor);
2649 	setupTexture();
2650 	gl.texImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, TEX_SIZE, TEX_SIZE, 0, GL_RGBA, GL_UNSIGNED_BYTE, 0);
2651 
2652 	gl.framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texColor, 0);
2653 	setDrawReadBuffer(GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT0);
2654 
2655 	// Step 1: Verify depth values
2656 	GLenum status = gl.checkFramebufferStatus(GL_FRAMEBUFFER);
2657 	if (status != GL_FRAMEBUFFER_COMPLETE)
2658 	{
2659 		m_testCtx.getLog() << tcu::TestLog::Message << "Framebuffer is incomplete: " << status
2660 						   << tcu::TestLog::EndMessage;
2661 		result = false;
2662 	}
2663 	else
2664 	{
2665 		gl.bindTexture(GL_TEXTURE_2D, m_textures[packedTexImage]);
2666 
2667 		gl.disable(GL_DEPTH_TEST);
2668 		gl.depthMask(GL_FALSE);
2669 		gl.disable(GL_STENCIL_TEST);
2670 		gl.viewport(0, 0, TEX_SIZE, TEX_SIZE);
2671 		gl.clearColor(0.8f, 0.8f, 0.8f, 0.8f);
2672 		gl.clear(GL_COLOR_BUFFER_BIT);
2673 
2674 		gl.texParameteri(GL_TEXTURE_2D, GL_DEPTH_STENCIL_TEXTURE_MODE, GL_DEPTH_COMPONENT);
2675 		setupTextureProgram();
2676 		drawQuad(DEFAULT, m_textureProgram);
2677 
2678 		std::vector<GLuint> dataColor(TEX_SIZE * TEX_SIZE, 0);
2679 		gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_RGBA, GL_UNSIGNED_BYTE, &dataColor[0]);
2680 		result &= verifyColorGradient(&dataColor[0], packedTexImage, COLOR_CHECK_DEPTH, TEX_SIZE, TEX_SIZE);
2681 
2682 		// Step 2: Verify stencil values
2683 		gl.texParameteri(GL_TEXTURE_2D, GL_DEPTH_STENCIL_TEXTURE_MODE, GL_STENCIL_INDEX);
2684 		setupStencilProgram();
2685 		drawQuad(DEFAULT, m_stencilProgram);
2686 
2687 		dataColor.assign(TEX_SIZE * TEX_SIZE, 0);
2688 		gl.readPixels(0, 0, TEX_SIZE, TEX_SIZE, GL_RGBA, GL_UNSIGNED_BYTE, &dataColor[0]);
2689 		result &= verifyColorGradient(&dataColor[0], packedTexImage, COLOR_CHECK_DEFAULT, TEX_SIZE, TEX_SIZE);
2690 	}
2691 
2692 	restoreDrawReadBuffer();
2693 	gl.deleteFramebuffers(1, &fbo);
2694 	gl.deleteTextures(1, &texColor);
2695 
2696 	destroyTextures();
2697 	if (result)
2698 		m_testCtx.setTestResult(QP_TEST_RESULT_PASS, "Pass");
2699 	else
2700 		m_testCtx.setTestResult(QP_TEST_RESULT_FAIL, "Fail");
2701 
2702 	return STOP;
2703 }
2704 
PackedDepthStencilTests(deqp::Context & context)2705 PackedDepthStencilTests::PackedDepthStencilTests(deqp::Context& context)
2706 	: TestCaseGroup(context, "packed_depth_stencil", "")
2707 {
2708 }
2709 
~PackedDepthStencilTests(void)2710 PackedDepthStencilTests::~PackedDepthStencilTests(void)
2711 {
2712 }
2713 
init(void)2714 void PackedDepthStencilTests::init(void)
2715 {
2716 	TestCaseGroup* validateErrorsGroup			 = new deqp::TestCaseGroup(m_context, "validate_errors", "");
2717 	TestCaseGroup* verifyReadPixelsGroup		 = new deqp::TestCaseGroup(m_context, "verify_read_pixels", "");
2718 	TestCaseGroup* verifyGetTexImageGroup		 = new deqp::TestCaseGroup(m_context, "verify_get_tex_image", "");
2719 	TestCaseGroup* verifyCopyTexImageGroup		 = new deqp::TestCaseGroup(m_context, "verify_copy_tex_image", "");
2720 	TestCaseGroup* verifyPartialAttachmentsGroup = new deqp::TestCaseGroup(m_context, "verify_partial_attachments", "");
2721 	TestCaseGroup* verifyMixedAttachmentsGroup   = new deqp::TestCaseGroup(m_context, "verify_mixed_attachments", "");
2722 	TestCaseGroup* verifyParametersGroup		 = new deqp::TestCaseGroup(m_context, "verify_parameters", "");
2723 	TestCaseGroup* renderbuffersGroup			 = new deqp::TestCaseGroup(m_context, "renderbuffers", "");
2724 	TestCaseGroup* clearBufferGroup				 = new deqp::TestCaseGroup(m_context, "clear_buffer", "");
2725 	TestCaseGroup* blitGroup					 = new deqp::TestCaseGroup(m_context, "blit", "");
2726 	TestCaseGroup* stencilTexturingGroup		 = new deqp::TestCaseGroup(m_context, "stencil_texturing", "");
2727 	TestCaseGroup* stencilSizeGroup				 = new deqp::TestCaseGroup(m_context, "stencil_size", "");
2728 
2729 	bool isContextCoreGL = !glu::isContextTypeES(m_context.getRenderContext().getType());
2730 	if (isContextCoreGL)
2731 		validateErrorsGroup->addChild(new InitialStateTest(m_context));
2732 
2733 	for (int i = 0; i < NUM_TEXTURE_TYPES; i++)
2734 	{
2735 		const TypeFormat& typeFormat = TextureTypes[i];
2736 		validateErrorsGroup->addChild(new ValidateErrorsTest(m_context, typeFormat));
2737 		verifyReadPixelsGroup->addChild(new VerifyReadPixelsTest(m_context, typeFormat));
2738 		verifyPartialAttachmentsGroup->addChild(new VerifyPartialAttachmentsTest(m_context, typeFormat));
2739 		verifyMixedAttachmentsGroup->addChild(new VerifyMixedAttachmentsTest(m_context, typeFormat));
2740 		verifyParametersGroup->addChild(new VerifyParametersTest(m_context, typeFormat));
2741 		renderbuffersGroup->addChild(new RenderbuffersTest(m_context, typeFormat));
2742 		clearBufferGroup->addChild(new ClearBufferTest(m_context, typeFormat));
2743 		blitGroup->addChild(new BlitTest(m_context, typeFormat));
2744 		stencilTexturingGroup->addChild(new StencilTexturingTest(m_context, typeFormat));
2745 
2746 		if (isContextCoreGL)
2747 		{
2748 			verifyGetTexImageGroup->addChild(new VerifyGetTexImageTest(m_context, typeFormat));
2749 			verifyCopyTexImageGroup->addChild(new VerifyCopyTexImageTest(m_context, typeFormat));
2750 			stencilSizeGroup->addChild(new StencilSizeTest(m_context, typeFormat));
2751 		}
2752 	}
2753 
2754 	addChild(validateErrorsGroup);
2755 	addChild(verifyReadPixelsGroup);
2756 	addChild(verifyGetTexImageGroup);
2757 	addChild(verifyCopyTexImageGroup);
2758 	addChild(verifyPartialAttachmentsGroup);
2759 	addChild(verifyMixedAttachmentsGroup);
2760 	addChild(verifyParametersGroup);
2761 	addChild(renderbuffersGroup);
2762 	addChild(clearBufferGroup);
2763 	addChild(blitGroup);
2764 	addChild(stencilTexturingGroup);
2765 	addChild(stencilSizeGroup);
2766 }
2767 
2768 } /* glcts namespace */
2769