2 * Copyright (C) 2019, 2020, 2021, 2022 Intel Corporation
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
25 /** @file depth-clear-precision-check.c
27 * Tests that glClearDepth store on gpu exactly the transferred values
28 * with different depth's values and with different depth formats.
31 #include "piglit-util-gl.h"
33 const struct piglit_subtest subtests
[];
34 enum piglit_result
test(void *data
);
35 static struct piglit_gl_test_config
*piglit_config
;
37 #define ftoh(x) (piglit_float_from_half(piglit_half_from_float(x)))
39 PIGLIT_GL_TEST_CONFIG_BEGIN
41 piglit_config
= &config
;
42 config
.subtests
= subtests
;
43 config
.supports_gl_compat_version
= 10;
44 config
.window_width
= 20;
45 config
.window_height
= 20;
46 config
.window_visual
= PIGLIT_GL_VISUAL_DOUBLE
;
47 config
.khr_no_error_support
= PIGLIT_NO_ERRORS
;
49 PIGLIT_GL_TEST_CONFIG_END
51 const struct piglit_subtest subtests
[] = {
56 (void *)GL_DEPTH_COMPONENT16
62 (void *)GL_DEPTH_COMPONENT24
68 (void *)GL_DEPTH_COMPONENT32
74 (void *)GL_DEPTH24_STENCIL8
80 (void *)GL_DEPTH_COMPONENT32F
86 (void *)GL_DEPTH32F_STENCIL8
92 static const char *vs_source
=
96 " gl_Position = gl_Vertex;\n"
99 static const char *fs_source
=
101 "uniform float depth;\n"
104 " gl_FragColor = vec4(0.0, 1.0, 0.0, 0.0);\n"
105 " gl_FragDepth = depth;\n"
109 * number of iteration must be below than all possible,
110 * because for big format (like 32bit) if testing every value,
111 * time of test approaches infinity. iteration_pow controls
112 * sampling rate, we test 2^iteration_pow number of values,
113 * independent of format and evenly chosen in all possible values
116 static const uint32_t iteration_pow
= 8;
119 depth_num_of_bits(uint32_t depth
)
122 case GL_DEPTH_COMPONENT16
: return 16;
123 case GL_DEPTH_COMPONENT24
: return 24;
124 case GL_DEPTH_COMPONENT32
: return 32;
125 case GL_DEPTH24_STENCIL8
: return 24;
126 case GL_DEPTH_COMPONENT32F
: return 32;
127 case GL_DEPTH32F_STENCIL8
: return 32;
133 check_color(float depth
)
136 static const GLfloat green
[] = {0.0, 1.0, 0.0, 1.0};
139 glClearColor(1.0, 0.0, 0.0, 1.0);
140 glClear(GL_DEPTH_BUFFER_BIT
| GL_COLOR_BUFFER_BIT
);
142 depth_location
= glGetUniformLocation(prog
, "depth");
143 glUniform1f(depth_location
, depth
);
145 piglit_draw_rect(-1, -1, 2, 2);
147 return piglit_probe_pixel_rgb(0, 0, green
);
155 GLenum depth_format
= (long unsigned)data
;
159 if (depth_format
== GL_DEPTH24_STENCIL8
)
160 if (!piglit_is_extension_supported(
161 "GL_EXT_packed_depth_stencil"))
164 if (depth_format
== GL_DEPTH_COMPONENT32F
||
165 depth_format
== GL_DEPTH32F_STENCIL8
)
166 if (!piglit_is_extension_supported(
167 "GL_ARB_depth_buffer_float"))
172 /* Create the FBO. */
173 glGenRenderbuffers(1, &db
);
174 glBindRenderbuffer(GL_RENDERBUFFER
, db
);
176 glRenderbufferStorage(GL_RENDERBUFFER
, depth_format
,
177 piglit_width
, piglit_height
);
179 glGenRenderbuffers(1, &cb
);
180 glBindRenderbuffer(GL_RENDERBUFFER
, cb
);
182 glRenderbufferStorage(GL_RENDERBUFFER
, GL_RGBA8
,
183 piglit_width
, piglit_height
);
185 glBindRenderbuffer(GL_RENDERBUFFER
, 0);
187 glGenFramebuffers(1, &fb
);
188 glBindFramebuffer(GL_FRAMEBUFFER
, fb
);
190 glFramebufferRenderbuffer(GL_FRAMEBUFFER
, GL_DEPTH_ATTACHMENT
,
191 GL_RENDERBUFFER
, db
);
193 glFramebufferRenderbuffer(GL_FRAMEBUFFER
, GL_COLOR_ATTACHMENT0
,
194 GL_RENDERBUFFER
, cb
);
196 status
= glCheckFramebufferStatus(GL_FRAMEBUFFER
);
198 if (status
== GL_FRAMEBUFFER_UNSUPPORTED
)
201 if (status
!= GL_FRAMEBUFFER_COMPLETE
) {
202 printf("FBO incomplete status %s\n",
203 piglit_get_gl_enum_name(status
));
209 glBindFramebuffer(GL_DRAW_FRAMEBUFFER
, fb
);
210 glEnable(GL_DEPTH_TEST
);
211 glDepthFunc(GL_EQUAL
);
213 uint32_t numOfBits
= depth_num_of_bits(depth_format
);
214 uint32_t maxStoreableValue
= (1l << numOfBits
) - 1;
215 uint32_t step
= 1 << (numOfBits
- iteration_pow
);
217 for (uint64_t depth
= 0; depth
< maxStoreableValue
; depth
+= step
) {
218 float fdepth
= depth
/ (float)maxStoreableValue
;
220 assert(maxStoreableValue
* fdepth
== depth
);
223 fdepth
= ftoh(depth
/ (float)maxStoreableValue
);
225 pass
= check_color(fdepth
);
228 printf("Testing format: %s.\n"
229 "Mismatch between value set with "
230 "glClearDepth and set in shader. "
232 piglit_get_gl_enum_name(depth_format
),
239 glDeleteRenderbuffers(1, &cb
);
240 glDeleteRenderbuffers(1, &db
);
241 glDeleteFramebuffers(1, &fb
);
243 if (!piglit_check_gl_error(GL_NO_ERROR
))
246 return pass
? PIGLIT_PASS
: PIGLIT_FAIL
;
252 enum piglit_result pass
= PIGLIT_SKIP
;
255 vs
= piglit_compile_shader_text(GL_VERTEX_SHADER
, vs_source
);
256 fs
= piglit_compile_shader_text(GL_FRAGMENT_SHADER
, fs_source
);
257 prog
= piglit_link_simple_program(vs
, fs
);
259 pass
= piglit_run_selected_subtests(piglit_config
->subtests
,
260 piglit_config
->selected_subtests
,
261 piglit_config
->num_selected_subtests
,
264 glDeleteProgram(prog
);
271 void piglit_init(int argc
, char **argv
)
273 piglit_require_extension("GL_ARB_framebuffer_object");