es3fPrimitiveRestartTests.cpp revision 3c827367444ee418f129b2c238299f49d3264554
13c827367444ee418f129b2c238299f49d3264554Jarkko Poyry/*-------------------------------------------------------------------------
23c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * drawElements Quality Program OpenGL ES 3.0 Module
33c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * -------------------------------------------------
43c827367444ee418f129b2c238299f49d3264554Jarkko Poyry *
53c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * Copyright 2014 The Android Open Source Project
63c827367444ee418f129b2c238299f49d3264554Jarkko Poyry *
73c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * Licensed under the Apache License, Version 2.0 (the "License");
83c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * you may not use this file except in compliance with the License.
93c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * You may obtain a copy of the License at
103c827367444ee418f129b2c238299f49d3264554Jarkko Poyry *
113c827367444ee418f129b2c238299f49d3264554Jarkko Poyry *      http://www.apache.org/licenses/LICENSE-2.0
123c827367444ee418f129b2c238299f49d3264554Jarkko Poyry *
133c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * Unless required by applicable law or agreed to in writing, software
143c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * distributed under the License is distributed on an "AS IS" BASIS,
153c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
163c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * See the License for the specific language governing permissions and
173c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * limitations under the License.
183c827367444ee418f129b2c238299f49d3264554Jarkko Poyry *
193c827367444ee418f129b2c238299f49d3264554Jarkko Poyry *//*!
203c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * \file
213c827367444ee418f129b2c238299f49d3264554Jarkko Poyry * \brief Primitive restart tests.
223c827367444ee418f129b2c238299f49d3264554Jarkko Poyry *//*--------------------------------------------------------------------*/
233c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
243c827367444ee418f129b2c238299f49d3264554Jarkko Poyry#include "es3fPrimitiveRestartTests.hpp"
253c827367444ee418f129b2c238299f49d3264554Jarkko Poyry#include "gluShaderProgram.hpp"
263c827367444ee418f129b2c238299f49d3264554Jarkko Poyry#include "gluPixelTransfer.hpp"
273c827367444ee418f129b2c238299f49d3264554Jarkko Poyry#include "tcuTestLog.hpp"
283c827367444ee418f129b2c238299f49d3264554Jarkko Poyry#include "tcuSurface.hpp"
293c827367444ee418f129b2c238299f49d3264554Jarkko Poyry#include "tcuImageCompare.hpp"
303c827367444ee418f129b2c238299f49d3264554Jarkko Poyry#include "tcuRenderTarget.hpp"
313c827367444ee418f129b2c238299f49d3264554Jarkko Poyry#include "deRandom.hpp"
323c827367444ee418f129b2c238299f49d3264554Jarkko Poyry#include "deMath.h"
333c827367444ee418f129b2c238299f49d3264554Jarkko Poyry#include "deString.h"
343c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
353c827367444ee418f129b2c238299f49d3264554Jarkko Poyry#include "glw.h"
363c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
373c827367444ee418f129b2c238299f49d3264554Jarkko Poyryusing tcu::Vec4;
383c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
393c827367444ee418f129b2c238299f49d3264554Jarkko Poyrynamespace deqp
403c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
413c827367444ee418f129b2c238299f49d3264554Jarkko Poyrynamespace gles3
423c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
433c827367444ee418f129b2c238299f49d3264554Jarkko Poyrynamespace Functional
443c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
453c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
463c827367444ee418f129b2c238299f49d3264554Jarkko Poyrystatic const int		MAX_RENDER_WIDTH				= 256;
473c827367444ee418f129b2c238299f49d3264554Jarkko Poyrystatic const int		MAX_RENDER_HEIGHT				= 256;
483c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
493c827367444ee418f129b2c238299f49d3264554Jarkko Poyrystatic const deUint32	MAX_UNSIGNED_BYTE				= (1<<8) - 1;
503c827367444ee418f129b2c238299f49d3264554Jarkko Poyrystatic const deUint32	MAX_UNSIGNED_SHORT				= (1<<16) - 1;
513c827367444ee418f129b2c238299f49d3264554Jarkko Poyrystatic const deUint32	MAX_UNSIGNED_INT				= (deUint32)((1ULL << 32) - 1);
523c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
533c827367444ee418f129b2c238299f49d3264554Jarkko Poyrystatic const deUint8	RESTART_INDEX_UNSIGNED_BYTE		= (deUint8)MAX_UNSIGNED_BYTE;
543c827367444ee418f129b2c238299f49d3264554Jarkko Poyrystatic const deUint16	RESTART_INDEX_UNSIGNED_SHORT	= (deUint16)MAX_UNSIGNED_SHORT;
553c827367444ee418f129b2c238299f49d3264554Jarkko Poyrystatic const deUint32	RESTART_INDEX_UNSIGNED_INT		= MAX_UNSIGNED_INT;
563c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
573c827367444ee418f129b2c238299f49d3264554Jarkko Poyryclass PrimitiveRestartCase : public TestCase
583c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
593c827367444ee418f129b2c238299f49d3264554Jarkko Poyrypublic:
603c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	enum PrimitiveType
613c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
623c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		PRIMITIVE_POINTS = 0,
633c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		PRIMITIVE_LINE_STRIP,
643c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		PRIMITIVE_LINE_LOOP,
653c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		PRIMITIVE_LINES,
663c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		PRIMITIVE_TRIANGLE_STRIP,
673c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		PRIMITIVE_TRIANGLE_FAN,
683c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		PRIMITIVE_TRIANGLES,
693c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
703c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		PRIMITIVE_LAST
713c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	};
723c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
733c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	enum IndexType
743c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
753c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		INDEX_UNSIGNED_BYTE = 0,
763c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		INDEX_UNSIGNED_SHORT,
773c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		INDEX_UNSIGNED_INT,
783c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
793c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		INDEX_LAST
803c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	};
813c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
823c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	enum Function
833c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
843c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		FUNCTION_DRAW_ELEMENTS = 0,
853c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		FUNCTION_DRAW_ELEMENTS_INSTANCED,
863c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		FUNCTION_DRAW_RANGE_ELEMENTS,
873c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
883c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		FUNCTION_LAST
893c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	};
903c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
913c827367444ee418f129b2c238299f49d3264554Jarkko Poyry							PrimitiveRestartCase	(Context& context, const char* name, const char* description, PrimitiveType primType, IndexType indexType, Function function, bool beginWithRestart, bool endWithRestart, bool duplicateRestarts);
923c827367444ee418f129b2c238299f49d3264554Jarkko Poyry							~PrimitiveRestartCase	(void);
933c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
943c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	void					init					(void);
953c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	void					deinit					(void);
963c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	IterateResult			iterate					(void);
973c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
983c827367444ee418f129b2c238299f49d3264554Jarkko Poyryprivate:
993c827367444ee418f129b2c238299f49d3264554Jarkko Poyry							PrimitiveRestartCase	(const PrimitiveRestartCase& other);
1003c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	PrimitiveRestartCase&	operator=				(const PrimitiveRestartCase& other);
1013c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1023c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	void					draw					(int startNdx, int count);
1033c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1043c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	void					renderWithRestart		(void);
1053c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	void					renderWithoutRestart	(void);
1063c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1073c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// Helper functions for handling the appropriate index vector (according to m_indexType).
1083c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	void					addIndex				(deUint32 index);
1093c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	deUint32				getIndex				(int indexNdx);
1103c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	int						getNumIndices			(void);
1113c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	void*					getIndexPtr				(int indexNdx);
1123c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1133c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// \note Only one of the following index vectors is used (according to m_indexType).
1143c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	std::vector<deUint8>	m_indicesUB;
1153c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	std::vector<deUint16>	m_indicesUS;
1163c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	std::vector<deUint32>	m_indicesUI;
1173c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1183c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	std::vector<float>		m_positions;
1193c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1203c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	PrimitiveType			m_primType;
1213c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	IndexType				m_indexType;
1223c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	Function				m_function;
1233c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1243c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	bool					m_beginWithRestart;		// Whether there will be restart indices at the beginning of the index array.
1253c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	bool					m_endWithRestart;		// Whether there will be restart indices at the end of the index array.
1263c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	bool					m_duplicateRestarts;	// Whether two consecutive restarts are used instead of one.
1273c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1283c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glu::ShaderProgram*		m_program;
1293c827367444ee418f129b2c238299f49d3264554Jarkko Poyry};
1303c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1313c827367444ee418f129b2c238299f49d3264554Jarkko PoyryPrimitiveRestartCase::PrimitiveRestartCase (Context& context, const char* name, const char* description, PrimitiveType primType, IndexType indexType, Function function, bool beginWithRestart, bool endWithRestart, bool duplicateRestarts)
1323c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	: TestCase				(context, name, description)
1333c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	, m_primType			(primType)
1343c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	, m_indexType			(indexType)
1353c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	, m_function			(function)
1363c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	, m_beginWithRestart	(beginWithRestart)
1373c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	, m_endWithRestart		(endWithRestart)
1383c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	, m_duplicateRestarts	(duplicateRestarts)
1393c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	, m_program				(DE_NULL)
1403c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
1413c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
1423c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1433c827367444ee418f129b2c238299f49d3264554Jarkko PoyryPrimitiveRestartCase::~PrimitiveRestartCase (void)
1443c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
1453c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	PrimitiveRestartCase::deinit();
1463c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
1473c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1483c827367444ee418f129b2c238299f49d3264554Jarkko Poyryvoid PrimitiveRestartCase::deinit (void)
1493c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
1503c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	delete m_program;
1513c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	m_program = DE_NULL;
1523c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
1533c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1543c827367444ee418f129b2c238299f49d3264554Jarkko Poyryvoid PrimitiveRestartCase::addIndex (deUint32 index)
1553c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
1563c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	if (m_indexType == INDEX_UNSIGNED_BYTE)
1573c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
1583c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		DE_ASSERT(de::inRange(index, (deUint32)0, MAX_UNSIGNED_BYTE));
1593c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		m_indicesUB.push_back((deUint8)index);
1603c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
1613c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	else if (m_indexType == INDEX_UNSIGNED_SHORT)
1623c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
1633c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		DE_ASSERT(de::inRange(index, (deUint32)0, MAX_UNSIGNED_SHORT));
1643c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		m_indicesUS.push_back((deUint16)index);
1653c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
1663c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	else if (m_indexType == INDEX_UNSIGNED_INT)
1673c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
1683c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		DE_ASSERT(de::inRange(index, (deUint32)0, MAX_UNSIGNED_INT));
1693c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		m_indicesUI.push_back((deUint32)index);
1703c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
1713c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	else
1723c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		DE_ASSERT(DE_FALSE);
1733c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
1743c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1753c827367444ee418f129b2c238299f49d3264554Jarkko PoyrydeUint32 PrimitiveRestartCase::getIndex (int indexNdx)
1763c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
1773c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	switch (m_indexType)
1783c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
1793c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_BYTE:	return (deUint32)m_indicesUB[indexNdx];
1803c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_SHORT:	return (deUint32)m_indicesUS[indexNdx];
1813c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_INT:	return m_indicesUI[indexNdx];
1823c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		default:
1833c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			DE_ASSERT(DE_FALSE);
1843c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			return 0;
1853c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
1863c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
1873c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
1883c827367444ee418f129b2c238299f49d3264554Jarkko Poyryint PrimitiveRestartCase::getNumIndices (void)
1893c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
1903c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	switch (m_indexType)
1913c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
1923c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_BYTE:	return (int)m_indicesUB.size();
1933c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_SHORT:	return (int)m_indicesUS.size();
1943c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_INT:	return (int)m_indicesUI.size();
1953c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		default:
1963c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			DE_ASSERT(DE_FALSE);
1973c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			return 0;
1983c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
1993c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
2003c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2013c827367444ee418f129b2c238299f49d3264554Jarkko Poyry// Pointer to the index value at index indexNdx.
2023c827367444ee418f129b2c238299f49d3264554Jarkko Poyryvoid* PrimitiveRestartCase::getIndexPtr (int indexNdx)
2033c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
2043c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	switch (m_indexType)
2053c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
2063c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_BYTE:	return (void*)&m_indicesUB[indexNdx];
2073c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_SHORT:	return (void*)&m_indicesUS[indexNdx];
2083c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_INT:	return (void*)&m_indicesUI[indexNdx];
2093c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		default:
2103c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			DE_ASSERT(DE_FALSE);
2113c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			return DE_NULL;
2123c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
2133c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
2143c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2153c827367444ee418f129b2c238299f49d3264554Jarkko Poyryvoid PrimitiveRestartCase::init (void)
2163c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
2173c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// Create shader program.
2183c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2193c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	static const char* vertShaderSource =
2203c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"#version 300 es\n"
2213c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"in highp vec4 a_position;\n"
2223c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"\n"
2233c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"void main()\n"
2243c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"{\n"
2253c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"	gl_Position = a_position;\n"
2263c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"}\n";
2273c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2283c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	static const char* fragShaderSource =
2293c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"#version 300 es\n"
2303c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"layout(location = 0) out mediump vec4 o_color;\n"
2313c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"\n"
2323c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"void main()\n"
2333c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"{\n"
2343c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"	o_color = vec4(1.0f);\n"
2353c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		"}\n";
2363c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2373c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	DE_ASSERT(!m_program);
2383c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	m_program = new glu::ShaderProgram(m_context.getRenderContext(), glu::makeVtxFragSources(vertShaderSource, fragShaderSource));
2393c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2403c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	if(!m_program->isOk())
2413c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
2423c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		m_testCtx.getLog() << *m_program;
2433c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		TCU_FAIL("Failed to compile shader");
2443c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
2453c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2463c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	deUint32 restartIndex = m_indexType == INDEX_UNSIGNED_BYTE	? RESTART_INDEX_UNSIGNED_BYTE
2473c827367444ee418f129b2c238299f49d3264554Jarkko Poyry						  : m_indexType == INDEX_UNSIGNED_SHORT	? RESTART_INDEX_UNSIGNED_SHORT
2483c827367444ee418f129b2c238299f49d3264554Jarkko Poyry						  : m_indexType == INDEX_UNSIGNED_INT	? RESTART_INDEX_UNSIGNED_INT
2493c827367444ee418f129b2c238299f49d3264554Jarkko Poyry						  : 0;
2503c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2513c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	DE_ASSERT(restartIndex != 0);
2523c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2533c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	DE_ASSERT(getNumIndices() == 0);
2543c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2553c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// If testing a case with restart at beginning, add it there.
2563c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	if (m_beginWithRestart)
2573c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
2583c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		addIndex(restartIndex);
2593c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		if (m_duplicateRestarts)
2603c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			addIndex(restartIndex);
2613c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
2623c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2633c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// Generate vertex positions and indices depending on primitive type.
2643c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// \note At this point, restarts shall not be added to the start or the end of the index vector. Those are special cases, and are done above and after the following if-else chain, respectively.
2653c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2663c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	if (m_primType == PRIMITIVE_POINTS)
2673c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
2683c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		// Generate rows with different numbers of points.
2693c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2703c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		deUint32	curIndex			= 0;
2713c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		const int	numRows				= 20;
2723c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2733c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		for (int row = 0; row < numRows; row++)
2743c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		{
2753c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			for (int col = 0; col < row + 1; col++)
2763c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			{
2773c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				float fx = -1.0f + 2.0f * ((float)col + 0.5f) / (float)numRows;
2783c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				float fy = -1.0f + 2.0f * ((float)row + 0.5f) / (float)numRows;
2793c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2803c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				m_positions.push_back(fx);
2813c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				m_positions.push_back(fy);
2823c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2833c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				addIndex(curIndex++);
2843c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			}
2853c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2863c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			if (row < numRows - 1) // Add a restart after all but last row.
2873c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			{
2883c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				addIndex(restartIndex);
2893c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				if (m_duplicateRestarts)
2903c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					addIndex(restartIndex);
2913c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			}
2923c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		}
2933c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
2943c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	else if (m_primType == PRIMITIVE_LINE_STRIP || m_primType == PRIMITIVE_LINE_LOOP || m_primType == PRIMITIVE_LINES)
2953c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
2963c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		// Generate a numRows x numCols arrangement of line polygons of different vertex counts.
2973c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
2983c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		deUint32	curIndex	= 0;
2993c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		const int	numRows		= 4;
3003c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		const int	numCols		= 4;
3013c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3023c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		for (int row = 0; row < numRows; row++)
3033c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		{
3043c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			float centerY = -1.0f + 2.0f * ((float)row + 0.5f) / (float)numRows;
3053c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3063c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			for (int col = 0; col < numCols; col++)
3073c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			{
3083c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				float	centerX		= -1.0f + 2.0f * ((float)col + 0.5f) / (float)numCols;
3093c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				int		numVertices	= row*numCols + col + 1;
3103c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3113c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				for (int i = 0; i < numVertices; i++)
3123c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				{
3133c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					float fx = centerX + 0.9f * deFloatCos((float)i*2.0f*DE_PI / (float)numVertices) / (float)numCols;
3143c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					float fy = centerY + 0.9f * deFloatSin((float)i*2.0f*DE_PI / (float)numVertices) / (float)numRows;
3153c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3163c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					m_positions.push_back(fx);
3173c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					m_positions.push_back(fy);
3183c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3193c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					addIndex(curIndex++);
3203c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				}
3213c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3223c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				if (col < numCols - 1 || row < numRows - 1) // Add a restart after all but last polygon.
3233c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				{
3243c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					addIndex(restartIndex);
3253c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					if (m_duplicateRestarts)
3263c827367444ee418f129b2c238299f49d3264554Jarkko Poyry						addIndex(restartIndex);
3273c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				}
3283c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			}
3293c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		}
3303c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
3313c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	else if (m_primType == PRIMITIVE_TRIANGLE_STRIP)
3323c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
3333c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		// Generate a number of horizontal triangle strips of different lengths.
3343c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3353c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		deUint32	curIndex	= 0;
3363c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		const int	numStrips	= 20;
3373c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3383c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		for (int stripNdx = 0; stripNdx < numStrips; stripNdx++)
3393c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		{
3403c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			int numVertices = stripNdx + 1;
3413c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3423c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			for (int i = 0; i < numVertices; i++)
3433c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			{
3443c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				float fx = -0.9f + 1.8f * (float)(i/2*2) / numStrips;
3453c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				float fy = -0.9f + 1.8f * ((float)stripNdx + (i%2 == 0 ? 0.0f : 0.8f)) / numStrips;
3463c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3473c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				m_positions.push_back(fx);
3483c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				m_positions.push_back(fy);
3493c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3503c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				addIndex(curIndex++);
3513c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			}
3523c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3533c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			if (stripNdx < numStrips - 1) // Add a restart after all but last strip.
3543c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			{
3553c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				addIndex(restartIndex);
3563c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				if (m_duplicateRestarts)
3573c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					addIndex(restartIndex);
3583c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			}
3593c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		}
3603c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
3613c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	else if (m_primType == PRIMITIVE_TRIANGLE_FAN)
3623c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
3633c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		// Generate a numRows x numCols arrangement of triangle fan polygons of different vertex counts.
3643c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3653c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		deUint32	curIndex	= 0;
3663c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		const int	numRows		= 4;
3673c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		const int	numCols		= 4;
3683c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3693c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		for (int row = 0; row < numRows; row++)
3703c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		{
3713c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			float centerY = -1.0f + 2.0f * ((float)row + 0.5f) / (float)numRows;
3723c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3733c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			for (int col = 0; col < numCols; col++)
3743c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			{
3753c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				float	centerX			= -1.0f + 2.0f * ((float)col + 0.5f) / (float)numCols;
3763c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				int		numArcVertices	= row*numCols + col;
3773c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3783c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				m_positions.push_back(centerX);
3793c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				m_positions.push_back(centerY);
3803c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3813c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				addIndex(curIndex++);
3823c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3833c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				for (int i = 0; i < numArcVertices; i++)
3843c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				{
3853c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					float fx = centerX + 0.9f * deFloatCos((float)i*2.0f*DE_PI / (float)numArcVertices) / (float)numCols;
3863c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					float fy = centerY + 0.9f * deFloatSin((float)i*2.0f*DE_PI / (float)numArcVertices) / (float)numRows;
3873c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3883c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					m_positions.push_back(fx);
3893c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					m_positions.push_back(fy);
3903c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3913c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					addIndex(curIndex++);
3923c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				}
3933c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
3943c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				if (col < numCols - 1 || row < numRows - 1) // Add a restart after all but last polygon.
3953c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				{
3963c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					addIndex(restartIndex);
3973c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					if (m_duplicateRestarts)
3983c827367444ee418f129b2c238299f49d3264554Jarkko Poyry						addIndex(restartIndex);
3993c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				}
4003c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			}
4013c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		}
4023c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
4033c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	else if (m_primType == PRIMITIVE_TRIANGLES)
4043c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
4053c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		// Generate a number of rows with (potentially incomplete) triangles.
4063c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4073c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		deUint32	curIndex	= 0;
4083c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		const int	numRows		= 3*7;
4093c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4103c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		for (int rowNdx = 0; rowNdx < numRows; rowNdx++)
4113c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		{
4123c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			int numVertices = rowNdx + 1;
4133c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4143c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			for (int i = 0; i < numVertices; i++)
4153c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			{
4163c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				float fx = -0.9f + 1.8f * ((i/3) + (i%3 == 2 ? 0.8f : 0.0f)) * 3 / numRows;
4173c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				float fy = -0.9f + 1.8f * ((float)rowNdx + (i%3 == 0 ? 0.0f : 0.8f)) / numRows;
4183c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4193c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				m_positions.push_back(fx);
4203c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				m_positions.push_back(fy);
4213c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4223c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				addIndex(curIndex++);
4233c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			}
4243c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4253c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			if (rowNdx < numRows - 1) // Add a restart after all but last row.
4263c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			{
4273c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				addIndex(restartIndex);
4283c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				if (m_duplicateRestarts)
4293c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					addIndex(restartIndex);
4303c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			}
4313c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		}
4323c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
4333c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	else
4343c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		DE_ASSERT(DE_FALSE);
4353c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4363c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// If testing a case with restart at end, add it there.
4373c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	if (m_endWithRestart)
4383c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
4393c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		addIndex(restartIndex);
4403c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		if (m_duplicateRestarts)
4413c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			addIndex(restartIndex);
4423c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
4433c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4443c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// Special case assertions.
4453c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4463c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	int numIndices = getNumIndices();
4473c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4483c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	DE_ASSERT(numIndices > 0);
4493c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	DE_ASSERT(m_beginWithRestart || getIndex(0) != restartIndex);						// We don't want restarts at beginning unless the case is a special case.
4503c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	DE_ASSERT(m_endWithRestart || getIndex(numIndices-1) != restartIndex);			// We don't want restarts at end unless the case is a special case.
4513c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4523c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	if (!m_duplicateRestarts)
4533c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		for (int i = 1; i < numIndices; i++)
4543c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			DE_ASSERT(getIndex(i) != restartIndex || getIndex(i-1) != restartIndex);	// We don't want duplicate restarts unless the case is a special case.
4553c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
4563c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4573c827367444ee418f129b2c238299f49d3264554Jarkko PoyryPrimitiveRestartCase::IterateResult PrimitiveRestartCase::iterate (void)
4583c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
4593c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	int							width			= deMin32(m_context.getRenderTarget().getWidth(), MAX_RENDER_WIDTH);
4603c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	int							height			= deMin32(m_context.getRenderTarget().getHeight(), MAX_RENDER_HEIGHT);
4613c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4623c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	int							xOffsetMax		= m_context.getRenderTarget().getWidth() - width;
4633c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	int							yOffsetMax		= m_context.getRenderTarget().getHeight() - height;
4643c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4653c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	de::Random					rnd				(deStringHash(getName()));
4663c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4673c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	int							xOffset			= rnd.getInt(0, xOffsetMax);
4683c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	int							yOffset			= rnd.getInt(0, yOffsetMax);
4693c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	tcu::Surface				referenceImg	(width, height);
4703c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	tcu::Surface				resultImg		(width, height);
4713c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4723c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glViewport(xOffset, yOffset, width, height);
4733c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
4743c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4753c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	deUint32 program = m_program->getProgram();
4763c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glUseProgram(program);
4773c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4783c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// Setup position attribute.
4793c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4803c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	int loc = glGetAttribLocation(program, "a_position");
4813c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glEnableVertexAttribArray(loc);
4823c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glVertexAttribPointer(loc, 2, GL_FLOAT, GL_FALSE, 0, &m_positions[0]);
4833c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4843c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// Render result.
4853c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4863c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	renderWithRestart();
4873c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glu::readPixels(m_context.getRenderContext(), xOffset, yOffset, resultImg.getAccess());
4883c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4893c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// Render reference (same scene as the real deal, but emulate primitive restart without actually using it).
4903c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4913c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	renderWithoutRestart();
4923c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glu::readPixels(m_context.getRenderContext(), xOffset, yOffset, referenceImg.getAccess());
4933c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4943c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// Compare.
4953c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4963c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	bool testOk = tcu::pixelThresholdCompare(m_testCtx.getLog(), "ComparisonResult", "Image comparison result", referenceImg, resultImg, tcu::RGBA(0, 0, 0, 0), tcu::COMPARE_LOG_RESULT);
4973c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
4983c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	m_testCtx.setTestResult(testOk ? QP_TEST_RESULT_PASS	: QP_TEST_RESULT_FAIL,
4993c827367444ee418f129b2c238299f49d3264554Jarkko Poyry							testOk ? "Pass"					: "Fail");
5003c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5013c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glUseProgram(0);
5023c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5033c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	return STOP;
5043c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
5053c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5063c827367444ee418f129b2c238299f49d3264554Jarkko Poyry// Draw with the appropriate GLES3 draw function.
5073c827367444ee418f129b2c238299f49d3264554Jarkko Poyryvoid PrimitiveRestartCase::draw (int startNdx, int count)
5083c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
5093c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	GLenum primTypeGL;
5103c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5113c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	switch (m_primType)
5123c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
5133c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case PRIMITIVE_POINTS:			primTypeGL = GL_POINTS;			break;
5143c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case PRIMITIVE_LINE_STRIP:		primTypeGL = GL_LINE_STRIP;		break;
5153c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case PRIMITIVE_LINE_LOOP:		primTypeGL = GL_LINE_LOOP;		break;
5163c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case PRIMITIVE_LINES:			primTypeGL = GL_LINES;			break;
5173c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case PRIMITIVE_TRIANGLE_STRIP:	primTypeGL = GL_TRIANGLE_STRIP;	break;
5183c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case PRIMITIVE_TRIANGLE_FAN:	primTypeGL = GL_TRIANGLE_FAN;	break;
5193c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case PRIMITIVE_TRIANGLES:		primTypeGL = GL_TRIANGLES;		break;
5203c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		default:
5213c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			DE_ASSERT(DE_FALSE);
5223c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			primTypeGL = 0;
5233c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
5243c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5253c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	GLenum indexTypeGL;
5263c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5273c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	switch (m_indexType)
5283c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
5293c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_BYTE:	indexTypeGL = GL_UNSIGNED_BYTE;		break;
5303c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_SHORT:	indexTypeGL = GL_UNSIGNED_SHORT;	break;
5313c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		case INDEX_UNSIGNED_INT:	indexTypeGL = GL_UNSIGNED_INT;		break;
5323c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		default:
5333c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			DE_ASSERT(DE_FALSE);
5343c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			indexTypeGL = 0;
5353c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
5363c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5373c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	deUint32 restartIndex = m_indexType == INDEX_UNSIGNED_BYTE	? RESTART_INDEX_UNSIGNED_BYTE
5383c827367444ee418f129b2c238299f49d3264554Jarkko Poyry						  : m_indexType == INDEX_UNSIGNED_SHORT	? RESTART_INDEX_UNSIGNED_SHORT
5393c827367444ee418f129b2c238299f49d3264554Jarkko Poyry						  : m_indexType == INDEX_UNSIGNED_INT	? RESTART_INDEX_UNSIGNED_INT
5403c827367444ee418f129b2c238299f49d3264554Jarkko Poyry						  : 0;
5413c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5423c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	DE_ASSERT(restartIndex != 0);
5433c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5443c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	if (m_function == FUNCTION_DRAW_ELEMENTS)
5453c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		glDrawElements(primTypeGL, (GLsizei)count, indexTypeGL, (GLvoid*)getIndexPtr(startNdx));
5463c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	else if (m_function == FUNCTION_DRAW_ELEMENTS_INSTANCED)
5473c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		glDrawElementsInstanced(primTypeGL, (GLsizei)count, indexTypeGL, (GLvoid*)getIndexPtr(startNdx), 1);
5483c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	else
5493c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
5503c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		DE_ASSERT(m_function == FUNCTION_DRAW_RANGE_ELEMENTS);
5513c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5523c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		// Find the largest non-restart index in the index array (for glDrawRangeElements() end parameter).
5533c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5543c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		deUint32 max = 0;
5553c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5563c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		int numIndices = getNumIndices();
5573c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		for (int i = 0; i < numIndices; i++)
5583c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		{
5593c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			deUint32 index = getIndex(i);
5603c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			if (index != restartIndex && index > max)
5613c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				max = index;
5623c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		}
5633c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5643c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		glDrawRangeElements(primTypeGL, 0, (GLuint)max, (GLsizei)count, indexTypeGL, (GLvoid*)getIndexPtr(startNdx));
5653c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
5663c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
5673c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5683c827367444ee418f129b2c238299f49d3264554Jarkko Poyryvoid PrimitiveRestartCase::renderWithRestart (void)
5693c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
5703c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	GLU_CHECK_MSG("PrimitiveRestartCase::renderWithRestart() begin");
5713c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5723c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glEnable(GL_PRIMITIVE_RESTART_FIXED_INDEX);
5733c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	GLU_CHECK_MSG("Enable primitive restart");
5743c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT|GL_STENCIL_BUFFER_BIT);
5753c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	GLU_CHECK_MSG("Clear in PrimitiveRestartCase::renderWithRestart()");
5763c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5773c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	draw(0, getNumIndices());
5783c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5793c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	GLU_CHECK_MSG("Draw in PrimitiveRestartCase::renderWithRestart()");
5803c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5813c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	GLU_CHECK_MSG("PrimitiveRestartCase::renderWithRestart() end");
5823c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
5833c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5843c827367444ee418f129b2c238299f49d3264554Jarkko Poyryvoid PrimitiveRestartCase::renderWithoutRestart (void)
5853c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
5863c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	GLU_CHECK_MSG("PrimitiveRestartCase::renderWithoutRestart() begin");
5873c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5883c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	deUint32 restartIndex = m_indexType == INDEX_UNSIGNED_BYTE	? RESTART_INDEX_UNSIGNED_BYTE
5893c827367444ee418f129b2c238299f49d3264554Jarkko Poyry						  : m_indexType == INDEX_UNSIGNED_SHORT	? RESTART_INDEX_UNSIGNED_SHORT
5903c827367444ee418f129b2c238299f49d3264554Jarkko Poyry						  : m_indexType == INDEX_UNSIGNED_INT	? RESTART_INDEX_UNSIGNED_INT
5913c827367444ee418f129b2c238299f49d3264554Jarkko Poyry						  : 0;
5923c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5933c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	DE_ASSERT(restartIndex != 0);
5943c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
5953c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glDisable(GL_PRIMITIVE_RESTART_FIXED_INDEX);
5963c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	GLU_CHECK_MSG("Disable primitive restart");
5973c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT|GL_STENCIL_BUFFER_BIT);
5983c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	GLU_CHECK_MSG("Clear in PrimitiveRestartCase::renderWithoutRestart()");
5993c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6003c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	// Draw, emulating primitive restart.
6013c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6023c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	int numIndices = getNumIndices();
6033c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6043c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	DE_ASSERT(numIndices >= 0);
6053c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6063c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	int indexArrayStartNdx = 0; // Keep track of the draw start index - first index after a primitive restart, or initially the first index altogether.
6073c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6083c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	for (int indexArrayNdx = 0; indexArrayNdx <= numIndices; indexArrayNdx++) // \note Goes one "too far" in order to detect end of array as well.
6093c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
6103c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		if (indexArrayNdx >= numIndices || getIndex(indexArrayNdx) == restartIndex) // \note Handle end of array the same way as a restart index encounter.
6113c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		{
6123c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			if (indexArrayStartNdx < numIndices)
6133c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			{
6143c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				// Draw from index indexArrayStartNdx to index indexArrayNdx-1 .
6153c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6163c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				draw(indexArrayStartNdx, indexArrayNdx - indexArrayStartNdx);
6173c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				GLU_CHECK_MSG("Draw in PrimitiveRestartCase::renderWithoutRestart()");
6183c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			}
6193c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6203c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			indexArrayStartNdx = indexArrayNdx + 1; // Next draw starts just after this restart index.
6213c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		}
6223c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
6233c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6243c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	GLU_CHECK_MSG("PrimitiveRestartCase::renderWithoutRestart() end");
6253c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
6263c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6273c827367444ee418f129b2c238299f49d3264554Jarkko PoyryPrimitiveRestartTests::PrimitiveRestartTests (Context& context)
6283c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	: TestCaseGroup(context, "primitive_restart", "Primitive restart tests")
6293c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
6303c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
6313c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6323c827367444ee418f129b2c238299f49d3264554Jarkko PoyryPrimitiveRestartTests::~PrimitiveRestartTests (void)
6333c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
6343c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
6353c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6363c827367444ee418f129b2c238299f49d3264554Jarkko Poyryvoid PrimitiveRestartTests::init (void)
6373c827367444ee418f129b2c238299f49d3264554Jarkko Poyry{
6383c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	for (int isRestartBeginCaseI = 0; isRestartBeginCaseI <= 1; isRestartBeginCaseI++)
6393c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	for (int isRestartEndCaseI = 0; isRestartEndCaseI <= 1; isRestartEndCaseI++)
6403c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	for (int isDuplicateRestartCaseI = 0; isDuplicateRestartCaseI <= 1; isDuplicateRestartCaseI++)
6413c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	{
6423c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		bool			isRestartBeginCase		= isRestartBeginCaseI != 0;
6433c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		bool			isRestartEndCase		= isRestartEndCaseI != 0;
6443c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		bool			isDuplicateRestartCase	= isDuplicateRestartCaseI != 0;
6453c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6463c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		std::string		specialCaseGroupName;
6473c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6483c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		if (isRestartBeginCase)		specialCaseGroupName = "begin_restart";
6493c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		if (isRestartEndCase)		specialCaseGroupName += std::string(specialCaseGroupName.empty() ? "" : "_") + "end_restart";
6503c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		if (isDuplicateRestartCase)	specialCaseGroupName += std::string(specialCaseGroupName.empty() ? "" : "_") + "duplicate_restarts";
6513c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6523c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		if (specialCaseGroupName.empty())
6533c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			specialCaseGroupName = "basic";
6543c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6553c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		TestCaseGroup* specialCaseGroup = new TestCaseGroup(m_context, specialCaseGroupName.c_str(), "");
6563c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		addChild(specialCaseGroup);
6573c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6583c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		for (int primType = 0; primType < (int)PrimitiveRestartCase::PRIMITIVE_LAST; primType++)
6593c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		{
6603c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			const char* primTypeName = primType == (int)PrimitiveRestartCase::PRIMITIVE_POINTS			? "points"
6613c827367444ee418f129b2c238299f49d3264554Jarkko Poyry									 : primType == (int)PrimitiveRestartCase::PRIMITIVE_LINE_STRIP		? "line_strip"
6623c827367444ee418f129b2c238299f49d3264554Jarkko Poyry									 : primType == (int)PrimitiveRestartCase::PRIMITIVE_LINE_LOOP		? "line_loop"
6633c827367444ee418f129b2c238299f49d3264554Jarkko Poyry									 : primType == (int)PrimitiveRestartCase::PRIMITIVE_LINES			? "lines"
6643c827367444ee418f129b2c238299f49d3264554Jarkko Poyry									 : primType == (int)PrimitiveRestartCase::PRIMITIVE_TRIANGLE_STRIP	? "triangle_strip"
6653c827367444ee418f129b2c238299f49d3264554Jarkko Poyry									 : primType == (int)PrimitiveRestartCase::PRIMITIVE_TRIANGLE_FAN	? "triangle_fan"
6663c827367444ee418f129b2c238299f49d3264554Jarkko Poyry									 : primType == (int)PrimitiveRestartCase::PRIMITIVE_TRIANGLES		? "triangles"
6673c827367444ee418f129b2c238299f49d3264554Jarkko Poyry									 : DE_NULL;
6683c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6693c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			DE_ASSERT(primTypeName != DE_NULL);
6703c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6713c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			TestCaseGroup* primTypeGroup = new TestCaseGroup(m_context, primTypeName, "");
6723c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			specialCaseGroup->addChild(primTypeGroup);
6733c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6743c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			for (int indexType = 0; indexType < (int)PrimitiveRestartCase::INDEX_LAST; indexType++)
6753c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			{
6763c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				const char *indexTypeName = indexType == (int)PrimitiveRestartCase::INDEX_UNSIGNED_BYTE		? "unsigned_byte"
6773c827367444ee418f129b2c238299f49d3264554Jarkko Poyry										  : indexType == (int)PrimitiveRestartCase::INDEX_UNSIGNED_SHORT	? "unsigned_short"
6783c827367444ee418f129b2c238299f49d3264554Jarkko Poyry										  : indexType == (int)PrimitiveRestartCase::INDEX_UNSIGNED_INT		? "unsigned_int"
6793c827367444ee418f129b2c238299f49d3264554Jarkko Poyry										  : DE_NULL;
6803c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6813c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				DE_ASSERT(indexTypeName != DE_NULL);
6823c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6833c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				TestCaseGroup* indexTypeGroup = new TestCaseGroup(m_context, indexTypeName, "");
6843c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				primTypeGroup->addChild(indexTypeGroup);
6853c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6863c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				for (int function = 0; function < (int)PrimitiveRestartCase::FUNCTION_LAST; function++)
6873c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				{
6883c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					const char* functionName = function == (int)PrimitiveRestartCase::FUNCTION_DRAW_ELEMENTS			? "draw_elements"
6893c827367444ee418f129b2c238299f49d3264554Jarkko Poyry											 : function == (int)PrimitiveRestartCase::FUNCTION_DRAW_ELEMENTS_INSTANCED	? "draw_elements_instanced"
6903c827367444ee418f129b2c238299f49d3264554Jarkko Poyry											 : function == (int)PrimitiveRestartCase::FUNCTION_DRAW_RANGE_ELEMENTS		? "draw_range_elements"
6913c827367444ee418f129b2c238299f49d3264554Jarkko Poyry											 : DE_NULL;
6923c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6933c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					DE_ASSERT(functionName != DE_NULL);
6943c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
6953c827367444ee418f129b2c238299f49d3264554Jarkko Poyry					indexTypeGroup->addChild(new PrimitiveRestartCase(m_context,
6963c827367444ee418f129b2c238299f49d3264554Jarkko Poyry																	  functionName,
6973c827367444ee418f129b2c238299f49d3264554Jarkko Poyry																	  "",
6983c827367444ee418f129b2c238299f49d3264554Jarkko Poyry																	  (PrimitiveRestartCase::PrimitiveType)primType,
6993c827367444ee418f129b2c238299f49d3264554Jarkko Poyry																	  (PrimitiveRestartCase::IndexType)indexType,
7003c827367444ee418f129b2c238299f49d3264554Jarkko Poyry																	  (PrimitiveRestartCase::Function)function,
7013c827367444ee418f129b2c238299f49d3264554Jarkko Poyry																	  isRestartBeginCase,
7023c827367444ee418f129b2c238299f49d3264554Jarkko Poyry																	  isRestartEndCase,
7033c827367444ee418f129b2c238299f49d3264554Jarkko Poyry																	  isDuplicateRestartCase));
7043c827367444ee418f129b2c238299f49d3264554Jarkko Poyry				}
7053c827367444ee418f129b2c238299f49d3264554Jarkko Poyry			}
7063c827367444ee418f129b2c238299f49d3264554Jarkko Poyry		}
7073c827367444ee418f129b2c238299f49d3264554Jarkko Poyry	}
7083c827367444ee418f129b2c238299f49d3264554Jarkko Poyry}
7093c827367444ee418f129b2c238299f49d3264554Jarkko Poyry
7103c827367444ee418f129b2c238299f49d3264554Jarkko Poyry} // Functional
7113c827367444ee418f129b2c238299f49d3264554Jarkko Poyry} // gles3
7123c827367444ee418f129b2c238299f49d3264554Jarkko Poyry} // deqp
713