1 //
2 // Copyright 2020 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6
7 #include "test_utils/ANGLETest.h"
8 #include "test_utils/gl_raii.h"
9
10 using namespace angle;
11
12 class BlendIntegerTest : public ANGLETest
13 {
14 protected:
BlendIntegerTest()15 BlendIntegerTest()
16 {
17 setWindowWidth(128);
18 setWindowHeight(128);
19 setConfigRedBits(8);
20 setConfigGreenBits(8);
21 setConfigBlueBits(8);
22 setConfigAlphaBits(8);
23 }
24
25 template <typename T, GLuint components>
compareValue(const T * value,const char * name)26 void compareValue(const T *value, const char *name)
27 {
28 T pixel[4];
29 glReadBuffer(GL_COLOR_ATTACHMENT0);
30 glReadPixels(0, 0, 1, 1, GL_RGBA_INTEGER,
31 std::is_same<T, int32_t>::value ? GL_INT : GL_UNSIGNED_INT, pixel);
32 for (size_t componentIdx = 0; componentIdx < components; componentIdx++)
33 {
34 EXPECT_EQ(value[componentIdx], pixel[componentIdx])
35 << " componentIdx=" << componentIdx << std::endl
36 << " " << name << "[0]=" << value[0] << " pixel[0]=" << pixel[0] << std::endl
37 << " " << name << "[1]=" << value[1] << " pixel[1]=" << pixel[1] << std::endl
38 << " " << name << "[2]=" << value[2] << " pixel[2]=" << pixel[2] << std::endl
39 << " " << name << "[3]=" << value[3] << " pixel[3]=" << pixel[3];
40 }
41 }
42
43 template <GLenum internalformat, GLuint components, bool isSigned>
runTest()44 void runTest()
45 {
46 // https://crbug.com/angleproject/4548
47 ANGLE_SKIP_TEST_IF(isVulkanRenderer() && IsIntel() && !isVulkanSwiftshaderRenderer());
48
49 constexpr char kFsui[] =
50 "#version 300 es\n"
51 "out highp uvec4 o_drawBuffer0;\n"
52 "void main(void)\n"
53 "{\n"
54 " o_drawBuffer0 = uvec4(1, 1, 1, 1);\n"
55 "}\n";
56
57 constexpr char kFssi[] =
58 "#version 300 es\n"
59 "out highp ivec4 o_drawBuffer0;\n"
60 "void main(void)\n"
61 "{\n"
62 " o_drawBuffer0 = ivec4(-1, -1, -1, -1);\n"
63 "}\n";
64
65 ANGLE_GL_PROGRAM(program, essl3_shaders::vs::Simple(), isSigned ? kFssi : kFsui);
66 glUseProgram(program);
67
68 GLFramebuffer framebuffer;
69 glBindFramebuffer(GL_FRAMEBUFFER, framebuffer);
70
71 GLRenderbuffer colorRenderbuffer;
72 glBindRenderbuffer(GL_RENDERBUFFER, colorRenderbuffer);
73 glRenderbufferStorage(GL_RENDERBUFFER, internalformat, getWindowWidth(), getWindowHeight());
74 glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER,
75 colorRenderbuffer);
76
77 if (isSigned)
78 {
79 const int32_t clearValueSigned[4] = {-128, -128, -128, -128};
80 glClearBufferiv(GL_COLOR, 0, clearValueSigned);
81 ASSERT_GL_NO_ERROR();
82 compareValue<int32_t, components>(clearValueSigned, "clearValueSigned");
83 }
84 else
85 {
86 const uint32_t clearValueUnsigned[4] = {127, 127, 127, 3};
87 glClearBufferuiv(GL_COLOR, 0, clearValueUnsigned);
88 ASSERT_GL_NO_ERROR();
89 compareValue<uint32_t, components>(clearValueUnsigned, "clearValueUnsigned");
90 }
91
92 glEnable(GL_BLEND);
93 glBlendEquation(GL_FUNC_ADD);
94 glBlendFunc(GL_ONE, GL_ONE);
95
96 drawQuad(program, essl3_shaders::PositionAttrib(), 0.5f);
97
98 ASSERT_GL_NO_ERROR();
99
100 // Enabled blending must be ignored for integer color attachment.
101 if (isSigned)
102 {
103 const int32_t colorValueSigned[4] = {-1, -1, -1, -1};
104 compareValue<int32_t, components>(colorValueSigned, "colorValueSigned");
105 }
106 else
107 {
108 const uint32_t colorValueUnsigned[4] = {1, 1, 1, 1};
109 compareValue<uint32_t, components>(colorValueUnsigned, "colorValueUnsigned");
110 }
111 }
112 };
113
114 // Test that blending is not applied to signed integer attachments.
TEST_P(BlendIntegerTest,R8I)115 TEST_P(BlendIntegerTest, R8I)
116 {
117 // TODO(http://anglebug.com/4571)
118 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
119 runTest<GL_R8I, 1, true>();
120 }
121
TEST_P(BlendIntegerTest,R16I)122 TEST_P(BlendIntegerTest, R16I)
123 {
124 // TODO(http://anglebug.com/4571)
125 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
126 runTest<GL_R16I, 1, true>();
127 }
128
TEST_P(BlendIntegerTest,R32I)129 TEST_P(BlendIntegerTest, R32I)
130 {
131 // TODO(http://anglebug.com/4571)
132 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
133 runTest<GL_R32I, 1, true>();
134 }
135
TEST_P(BlendIntegerTest,RG8I)136 TEST_P(BlendIntegerTest, RG8I)
137 {
138 // TODO(http://anglebug.com/4571)
139 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
140 runTest<GL_RG8I, 2, true>();
141 }
142
TEST_P(BlendIntegerTest,RG16I)143 TEST_P(BlendIntegerTest, RG16I)
144 {
145 // TODO(http://anglebug.com/4571)
146 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
147 runTest<GL_RG16I, 2, true>();
148 }
149
TEST_P(BlendIntegerTest,RG32I)150 TEST_P(BlendIntegerTest, RG32I)
151 {
152 // TODO(http://anglebug.com/4571)
153 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
154 runTest<GL_RG32I, 2, true>();
155 }
156
TEST_P(BlendIntegerTest,RGBA8I)157 TEST_P(BlendIntegerTest, RGBA8I)
158 {
159 // TODO(http://anglebug.com/4571)
160 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
161 runTest<GL_RGBA8I, 4, true>();
162 }
163
TEST_P(BlendIntegerTest,RGBA16I)164 TEST_P(BlendIntegerTest, RGBA16I)
165 {
166 // TODO(http://anglebug.com/4571)
167 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
168 runTest<GL_RGBA16I, 4, true>();
169 }
170
TEST_P(BlendIntegerTest,RGBA32I)171 TEST_P(BlendIntegerTest, RGBA32I)
172 {
173 // TODO(http://anglebug.com/4571)
174 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
175 runTest<GL_RGBA32I, 4, true>();
176 }
177
178 // Test that blending is not applied to unsigned integer attachments.
TEST_P(BlendIntegerTest,R8UI)179 TEST_P(BlendIntegerTest, R8UI)
180 {
181 // TODO(http://anglebug.com/4571)
182 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
183 runTest<GL_R8UI, 1, false>();
184 }
185
TEST_P(BlendIntegerTest,R16UI)186 TEST_P(BlendIntegerTest, R16UI)
187 {
188 // TODO(http://anglebug.com/4571)
189 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
190 runTest<GL_R16UI, 1, false>();
191 }
192
TEST_P(BlendIntegerTest,R32UI)193 TEST_P(BlendIntegerTest, R32UI)
194 {
195 // TODO(http://anglebug.com/4571)
196 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
197 runTest<GL_R32UI, 1, false>();
198 }
199
TEST_P(BlendIntegerTest,RG8UI)200 TEST_P(BlendIntegerTest, RG8UI)
201 {
202 // TODO(http://anglebug.com/4571)
203 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
204 runTest<GL_RG8UI, 2, false>();
205 }
206
TEST_P(BlendIntegerTest,RG16UI)207 TEST_P(BlendIntegerTest, RG16UI)
208 {
209 // TODO(http://anglebug.com/4571)
210 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
211 runTest<GL_RG16UI, 2, false>();
212 }
213
TEST_P(BlendIntegerTest,RG32UI)214 TEST_P(BlendIntegerTest, RG32UI)
215 {
216 // TODO(http://anglebug.com/4571)
217 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
218 runTest<GL_RG32UI, 2, false>();
219 }
220
TEST_P(BlendIntegerTest,RGBA8UI)221 TEST_P(BlendIntegerTest, RGBA8UI)
222 {
223 // TODO(http://anglebug.com/4571)
224 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
225 runTest<GL_RGBA8UI, 4, false>();
226 }
227
TEST_P(BlendIntegerTest,RGBA16UI)228 TEST_P(BlendIntegerTest, RGBA16UI)
229 {
230 // TODO(http://anglebug.com/4571)
231 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
232 runTest<GL_RGBA16UI, 4, false>();
233 }
234
TEST_P(BlendIntegerTest,RGBA32UI)235 TEST_P(BlendIntegerTest, RGBA32UI)
236 {
237 // TODO(http://anglebug.com/4571)
238 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
239 runTest<GL_RGBA32UI, 4, false>();
240 }
241
TEST_P(BlendIntegerTest,RGB10_A2UI)242 TEST_P(BlendIntegerTest, RGB10_A2UI)
243 {
244 // TODO(http://anglebug.com/4571)
245 ANGLE_SKIP_TEST_IF(isVulkanRenderer());
246 runTest<GL_RGB10_A2UI, 4, false>();
247 }
248
249 // Use this to select which configurations (e.g. which renderer, which GLES major version) these
250 // tests should be run against.
251 ANGLE_INSTANTIATE_TEST_ES3(BlendIntegerTest);
252