[Mesa-dev] [PATCH 41/45] st/nine: Use fast clears more often for MRTs

Axel Davy axel.davy at ens.fr
Fri Jan 29 08:09:05 PST 2016


This enables to use fast clears in the following
case:

pixel shader renders to 1 RT
4 RT bound
clear
new pixel shader bound that renders to 4 RTs

Previously the fast clear path wouldn't be hit,
because when trying the fast clear path,
the framebuffer state would be configured for 1 RT,
instead of 4.

Signed-off-by: Axel Davy <axel.davy at ens.fr>
Reviewed-by: Patrick Rudolph <siro at das-labor.org>
---
 src/gallium/state_trackers/nine/device9.c    |  2 +-
 src/gallium/state_trackers/nine/nine_state.c | 18 +++++++++---------
 src/gallium/state_trackers/nine/nine_state.h |  2 +-
 src/gallium/state_trackers/nine/swapchain9.c |  1 -
 4 files changed, 11 insertions(+), 12 deletions(-)

diff --git a/src/gallium/state_trackers/nine/device9.c b/src/gallium/state_trackers/nine/device9.c
index 06d7126..593f2b5 100644
--- a/src/gallium/state_trackers/nine/device9.c
+++ b/src/gallium/state_trackers/nine/device9.c
@@ -1923,7 +1923,7 @@ NineDevice9_Clear( struct NineDevice9 *This,
         Count = 0;
 #endif
 
-    nine_update_state_framebuffer(This);
+    nine_update_state_framebuffer_clear(This);
 
     if (Flags & D3DCLEAR_TARGET) bufs |= PIPE_CLEAR_COLOR;
     /* Ignore Z buffer if not bound */
diff --git a/src/gallium/state_trackers/nine/nine_state.c b/src/gallium/state_trackers/nine/nine_state.c
index f2d0665..46eb3dc 100644
--- a/src/gallium/state_trackers/nine/nine_state.c
+++ b/src/gallium/state_trackers/nine/nine_state.c
@@ -427,8 +427,8 @@ prepare_ps(struct NineDevice9 *device, uint8_t shader_changed)
 
 /* State preparation + State commit */
 
-static uint32_t
-update_framebuffer(struct NineDevice9 *device)
+static void
+update_framebuffer(struct NineDevice9 *device, bool is_clear)
 {
     struct pipe_context *pipe = device->pipe;
     struct nine_state *state = &device->state;
@@ -438,7 +438,8 @@ update_framebuffer(struct NineDevice9 *device)
     unsigned w = rt0->desc.Width;
     unsigned h = rt0->desc.Height;
     D3DMULTISAMPLE_TYPE nr_samples = rt0->desc.MultiSampleType;
-    unsigned mask = state->ps ? state->ps->rt_mask : 1;
+    unsigned ps_mask = state->ps ? state->ps->rt_mask : 1;
+    unsigned mask = is_clear ? 0xf : ps_mask;
     const int sRGB = state->rs[D3DRS_SRGBWRITEENABLE] ? 1 : 0;
 
     DBG("\n");
@@ -498,7 +499,8 @@ update_framebuffer(struct NineDevice9 *device)
 
     pipe->set_framebuffer_state(pipe, fb); /* XXX: cso ? */
 
-    return state->changed.group;
+    if (is_clear && state->rt_mask == ps_mask)
+        state->changed.group &= ~NINE_STATE_FB;
 }
 
 static void
@@ -934,16 +936,14 @@ validate_textures(struct NineDevice9 *device)
 }
 
 void
-nine_update_state_framebuffer(struct NineDevice9 *device)
+nine_update_state_framebuffer_clear(struct NineDevice9 *device)
 {
     struct nine_state *state = &device->state;
 
     validate_textures(device);
 
     if (state->changed.group & NINE_STATE_FB)
-        update_framebuffer(device);
-
-    state->changed.group &= ~NINE_STATE_FB;
+        update_framebuffer(device, TRUE);
 }
 
 boolean
@@ -977,7 +977,7 @@ nine_update_state(struct NineDevice9 *device)
 
     if (group & (NINE_STATE_COMMON | NINE_STATE_VS)) {
         if (group & NINE_STATE_FB)
-            group |= update_framebuffer(device); /* may set NINE_STATE_RASTERIZER */
+            update_framebuffer(device, FALSE);
         if (group & NINE_STATE_BLEND)
             prepare_blend(device);
         if (group & NINE_STATE_DSA)
diff --git a/src/gallium/state_trackers/nine/nine_state.h b/src/gallium/state_trackers/nine/nine_state.h
index 34bdd22..a4ec4e3 100644
--- a/src/gallium/state_trackers/nine/nine_state.h
+++ b/src/gallium/state_trackers/nine/nine_state.h
@@ -239,7 +239,7 @@ extern const uint32_t nine_render_states_vertex[(NINED3DRS_COUNT + 31) / 32];
 
 struct NineDevice9;
 
-void nine_update_state_framebuffer(struct NineDevice9 *);
+void nine_update_state_framebuffer_clear(struct NineDevice9 *);
 boolean nine_update_state(struct NineDevice9 *);
 
 void nine_state_restore_non_cso(struct NineDevice9 *device);
diff --git a/src/gallium/state_trackers/nine/swapchain9.c b/src/gallium/state_trackers/nine/swapchain9.c
index 5d05f1f..82d4173 100644
--- a/src/gallium/state_trackers/nine/swapchain9.c
+++ b/src/gallium/state_trackers/nine/swapchain9.c
@@ -854,7 +854,6 @@ NineSwapChain9_Present( struct NineSwapChain9 *This,
     ID3DPresent_WaitBufferReleased(This->present, This->present_handles[0]);
 
     This->base.device->state.changed.group |= NINE_STATE_FB;
-    nine_update_state_framebuffer(This->base.device);
 
     return hr;
 }
-- 
2.7.0



More information about the mesa-dev mailing list