Home | History | Annotate | Download | only in functional
      1 /*-------------------------------------------------------------------------
      2  * drawElements Quality Program OpenGL ES 3.1 Module
      3  * -------------------------------------------------
      4  *
      5  * Copyright 2016 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 Advanced Blend Equation Tests
     22  *//*--------------------------------------------------------------------*/
     23 
     24 #include "es31fNegativeAdvancedBlendEquationTests.hpp"
     25 
     26 #include "gluShaderProgram.hpp"
     27 #include "glwEnums.hpp"
     28 
     29 namespace deqp
     30 {
     31 namespace gles31
     32 {
     33 namespace Functional
     34 {
     35 namespace NegativeTestShared
     36 {
     37 namespace
     38 {
     39 
     40 enum BlendEquation
     41 {
     42 	BLEND_EQUATION_MULTIPLY = 0,
     43 	BLEND_EQUATION_SCREEN,
     44 	BLEND_EQUATION_OVERLAY,
     45 	BLEND_EQUATION_DARKEN,
     46 	BLEND_EQUATION_LIGHTEN,
     47 	BLEND_EQUATION_COLORDODGE,
     48 	BLEND_EQUATION_COLORBURN,
     49 	BLEND_EQUATION_HARDLIGHT,
     50 	BLEND_EQUATION_SOFTLIGHT,
     51 	BLEND_EQUATION_DIFFERENCE,
     52 	BLEND_EQUATION_EXCLUSION,
     53 	BLEND_EQUATION_HSL_HUE,
     54 	BLEND_EQUATION_HSL_SATURATION,
     55 	BLEND_EQUATION_HSL_COLOR,
     56 	BLEND_EQUATION_HSL_LUMINOSITY,
     57 	BLEND_EQUATION_ALL_EQUATIONS,
     58 
     59 	BLEND_EQUATION_LAST
     60 };
     61 
     62 static const BlendEquation s_equations[] =
     63 {
     64 	BLEND_EQUATION_MULTIPLY,
     65 	BLEND_EQUATION_SCREEN,
     66 	BLEND_EQUATION_OVERLAY,
     67 	BLEND_EQUATION_DARKEN,
     68 	BLEND_EQUATION_LIGHTEN,
     69 	BLEND_EQUATION_COLORDODGE,
     70 	BLEND_EQUATION_COLORBURN,
     71 	BLEND_EQUATION_HARDLIGHT,
     72 	BLEND_EQUATION_SOFTLIGHT,
     73 	BLEND_EQUATION_DIFFERENCE,
     74 	BLEND_EQUATION_EXCLUSION,
     75 	BLEND_EQUATION_HSL_HUE,
     76 	BLEND_EQUATION_HSL_SATURATION,
     77 	BLEND_EQUATION_HSL_COLOR,
     78 	BLEND_EQUATION_HSL_LUMINOSITY
     79 };
     80 
     81 std::string getShaderLayoutEquation (BlendEquation equation)
     82 {
     83 	switch (equation)
     84 	{
     85 		case BLEND_EQUATION_MULTIPLY:          return "blend_support_multiply";
     86 		case BLEND_EQUATION_SCREEN:            return "blend_support_screen";
     87 		case BLEND_EQUATION_OVERLAY:           return "blend_support_overlay";
     88 		case BLEND_EQUATION_DARKEN:            return "blend_support_darken";
     89 		case BLEND_EQUATION_LIGHTEN:           return "blend_support_lighten";
     90 		case BLEND_EQUATION_COLORDODGE:        return "blend_support_colordodge";
     91 		case BLEND_EQUATION_COLORBURN:         return "blend_support_colorburn";
     92 		case BLEND_EQUATION_HARDLIGHT:         return "blend_support_hardlight";
     93 		case BLEND_EQUATION_SOFTLIGHT:         return "blend_support_softlight";
     94 		case BLEND_EQUATION_DIFFERENCE:        return "blend_support_difference";
     95 		case BLEND_EQUATION_EXCLUSION:         return "blend_support_exclusion";
     96 		case BLEND_EQUATION_HSL_HUE:           return "blend_support_hsl_hue";
     97 		case BLEND_EQUATION_HSL_SATURATION:    return "blend_support_hsl_saturation";
     98 		case BLEND_EQUATION_HSL_COLOR:         return "blend_support_hsl_color";
     99 		case BLEND_EQUATION_HSL_LUMINOSITY:    return "blend_support_hsl_luminosity";
    100 		case BLEND_EQUATION_ALL_EQUATIONS:     return "blend_support_all_equations";
    101 		default:
    102 			DE_FATAL("Equation not supported.");
    103 	}
    104 	return DE_NULL;
    105 }
    106 
    107 glw::GLenum getEquation (BlendEquation equation)
    108 {
    109 	switch (equation)
    110 	{
    111 		case BLEND_EQUATION_MULTIPLY:          return GL_MULTIPLY;
    112 		case BLEND_EQUATION_SCREEN:            return GL_SCREEN;
    113 		case BLEND_EQUATION_OVERLAY:           return GL_OVERLAY;
    114 		case BLEND_EQUATION_DARKEN:            return GL_DARKEN;
    115 		case BLEND_EQUATION_LIGHTEN:           return GL_LIGHTEN;
    116 		case BLEND_EQUATION_COLORDODGE:        return GL_COLORDODGE;
    117 		case BLEND_EQUATION_COLORBURN:         return GL_COLORBURN;
    118 		case BLEND_EQUATION_HARDLIGHT:         return GL_HARDLIGHT;
    119 		case BLEND_EQUATION_SOFTLIGHT:         return GL_SOFTLIGHT;
    120 		case BLEND_EQUATION_DIFFERENCE:        return GL_DIFFERENCE;
    121 		case BLEND_EQUATION_EXCLUSION:         return GL_EXCLUSION;
    122 		case BLEND_EQUATION_HSL_HUE:           return GL_HSL_HUE;
    123 		case BLEND_EQUATION_HSL_SATURATION:    return GL_HSL_SATURATION;
    124 		case BLEND_EQUATION_HSL_COLOR:         return GL_HSL_COLOR;
    125 		case BLEND_EQUATION_HSL_LUMINOSITY:    return GL_HSL_LUMINOSITY;
    126 		default:
    127 			DE_FATAL("Equation not supported.");
    128 	}
    129 	return DE_NULL;
    130 }
    131 
    132 std::string generateVertexShaderSource (NegativeTestContext& ctx)
    133 {
    134 	const bool				supportsES32	= contextSupports(ctx.getRenderContext().getType(), glu::ApiType::es(3, 2));
    135 	const glu::GLSLVersion	version	= supportsES32 ? glu::GLSL_VERSION_320_ES : glu::GLSL_VERSION_310_ES;
    136 	std::ostringstream		source;
    137 
    138 	source	<< glu::getGLSLVersionDeclaration(version) << "\n"
    139 			<< "void main ()\n"
    140 			<< "{\n"
    141 			<< "	gl_Position = vec4(0.0);\n"
    142 			<< "}\n";
    143 
    144 	return source.str();
    145 }
    146 
    147 std::string generateFragmentShaderSource (NegativeTestContext& ctx, BlendEquation equation)
    148 {
    149 	const bool				supportsES32	= contextSupports(ctx.getRenderContext().getType(), glu::ApiType::es(3, 2));
    150 	const glu::GLSLVersion	version	= supportsES32 ? glu::GLSL_VERSION_320_ES : glu::GLSL_VERSION_310_ES;
    151 	std::ostringstream		source;
    152 
    153 	source	<< glu::getGLSLVersionDeclaration(version) << "\n"
    154 			<< (supportsES32 ? "" : "#extension GL_KHR_blend_equation_advanced : enable\n")
    155 			<< "layout(" << getShaderLayoutEquation(equation) << ") out;\n"
    156 			<< "layout(location=0) out mediump vec4 o_color;\n"
    157 			<< "void main ()\n"
    158 			<< "{\n"
    159 			<< "	o_color = vec4(0);\n"
    160 			<< "}\n";
    161 
    162 	return source.str();
    163 }
    164 
    165 glu::ProgramSources generateProgramSources (NegativeTestContext& ctx, BlendEquation equation)
    166 {
    167 	return glu::ProgramSources()
    168 		<< glu::VertexSource(generateVertexShaderSource(ctx))
    169 		<< glu::FragmentSource(generateFragmentShaderSource(ctx, equation));
    170 }
    171 
    172 void blend_qualifier_mismatch (NegativeTestContext& ctx)
    173 {
    174 	TCU_CHECK_AND_THROW(NotSupportedError,
    175 		ctx.isExtensionSupported("GL_KHR_blend_equation_advanced") || contextSupports(ctx.getRenderContext().getType(), glu::ApiType::es(3, 2)),
    176 		"This test requires support for the extension GL_KHR_blend_equation_advanced or context version 3.2 or higher.");
    177 
    178 	ctx.beginSection("GL_INVALID_OPERATION is generated if blending is enabled, and the blend qualifier is different from blend_support_all_equations and does not match the blend equation.");
    179 	for (int ndx = 0; ndx < DE_LENGTH_OF_ARRAY(s_equations); ++ndx)
    180 	{
    181 		glu::ShaderProgram program(ctx.getRenderContext(), generateProgramSources(ctx, s_equations[ndx]));
    182 
    183 		ctx.getLog() << program;
    184 		TCU_CHECK(program.isOk());
    185 
    186 		ctx.glUseProgram(program.getProgram());
    187 		ctx.expectError(GL_NO_ERROR);
    188 
    189 		for (int ndx2 = 0; ndx2 < DE_LENGTH_OF_ARRAY(s_equations); ++ndx2)
    190 		{
    191 			if (s_equations[ndx] == s_equations[ndx2])
    192 				continue;
    193 
    194 			ctx.glEnable(GL_BLEND);
    195 			ctx.glBlendEquation(getEquation(s_equations[ndx2]));
    196 			ctx.expectError(GL_NO_ERROR);
    197 			ctx.glDrawElements(GL_TRIANGLES, 0, GL_UNSIGNED_INT, 0);
    198 			ctx.expectError(GL_INVALID_OPERATION);
    199 
    200 			ctx.glDisable(GL_BLEND);
    201 			ctx.glDrawElements(GL_TRIANGLES, 0, GL_UNSIGNED_INT, 0);
    202 			ctx.expectError(GL_NO_ERROR);
    203 		}
    204 	}
    205 	ctx.endSection();
    206 }
    207 
    208 void attachment_advanced_equation (NegativeTestContext& ctx)
    209 {
    210 	TCU_CHECK_AND_THROW(NotSupportedError,
    211 		ctx.isExtensionSupported("GL_KHR_blend_equation_advanced") || contextSupports(ctx.getRenderContext().getType(), glu::ApiType::es(3, 2)),
    212 		"This test requires support for the extension GL_KHR_blend_equation_advanced or context version 3.2 or higher.");
    213 
    214 	glw::GLuint			fbo				= 0x1234;
    215 	glw::GLuint			texture			= 0x1234;
    216 	const glw::GLenum	attachments[]	= { GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT1 };
    217 
    218 	ctx.glGenTextures(1, &texture);
    219 	ctx.glBindTexture(GL_TEXTURE_2D, texture);
    220 	ctx.glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, 32, 32, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
    221 	ctx.glGenFramebuffers(1, &fbo);
    222 	ctx.glBindFramebuffer(GL_FRAMEBUFFER, fbo);
    223 	ctx.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texture, 0);
    224 	ctx.expectError(GL_NO_ERROR);
    225 	ctx.glCheckFramebufferStatus(GL_FRAMEBUFFER);
    226 
    227 	ctx.beginSection("GL_INVALID_OPERATION is generated if blending is enabled, advanced equations are used, and the draw buffer for other color outputs is not NONE unless NVX_blend_equation_advanced_multi_draw_buffers is supported.");
    228 	for (int ndx = 0; ndx < DE_LENGTH_OF_ARRAY(s_equations); ++ndx)
    229 	{
    230 		glu::ShaderProgram	program(ctx.getRenderContext(), generateProgramSources(ctx, s_equations[ndx]));
    231 		ctx.getLog() << program;
    232 		TCU_CHECK(program.isOk());
    233 
    234 		ctx.glUseProgram(program.getProgram());
    235 		ctx.glEnable(GL_BLEND);
    236 		ctx.glDrawBuffers(2, attachments);
    237 		ctx.expectError(GL_NO_ERROR);
    238 		ctx.glBlendEquation(getEquation(s_equations[ndx]));
    239 		ctx.glDrawElements(GL_TRIANGLES, 0, GL_UNSIGNED_INT, 0);
    240 		if (ctx.isExtensionSupported("GL_NVX_blend_equation_advanced_multi_draw_buffers"))
    241 			ctx.expectError(GL_NO_ERROR);
    242 		else
    243 			ctx.expectError(GL_INVALID_OPERATION);
    244 	}
    245 	ctx.endSection();
    246 
    247 	ctx.beginSection("GL_NO_ERROR is generated if no advanced blend equations are used.");
    248 	ctx.glBlendEquation(GL_FUNC_ADD);
    249 	ctx.glDrawElements(GL_TRIANGLES, 0, GL_UNSIGNED_INT, 0);
    250 	ctx.expectError(GL_NO_ERROR);
    251 	ctx.endSection();
    252 
    253 	ctx.beginSection("GL_NO_ERROR is generated if blending is disabled.");
    254 	ctx.glDisable(GL_BLEND);
    255 	for (int ndx = 0; ndx < DE_LENGTH_OF_ARRAY(s_equations); ++ndx)
    256 	{
    257 		ctx.glBlendEquation(getEquation(s_equations[ndx]));
    258 		ctx.glDrawElements(GL_TRIANGLES, 0, GL_UNSIGNED_INT, 0);
    259 		ctx.expectError(GL_NO_ERROR);
    260 	}
    261 	ctx.endSection();
    262 
    263 	ctx.glDeleteFramebuffers(1, &fbo);
    264 	ctx.glDeleteTextures(1, &texture);
    265 }
    266 
    267 } // anonymous
    268 
    269 std::vector<FunctionContainer> getNegativeAdvancedBlendEquationTestFunctions (void)
    270 {
    271 	const FunctionContainer funcs[] =
    272 	{
    273 		{blend_qualifier_mismatch,			"blend_qualifier_mismatch",			"Test blend qualifier mismatch."			},
    274 		{attachment_advanced_equation,		"attachment_advanced_equation",		"Test draw buffer for other color outputs." },
    275 	};
    276 
    277 	return std::vector<FunctionContainer>(DE_ARRAY_BEGIN(funcs), DE_ARRAY_END(funcs));
    278 }
    279 
    280 } // NegativeTestShared
    281 } // Functional
    282 } // gles31
    283 } // deqp
    284