2 * Copyright © 2013 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
21 * DEALINGS IN THE SOFTWARE.
25 * \file read-to-pbo-after-clear.c
27 * On i965/gen7+, glReadPixels uses the hardware blitter when reading
28 * from the window system buffer to a PBO, provided that no format
29 * conversions need to be performed. This test verifies that fast
30 * color clears are properly resolved before this blit occurs.
32 * The test operates by painting the window system framebuffer red
33 * using a non-fast-clear technique (rendering a quad using a shader),
34 * and then clearing it to green using a fast clear. Then it reads
35 * from the window to a PBO using glReadPixels(), and then maps the
36 * PBO into CPU memory and verifies that it contains green.
39 #include "piglit-util-gl.h"
42 #define TEX_HEIGHT 512
44 PIGLIT_GL_TEST_CONFIG_BEGIN
45 config
.supports_gl_compat_version
= 11;
46 config
.window_width
= TEX_WIDTH
;
47 config
.window_height
= TEX_HEIGHT
;
48 config
.window_visual
= PIGLIT_GL_VISUAL_DOUBLE
| PIGLIT_GL_VISUAL_RGBA
;
49 config
.khr_no_error_support
= PIGLIT_NO_ERRORS
;
50 PIGLIT_GL_TEST_CONFIG_END
53 static const char *vs_text
=
56 " gl_Position = gl_Vertex;\n"
57 " gl_TexCoord[0] = gl_MultiTexCoord0;\n"
60 static const char *fs_text_paint_red
=
63 " gl_FragColor = vec4(1.0, 0.0, 0.0, 1.0);\n"
66 static const char *fs_text_sample
=
67 "uniform sampler2D samp;\n"
70 " gl_FragColor = texture2D(samp, gl_TexCoord[0].xy);\n"
73 static GLuint prog_paint_red
, prog_sample
, pbo
;
77 piglit_init(int argc
, char **argv
)
79 GLuint vs
, fs_paint_red
, fs_sample
;
82 piglit_require_gl_version(11);
83 piglit_require_GLSL_version(110);
84 piglit_require_extension("GL_ARB_pixel_buffer_object");
87 vs
= piglit_compile_shader_text(GL_VERTEX_SHADER
, vs_text
);
88 fs_paint_red
= piglit_compile_shader_text(GL_FRAGMENT_SHADER
,
90 prog_paint_red
= piglit_link_simple_program(vs
, fs_paint_red
);
92 piglit_report_result(PIGLIT_FAIL
);
93 fs_sample
= piglit_compile_shader_text(GL_FRAGMENT_SHADER
,
95 prog_sample
= piglit_link_simple_program(vs
, fs_sample
);
97 piglit_report_result(PIGLIT_FAIL
);
98 if (!piglit_check_gl_error(GL_NO_ERROR
))
99 piglit_report_result(PIGLIT_FAIL
);
102 glGenBuffers(1, &pbo
);
103 glBindBuffer(GL_PIXEL_PACK_BUFFER
, pbo
);
104 glBufferData(GL_PIXEL_PACK_BUFFER
, 4 * TEX_WIDTH
* TEX_HEIGHT
, NULL
,
106 glBindBuffer(GL_PIXEL_PACK_BUFFER
, 0);
108 if (!piglit_check_gl_error(GL_NO_ERROR
))
109 piglit_report_result(PIGLIT_FAIL
);
114 check_pbo_data(const GLubyte
*expected
)
117 const GLubyte
*data
= glMapBuffer(GL_PIXEL_PACK_BUFFER
, GL_READ_ONLY
);
118 for (i
= 0; i
< TEX_HEIGHT
; i
++) {
119 for (j
= 0; j
< TEX_WIDTH
; j
++) {
120 const GLubyte
*actual
= &data
[(i
* TEX_WIDTH
+ j
) * 4];
121 for (k
= 0; k
< 4; k
++) {
122 if (actual
[k
] != expected
[k
]) {
123 printf("Failure at (%d, %d):\n"
124 "Expected BGRA %d, %d, %d, %d\n"
125 "Got BGRA %d, %d, %d, %d\n",
127 expected
[0], expected
[1],
128 expected
[2], expected
[3],
129 actual
[0], actual
[1],
130 actual
[2], actual
[3]);
131 glUnmapBuffer(GL_PIXEL_PACK_BUFFER
);
137 glUnmapBuffer(GL_PIXEL_PACK_BUFFER
);
146 static const GLubyte green_ubytes
[] = { 0, 255, 0, 255 };
148 /* Paint the window red using a shader (not a fast clear). */
149 glUseProgram(prog_paint_red
);
150 glViewport(0, 0, TEX_WIDTH
, TEX_HEIGHT
);
151 piglit_draw_rect(-1, -1, 2, 2);
153 /* Clear the window to green; this will be optimized using a
154 * fast color clear if the hardware is capable of it.
156 glClearColor(0, 1, 0, 1);
157 glClear(GL_COLOR_BUFFER_BIT
);
159 /* Read directly from the window into a PBO using
160 * glReadPixels(). Note: we read using GL_UNSIGNED_BYTE and
161 * GL_BGRA since that's the case that causes the i965 driver
162 * to perform the read using a blit.
164 glBindBuffer(GL_PIXEL_PACK_BUFFER
, pbo
);
165 glReadPixels(0, 0, TEX_WIDTH
, TEX_HEIGHT
, GL_BGRA
,
166 GL_UNSIGNED_BYTE
, NULL
);
167 pass
= check_pbo_data(green_ubytes
) && pass
;
169 /* Note: piglit_present_results() will force a resolve to
170 * occur, so even if the test has failed, the window might
171 * appear green. To avoid confusing the user, clear the
172 * window to black before calling piglit_present_results().
174 glClearColor(0, 0, 0, 1);
175 glClear(GL_COLOR_BUFFER_BIT
);
177 if (!piglit_check_gl_error(GL_NO_ERROR
))
180 piglit_present_results();
181 return pass
? PIGLIT_PASS
: PIGLIT_FAIL
;