[Piglit] [PATCH] varying: Checks if driver can handle MAX_VARYING_FLOATS in mixed float, vec*.
Vincent Lejeune
vljn at ovi.com
Sat Feb 11 15:12:01 PST 2012
v2: - Rewrite the test, following Paul Berry recommandations.
---
tests/all.tests | 6 +
tests/shaders/CMakeLists.gl.txt | 1 +
tests/shaders/glsl-max-varyings-mixed.c | 330 +++++++++++++++++++++++++++++++
3 files changed, 337 insertions(+), 0 deletions(-)
create mode 100644 tests/shaders/glsl-max-varyings-mixed.c
diff --git a/tests/all.tests b/tests/all.tests
index d0f18b4..a787822 100644
--- a/tests/all.tests
+++ b/tests/all.tests
@@ -431,6 +431,12 @@ add_plain_test(shaders, 'glsl-fs-texturelod-01')
add_plain_test(shaders, 'glsl-fs-user-varying-ff')
add_plain_test(shaders, 'glsl-mat-attribute')
add_plain_test(shaders, 'glsl-max-varyings')
+shaders['glsl-max-varyings-mixed floats'] = PlainExecTest('glsl-max-varyings-mixed 1.0 0.0 0.0 0.0 -auto')
+shaders['glsl-max-varyings-mixed floats vec2s'] = PlainExecTest('glsl-max-varyings-mixed 0.5 0.5 0.0 0.0 -auto')
+shaders['glsl-max-varyings-mixed floats vec2s vec3s'] = PlainExecTest('glsl-max-varyings-mixed 0.3 0.3 0.3 0.0 -auto')
+shaders['glsl-max-varyings-mixed float vec3s full'] = PlainExecTest('glsl-max-varyings-mixed 0.0 1.0 0.0 -auto')
+shaders['glsl-max-varyings-mixed float vec2s vec3s vec4'] = PlainExecTest('glsl-max-varyings-mixed 0.25 0.25 0.25 0.25 -auto')
+shaders['glsl-max-varyings-mixed float vec2s vec3s vec4 full'] = PlainExecTest('glsl-max-varyings-mixed 0.25 0.25 0.25 -auto')
add_plain_test(shaders, 'glsl-orangebook-ch06-bump')
add_plain_test(shaders, 'glsl-routing')
add_plain_test(shaders, 'glsl-vs-arrays')
diff --git a/tests/shaders/CMakeLists.gl.txt b/tests/shaders/CMakeLists.gl.txt
index 9d72260..c606ecb 100644
--- a/tests/shaders/CMakeLists.gl.txt
+++ b/tests/shaders/CMakeLists.gl.txt
@@ -143,6 +143,7 @@ add_executable (vp-ignore-input vp-ignore-input.c)
add_executable (glsl-empty-vs-no-fs glsl-empty-vs-no-fs.c)
add_executable (glsl-mat-attribute glsl-mat-attribute.c)
add_executable (glsl-max-varyings glsl-max-varyings.c)
+add_executable (glsl-max-varyings-mixed glsl-max-varyings-mixed.c)
add_executable (glsl-useprogram-displaylist glsl-useprogram-displaylist.c)
add_executable (glsl-routing glsl-routing.c)
add_executable (shader_runner shader_runner.c)
diff --git a/tests/shaders/glsl-max-varyings-mixed.c b/tests/shaders/glsl-max-varyings-mixed.c
new file mode 100644
index 0000000..2a1b44c
--- /dev/null
+++ b/tests/shaders/glsl-max-varyings-mixed.c
@@ -0,0 +1,330 @@
+/*
+ * Copyright © 2010 Intel Corporation
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+ * IN THE SOFTWARE.
+ *
+ * Authors:
+ * Eric Anholt <eric at anholt.net>
+ * Vincent Lejeune <vljn at ovi.com>
+ *
+ */
+
+/** @file glsl-max-varyings-mixed.c
+ *
+ * Tests whether GL_MAX_VARYING_FLOATS varying components can be used when packed
+ * as vec4, vec3, vec2, or float. Drivers have to pack varyings to pass this test.
+ *
+ * This test takes 3 or 4 args : the ratio of float, vec2, vec3, vec4 components in the
+ * shaders. These are ratio because the max amount of components is hardware
+ * specific. If the float ratio is not set, floats varyings will fill varying components
+ * up to GL_MAX_VARYING_FLOATS.
+ */
+
+#include "piglit-util.h"
+
+int piglit_width = 24, piglit_height = 24;
+int piglit_window_mode = GLUT_RGB | GLUT_DOUBLE;
+
+
+enum varyings_type {
+ FLT = 0,
+ V2 = 1,
+ V3 = 2,
+ V4 = 3
+};
+
+const char* glsl_type_names[] = { "float", "vec2", "vec3", "vec4" };
+
+bool variable_float_varying_amount;
+float ratio[4];
+
+
+static void generate_varyings_decl(char* code, unsigned amounts[4])
+{
+ char temp[128];
+ unsigned index = 0, i, type;
+
+ for (type = 0; type < 4; type ++) {
+ for (i = 0; i < amounts[type]; i++) {
+ sprintf(temp, "varying %s v%d;\n", glsl_type_names[type], index);
+ strcat(code, temp);
+ index++;
+ }
+ }
+
+ return;
+}
+
+static void
+vs_write_varying(char *code, unsigned amounts[4])
+{
+ char temp[128];
+ unsigned index = 0, i;
+ float component_content = 0.;
+
+ for (i = 0; i < amounts[FLT]; i++) {
+ sprintf(temp," v%d = %f;\n", index, component_content);
+ strcat(code, temp);
+ index ++, component_content += 1.;
+ }
+ for (i = 0; i < amounts[V2]; i++) {
+ sprintf(temp," v%d = vec2(%f, %f);\n", index, component_content, component_content + 1.);
+ strcat(code, temp);
+ index ++, component_content += 2.;
+ }
+ for (i = 0; i < amounts[V3]; i++) {
+ sprintf(temp," v%d = vec3(%f, %f, %f);\n", index, component_content, component_content + 1., component_content + 2.);
+ strcat(code, temp);
+ index ++, component_content += 3.;
+ }
+ for (i = 0; i < amounts[V4]; i++) {
+ sprintf(temp," v%d = vec4(%f, %f, %f, %f);\n", index, component_content, component_content + 1, component_content + 2., component_content + 3.);
+ strcat(code, temp);
+ index ++, component_content += 4.;
+ }
+}
+
+/* Generate a VS that writes to amounts[type] varyings for each type.
+ */
+static GLint get_vs(unsigned amounts[4])
+{
+ char temp[128];
+ GLuint shader;
+ char *code;
+
+ code = malloc(2048 * 4);
+ code[0] = 0;
+
+ generate_varyings_decl(code, amounts);
+
+ sprintf(temp,
+ "attribute vec4 green;\n"
+ "attribute float v_zero;\n"
+ "void main()\n"
+ "{\n"
+ " gl_Position = (gl_ModelViewProjectionMatrix * \n"
+ " gl_Vertex);\n"
+ );
+ strcat(code, temp);
+
+ vs_write_varying(code, amounts);
+
+ sprintf(temp,
+ "}\n"
+ );
+ strcat(code, temp);
+
+ shader = piglit_compile_shader_text(GL_VERTEX_SHADER, code);
+ /* printf("%s\n", code); */
+ free(code);
+
+ return shader;
+}
+
+static void
+fs_read_varying(char *code, unsigned amounts[4])
+{
+ char temp[128];
+ unsigned index = 0, i;
+ float component_content = 0.;
+
+ for (i = 0; i < amounts[FLT]; i++) {
+ sprintf(temp," v%d == %f &&\n", index, component_content);
+ strcat(code, temp);
+ index ++, component_content += 1.;
+ }
+ for (i = 0; i < amounts[V2]; i++) {
+ sprintf(temp," v%d == vec2(%f, %f) &&\n", index, component_content, component_content + 1.);
+ strcat(code, temp);
+ index ++, component_content += 2.;
+ }
+ for (i = 0; i < amounts[V3]; i++) {
+ sprintf(temp," v%d == vec3(%f, %f, %f) &&\n", index, component_content, component_content + 1., component_content + 2.);
+ strcat(code, temp);
+ index ++, component_content += 3.;
+ }
+ for (i = 0; i < amounts[V4]; i++) {
+ sprintf(temp," v%d == vec4(%f, %f, %f,%f) &&\n", index, component_content, component_content + 1, component_content + 2., component_content + 3.);
+ strcat(code, temp);
+ index ++, component_content += 4.;
+ }
+}
+
+/* Generate a FS that compares each varying with
+ * the expected content.
+ */
+static GLint get_fs(unsigned amounts[4])
+{
+ GLuint shader;
+ char temp[2048];
+ char *code;
+
+ code = malloc(2048 * 4);
+ code[0] = 0;
+
+ generate_varyings_decl(code, amounts);
+
+ sprintf(temp,
+ "void main()\n"
+ "{\n"
+ " if ("
+ );
+ strcat(code, temp);
+
+ fs_read_varying(code, amounts);
+
+ sprintf(temp,
+ " 1.0 == 1.0)\n"
+ " gl_FragColor = vec4(0.0,1.0,0.0,1.0);\n"
+ " else \n"
+ " gl_FragColor = vec4(1.0,0.0,0.0,1.0);\n"
+ "}\n"
+ );
+ strcat(code, temp);
+ /* printf("%s\n", code); */
+ shader = piglit_compile_shader_text(GL_FRAGMENT_SHADER, code);
+ free(code);
+
+ return shader;
+}
+
+static void
+draw(unsigned amounts[4])
+{
+ GLuint prog, vs, fs;
+
+ float green[4][4] = { {0.0, 1.0, 0.0, 0.0},
+ {0.0, 1.0, 0.0, 0.0},
+ {0.0, 1.0, 0.0, 0.0},
+ {0.0, 1.0, 0.0, 0.0} };
+
+ glVertexAttribPointer(1, 4, GL_FLOAT, GL_FALSE, 4 * sizeof(float),
+ green);
+ glVertexAttribPointer(2, 1, GL_FLOAT, GL_FALSE, 4 * sizeof(float),
+ green);
+ glEnableVertexAttribArray(1);
+ glEnableVertexAttribArray(2);
+
+ vs = get_vs(amounts);
+ fs = get_fs(amounts);
+
+ prog = glCreateProgram();
+ glAttachShader(prog, vs);
+ glAttachShader(prog, fs);
+
+ glBindAttribLocation(prog, 1, "green");
+ glBindAttribLocation(prog, 2, "v_zero");
+
+ glLinkProgram(prog);
+ if (!piglit_link_check_status(prog))
+ piglit_report_result(PIGLIT_FAIL);
+
+ glUseProgram(prog);
+
+ piglit_draw_rect(12, 12, 10, 10);
+
+ glDeleteShader(vs);
+ glDeleteShader(fs);
+ glDeleteProgram(prog);
+
+}
+
+enum piglit_result
+ piglit_display(void)
+{
+ int max_components;
+ unsigned amounts[4];
+ float green[3] = {0.0, 1.0, 0.0};
+ GLboolean pass = GL_TRUE;
+
+ piglit_ortho_projection(piglit_width, piglit_height, GL_FALSE);
+
+ glGetIntegerv(GL_MAX_VARYING_FLOATS, &max_components);
+
+ //printf("GL_MAX_VARYING_FLOATS = %i\n", max_components);
+
+
+ amounts[V2] = (max_components * ratio[V2]) / 2;
+ amounts[V3] = (max_components * ratio[V3]) / 3;
+ amounts[V4] = (max_components * ratio[V4]) /4;
+ if (variable_float_varying_amount) {
+ amounts[FLT] = max_components - 2 * amounts[V2] - 3 * amounts[V3] - 4 * amounts[V4];
+ } else {
+ amounts[FLT] = max_components * ratio[FLT];
+ }
+
+
+ glClearColor(0.5, 0.5, 0.5, 0.5);
+ glClear(GL_COLOR_BUFFER_BIT);
+
+ draw(amounts);
+
+ pass = piglit_probe_rect_rgb(12, 12, 10, 10, green);
+
+ glutSwapBuffers();
+
+ if (!pass)
+ return PIGLIT_FAIL;
+ else
+ return PIGLIT_PASS;
+}
+
+void piglit_init(int argc, char **argv)
+{
+ unsigned i, j;
+
+ piglit_require_gl_version(20);
+
+ if (argc < 4) {
+ fprintf(stderr, "Not enough args.\n");
+ exit(1);
+ }
+
+ if (argc > 5) {
+ fprintf(stderr, "Too many args.\n");
+ exit(1);
+ }
+
+ if (argc == 4) {
+ variable_float_varying_amount = true;
+ ratio[FLT] = 0;
+ j = 1;
+ } else {
+ j = 0;
+ }
+
+ for (i = 1; i < argc; i++, j++) {
+ sscanf(argv[i], "%f",&ratio[j]);
+ }
+
+ for (i = 0; i < 4; i++) {
+ if (ratio[i] < 0) {
+ fprintf(stderr, "Ratio must be positive.\n");
+ exit(1);
+ }
+ }
+
+ if (ratio[FLT] + ratio[V2] + ratio[V3] + ratio[V4] > 1.0) {
+ fprintf(stderr, "Ratio are not normalised.\n");
+ exit(1);
+ }
+}
+
+
--
1.7.7
More information about the Piglit
mailing list