1 //
2 // Copyright 2015 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 // Texture upload format tests:
7 // Test all texture unpack/upload formats for sampling correctness.
8 //
9
10 #include "common/mathutil.h"
11 #include "image_util/copyimage.h"
12 #include "test_utils/ANGLETest.h"
13 #include "test_utils/gl_raii.h"
14
15 using namespace angle;
16
17 namespace
18 {
19
20 class TextureUploadFormatTest : public ANGLETest
21 {};
22
23 struct TexFormat final
24 {
25 GLenum internalFormat;
26 GLenum unpackFormat;
27 GLenum unpackType;
28
29 TexFormat() = delete;
30
bytesPerPixel__anonad622d3c0111::TexFormat31 uint8_t bytesPerPixel() const
32 {
33 uint8_t bytesPerChannel;
34 switch (unpackType)
35 {
36 case GL_UNSIGNED_SHORT_5_6_5:
37 case GL_UNSIGNED_SHORT_4_4_4_4:
38 case GL_UNSIGNED_SHORT_5_5_5_1:
39 return 2;
40
41 case GL_UNSIGNED_INT_2_10_10_10_REV:
42 case GL_UNSIGNED_INT_24_8:
43 case GL_UNSIGNED_INT_10F_11F_11F_REV:
44 case GL_UNSIGNED_INT_5_9_9_9_REV:
45 return 4;
46
47 case GL_FLOAT_32_UNSIGNED_INT_24_8_REV:
48 return 8;
49
50 case GL_UNSIGNED_BYTE:
51 case GL_BYTE:
52 bytesPerChannel = 1;
53 break;
54
55 case GL_UNSIGNED_SHORT:
56 case GL_SHORT:
57 case GL_HALF_FLOAT:
58 case GL_HALF_FLOAT_OES:
59 bytesPerChannel = 2;
60 break;
61
62 case GL_UNSIGNED_INT:
63 case GL_INT:
64 case GL_FLOAT:
65 bytesPerChannel = 4;
66 break;
67
68 default:
69 assert(false);
70 return 0;
71 }
72
73 switch (unpackFormat)
74 {
75 case GL_RGBA:
76 case GL_RGBA_INTEGER:
77 return bytesPerChannel * 4;
78
79 case GL_RGB:
80 case GL_RGB_INTEGER:
81 return bytesPerChannel * 3;
82
83 case GL_RG:
84 case GL_RG_INTEGER:
85 case GL_LUMINANCE_ALPHA:
86 return bytesPerChannel * 2;
87
88 case GL_RED:
89 case GL_RED_INTEGER:
90 case GL_LUMINANCE:
91 case GL_ALPHA:
92 case GL_DEPTH_COMPONENT:
93 return bytesPerChannel * 1;
94
95 default:
96 assert(false);
97 return 0;
98 }
99 }
100 };
101
102 template <const uint8_t bits>
EncodeNormUint(const float val)103 constexpr uint32_t EncodeNormUint(const float val)
104 {
105 return static_cast<uint32_t>(val * static_cast<float>(UINT32_MAX >> (32 - bits)) +
106 0.5f); // round-half-up
107 }
108
109 } // anonymous namespace
110
111 namespace
112 {
113
114 template <typename DestT, typename SrcT, size_t SrcN>
ZeroAndCopy(DestT & dest,const SrcT (& src)[SrcN])115 void ZeroAndCopy(DestT &dest, const SrcT (&src)[SrcN])
116 {
117 dest.fill(0);
118 memcpy(dest.data(), src, sizeof(SrcT) * SrcN);
119 }
120
EnumStr(const GLenum v)121 std::string EnumStr(const GLenum v)
122 {
123 std::stringstream ret;
124 ret << "0x" << std::hex << v;
125 return ret.str();
126 }
127
128 template <typename ColorT, typename DestT>
EncodeThenZeroAndCopy(DestT & dest,const float srcVals[4])129 void EncodeThenZeroAndCopy(DestT &dest, const float srcVals[4])
130 {
131 ColorF srcValsF(srcVals[0], srcVals[1], srcVals[2], srcVals[3]);
132
133 ColorT encoded;
134 ColorT::writeColor(&encoded, &srcValsF);
135
136 dest.fill(0);
137 memcpy(dest.data(), &encoded, sizeof(ColorT));
138 }
139 } // anonymous namespace
140
141 // Upload (1,2,5,3) to integer formats, and (1,2,5,3)/8.0 to float formats.
142 // Draw a point into a 1x1 renderbuffer and readback the result for comparison with expectations.
143 // Test all internalFormat/unpackFormat/unpackType combinations from ES3.0.
TEST_P(TextureUploadFormatTest,All)144 TEST_P(TextureUploadFormatTest, All)
145 {
146 ANGLE_SKIP_TEST_IF(IsD3D9());
147
148 constexpr char kVertShaderES2[] = R"(
149 void main()
150 {
151 gl_PointSize = 1.0;
152 gl_Position = vec4(0, 0, 0, 1);
153 })";
154 constexpr char kFragShader_Floats[] = R"(
155 precision mediump float;
156 uniform sampler2D uTex;
157
158 void main()
159 {
160 gl_FragColor = texture2D(uTex, vec2(0,0));
161 })";
162 ANGLE_GL_PROGRAM(floatsProg, kVertShaderES2, kFragShader_Floats);
163
164 glDisable(GL_DITHER);
165
166 ASSERT_GL_NO_ERROR();
167
168 // Create the 1x1 framebuffer
169
170 GLRenderbuffer backbufferRB;
171 glBindRenderbuffer(GL_RENDERBUFFER, backbufferRB);
172 glRenderbufferStorage(GL_RENDERBUFFER, GL_RGBA8, 1, 1);
173 glBindRenderbuffer(GL_RENDERBUFFER, 0);
174
175 GLFramebuffer backbufferFB;
176 glBindFramebuffer(GL_FRAMEBUFFER, backbufferFB);
177 glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, backbufferRB);
178 ASSERT_GL_NO_ERROR();
179 ASSERT_GLENUM_EQ(GL_FRAMEBUFFER_COMPLETE, glCheckFramebufferStatus(GL_FRAMEBUFFER));
180
181 glViewport(0, 0, 1, 1);
182
183 // Create and bind our test texture
184
185 GLTexture testTex;
186 glBindTexture(GL_TEXTURE_2D, testTex);
187 // Must be nearest because some texture formats aren't filterable!
188 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
189 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
190
191 ASSERT_GL_NO_ERROR();
192
193 // Initialize our test variables
194
195 glPixelStorei(GL_UNPACK_SKIP_PIXELS, 0);
196 const bool hasSubrectUploads = !glGetError();
197
198 constexpr uint8_t srcIntVals[4] = {1u, 2u, 5u, 3u};
199 constexpr float srcVals[4] = {srcIntVals[0] / 8.0f, srcIntVals[1] / 8.0f, srcIntVals[2] / 8.0f,
200 srcIntVals[3] / 8.0f};
201 constexpr uint8_t refVals[4] = {static_cast<uint8_t>(EncodeNormUint<8>(srcVals[0])),
202 static_cast<uint8_t>(EncodeNormUint<8>(srcVals[1])),
203 static_cast<uint8_t>(EncodeNormUint<8>(srcVals[2])),
204 static_cast<uint8_t>(EncodeNormUint<8>(srcVals[3]))};
205
206 // Test a format with the specified data
207
208 const auto fnTestData = [&](const TexFormat &format, const void *const data, const GLColor &err,
209 const char *const info) {
210 ASSERT_GL_NO_ERROR();
211 glTexImage2D(GL_TEXTURE_2D, 0, format.internalFormat, 1, 1, 0, format.unpackFormat,
212 format.unpackType, data);
213 const auto uploadErr = glGetError();
214 if (uploadErr) // Format might not be supported. (e.g. on ES2)
215 return;
216
217 glClearColor(1, 0, 1, 1);
218 glClear(GL_COLOR_BUFFER_BIT);
219 glDrawArrays(GL_POINTS, 0, 1);
220
221 const auto actual = ReadColor(0, 0);
222
223 GLColor expected;
224 switch (format.unpackFormat)
225 {
226 case GL_RGBA:
227 case GL_RGBA_INTEGER:
228 expected = {refVals[0], refVals[1], refVals[2], refVals[3]};
229 break;
230 case GL_RGB:
231 expected = {refVals[0], refVals[1], refVals[2], 255};
232 break;
233 case GL_RG:
234 expected = {refVals[0], refVals[1], 0, 255};
235 break;
236 case GL_DEPTH_COMPONENT:
237 case GL_DEPTH_STENCIL:
238 // Metal back-end requires swizzle feature to return (depth, 0, 0, 1) from sampling
239 // a depth texture.
240 // http://anglebug.com/5243
241 if (IsMetal() && !IsMetalTextureSwizzleAvailable())
242 {
243 // If texture swizzle is not supported, we should only compare the first
244 // component.
245 expected = {refVals[0], actual[1], actual[2], actual[3]};
246 }
247 else
248 {
249
250 expected = {refVals[0], 0, 0, 255};
251 }
252 break;
253 case GL_RED:
254 expected = {refVals[0], 0, 0, 255};
255 break;
256
257 case GL_RGB_INTEGER:
258 expected = {refVals[0], refVals[1], refVals[2], refVals[0]};
259 break;
260 case GL_RG_INTEGER:
261 expected = {refVals[0], refVals[1], 0, refVals[0]};
262 break;
263 case GL_RED_INTEGER:
264 expected = {refVals[0], 0, 0, refVals[0]};
265 break;
266
267 case GL_LUMINANCE_ALPHA:
268 expected = {refVals[0], refVals[0], refVals[0], refVals[1]};
269 break;
270 case GL_LUMINANCE:
271 expected = {refVals[0], refVals[0], refVals[0], 255};
272 break;
273 case GL_ALPHA:
274 expected = {0, 0, 0, refVals[0]};
275 break;
276
277 default:
278 assert(false);
279 }
280
281 ASSERT_GL_NO_ERROR();
282 auto result = actual.ExpectNear(expected, err);
283 if (!result)
284 {
285 result << " [" << EnumStr(format.internalFormat) << "/" << EnumStr(format.unpackFormat)
286 << "/" << EnumStr(format.unpackType) << " " << info << "]";
287 }
288 EXPECT_TRUE(result);
289 };
290
291 // Provide buffers for test data, and a func to run the test on both the data directly, and on
292 // a basic subrect selection to ensure pixel byte size is calculated correctly.
293 // Possible todo here is to add tests to ensure stride calculation.
294
295 std::array<uint8_t, sizeof(float) * 4> srcBuffer;
296
297 std::array<uint8_t, srcBuffer.size() * 2> subrectBuffer;
298 const auto fnTest = [&](const TexFormat &format, const GLColor &err) {
299 fnTestData(format, srcBuffer.data(), err, "simple");
300
301 if (!hasSubrectUploads)
302 return;
303
304 const auto bytesPerPixel = format.bytesPerPixel();
305
306 glPixelStorei(GL_UNPACK_SKIP_PIXELS, 1);
307
308 subrectBuffer.fill(0);
309 memcpy(subrectBuffer.data() + bytesPerPixel, srcBuffer.data(), bytesPerPixel);
310 fnTestData(format, subrectBuffer.data(), err, "subrect");
311
312 glPixelStorei(GL_UNPACK_SKIP_PIXELS, 0);
313 };
314
315 // Test All The Formats, organized by unpack format and type.
316 // (Combos from GLES 3.0.5 p111-112: Table 3.2: "Valid combinations of format, type, and sized
317 // internalformat.")
318
319 // Start with normalized ints
320 glUseProgram(floatsProg);
321
322 // RGBA+UNSIGNED_BYTE
323 {
324 constexpr uint8_t src[] = {static_cast<uint8_t>(EncodeNormUint<8>(srcVals[0])),
325 static_cast<uint8_t>(EncodeNormUint<8>(srcVals[1])),
326 static_cast<uint8_t>(EncodeNormUint<8>(srcVals[2])),
327 static_cast<uint8_t>(EncodeNormUint<8>(srcVals[3]))};
328 ZeroAndCopy(srcBuffer, src);
329
330 fnTest({GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE}, {1, 1, 1, 1});
331 fnTest({GL_RGB5_A1, GL_RGBA, GL_UNSIGNED_BYTE}, {8, 8, 8, 255});
332 fnTest({GL_RGBA4, GL_RGBA, GL_UNSIGNED_BYTE}, {16, 16, 16, 16});
333
334 fnTest({GL_RGB8, GL_RGB, GL_UNSIGNED_BYTE}, {1, 1, 1, 0});
335 fnTest({GL_RGB565, GL_RGB, GL_UNSIGNED_BYTE}, {8, 4, 8, 0});
336
337 fnTest({GL_RG8, GL_RG, GL_UNSIGNED_BYTE}, {1, 1, 0, 0});
338
339 fnTest({GL_R8, GL_RED, GL_UNSIGNED_BYTE}, {1, 0, 0, 0});
340
341 fnTest({GL_RGBA, GL_RGBA, GL_UNSIGNED_BYTE}, {1, 1, 1, 1});
342 fnTest({GL_RGB, GL_RGB, GL_UNSIGNED_BYTE}, {1, 1, 1, 0});
343 fnTest({GL_LUMINANCE_ALPHA, GL_LUMINANCE_ALPHA, GL_UNSIGNED_BYTE}, {1, 1, 1, 1});
344 fnTest({GL_LUMINANCE, GL_LUMINANCE, GL_UNSIGNED_BYTE}, {1, 1, 1, 0});
345 fnTest({GL_ALPHA, GL_ALPHA, GL_UNSIGNED_BYTE}, {0, 0, 0, 1});
346 }
347
348 // RGBA+BYTE
349 {
350 constexpr uint8_t src[] = {static_cast<uint8_t>(EncodeNormUint<7>(srcVals[0])),
351 static_cast<uint8_t>(EncodeNormUint<7>(srcVals[1])),
352 static_cast<uint8_t>(EncodeNormUint<7>(srcVals[2])),
353 static_cast<uint8_t>(EncodeNormUint<7>(srcVals[3]))};
354 ZeroAndCopy(srcBuffer, src);
355
356 fnTest({GL_RGBA8_SNORM, GL_RGBA, GL_BYTE}, {2, 2, 2, 2});
357 fnTest({GL_RGB8_SNORM, GL_RGB, GL_BYTE}, {2, 2, 2, 0});
358 fnTest({GL_RG8_SNORM, GL_RG, GL_BYTE}, {2, 2, 0, 0});
359 fnTest({GL_R8_SNORM, GL_RED, GL_BYTE}, {2, 0, 0, 0});
360 }
361
362 // RGB+UNSIGNED_SHORT_5_6_5
363 {
364 constexpr uint16_t src[] = {static_cast<uint16_t>((EncodeNormUint<5>(srcVals[0]) << 11) |
365 (EncodeNormUint<6>(srcVals[1]) << 5) |
366 (EncodeNormUint<5>(srcVals[2]) << 0))};
367 ZeroAndCopy(srcBuffer, src);
368
369 fnTest({GL_RGB565, GL_RGB, GL_UNSIGNED_SHORT_5_6_5}, {8, 4, 8, 0});
370 fnTest({GL_RGB, GL_RGB, GL_UNSIGNED_SHORT_5_6_5}, {8, 4, 8, 0});
371 }
372
373 // RGBA+UNSIGNED_SHORT_4_4_4_4
374 {
375 constexpr uint16_t src[] = {static_cast<uint16_t>(
376 (EncodeNormUint<4>(srcVals[0]) << 12) | (EncodeNormUint<4>(srcVals[1]) << 8) |
377 (EncodeNormUint<4>(srcVals[2]) << 4) | (EncodeNormUint<4>(srcVals[3]) << 0))};
378 ZeroAndCopy(srcBuffer, src);
379
380 fnTest({GL_RGBA4, GL_RGBA, GL_UNSIGNED_SHORT_4_4_4_4}, {16, 16, 16, 16});
381 fnTest({GL_RGBA, GL_RGBA, GL_UNSIGNED_SHORT_4_4_4_4}, {16, 16, 16, 16});
382 }
383
384 // RGBA+UNSIGNED_SHORT_5_5_5_1
385 {
386 constexpr uint16_t src[] = {static_cast<uint16_t>(
387 (EncodeNormUint<5>(srcVals[0]) << 11) | (EncodeNormUint<5>(srcVals[1]) << 6) |
388 (EncodeNormUint<5>(srcVals[2]) << 1) | (EncodeNormUint<1>(srcVals[3]) << 0))};
389 ZeroAndCopy(srcBuffer, src);
390
391 fnTest({GL_RGBA, GL_RGBA, GL_UNSIGNED_SHORT_5_5_5_1}, {8, 8, 8, 255});
392 }
393
394 // RGBA+UNSIGNED_INT_2_10_10_10_REV
395 {
396 constexpr uint32_t src[] = {
397 (EncodeNormUint<10>(srcVals[0]) << 0) | (EncodeNormUint<10>(srcVals[1]) << 10) |
398 (EncodeNormUint<10>(srcVals[2]) << 20) | (EncodeNormUint<2>(srcVals[3]) << 30)};
399 ZeroAndCopy(srcBuffer, src);
400
401 fnTest({GL_RGB10_A2, GL_RGBA, GL_UNSIGNED_INT_2_10_10_10_REV}, {1, 1, 1, 128});
402 fnTest({GL_RGB5_A1, GL_RGBA, GL_UNSIGNED_INT_2_10_10_10_REV}, {8, 8, 8, 255});
403 fnTest({GL_RGBA, GL_RGBA, GL_UNSIGNED_INT_2_10_10_10_REV}, {1, 1, 1, 128});
404 }
405
406 // RGB+UNSIGNED_INT_2_10_10_10_REV
407 {
408 constexpr uint32_t src[] = {
409 (EncodeNormUint<10>(srcVals[0]) << 0) | (EncodeNormUint<10>(srcVals[1]) << 10) |
410 (EncodeNormUint<10>(srcVals[2]) << 20) | (EncodeNormUint<2>(srcVals[3]) << 30)};
411 ZeroAndCopy(srcBuffer, src);
412
413 fnTest({GL_RGB, GL_RGB, GL_UNSIGNED_INT_2_10_10_10_REV}, {1, 1, 1, 0});
414 }
415
416 // DEPTH_COMPONENT+UNSIGNED_SHORT
417 {
418 const uint16_t src[] = {static_cast<uint16_t>(EncodeNormUint<16>(srcVals[0]))};
419 ZeroAndCopy(srcBuffer, src);
420
421 fnTest({GL_DEPTH_COMPONENT16, GL_DEPTH_COMPONENT, GL_UNSIGNED_SHORT}, {1, 0, 0, 0});
422 }
423
424 // DEPTH_COMPONENT+UNSIGNED_INT
425 {
426 constexpr uint32_t src[] = {EncodeNormUint<32>(srcVals[0])};
427 ZeroAndCopy(srcBuffer, src);
428
429 fnTest({GL_DEPTH_COMPONENT24, GL_DEPTH_COMPONENT, GL_UNSIGNED_INT}, {1, 0, 0, 0});
430 fnTest({GL_DEPTH_COMPONENT16, GL_DEPTH_COMPONENT, GL_UNSIGNED_INT}, {1, 0, 0, 0});
431 }
432
433 // DEPTH_STENCIL+UNSIGNED_INT_24_8
434 {
435 // Drop stencil.
436 constexpr uint32_t src[] = {EncodeNormUint<24>(srcVals[0]) << 8};
437 ZeroAndCopy(srcBuffer, src);
438
439 fnTest({GL_DEPTH24_STENCIL8, GL_DEPTH_STENCIL, GL_UNSIGNED_INT_24_8}, {1, 0, 0, 0});
440 }
441
442 if (getClientMajorVersion() < 3)
443 return;
444
445 constexpr char kVertShaderES3[] = R"(#version 300 es
446 void main()
447 {
448 gl_PointSize = 1.0;
449 gl_Position = vec4(0, 0, 0, 1);
450 })";
451 constexpr char kFragShader_Ints[] = R"(#version 300 es
452 precision mediump float;
453 uniform highp isampler2D uTex;
454 out vec4 oFragColor;
455
456 void main()
457 {
458 oFragColor = vec4(texture(uTex, vec2(0,0))) / 8.0;
459 })";
460 constexpr char kFragShader_Uints[] = R"(#version 300 es
461 precision mediump float;
462 uniform highp usampler2D uTex;
463 out vec4 oFragColor;
464
465 void main()
466 {
467 oFragColor = vec4(texture(uTex, vec2(0,0))) / 8.0;
468 })";
469 ANGLE_GL_PROGRAM(intsProg, kVertShaderES3, kFragShader_Ints);
470 ANGLE_GL_PROGRAM(uintsProg, kVertShaderES3, kFragShader_Uints);
471
472 // Non-normalized ints
473 glUseProgram(intsProg);
474
475 // RGBA_INTEGER+UNSIGNED_BYTE
476 {
477 constexpr uint8_t src[4] = {srcIntVals[0], srcIntVals[1], srcIntVals[2], srcIntVals[3]};
478 ZeroAndCopy(srcBuffer, src);
479
480 fnTest({GL_RGBA8I, GL_RGBA_INTEGER, GL_BYTE}, {1, 1, 1, 1});
481 fnTest({GL_RGB8I, GL_RGB_INTEGER, GL_BYTE}, {1, 1, 1, 1});
482 fnTest({GL_RG8I, GL_RG_INTEGER, GL_BYTE}, {1, 1, 1, 1});
483 fnTest({GL_R8I, GL_RED_INTEGER, GL_BYTE}, {1, 1, 1, 1});
484 }
485
486 // RGBA_INTEGER+UNSIGNED_SHORT
487 {
488 constexpr uint16_t src[4] = {srcIntVals[0], srcIntVals[1], srcIntVals[2], srcIntVals[3]};
489 ZeroAndCopy(srcBuffer, src);
490
491 fnTest({GL_RGBA16I, GL_RGBA_INTEGER, GL_SHORT}, {1, 1, 1, 1});
492 fnTest({GL_RGB16I, GL_RGB_INTEGER, GL_SHORT}, {1, 1, 1, 1});
493 fnTest({GL_RG16I, GL_RG_INTEGER, GL_SHORT}, {1, 1, 1, 1});
494 fnTest({GL_R16I, GL_RED_INTEGER, GL_SHORT}, {1, 1, 1, 1});
495 }
496
497 // RGBA_INTEGER+UNSIGNED_INT
498 {
499 constexpr uint32_t src[4] = {srcIntVals[0], srcIntVals[1], srcIntVals[2], srcIntVals[3]};
500 ZeroAndCopy(srcBuffer, src);
501
502 fnTest({GL_RGBA32I, GL_RGBA_INTEGER, GL_INT}, {1, 1, 1, 1});
503 fnTest({GL_RGB32I, GL_RGB_INTEGER, GL_INT}, {1, 1, 1, 1});
504 fnTest({GL_RG32I, GL_RG_INTEGER, GL_INT}, {1, 1, 1, 1});
505 fnTest({GL_R32I, GL_RED_INTEGER, GL_INT}, {1, 1, 1, 1});
506 }
507
508 // Non-normalized uints
509 glUseProgram(uintsProg);
510
511 // RGBA_INTEGER+UNSIGNED_BYTE
512 {
513 constexpr uint8_t src[4] = {srcIntVals[0], srcIntVals[1], srcIntVals[2], srcIntVals[3]};
514 ZeroAndCopy(srcBuffer, src);
515
516 fnTest({GL_RGBA8UI, GL_RGBA_INTEGER, GL_UNSIGNED_BYTE}, {1, 1, 1, 1});
517 fnTest({GL_RGB8UI, GL_RGB_INTEGER, GL_UNSIGNED_BYTE}, {1, 1, 1, 1});
518 fnTest({GL_RG8UI, GL_RG_INTEGER, GL_UNSIGNED_BYTE}, {1, 1, 1, 1});
519 fnTest({GL_R8UI, GL_RED_INTEGER, GL_UNSIGNED_BYTE}, {1, 1, 1, 1});
520 }
521
522 // RGBA_INTEGER+UNSIGNED_SHORT
523 {
524 constexpr uint16_t src[4] = {srcIntVals[0], srcIntVals[1], srcIntVals[2], srcIntVals[3]};
525 ZeroAndCopy(srcBuffer, src);
526
527 fnTest({GL_RGBA16UI, GL_RGBA_INTEGER, GL_UNSIGNED_SHORT}, {1, 1, 1, 1});
528 fnTest({GL_RGB16UI, GL_RGB_INTEGER, GL_UNSIGNED_SHORT}, {1, 1, 1, 1});
529 fnTest({GL_RG16UI, GL_RG_INTEGER, GL_UNSIGNED_SHORT}, {1, 1, 1, 1});
530 fnTest({GL_R16UI, GL_RED_INTEGER, GL_UNSIGNED_SHORT}, {1, 1, 1, 1});
531 }
532
533 // RGBA_INTEGER+UNSIGNED_INT
534 {
535 constexpr uint32_t src[4] = {srcIntVals[0], srcIntVals[1], srcIntVals[2], srcIntVals[3]};
536 ZeroAndCopy(srcBuffer, src);
537
538 fnTest({GL_RGBA32UI, GL_RGBA_INTEGER, GL_UNSIGNED_INT}, {1, 1, 1, 1});
539 fnTest({GL_RGB32UI, GL_RGB_INTEGER, GL_UNSIGNED_INT}, {1, 1, 1, 1});
540 fnTest({GL_RG32UI, GL_RG_INTEGER, GL_UNSIGNED_INT}, {1, 1, 1, 1});
541 fnTest({GL_R32UI, GL_RED_INTEGER, GL_UNSIGNED_INT}, {1, 1, 1, 1});
542 }
543
544 // RGBA_INTEGER+UNSIGNED_INT_2_10_10_10_REV
545 {
546 constexpr uint32_t src[] = {static_cast<uint32_t>(srcIntVals[0] << 0) |
547 static_cast<uint32_t>(srcIntVals[1] << 10) |
548 static_cast<uint32_t>(srcIntVals[2] << 20) |
549 static_cast<uint32_t>(srcIntVals[3] << 30)};
550 ZeroAndCopy(srcBuffer, src);
551
552 fnTest({GL_RGB10_A2UI, GL_RGBA_INTEGER, GL_UNSIGNED_INT_2_10_10_10_REV}, {1, 1, 1, 1});
553 }
554
555 // True floats
556 glUseProgram(floatsProg);
557
558 // RGBA+HALF_FLOAT
559 {
560 EncodeThenZeroAndCopy<R16G16B16A16F>(srcBuffer, srcVals);
561
562 fnTest({GL_RGBA16F, GL_RGBA, GL_HALF_FLOAT}, {1, 1, 1, 1});
563
564 fnTest({GL_RGB16F, GL_RGB, GL_HALF_FLOAT}, {1, 1, 1, 0});
565 fnTest({GL_R11F_G11F_B10F, GL_RGB, GL_HALF_FLOAT}, {1, 1, 1, 0});
566 fnTest({GL_RGB9_E5, GL_RGB, GL_HALF_FLOAT}, {1, 1, 1, 0});
567
568 fnTest({GL_RG16F, GL_RG, GL_HALF_FLOAT}, {1, 1, 0, 0});
569
570 fnTest({GL_R16F, GL_RED, GL_HALF_FLOAT}, {1, 0, 0, 0});
571
572 fnTest({GL_RGBA, GL_RGBA, GL_HALF_FLOAT_OES}, {1, 1, 1, 1});
573 fnTest({GL_RGB, GL_RGB, GL_HALF_FLOAT_OES}, {1, 1, 1, 0});
574 fnTest({GL_LUMINANCE_ALPHA, GL_LUMINANCE_ALPHA, GL_HALF_FLOAT_OES}, {1, 1, 1, 1});
575 fnTest({GL_LUMINANCE, GL_LUMINANCE, GL_HALF_FLOAT_OES}, {1, 1, 1, 0});
576 fnTest({GL_ALPHA, GL_ALPHA, GL_HALF_FLOAT_OES}, {0, 0, 0, 1});
577 }
578
579 // RGBA+FLOAT
580 {
581 ZeroAndCopy(srcBuffer, srcVals);
582
583 fnTest({GL_RGBA32F, GL_RGBA, GL_FLOAT}, {1, 1, 1, 1});
584 fnTest({GL_RGBA16F, GL_RGBA, GL_FLOAT}, {1, 1, 1, 1});
585
586 fnTest({GL_RGB32F, GL_RGB, GL_FLOAT}, {1, 1, 1, 0});
587 fnTest({GL_RGB16F, GL_RGB, GL_FLOAT}, {1, 1, 1, 0});
588 fnTest({GL_R11F_G11F_B10F, GL_RGB, GL_FLOAT}, {1, 1, 1, 0});
589 fnTest({GL_RGB9_E5, GL_RGB, GL_FLOAT}, {1, 1, 1, 0});
590
591 fnTest({GL_RG32F, GL_RG, GL_FLOAT}, {1, 1, 0, 0});
592 fnTest({GL_RG16F, GL_RG, GL_FLOAT}, {1, 1, 0, 0});
593
594 fnTest({GL_R32F, GL_RED, GL_FLOAT}, {1, 0, 0, 0});
595 fnTest({GL_R16F, GL_RED, GL_FLOAT}, {1, 0, 0, 0});
596 }
597
598 // UNSIGNED_INT_10F_11F_11F_REV
599 {
600 EncodeThenZeroAndCopy<R11G11B10F>(srcBuffer, srcVals);
601
602 fnTest({GL_R11F_G11F_B10F, GL_RGB, GL_UNSIGNED_INT_10F_11F_11F_REV}, {1, 1, 1, 0});
603 }
604
605 // UNSIGNED_INT_5_9_9_9_REV
606 {
607 EncodeThenZeroAndCopy<R9G9B9E5>(srcBuffer, srcVals);
608
609 fnTest({GL_RGB9_E5, GL_RGB, GL_UNSIGNED_INT_5_9_9_9_REV}, {1, 1, 1, 0});
610 }
611
612 // DEPTH_COMPONENT+FLOAT
613 {
614 // Skip stencil.
615 constexpr float src[] = {srcVals[0], 0};
616 ZeroAndCopy(srcBuffer, src);
617
618 fnTest({GL_DEPTH_COMPONENT32F, GL_DEPTH_COMPONENT, GL_FLOAT}, {1, 0, 0, 0});
619 fnTest({GL_DEPTH32F_STENCIL8, GL_DEPTH_STENCIL, GL_FLOAT_32_UNSIGNED_INT_24_8_REV},
620 {1, 0, 0, 0});
621 }
622
623 EXPECT_GL_NO_ERROR();
624 }
625
626 ANGLE_INSTANTIATE_TEST_ES2_AND_ES3(TextureUploadFormatTest);
627