panfrost: Track point sprites in fragment shader key
authorAlyssa Rosenzweig <alyssa.rosenzweig@collabora.com>
Mon, 24 Jun 2019 18:01:05 +0000 (11:01 -0700)
committerAlyssa Rosenzweig <alyssa.rosenzweig@collabora.com>
Mon, 24 Jun 2019 19:56:16 +0000 (12:56 -0700)
In preparation for lowering point sprites, track them like we track
alpha testing state.

Signed-off-by: Alyssa Rosenzweig <alyssa.rosenzweig@collabora.com>
src/gallium/drivers/panfrost/pan_context.c
src/gallium/drivers/panfrost/pan_context.h

index ceea48c401a364c76a2a154a6a70c3264a34ebbe..1e3c0dccc79abd48b167e1852cf68aa8266beaa1 100644 (file)
@@ -1665,6 +1665,11 @@ panfrost_bind_rasterizer_state(
 
         ctx->rasterizer = hwcso;
         ctx->dirty |= PAN_DIRTY_RASTERIZER;
+
+        /* Point sprites are emulated */
+
+        if (ctx->rasterizer->base.sprite_coord_enable)
+                ctx->base.bind_fs_state(&ctx->base, ctx->fs);
 }
 
 static void *
@@ -1805,6 +1810,7 @@ panfrost_variant_matches(
                 struct panfrost_shader_state *variant,
                 enum pipe_shader_type type)
 {
+        struct pipe_rasterizer_state *rasterizer = &ctx->rasterizer->base;
         struct pipe_alpha_state *alpha = &ctx->depth_stencil->alpha;
 
         bool is_fragment = (type == PIPE_SHADER_FRAGMENT);
@@ -1823,6 +1829,22 @@ panfrost_variant_matches(
                         return false;
                 }
         }
+
+        if (is_fragment && rasterizer && (rasterizer->sprite_coord_enable |
+                                variant->point_sprite_mask)) {
+                /* Ensure the same varyings are turned to point sprites */
+                if (rasterizer->sprite_coord_enable != variant->point_sprite_mask)
+                        return false;
+
+                /* Ensure the orientation is correct */
+                bool upper_left =
+                        rasterizer->sprite_coord_mode ==
+                        PIPE_SPRITE_COORD_UPPER_LEFT;
+
+                if (variant->point_sprite_upper_left != upper_left)
+                        return false;
+        }
+
         /* Otherwise, we're good to go */
         return true;
 }
@@ -1863,10 +1885,21 @@ panfrost_bind_shader_state(
                 variant = variants->variant_count++;
                 assert(variants->variant_count < MAX_SHADER_VARIANTS);
 
-                variants->variants[variant].base = hwcso;
+                struct panfrost_shader_state *v =
+                        &variants->variants[variant];
+
+                v->base = hwcso;
 
-                if (type == PIPE_SHADER_FRAGMENT)
-                        variants->variants[variant].alpha_state = ctx->depth_stencil->alpha;
+                if (type == PIPE_SHADER_FRAGMENT) {
+                        v->alpha_state = ctx->depth_stencil->alpha;
+
+                        if (ctx->rasterizer) {
+                                v->point_sprite_mask = ctx->rasterizer->base.sprite_coord_enable;
+                                v->point_sprite_upper_left =
+                                        ctx->rasterizer->base.sprite_coord_mode ==
+                                        PIPE_SPRITE_COORD_UPPER_LEFT;
+                        }
+                }
 
                 /* Allocate the mapped descriptor ahead-of-time. */
                 struct panfrost_context *ctx = pan_context(pctx);
index 1f718bcd9c4fd048d42618d4c4f2afd30c9a54e5..fc8fc3c12914f0bd21a5e637092cfa1dd5a347f7 100644 (file)
@@ -258,6 +258,9 @@ struct panfrost_shader_state {
 
         /* Information on this particular shader variant */
         struct pipe_alpha_state alpha_state;
+
+        uint16_t point_sprite_mask;
+        unsigned point_sprite_upper_left : 1;
 };
 
 /* A collection of varyings (the CSO) */