1 /*-------------------------------------------------------------------------
2  * drawElements Quality Program OpenGL ES 3.1 Module
3  * -------------------------------------------------
4  *
5  * Copyright 2014 The Android Open Source Project
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  *//*!
20  * \file
21  * \brief Negative Fragment Pipe API tests.
22  *//*--------------------------------------------------------------------*/
23 
24 #include "es31fNegativeFragmentApiTests.hpp"
25 
26 #include "gluCallLogWrapper.hpp"
27 
28 #include "glwDefs.hpp"
29 #include "glwEnums.hpp"
30 
31 namespace deqp
32 {
33 namespace gles31
34 {
35 namespace Functional
36 {
37 namespace NegativeTestShared
38 {
39 
40 using tcu::TestLog;
41 using glu::CallLogWrapper;
42 using namespace glw;
43 
44 using tcu::TestLog;
45 
scissor(NegativeTestContext & ctx)46 void scissor (NegativeTestContext& ctx)
47 {
48 	ctx.beginSection("GL_INVALID_VALUE is generated if either width or height is negative.");
49 	ctx.glScissor(0, 0, -1, 0);
50 	ctx.expectError(GL_INVALID_VALUE);
51 	ctx.glScissor(0, 0, 0, -1);
52 	ctx.expectError(GL_INVALID_VALUE);
53 	ctx.glScissor(0, 0, -1, -1);
54 	ctx.expectError(GL_INVALID_VALUE);
55 	ctx.endSection();
56 }
57 
depth_func(NegativeTestContext & ctx)58 void depth_func (NegativeTestContext& ctx)
59 {
60 	ctx.beginSection("GL_INVALID_ENUM is generated if func is not an accepted value.");
61 	ctx.glDepthFunc(-1);
62 	ctx.expectError(GL_INVALID_ENUM);
63 	ctx.endSection();
64 }
65 
viewport(NegativeTestContext & ctx)66 void viewport (NegativeTestContext& ctx)
67 {
68 	ctx.beginSection("GL_INVALID_VALUE is generated if either width or height is negative.");
69 	ctx.glViewport(0, 0, -1, 1);
70 	ctx.expectError(GL_INVALID_VALUE);
71 	ctx.glViewport(0, 0, 1, -1);
72 	ctx.expectError(GL_INVALID_VALUE);
73 	ctx.glViewport(0, 0, -1, -1);
74 	ctx.expectError(GL_INVALID_VALUE);
75 	ctx.endSection();
76 }
77 
78 // Stencil functions
stencil_func(NegativeTestContext & ctx)79 void stencil_func (NegativeTestContext& ctx)
80 {
81 	ctx.beginSection("GL_INVALID_ENUM is generated if func is not one of the eight accepted values.");
82 	ctx.glStencilFunc(-1, 0, 1);
83 	ctx.expectError(GL_INVALID_ENUM);
84 	ctx.endSection();
85 }
86 
stencil_func_separate(NegativeTestContext & ctx)87 void stencil_func_separate (NegativeTestContext& ctx)
88 {
89 	ctx.beginSection("GL_INVALID_ENUM is generated if face is not GL_FRONT, GL_BACK, or GL_FRONT_AND_BACK.");
90 	ctx.glStencilFuncSeparate(-1, GL_NEVER, 0, 1);
91 	ctx.expectError(GL_INVALID_ENUM);
92 	ctx.endSection();
93 
94 	ctx.beginSection("GL_INVALID_ENUM is generated if func is not one of the eight accepted values.");
95 	ctx.glStencilFuncSeparate(GL_FRONT, -1, 0, 1);
96 	ctx.expectError(GL_INVALID_ENUM);
97 	ctx.endSection();
98 }
99 
stencil_op(NegativeTestContext & ctx)100 void stencil_op (NegativeTestContext& ctx)
101 {
102 	ctx.beginSection("GL_INVALID_ENUM is generated if sfail, dpfail, or dppass is any value other than the defined symbolic constant values.");
103 	ctx.glStencilOp(-1, GL_ZERO, GL_REPLACE);
104 	ctx.expectError(GL_INVALID_ENUM);
105 	ctx.glStencilOp(GL_KEEP, -1, GL_REPLACE);
106 	ctx.expectError(GL_INVALID_ENUM);
107 	ctx.glStencilOp(GL_KEEP, GL_ZERO, -1);
108 	ctx.expectError(GL_INVALID_ENUM);
109 	ctx.endSection();
110 }
111 
stencil_op_separate(NegativeTestContext & ctx)112 void stencil_op_separate (NegativeTestContext& ctx)
113 {
114 	ctx.beginSection("GL_INVALID_ENUM is generated if face is any value other than GL_FRONT, GL_BACK, or GL_FRONT_AND_BACK.");
115 	ctx.glStencilOpSeparate(-1, GL_KEEP, GL_ZERO, GL_REPLACE);
116 	ctx.expectError(GL_INVALID_ENUM);
117 	ctx.endSection();
118 
119 	ctx.beginSection("GL_INVALID_ENUM is generated if sfail, dpfail, or dppass is any value other than the eight defined symbolic constant values.");
120 	ctx.glStencilOpSeparate(GL_FRONT, -1, GL_ZERO, GL_REPLACE);
121 	ctx.expectError(GL_INVALID_ENUM);
122 	ctx.glStencilOpSeparate(GL_FRONT, GL_KEEP, -1, GL_REPLACE);
123 	ctx.expectError(GL_INVALID_ENUM);
124 	ctx.glStencilOpSeparate(GL_FRONT, GL_KEEP, GL_ZERO, -1);
125 	ctx.expectError(GL_INVALID_ENUM);
126 	ctx.endSection();
127 }
128 
stencil_mask_separate(NegativeTestContext & ctx)129 void stencil_mask_separate (NegativeTestContext& ctx)
130 {
131 	ctx.beginSection("GL_INVALID_ENUM is generated if face is not GL_FRONT, GL_BACK, or GL_FRONT_AND_BACK.");
132 	ctx.glStencilMaskSeparate(-1, 0);
133 	ctx.expectError(GL_INVALID_ENUM);
134 	ctx.endSection();
135 }
136 
137 // Blend functions
blend_equation(NegativeTestContext & ctx)138 void blend_equation (NegativeTestContext& ctx)
139 {
140 	ctx.beginSection("GL_INVALID_ENUM is generated if mode is not GL_FUNC_ADD, GL_FUNC_SUBTRACT, GL_FUNC_REVERSE_SUBTRACT, GL_MAX or GL_MIN.");
141 	ctx.glBlendEquation(-1);
142 	ctx.expectError(GL_INVALID_ENUM);
143 	ctx.endSection();
144 }
145 
blend_equation_separate(NegativeTestContext & ctx)146 void blend_equation_separate (NegativeTestContext& ctx)
147 {
148 	ctx.beginSection("GL_INVALID_ENUM is generated if modeRGB is not GL_FUNC_ADD, GL_FUNC_SUBTRACT, GL_FUNC_REVERSE_SUBTRACT, GL_MAX or GL_MIN.");
149 	ctx.glBlendEquationSeparate(-1, GL_FUNC_ADD);
150 	ctx.expectError(GL_INVALID_ENUM);
151 	ctx.endSection();
152 	ctx.beginSection("GL_INVALID_ENUM is generated if modeAlpha is not GL_FUNC_ADD, GL_FUNC_SUBTRACT, GL_FUNC_REVERSE_SUBTRACT, GL_MAX or GL_MIN.");
153 	ctx.glBlendEquationSeparate(GL_FUNC_ADD, -1);
154 	ctx.expectError(GL_INVALID_ENUM);
155 	ctx.endSection();
156 }
157 
blend_func(NegativeTestContext & ctx)158 void blend_func (NegativeTestContext& ctx)
159 {
160 	ctx.beginSection("GL_INVALID_ENUM is generated if either sfactor or dfactor is not an accepted value.");
161 	ctx.glBlendFunc(-1, GL_ONE);
162 	ctx.expectError(GL_INVALID_ENUM);
163 	ctx.glBlendFunc(GL_ONE, -1);
164 	ctx.expectError(GL_INVALID_ENUM);
165 	ctx.endSection();
166 }
167 
blend_func_separate(NegativeTestContext & ctx)168 void blend_func_separate (NegativeTestContext& ctx)
169 {
170 	ctx.beginSection("GL_INVALID_ENUM is generated if srcRGB, dstRGB, srcAlpha, or dstAlpha is not an accepted value.");
171 	ctx.glBlendFuncSeparate(-1, GL_ONE, GL_SRC_COLOR, GL_ONE_MINUS_SRC_COLOR);
172 	ctx.expectError(GL_INVALID_ENUM);
173 	ctx.glBlendFuncSeparate(GL_ZERO, -1, GL_SRC_COLOR, GL_ONE_MINUS_SRC_COLOR);
174 	ctx.expectError(GL_INVALID_ENUM);
175 	ctx.glBlendFuncSeparate(GL_ZERO, GL_ONE, -1, GL_ONE_MINUS_SRC_COLOR);
176 	ctx.expectError(GL_INVALID_ENUM);
177 	ctx.glBlendFuncSeparate(GL_ZERO, GL_ONE, GL_SRC_COLOR, -1);
178 	ctx.expectError(GL_INVALID_ENUM);
179 	ctx.endSection();
180 }
181 
182 // Rasterization API functions
cull_face(NegativeTestContext & ctx)183 void cull_face (NegativeTestContext& ctx)
184 {
185 	ctx.beginSection("GL_INVALID_ENUM is generated if mode is not an accepted value.");
186 	ctx.glCullFace(-1);
187 	ctx.expectError(GL_INVALID_ENUM);
188 	ctx.endSection();
189 }
190 
front_face(NegativeTestContext & ctx)191 void front_face (NegativeTestContext& ctx)
192 {
193 	ctx.beginSection("GL_INVALID_ENUM is generated if mode is not an accepted value.");
194 	ctx.glFrontFace(-1);
195 	ctx.expectError(GL_INVALID_ENUM);
196 	ctx.endSection();
197 }
198 
line_width(NegativeTestContext & ctx)199 void line_width (NegativeTestContext& ctx)
200 {
201 	ctx.beginSection("GL_INVALID_VALUE is generated if width is less than or equal to 0.");
202 	ctx.glLineWidth(0);
203 	ctx.expectError(GL_INVALID_VALUE);
204 	ctx.glLineWidth(-1);
205 	ctx.expectError(GL_INVALID_VALUE);
206 	ctx.endSection();
207 }
208 
209 // Asynchronous queries
gen_queries(NegativeTestContext & ctx)210 void gen_queries (NegativeTestContext& ctx)
211 {
212 	ctx.beginSection("GL_INVALID_VALUE is generated if n is negative.");
213 	GLuint ids = 0;
214 	ctx.glGenQueries	(-1, &ids);
215 	ctx.expectError		(GL_INVALID_VALUE);
216 	ctx.endSection();
217 }
218 
begin_query(NegativeTestContext & ctx)219 void begin_query (NegativeTestContext& ctx)
220 {
221 	GLuint ids[3];
222 	ctx.glGenQueries	(3, ids);
223 
224 	ctx.beginSection("GL_INVALID_ENUM is generated if target is not one of the accepted tokens.");
225 	ctx.glBeginQuery	(-1, ids[0]);
226 	ctx.expectError		(GL_INVALID_ENUM);
227 	ctx.endSection();
228 
229 	ctx.beginSection("GL_INVALID_OPERATION is generated if ctx.glBeginQuery is executed while a query object of the same target is already active.");
230 	ctx.glBeginQuery	(GL_ANY_SAMPLES_PASSED, ids[0]);
231 	ctx.expectError		(GL_NO_ERROR);
232 	ctx.glBeginQuery	(GL_ANY_SAMPLES_PASSED, ids[1]);
233 	ctx.expectError		(GL_INVALID_OPERATION);
234 	// \note GL_ANY_SAMPLES_PASSED and GL_ANY_SAMPLES_PASSED_CONSERVATIVE alias to the same target for the purposes of this error.
235 	ctx.glBeginQuery	(GL_ANY_SAMPLES_PASSED_CONSERVATIVE, ids[1]);
236 	ctx.expectError		(GL_INVALID_OPERATION);
237 	ctx.glBeginQuery	(GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN, ids[1]);
238 	ctx.expectError		(GL_NO_ERROR);
239 	ctx.glBeginQuery	(GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN, ids[2]);
240 	ctx.expectError		(GL_INVALID_OPERATION);
241 	ctx.glEndQuery		(GL_ANY_SAMPLES_PASSED);
242 	ctx.glEndQuery		(GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN);
243 	ctx.expectError		(GL_NO_ERROR);
244 	ctx.endSection();
245 
246 	ctx.beginSection("GL_INVALID_OPERATION is generated if id is 0.");
247 	ctx.glBeginQuery	(GL_ANY_SAMPLES_PASSED, 0);
248 	ctx.expectError		(GL_INVALID_OPERATION);
249 	ctx.endSection();
250 
251 	ctx.beginSection("GL_INVALID_OPERATION is generated if id not a name returned from a previous call to ctx.glGenQueries, or if such a name has since been deleted with ctx.glDeleteQueries.");
252 	ctx.glBeginQuery	(GL_ANY_SAMPLES_PASSED, -1);
253 	ctx.expectError		(GL_INVALID_OPERATION);
254 	ctx.glDeleteQueries	(1, &ids[2]);
255 	ctx.expectError		(GL_NO_ERROR);
256 	ctx.glBeginQuery	(GL_ANY_SAMPLES_PASSED, ids[2]);
257 	ctx.expectError		(GL_INVALID_OPERATION);
258 	ctx.endSection();
259 
260 	ctx.beginSection("GL_INVALID_OPERATION is generated if id is the name of an already active query object.");
261 	ctx.glBeginQuery	(GL_ANY_SAMPLES_PASSED, ids[0]);
262 	ctx.expectError		(GL_NO_ERROR);
263 	ctx.glBeginQuery	(GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN, ids[0]);
264 	ctx.expectError		(GL_INVALID_OPERATION);
265 	ctx.endSection();
266 
267 	ctx.beginSection("GL_INVALID_OPERATION is generated if id refers to an existing query object whose type does not does not match target.");
268 	ctx.glEndQuery		(GL_ANY_SAMPLES_PASSED);
269 	ctx.expectError		(GL_NO_ERROR);
270 	ctx.glBeginQuery	(GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN, ids[0]);
271 	ctx.expectError		(GL_INVALID_OPERATION);
272 	ctx.endSection();
273 
274 	ctx.glDeleteQueries	(2, &ids[0]);
275 	ctx.expectError		(GL_NO_ERROR);
276 }
277 
end_query(NegativeTestContext & ctx)278 void end_query (NegativeTestContext& ctx)
279 {
280 	GLuint id = 0;
281 	ctx.glGenQueries	(1, &id);
282 
283 	ctx.beginSection("GL_INVALID_ENUM is generated if target is not one of the accepted tokens.");
284 	ctx.glEndQuery		(-1);
285 	ctx.expectError		(GL_INVALID_ENUM);
286 	ctx.endSection();
287 
288 	ctx.beginSection("GL_INVALID_OPERATION is generated if ctx.glEndQuery is executed when a query object of the same target is not active.");
289 	ctx.glEndQuery		(GL_ANY_SAMPLES_PASSED);
290 	ctx.expectError		(GL_INVALID_OPERATION);
291 	ctx.glBeginQuery	(GL_ANY_SAMPLES_PASSED, id);
292 	ctx.expectError		(GL_NO_ERROR);
293 	ctx.glEndQuery		(GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN);
294 	ctx.expectError		(GL_INVALID_OPERATION);
295 	ctx.glEndQuery		(GL_ANY_SAMPLES_PASSED);
296 	ctx.expectError		(GL_NO_ERROR);
297 	ctx.endSection();
298 
299 	ctx.glDeleteQueries	(1, &id);
300 	ctx.expectError		(GL_NO_ERROR);
301 }
302 
delete_queries(NegativeTestContext & ctx)303 void delete_queries (NegativeTestContext& ctx)
304 {
305 	GLuint id = 0;
306 	ctx.glGenQueries	(1, &id);
307 
308 	ctx.beginSection("GL_INVALID_VALUE is generated if n is negative.");
309 	ctx.glDeleteQueries	(-1, &id);
310 	ctx.expectError		(GL_INVALID_VALUE);
311 	ctx.endSection();
312 
313 	ctx.glDeleteQueries	(1, &id);
314 }
315 
316 // Sync objects
fence_sync(NegativeTestContext & ctx)317 void fence_sync (NegativeTestContext& ctx)
318 {
319 	ctx.beginSection("GL_INVALID_ENUM is generated if condition is not GL_SYNC_GPU_COMMANDS_COMPLETE.");
320 	ctx.glFenceSync(-1, 0);
321 	ctx.expectError(GL_INVALID_ENUM);
322 	ctx.endSection();
323 
324 	ctx.beginSection("GL_INVALID_VALUE is generated if flags is not zero.");
325 	ctx.glFenceSync(GL_SYNC_GPU_COMMANDS_COMPLETE, 0x0010);
326 	ctx.expectError(GL_INVALID_VALUE);
327 	ctx.endSection();
328 }
329 
wait_sync(NegativeTestContext & ctx)330 void wait_sync (NegativeTestContext& ctx)
331 {
332 	GLsync sync = ctx.glFenceSync(GL_SYNC_GPU_COMMANDS_COMPLETE, 0);
333 
334 	ctx.beginSection("GL_INVALID_VALUE is generated if sync is not the name of a sync object.");
335 	ctx.glWaitSync(0, 0, GL_TIMEOUT_IGNORED);
336 	ctx.expectError(GL_INVALID_VALUE);
337 	ctx.endSection();
338 
339 	ctx.beginSection("GL_INVALID_VALUE is generated if flags is not zero.");
340 	ctx.glWaitSync(sync, 0x0010, GL_TIMEOUT_IGNORED);
341 	ctx.expectError(GL_INVALID_VALUE);
342 	ctx.endSection();
343 
344 	ctx.beginSection("GL_INVALID_VALUE is generated if timeout is not GL_TIMEOUT_IGNORED.");
345 	ctx.glWaitSync(sync, 0, 0);
346 	ctx.expectError(GL_INVALID_VALUE);
347 	ctx.endSection();
348 
349 	ctx.glDeleteSync(sync);
350 }
351 
client_wait_sync(NegativeTestContext & ctx)352 void client_wait_sync (NegativeTestContext& ctx)
353 {
354 	GLsync sync = ctx.glFenceSync(GL_SYNC_GPU_COMMANDS_COMPLETE, 0);
355 
356 	ctx.beginSection("GL_INVALID_VALUE is generated if sync is not the name of an existing sync object.");
357 	ctx.glClientWaitSync (0, 0, 10000);
358 	ctx.expectError(GL_INVALID_VALUE);
359 	ctx.endSection();
360 
361 	ctx.beginSection("GL_INVALID_VALUE is generated if flags contains any unsupported flag.");
362 	ctx.glClientWaitSync(sync, 0x00000004, 10000);
363 	ctx.expectError(GL_INVALID_VALUE);
364 	ctx.endSection();
365 
366 	ctx.glDeleteSync(sync);
367 }
368 
delete_sync(NegativeTestContext & ctx)369 void delete_sync (NegativeTestContext& ctx)
370 {
371 	ctx.beginSection("GL_INVALID_VALUE is generated if sync is neither zero or the name of a sync object.");
372 	ctx.glDeleteSync((GLsync)1);
373 	ctx.expectError(GL_INVALID_VALUE);
374 	ctx.glDeleteSync(0);
375 	ctx.expectError(GL_NO_ERROR);
376 	ctx.endSection();
377 }
378 
getNegativeFragmentApiTestFunctions()379 std::vector<FunctionContainer> getNegativeFragmentApiTestFunctions ()
380 {
381 	FunctionContainer funcs[] =
382 	{
383 		{scissor,					"scissor",					"Invalid glScissor() usage"				 },
384 		{depth_func,				"depth_func",				"Invalid glDepthFunc() usage"			 },
385 		{viewport,					"viewport",					"Invalid glViewport() usage"			 },
386 		{stencil_func,				"stencil_func",				"Invalid glStencilFunc() usage"			 },
387 		{stencil_func_separate,		"stencil_func_separate",	"Invalid glStencilFuncSeparate() usage"	 },
388 		{stencil_op,				"stencil_op",				"Invalid glStencilOp() usage"			 },
389 		{stencil_op_separate,		"stencil_op_separate",		"Invalid glStencilOpSeparate() usage"	 },
390 		{stencil_mask_separate,		"stencil_mask_separate",	"Invalid glStencilMaskSeparate() usage"	 },
391 		{blend_equation,			"blend_equation",			"Invalid glBlendEquation() usage"		 },
392 		{blend_equation_separate,	"blend_equation_separate",	"Invalid glBlendEquationSeparate() usage"},
393 		{blend_func,				"blend_func",				"Invalid glBlendFunc() usage"			 },
394 		{blend_func_separate,		"blend_func_separate",		"Invalid glBlendFuncSeparate() usage"	 },
395 		{cull_face,					"cull_face",				"Invalid glCullFace() usage"			 },
396 		{front_face,				"front_face",				"Invalid glFrontFace() usage"			 },
397 		{line_width,				"line_width",				"Invalid glLineWidth() usage"			 },
398 		{gen_queries,				"gen_queries",				"Invalid glGenQueries() usage"			 },
399 		{begin_query,				"begin_query",				"Invalid glBeginQuery() usage"			 },
400 		{end_query,					"end_query",				"Invalid glEndQuery() usage"			 },
401 		{delete_queries,			"delete_queries",			"Invalid glDeleteQueries() usage"		 },
402 		{fence_sync,				"fence_sync",				"Invalid glFenceSync() usage"			 },
403 		{wait_sync,					"wait_sync",				"Invalid glWaitSync() usage"			 },
404 		{client_wait_sync,			"client_wait_sync",			"Invalid glClientWaitSync() usage"		 },
405 		{delete_sync,				"delete_sync",				"Invalid glDeleteSync() usage"			 },
406 	};
407 
408 	return std::vector<FunctionContainer>(DE_ARRAY_BEGIN(funcs), DE_ARRAY_END(funcs));
409 }
410 
411 } // NegativeTestShared
412 } // Functional
413 } // gles31
414 } // deqp
415