[Mesa-dev] [PATCH 3/3] freedreno/ir3: cmdline compiler for glsl

Rob Clark robdclark at gmail.com
Sat May 14 20:10:59 UTC 2016


From: Rob Clark <robclark at freedesktop.org>

use glsl/libstandalone.la to add support for taking glsl src files (in
addition to .tgsi) as input.  Then glsl->nir and feed the result into
the ir3 backend as normal.

Signed-off-by: Rob Clark <robclark at freedesktop.org>
---
 src/gallium/drivers/freedreno/Makefile.am       |  2 +
 src/gallium/drivers/freedreno/ir3/ir3_cmdline.c | 89 +++++++++++++++++++++----
 2 files changed, 77 insertions(+), 14 deletions(-)

diff --git a/src/gallium/drivers/freedreno/Makefile.am b/src/gallium/drivers/freedreno/Makefile.am
index 9c0ccdf..1af8dec 100644
--- a/src/gallium/drivers/freedreno/Makefile.am
+++ b/src/gallium/drivers/freedreno/Makefile.am
@@ -37,6 +37,8 @@ ir3_compiler_LDADD = \
 	libfreedreno.la \
 	$(top_builddir)/src/gallium/auxiliary/libgallium.la \
 	$(top_builddir)/src/compiler/nir/libnir.la \
+	$(top_builddir)/src/compiler/glsl/libstandalone.la \
 	$(top_builddir)/src/util/libmesautil.la \
+	$(top_builddir)/src/mesa/libmesagallium.la \
 	$(GALLIUM_COMMON_LIB_DEPS) \
 	$(FREEDRENO_LIBS)
diff --git a/src/gallium/drivers/freedreno/ir3/ir3_cmdline.c b/src/gallium/drivers/freedreno/ir3/ir3_cmdline.c
index 47bcec4..0e4827c 100644
--- a/src/gallium/drivers/freedreno/ir3/ir3_cmdline.c
+++ b/src/gallium/drivers/freedreno/ir3/ir3_cmdline.c
@@ -44,6 +44,9 @@
 #include "instr-a3xx.h"
 #include "ir3.h"
 
+#include "compiler/glsl/standalone.h"
+#include "compiler/nir/glsl_to_nir.h"
+
 static void dump_info(struct ir3_shader_variant *so, const char *str)
 {
 	uint32_t *bin;
@@ -55,6 +58,47 @@ static void dump_info(struct ir3_shader_variant *so, const char *str)
 	free(bin);
 }
 
+int st_glsl_type_size(const struct glsl_type *type);
+
+static nir_shader *
+load_glsl(const char *filename, gl_shader_stage stage)
+{
+	static const struct standalone_options options = {
+			.glsl_version = 140,
+			.do_link = true,
+	};
+	struct gl_shader_program *prog;
+
+	prog = standalone_compile_shader(&options, 1, (char * const*)&filename);
+	if (!prog)
+		errx(1, "couldn't parse `%s'", filename);
+
+	nir_shader *nir = glsl_to_nir(prog, stage, ir3_get_compiler_options());
+
+	standalone_compiler_cleanup(prog);
+
+	/* required NIR passes: */
+	/* TODO cmdline args for some of the conditional lowering passes? */
+
+	NIR_PASS_V(nir, nir_lower_io_to_temporaries,
+			nir_shader_get_entrypoint(nir),
+			true, true);
+	NIR_PASS_V(nir, nir_lower_global_vars_to_local);
+	NIR_PASS_V(nir, nir_split_var_copies);
+	NIR_PASS_V(nir, nir_lower_var_copies);
+
+	NIR_PASS_V(nir, nir_split_var_copies);
+	NIR_PASS_V(nir, nir_lower_var_copies);
+	NIR_PASS_V(nir, nir_lower_io_types);
+
+	// TODO nir_assign_var_locations??
+
+	NIR_PASS_V(nir, nir_lower_system_values);
+	NIR_PASS_V(nir, nir_lower_io, nir_var_all, st_glsl_type_size);
+	NIR_PASS_V(nir, nir_lower_samplers, prog);
+
+	return nir;
+}
 
 static int
 read_file(const char *filename, void **ptr, size_t *size)
@@ -86,7 +130,7 @@ read_file(const char *filename, void **ptr, size_t *size)
 
 static void print_usage(void)
 {
-	printf("Usage: ir3_compiler [OPTIONS]... FILE\n");
+	printf("Usage: ir3_compiler [OPTIONS]... <file.tgsi | file.vert | file.frag>\n");
 	printf("    --verbose         - verbose compiler/debug messages\n");
 	printf("    --binning-pass    - generate binning pass shader (VERT)\n");
 	printf("    --color-two-side  - emulate two-sided color (FRAG)\n");
@@ -105,8 +149,6 @@ int main(int argc, char **argv)
 {
 	int ret = 0, n = 1;
 	const char *filename;
-	struct tgsi_token toks[65536];
-	struct tgsi_parse_context parse;
 	struct ir3_shader_variant v;
 	struct ir3_shader s;
 	struct ir3_shader_key key = {};
@@ -234,31 +276,50 @@ int main(int argc, char **argv)
 	if (fd_mesa_debug & FD_DBG_OPTMSGS)
 		debug_printf("%s\n", (char *)ptr);
 
-	if (!tgsi_text_translate(ptr, toks, ARRAY_SIZE(toks)))
-		errx(1, "could not parse `%s'", filename);
+	nir_shader *nir;
 
-	if (fd_mesa_debug & FD_DBG_OPTMSGS)
-		tgsi_dump(toks, 0);
+	char *ext = rindex(filename, '.');
+
+	if (strcmp(ext, ".tgsi") == 0) {
+		struct tgsi_token toks[65536];
+
+		if (!tgsi_text_translate(ptr, toks, ARRAY_SIZE(toks)))
+			errx(1, "could not parse `%s'", filename);
+
+		if (fd_mesa_debug & FD_DBG_OPTMSGS)
+			tgsi_dump(toks, 0);
+
+		nir = ir3_tgsi_to_nir(toks);
+		s.from_tgsi = true;
+	} else if (strcmp(ext, ".frag") == 0) {
+		nir = load_glsl(filename, MESA_SHADER_FRAGMENT);
+		s.from_tgsi = false;
+	} else if (strcmp(ext, ".vert") == 0) {
+		nir = load_glsl(filename, MESA_SHADER_FRAGMENT);
+		s.from_tgsi = false;
+	} else {
+		print_usage();
+		return -1;
+	}
 
-	nir_shader *nir = ir3_tgsi_to_nir(toks);
-	s.from_tgsi = true;
 	s.compiler = ir3_compiler_create(NULL, gpu_id);
 	s.nir = ir3_optimize_nir(&s, nir, NULL);
 
 	v.key = key;
 	v.shader = &s;
 
-	tgsi_parse_init(&parse, toks);
-	switch (parse.FullHeader.Processor.Processor) {
-	case PIPE_SHADER_FRAGMENT:
+	switch (nir->stage) {
+	case MESA_SHADER_FRAGMENT:
 		s.type = v.type = SHADER_FRAGMENT;
 		break;
-	case PIPE_SHADER_VERTEX:
+	case MESA_SHADER_VERTEX:
 		s.type = v.type = SHADER_VERTEX;
 		break;
-	case PIPE_SHADER_COMPUTE:
+	case MESA_SHADER_COMPUTE:
 		s.type = v.type = SHADER_COMPUTE;
 		break;
+	default:
+		errx(1, "unhandled shader stage: %d", nir->stage);
 	}
 
 	info = "NIR compiler";
-- 
2.5.5



More information about the mesa-dev mailing list