freedreno/a3xx: fix blend state corruption issue
[mesa.git] / src / gallium / drivers / freedreno / freedreno_context.h
index db37f9cb8a3f1c79f07fad911611d6ff41d32db1..a8abbca7a62e031246b917db145e5826c76a8af0 100644 (file)
@@ -38,6 +38,7 @@
 
 #include "freedreno_screen.h"
 #include "freedreno_gmem.h"
+#include "freedreno_util.h"
 
 struct fd_vertex_stateobj;
 
@@ -150,6 +151,20 @@ struct fd_context {
        struct fd_ringbuffer *ring;
        struct fd_ringmarker *draw_start, *draw_end;
 
+       /* Keep track if WAIT_FOR_IDLE is needed for registers we need
+        * to update via RMW:
+        */
+       struct {
+               bool need_wfi;
+               /* note: would be nicer to have in fd3_context, fd2_context,
+                * etc, because the registered modified via RMR differ across
+                * generation.  But as long as it is a small set of registers
+                * that might be more hassle than it's worth.
+                */
+               /* state for RB_RENDER_CONTROL: */
+               uint32_t rbrc_draw;
+       } rmw;
+
        struct pipe_scissor_state scissor;
 
        /* we don't have a disable/enable bit for scissor, so instead we keep
@@ -249,6 +264,23 @@ fd_supported_prim(struct fd_context *ctx, unsigned prim)
        return (1 << prim) & ctx->primtype_mask;
 }
 
+static INLINE void
+fd_reset_rmw_state(struct fd_context *ctx)
+{
+       ctx->rmw.need_wfi = true;
+       ctx->rmw.rbrc_draw = ~0;
+}
+
+/* emit before a RMW a WAIT_FOR_IDLE only if needed: */
+static inline void
+fd_rmw_wfi(struct fd_context *ctx, struct fd_ringbuffer *ring)
+{
+       if (ctx->rmw.need_wfi) {
+               OUT_WFI(ring);
+               ctx->rmw.need_wfi = false;
+       }
+}
+
 struct pipe_context * fd_context_init(struct fd_context *ctx,
                struct pipe_screen *pscreen, const uint8_t *primtypes,
                void *priv);