2 * Copyright © 2012 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
24 #include "piglit-fbo.h"
25 using namespace piglit_util_fbo
;
28 * \file polygon-stipple.cpp
30 * This test case just verifies the functionality of polygon stipple in
31 * multisample FBO and assumes that MSAA accuracy test already passes.
32 * Polygon stipple is expected to work exactly the same way on multisample
33 * FBO as it works on a single sample FBO.
35 * This test operates by drawing a test pattern with GL_POLYGON_STIPPLE
36 * enabled. Test pattern is first drawn in a single sample FBO to generate
37 * a reference image in right half of default framebuffer.
39 * Draw the same test pattern in multisample buffer with GL_POLYGON_STIPPLE
40 * enabled. Blit it in to left half of window system framebuffer.
41 * This is the test image.
43 * Verify the accuracy of polygon stippling in multisample buffer by
44 * comparing the two halves of default framebuffer.
47 PIGLIT_GL_TEST_CONFIG_BEGIN
49 config
.supports_gl_compat_version
= 10;
51 config
.window_width
= 512;
52 config
.window_height
= 256;
53 config
.window_visual
= PIGLIT_GL_VISUAL_DOUBLE
| PIGLIT_GL_VISUAL_RGBA
;
54 config
.khr_no_error_support
= PIGLIT_NO_ERRORS
;
56 PIGLIT_GL_TEST_CONFIG_END
58 const int pattern_width
= 256; const int pattern_height
= 256;
60 static Fbo ms_fbo
, resolve_fbo
;
61 static GLint num_samples
;
62 static GLbitfield buffer_to_test
;
64 static const float bg_color
[4] =
67 static const float color
[4][4] = {
75 {0.0, 1.0, 1.0, 1.0} };
78 static GLint color_loc
;
79 static GLint depth_loc
;
81 static GLubyte stipple_pattern
[] =
83 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
84 0xc0, 0x00, 0x00, 0x03, 0xc0, 0x00, 0x00, 0x03,
85 0xcf, 0xff, 0xff, 0xf3, 0xcf, 0xff, 0xff, 0xf3,
86 0xcc, 0x00, 0x00, 0x33, 0xcc, 0x00, 0x00, 0x33,
87 0xcc, 0xff, 0xff, 0x33, 0xcc, 0xff, 0xff, 0x33,
88 0xcc, 0xc0, 0x03, 0x33, 0xcc, 0xc0, 0x03, 0x33,
89 0xcc, 0xcf, 0xf3, 0x33, 0xcc, 0xcf, 0xf3, 0x33,
90 0xcc, 0xcf, 0xf3, 0x33, 0xcc, 0xcf, 0xf3, 0x33,
91 0xcc, 0xcf, 0xf3, 0x33, 0xcc, 0xcf, 0xf3, 0x33,
92 0xcc, 0xcf, 0xf3, 0x33, 0xcc, 0xcf, 0xf3, 0x33,
93 0xcc, 0xc0, 0x03, 0x33, 0xcc, 0xc0, 0x03, 0x33,
94 0xcc, 0xff, 0xff, 0x33, 0xcc, 0xff, 0xff, 0x33,
95 0xcc, 0x00, 0x00, 0x33, 0xcc, 0x00, 0x00, 0x33,
96 0xcf, 0xff, 0xff, 0xf3, 0xcf, 0xff, 0xff, 0xf3,
97 0xc0, 0x00, 0x00, 0x03, 0xc0, 0x00, 0x00, 0x03,
98 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
101 static const char *vert
=
103 "attribute vec2 pos;\n"
104 "uniform float depth;\n"
107 " vec4 eye_pos = gl_ModelViewProjectionMatrix * vec4(pos, 0.0, 1.0);\n"
108 " gl_Position = vec4(eye_pos.xy, depth, 1.0);\n"
111 static const char *frag
=
113 "uniform vec4 color;\n"
116 " gl_FragColor = color;\n"
122 /* Compile program */
123 GLint vs
= piglit_compile_shader_text(GL_VERTEX_SHADER
, vert
);
124 GLint fs
= piglit_compile_shader_text(GL_FRAGMENT_SHADER
, frag
);
125 prog
= piglit_link_simple_program(vs
, fs
);
127 if (!piglit_link_check_status(prog
)) {
128 piglit_report_result(PIGLIT_FAIL
);
131 glBindAttribLocation(prog
, 0, "pos");
132 glEnableVertexAttribArray(0);
134 /* Set up uniforms */
136 color_loc
= glGetUniformLocation(prog
, "color");
137 depth_loc
= glGetUniformLocation(prog
, "depth");
143 float vertex_data
[10][2] = {
145 { 0, pattern_height
},
146 { pattern_width
/ 4, pattern_height
},
147 { pattern_width
/ 4, 0 },
148 { pattern_width
/ 2, pattern_height
},
149 { pattern_width
/ 2, 0 },
150 { 3 * pattern_width
/ 4, pattern_height
},
151 { 3 * pattern_width
/ 4, 0 },
152 { pattern_width
, pattern_height
},
153 { pattern_width
, 0 },
156 unsigned int indices
[24] = {0, 1, 2, 0, 2, 3,
161 glClearColor(bg_color
[0], bg_color
[1],
162 bg_color
[2], bg_color
[3]);
163 glClear(buffer_to_test
);
165 glVertexAttribPointer(0, 2, GL_FLOAT
, GL_FALSE
, sizeof(vertex_data
[0]),
166 (void *) vertex_data
);
167 glUniform1f(depth_loc
, 0.0);
169 for (int i
= 0; i
< 4; ++i
) {
170 glUniform4fv(color_loc
, 1, color
[i
]);
171 glDrawElements(GL_TRIANGLES
, 6, GL_UNSIGNED_INT
,
172 (void *) (indices
+ 6 * i
));
177 test_polygon_stipple()
180 glBindFramebuffer(GL_DRAW_FRAMEBUFFER
, ms_fbo
.handle
);
183 /* Blit ms_fbo to resolve_fbo to resolve multisample buffer */
184 glBindFramebuffer(GL_READ_FRAMEBUFFER
, ms_fbo
.handle
);
185 glBindFramebuffer(GL_DRAW_FRAMEBUFFER
, resolve_fbo
.handle
);
186 glBlitFramebuffer(0, 0, pattern_width
, pattern_height
,
187 0, 0, pattern_width
, pattern_height
,
188 buffer_to_test
, GL_NEAREST
);
190 /* Blit resolve_fbo to the left half of window system framebuffer.
191 * This is the test image.
193 glBindFramebuffer(GL_READ_FRAMEBUFFER
, resolve_fbo
.handle
);
194 glBindFramebuffer(GL_DRAW_FRAMEBUFFER
, piglit_winsys_fbo
);
195 glBlitFramebuffer(0, 0, pattern_width
, pattern_height
,
196 0, 0, pattern_width
, pattern_height
,
197 buffer_to_test
, GL_NEAREST
);
199 /* Check that the left and right halves of the screen match */
200 glBindFramebuffer(GL_READ_FRAMEBUFFER
, piglit_winsys_fbo
);
201 result
= piglit_probe_rect_halves_equal_rgba(0, 0, piglit_width
,
205 glBindFramebuffer(GL_DRAW_FRAMEBUFFER
, piglit_winsys_fbo
);
206 result
= piglit_check_gl_error(GL_NO_ERROR
) && result
;
211 print_usage_and_exit(char *prog_name
)
213 printf("Usage: %s <num_samples>\n", prog_name
);
214 piglit_report_result(PIGLIT_FAIL
);
218 piglit_init(int argc
, char **argv
)
221 print_usage_and_exit(argv
[0]);
224 num_samples
= strtol(argv
[1], &endptr
, 0);
225 if (endptr
!= argv
[1] + strlen(argv
[1]))
226 print_usage_and_exit(argv
[0]);
229 piglit_require_gl_version(21);
230 piglit_require_extension("GL_ARB_framebuffer_object");
231 piglit_require_extension("GL_ARB_vertex_array_object");
233 piglit_ortho_projection(pattern_width
, pattern_height
, GL_TRUE
);
235 /* Skip the test if num_samples > GL_MAX_SAMPLES */
237 glGetIntegerv(GL_MAX_SAMPLES
, &max_samples
);
238 if (num_samples
> max_samples
)
239 piglit_report_result(PIGLIT_SKIP
);
241 ms_fbo
.setup(FboConfig(num_samples
, pattern_width
, pattern_height
));
242 resolve_fbo
.setup(FboConfig(0, pattern_width
, pattern_height
));
244 buffer_to_test
= GL_COLOR_BUFFER_BIT
;
246 glEnable(GL_POLYGON_STIPPLE
);
247 glPolygonStipple(stipple_pattern
);
255 glClearColor(0.0, 0.0, 0.0, 1.0);
256 glClear(GL_COLOR_BUFFER_BIT
);
258 /* Draw test pattern in single sample resolve_fbo with GL_POLYGON_STIPPLE
261 glBindFramebuffer(GL_DRAW_FRAMEBUFFER
, resolve_fbo
.handle
);
262 resolve_fbo
.set_viewport();
265 /* Blit resolve_fbo to the right half of window system framebuffer. This
266 * is a reference image.
268 glBindFramebuffer(GL_READ_FRAMEBUFFER
, resolve_fbo
.handle
);
269 glBindFramebuffer(GL_DRAW_FRAMEBUFFER
, piglit_winsys_fbo
);
270 glBlitFramebuffer(0, 0, pattern_width
, pattern_height
,
271 pattern_width
, 0, 2 * pattern_width
, pattern_height
,
272 buffer_to_test
, GL_NEAREST
);
274 /* Test with multisample FBO and GL_POLYGON_STIPPLE enabled */
275 pass
= test_polygon_stipple() && pass
;
277 if (!piglit_automatic
&&
278 buffer_to_test
!= GL_DEPTH_BUFFER_BIT
)
279 piglit_present_results();
281 return pass
? PIGLIT_PASS
: PIGLIT_FAIL
;