radeonsi: process TGSI property NEXT_SHADER
authorMarek Olšák <marek.olsak@amd.com>
Thu, 10 Mar 2016 12:29:12 +0000 (13:29 +0100)
committerMarek Olšák <marek.olsak@amd.com>
Sat, 19 Mar 2016 22:20:01 +0000 (23:20 +0100)
This allows compiling the main shader part as ES or LS.

If we get the correct hint, non-separable GLSL shaders no longer have to be
compiled as VS first, followed by LS or ES compiled on demand.

The result is that fewer shaders are compiled by piglit, but it doesn't
improve piglit running time.

Reviewed-by: Nicolai Hähnle <nicolai.haehnle@amd.com>
src/gallium/drivers/radeonsi/si_shader.c
src/gallium/drivers/radeonsi/si_state_shaders.c

index 8c1151aa493cb6f430fa3b94486ba9985b7e27dc..151615eb4e7057a982d1f82839b79851b5b624f5 100644 (file)
@@ -5897,12 +5897,15 @@ int si_shader_create(struct si_screen *sscreen, LLVMTargetMachineRef tm,
        struct si_shader *mainp = shader->selector->main_shader_part;
        int r;
 
-       /* LS and ES are always compiled on demand. */
+       /* LS, ES, VS are compiled on demand if the main part hasn't been
+        * compiled for that stage.
+        */
        if (!mainp ||
            (shader->selector->type == PIPE_SHADER_VERTEX &&
-            (shader->key.vs.as_es || shader->key.vs.as_ls)) ||
+            (shader->key.vs.as_es != mainp->key.vs.as_es ||
+             shader->key.vs.as_ls != mainp->key.vs.as_ls)) ||
            (shader->selector->type == PIPE_SHADER_TESS_EVAL &&
-            shader->key.tes.as_es)) {
+            shader->key.tes.as_es != mainp->key.tes.as_es)) {
                /* Monolithic shader (compiled as a whole, has many variants,
                 * may take a long time to compile).
                 */
index 5fe1f7960f3ccf8f210e1f72564745a29bb966eb..d69bb2e317ace3a17d426c0249b1c6c9aa240bc9 100644 (file)
@@ -1042,6 +1042,31 @@ static int si_shader_select(struct pipe_context *ctx,
        return si_shader_select_with_key(ctx, state, &key);
 }
 
+static void si_parse_next_shader_property(const struct tgsi_shader_info *info,
+                                         union si_shader_key *key)
+{
+       unsigned next_shader = info->properties[TGSI_PROPERTY_NEXT_SHADER];
+
+       switch (info->processor) {
+       case TGSI_PROCESSOR_VERTEX:
+               switch (next_shader) {
+               case TGSI_PROCESSOR_GEOMETRY:
+                       key->vs.as_es = 1;
+                       break;
+               case TGSI_PROCESSOR_TESS_CTRL:
+               case TGSI_PROCESSOR_TESS_EVAL:
+                       key->vs.as_ls = 1;
+                       break;
+               }
+               break;
+
+       case TGSI_PROCESSOR_TESS_EVAL:
+               if (next_shader == TGSI_PROCESSOR_GEOMETRY)
+                       key->tes.as_es = 1;
+               break;
+       }
+}
+
 static void *si_create_shader_selector(struct pipe_context *ctx,
                                       const struct pipe_shader_state *state)
 {
@@ -1167,6 +1192,7 @@ static void *si_create_shader_selector(struct pipe_context *ctx,
                        goto error;
 
                shader->selector = sel;
+               si_parse_next_shader_property(&sel->info, &shader->key);
 
                tgsi_binary = si_get_tgsi_binary(sel);
 
@@ -1202,6 +1228,7 @@ static void *si_create_shader_selector(struct pipe_context *ctx,
                union si_shader_key key;
 
                memset(&key, 0, sizeof(key));
+               si_parse_next_shader_property(&sel->info, &key);
 
                /* Set reasonable defaults, so that the shader key doesn't
                 * cause any code to be eliminated.