Re: [Piglit] [PATCH] shader_runner: Add basic SSO support to shader runner
On Thu, 2015-12-03 at 17:41 +1100, Timothy Arceri wrote: > This sets up the basics for using SSO with shader runner. This will > only support vertex and fragment shaders but is easily extended. > > Example shader: > > [require] > GLSL >= 1.50 > > [vertex sso] Git commit ate the version and extensions #version 150 #extension GL_ARB_explicit_attrib_location: require #extension GL_ARB_separate_shader_objects: require here and for frag shader below. > > layout(location = 0) in vec4 piglit_vertex; > > layout(location = 2) out vec3 a; > layout(location = 3) out vec3 b; > > void main() > { > gl_Position = piglit_vertex; > a = vec3(0, 0, 1); > b = vec3(1, 0, 0); > } > > [fragment sso] > > layout(location = 0) out vec4 out_color; > > layout(location = 2) in vec3 b; /* should get vec3(0, 0, 1) */ > layout(location = 3) in vec3 a; /* should get vec3(1, 0, 0) */ > > void main() > { > out_color = vec4(cross(b, a), 1); > } > > [test] > draw rect -1 -1 2 2 > probe all rgb 0 1 0 > --- > tests/shaders/shader_runner.c | 78 > ++- > 1 file changed, 77 insertions(+), 1 deletion(-) > > diff --git a/tests/shaders/shader_runner.c > b/tests/shaders/shader_runner.c > index eeb1aac..6010ae2 100644 > --- a/tests/shaders/shader_runner.c > +++ b/tests/shaders/shader_runner.c > @@ -123,10 +123,12 @@ GLint shader_string_size; > const char *vertex_data_start = NULL; > const char *vertex_data_end = NULL; > GLuint prog; > +GLuint pipeline; > size_t num_vbo_rows = 0; > bool vbo_present = false; > bool link_ok = false; > bool prog_in_use = false; > +bool sso_in_use = false; > GLchar *prog_err_info = NULL; > GLuint vao = 0; > GLuint fbo = 0; > @@ -137,12 +139,14 @@ enum states { > requirements, > vertex_shader, > vertex_shader_passthrough, > + vertex_sso, > vertex_program, > tess_ctrl_shader, > tess_eval_shader, > geometry_shader, > geometry_layout, > fragment_shader, > + fragment_sso, > fragment_program, > compute_shader, > vertex_data, > @@ -480,6 +484,48 @@ compile_and_bind_program(GLenum target, const > char *start, int len) > prog_in_use = true; > } > > +void > +create_sso(GLenum target, const char *start, int len) > +{ > + GLuint prog; > + GLint ok; > + char *source; > + > + piglit_require_extension("GL_ARB_separate_shader_objects"); > + > + source = malloc(len + 1); > + memcpy(source, start, len); > + source[len] = 0; > + prog = glCreateShaderProgramv(target, 1, > + (const GLchar *const *) > ); > + > + glGetProgramiv(prog, GL_LINK_STATUS, ); > + if (ok) { > + link_ok = true; > + } else { > + GLint size; > + > + glGetProgramiv(prog, GL_INFO_LOG_LENGTH, ); > + prog_err_info = malloc(size); > + > + glGetProgramInfoLog(prog, size, NULL, > prog_err_info); > + > + return; > + } > + > + switch (target) { > + case GL_VERTEX_SHADER: > + glUseProgramStages(pipeline, GL_VERTEX_SHADER_BIT, > prog); > + break; > + case GL_FRAGMENT_SHADER: > + glUseProgramStages(pipeline, GL_FRAGMENT_SHADER_BIT, > prog); > + break; > + } > + > + sso_in_use = true; > + prog_in_use = true; > +} > + > /** > * Compare two values given a specified comparison operator > */ > @@ -846,6 +892,13 @@ leave_state(enum states state, const char *line) > compile_glsl(GL_VERTEX_SHADER); > break; > > + case vertex_sso: > + shader_string_size = line - shader_string; > + create_sso(GL_VERTEX_SHADER, > +shader_string, > +line - shader_string); > + break; > + > case vertex_program: > compile_and_bind_program(GL_VERTEX_PROGRAM_ARB, >shader_string, > @@ -875,6 +928,12 @@ leave_state(enum states state, const char *line) > compile_glsl(GL_FRAGMENT_SHADER); > break; > > + case fragment_sso: > + create_sso(GL_FRAGMENT_SHADER, > +shader_string, > +line - shader_string); > + break; > + > case fragment_program: > compile_and_bind_program(GL_FRAGMENT_PROGRAM_ARB, >shader_string, > @@ -1043,6 +1102,9 @@ process_test_script(const char *script_name) > } else if (string_match("[vertex program]", > line)) { > state = vertex_program; > shader_string = NULL; > + } else if (string_match("[vertex sso]", > line)) { > + state = vertex_sso; > + shader_string = NULL; > } else if
[Piglit] [PATCH] shader_runner: Add basic SSO support to shader runner
This sets up the basics for using SSO with shader runner. This will only support vertex and fragment shaders but is easily extended. Example shader: [require] GLSL >= 1.50 [vertex sso] layout(location = 0) in vec4 piglit_vertex; layout(location = 2) out vec3 a; layout(location = 3) out vec3 b; void main() { gl_Position = piglit_vertex; a = vec3(0, 0, 1); b = vec3(1, 0, 0); } [fragment sso] layout(location = 0) out vec4 out_color; layout(location = 2) in vec3 b; /* should get vec3(0, 0, 1) */ layout(location = 3) in vec3 a; /* should get vec3(1, 0, 0) */ void main() { out_color = vec4(cross(b, a), 1); } [test] draw rect -1 -1 2 2 probe all rgb 0 1 0 --- tests/shaders/shader_runner.c | 78 ++- 1 file changed, 77 insertions(+), 1 deletion(-) diff --git a/tests/shaders/shader_runner.c b/tests/shaders/shader_runner.c index eeb1aac..6010ae2 100644 --- a/tests/shaders/shader_runner.c +++ b/tests/shaders/shader_runner.c @@ -123,10 +123,12 @@ GLint shader_string_size; const char *vertex_data_start = NULL; const char *vertex_data_end = NULL; GLuint prog; +GLuint pipeline; size_t num_vbo_rows = 0; bool vbo_present = false; bool link_ok = false; bool prog_in_use = false; +bool sso_in_use = false; GLchar *prog_err_info = NULL; GLuint vao = 0; GLuint fbo = 0; @@ -137,12 +139,14 @@ enum states { requirements, vertex_shader, vertex_shader_passthrough, + vertex_sso, vertex_program, tess_ctrl_shader, tess_eval_shader, geometry_shader, geometry_layout, fragment_shader, + fragment_sso, fragment_program, compute_shader, vertex_data, @@ -480,6 +484,48 @@ compile_and_bind_program(GLenum target, const char *start, int len) prog_in_use = true; } +void +create_sso(GLenum target, const char *start, int len) +{ + GLuint prog; + GLint ok; + char *source; + + piglit_require_extension("GL_ARB_separate_shader_objects"); + + source = malloc(len + 1); + memcpy(source, start, len); + source[len] = 0; + prog = glCreateShaderProgramv(target, 1, + (const GLchar *const *) ); + + glGetProgramiv(prog, GL_LINK_STATUS, ); + if (ok) { + link_ok = true; + } else { + GLint size; + + glGetProgramiv(prog, GL_INFO_LOG_LENGTH, ); + prog_err_info = malloc(size); + + glGetProgramInfoLog(prog, size, NULL, prog_err_info); + + return; + } + + switch (target) { + case GL_VERTEX_SHADER: + glUseProgramStages(pipeline, GL_VERTEX_SHADER_BIT, prog); + break; + case GL_FRAGMENT_SHADER: + glUseProgramStages(pipeline, GL_FRAGMENT_SHADER_BIT, prog); + break; + } + + sso_in_use = true; + prog_in_use = true; +} + /** * Compare two values given a specified comparison operator */ @@ -846,6 +892,13 @@ leave_state(enum states state, const char *line) compile_glsl(GL_VERTEX_SHADER); break; + case vertex_sso: + shader_string_size = line - shader_string; + create_sso(GL_VERTEX_SHADER, + shader_string, + line - shader_string); + break; + case vertex_program: compile_and_bind_program(GL_VERTEX_PROGRAM_ARB, shader_string, @@ -875,6 +928,12 @@ leave_state(enum states state, const char *line) compile_glsl(GL_FRAGMENT_SHADER); break; + case fragment_sso: + create_sso(GL_FRAGMENT_SHADER, + shader_string, + line - shader_string); + break; + case fragment_program: compile_and_bind_program(GL_FRAGMENT_PROGRAM_ARB, shader_string, @@ -1043,6 +1102,9 @@ process_test_script(const char *script_name) } else if (string_match("[vertex program]", line)) { state = vertex_program; shader_string = NULL; + } else if (string_match("[vertex sso]", line)) { + state = vertex_sso; + shader_string = NULL; } else if (string_match("[vertex shader passthrough]", line)) { state = vertex_shader_passthrough; shader_string = @@ -1063,6 +1125,9 @@ process_test_script(const char *script_name) } else if (string_match("[fragment shader]", line)) { state = fragment_shader; shader_string = NULL; + } else