xref: /aosp_15_r20/external/angle/src/tests/gl_tests/RobustClientMemoryTest.cpp (revision 8975f5c5ed3d1c378011245431ada316dfb6f244)
1 //
2 // Copyright 2016 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 // RobustClientMemoryTest.cpp : Tests of the GL_ANGLE_robust_client_memory extension.
8 
9 #include "test_utils/ANGLETest.h"
10 
11 #include "test_utils/gl_raii.h"
12 
13 namespace angle
14 {
15 
16 constexpr GLsizei kWindowSize = 128;
17 
18 class RobustClientMemoryTest : public ANGLETest<>
19 {
20   protected:
RobustClientMemoryTest()21     RobustClientMemoryTest()
22     {
23         setWindowWidth(kWindowSize);
24         setWindowHeight(kWindowSize);
25         setConfigRedBits(8);
26         setConfigGreenBits(8);
27         setConfigBlueBits(8);
28         setConfigAlphaBits(8);
29     }
30 
extensionsPresent() const31     bool extensionsPresent() const
32     {
33         if (!IsGLExtensionEnabled("GL_ANGLE_robust_client_memory"))
34         {
35             std::cout << "Test skipped because GL_ANGLE_robust_client_memory is not available.";
36             return false;
37         }
38 
39         return true;
40     }
41 };
42 
43 // Test basic usage and validation of glGetIntegervRobustANGLE
TEST_P(RobustClientMemoryTest,GetInteger)44 TEST_P(RobustClientMemoryTest, GetInteger)
45 {
46     if (!extensionsPresent())
47     {
48         return;
49     }
50 
51     // Verify that the robust and regular entry points return the same values
52     GLint resultRobust;
53     GLsizei length;
54     glGetIntegervRobustANGLE(GL_MAX_VERTEX_ATTRIBS, 1, &length, &resultRobust);
55     EXPECT_GL_NO_ERROR();
56     EXPECT_EQ(1, length);
57 
58     GLint resultRegular;
59     glGetIntegerv(GL_MAX_VERTEX_ATTRIBS, &resultRegular);
60     EXPECT_GL_NO_ERROR();
61     EXPECT_EQ(resultRegular, resultRobust);
62 
63     // Query a dynamic value
64     GLint numCompressedFormats;
65     glGetIntegervRobustANGLE(GL_NUM_COMPRESSED_TEXTURE_FORMATS, 1, &length, &numCompressedFormats);
66     ASSERT_GL_NO_ERROR();
67     EXPECT_EQ(1, length);
68 
69     if (numCompressedFormats > 0)
70     {
71         std::vector<GLint> resultBuf(numCompressedFormats * 2, 0);
72 
73         // Test when the bufSize is too low
74         glGetIntegervRobustANGLE(GL_COMPRESSED_TEXTURE_FORMATS, numCompressedFormats - 1, &length,
75                                  resultBuf.data());
76         EXPECT_GL_ERROR(GL_INVALID_OPERATION);
77         EXPECT_TRUE(std::all_of(resultBuf.begin(), resultBuf.end(),
78                                 [](GLint value) { return value == 0; }));
79 
80         // Make sure the GL doesn't touch the end of the buffer
81         glGetIntegervRobustANGLE(GL_COMPRESSED_TEXTURE_FORMATS,
82                                  static_cast<GLsizei>(resultBuf.size()), &length, resultBuf.data());
83         EXPECT_GL_NO_ERROR();
84         EXPECT_EQ(numCompressedFormats, length);
85         EXPECT_TRUE(std::none_of(resultBuf.begin(), resultBuf.begin() + length,
86                                  [](GLint value) { return value == 0; }));
87         EXPECT_TRUE(std::all_of(resultBuf.begin() + length, resultBuf.end(),
88                                 [](GLint value) { return value == 0; }));
89     }
90 
91     // Test with null length
92     glGetIntegervRobustANGLE(GL_MAX_VARYING_VECTORS, 1, nullptr, &resultRobust);
93     EXPECT_GL_NO_ERROR();
94 
95     glGetIntegervRobustANGLE(GL_MAX_VIEWPORT_DIMS, 1, nullptr, &resultRobust);
96     EXPECT_GL_ERROR(GL_INVALID_OPERATION);
97 
98     GLint maxViewportDims[2];
99     glGetIntegervRobustANGLE(GL_MAX_VIEWPORT_DIMS, 2, nullptr, maxViewportDims);
100     EXPECT_GL_NO_ERROR();
101 }
102 
103 // Test basic usage and validation of glTexImage2DRobustANGLE and glTexSubImage2DRobustANGLE
TEST_P(RobustClientMemoryTest,TexImage2D)104 TEST_P(RobustClientMemoryTest, TexImage2D)
105 {
106     if (!extensionsPresent())
107     {
108         return;
109     }
110     GLTexture tex;
111     glBindTexture(GL_TEXTURE_2D, tex);
112 
113     GLsizei dataDimension = 1024;
114     std::vector<GLubyte> rgbaData(dataDimension * dataDimension * 4);
115 
116     // Test the regular case
117     glTexImage2DRobustANGLE(GL_TEXTURE_2D, 0, GL_RGBA, dataDimension, dataDimension, 0, GL_RGBA,
118                             GL_UNSIGNED_BYTE, static_cast<GLsizei>(rgbaData.size()),
119                             rgbaData.data());
120     EXPECT_GL_NO_ERROR();
121 
122     glTexSubImage2DRobustANGLE(GL_TEXTURE_2D, 0, 0, 0, dataDimension, dataDimension, GL_RGBA,
123                                GL_UNSIGNED_BYTE, static_cast<GLsizei>(rgbaData.size()),
124                                rgbaData.data());
125     EXPECT_GL_NO_ERROR();
126 
127     // Test with a data size that is too small
128     glTexImage2DRobustANGLE(GL_TEXTURE_2D, 0, GL_RGBA, dataDimension, dataDimension, 0, GL_RGBA,
129                             GL_UNSIGNED_BYTE, static_cast<GLsizei>(rgbaData.size()) / 2,
130                             rgbaData.data());
131     EXPECT_GL_ERROR(GL_INVALID_OPERATION);
132 
133     glTexSubImage2DRobustANGLE(GL_TEXTURE_2D, 0, 0, 0, dataDimension, dataDimension, GL_RGBA,
134                                GL_UNSIGNED_BYTE, static_cast<GLsizei>(rgbaData.size()) / 2,
135                                rgbaData.data());
136     EXPECT_GL_ERROR(GL_INVALID_OPERATION);
137 
138     if (getClientMajorVersion() >= 3)
139     {
140         // Set an unpack parameter that would cause the driver to read past the end of the buffer
141         glPixelStorei(GL_UNPACK_ROW_LENGTH, dataDimension + 1);
142         glTexImage2DRobustANGLE(GL_TEXTURE_2D, 0, GL_RGBA, dataDimension, dataDimension, 0, GL_RGBA,
143                                 GL_UNSIGNED_BYTE, static_cast<GLsizei>(rgbaData.size()),
144                                 rgbaData.data());
145         EXPECT_GL_ERROR(GL_INVALID_OPERATION);
146     }
147 }
148 
149 // Test basic usage and validation of glReadPixelsRobustANGLE
TEST_P(RobustClientMemoryTest,ReadPixels)150 TEST_P(RobustClientMemoryTest, ReadPixels)
151 {
152     if (!extensionsPresent())
153     {
154         return;
155     }
156 
157     // TODO(ynovikov): Looks like a driver bug on Intel HD 530 http://anglebug.com/42260689
158     ANGLE_SKIP_TEST_IF(IsLinux() && IsIntel() && IsDesktopOpenGL());
159 
160     GLsizei dataDimension = 16;
161     std::vector<GLubyte> rgbaData(dataDimension * dataDimension * 4);
162 
163     // Test the regular case
164     GLsizei length = 0;
165     GLsizei width  = 0;
166     GLsizei height = 0;
167     glReadPixelsRobustANGLE(0, 0, dataDimension, dataDimension, GL_RGBA, GL_UNSIGNED_BYTE,
168                             static_cast<GLsizei>(rgbaData.size()), &length, &width, &height,
169                             rgbaData.data());
170     EXPECT_GL_NO_ERROR();
171     EXPECT_EQ(static_cast<GLsizei>(rgbaData.size()), length);
172     EXPECT_EQ(dataDimension, width);
173     EXPECT_EQ(dataDimension, height);
174 
175     // Test a case that would be partially clipped
176     glReadPixelsRobustANGLE(-1, kWindowSize - dataDimension + 3, dataDimension, dataDimension,
177                             GL_RGBA, GL_UNSIGNED_BYTE, static_cast<GLsizei>(rgbaData.size()),
178                             &length, &width, &height, rgbaData.data());
179     EXPECT_GL_NO_ERROR();
180     EXPECT_EQ(static_cast<GLsizei>(rgbaData.size()), length);
181     EXPECT_EQ(dataDimension - 1, width);
182     EXPECT_EQ(dataDimension - 3, height);
183 
184     // Test with a data size that is too small
185     glReadPixelsRobustANGLE(0, 0, dataDimension, dataDimension, GL_RGBA, GL_UNSIGNED_BYTE,
186                             static_cast<GLsizei>(rgbaData.size()) - 1, &length, nullptr, nullptr,
187                             rgbaData.data());
188     EXPECT_GL_ERROR(GL_INVALID_OPERATION);
189 
190     if (getClientMajorVersion() >= 3)
191     {
192         // Set a pack parameter that would cause the driver to write past the end of the buffer
193         glPixelStorei(GL_PACK_ROW_LENGTH, dataDimension + 1);
194         glReadPixelsRobustANGLE(0, 0, dataDimension, dataDimension, GL_RGBA, GL_UNSIGNED_BYTE,
195                                 static_cast<GLsizei>(rgbaData.size()), &length, nullptr, nullptr,
196                                 rgbaData.data());
197         EXPECT_GL_ERROR(GL_INVALID_OPERATION);
198     }
199 }
200 
201 // Use this to select which configurations (e.g. which renderer, which GLES major version) these
202 // tests should be run against.
203 ANGLE_INSTANTIATE_TEST_ES2_AND_ES3(RobustClientMemoryTest);
204 
205 }  // namespace angle
206