Module: Mesa
Branch: master
Commit: d3c1be530a9e13378b66fb1ff8760ba0faa1a260
URL:    
http://cgit.freedesktop.org/mesa/mesa/commit/?id=d3c1be530a9e13378b66fb1ff8760ba0faa1a260

Author: Marek Olšák <[email protected]>
Date:   Thu Mar  6 02:14:42 2014 +0100

r600g,radeonsi: move CMASK register values from r600_surface to r600_texture

When doing fast clear for single-sample color buffers for the first time,
a CMASK buffer has to be allocated and the CMASK state in all pipe_surfaces
referencing the color buffer must be updated. Updating all surfaces is kinda
silly, so let's move the values to r600_texture instead.

This is only for Evergreen and later. R600-R700 don't have fast clear.

Reviewed-by: Michel Dänzer <[email protected]>

---

 src/gallium/drivers/r600/evergreen_state.c    |   25 +++++++----------------
 src/gallium/drivers/r600/r600_blit.c          |   23 +--------------------
 src/gallium/drivers/radeon/r600_pipe_common.h |    9 +++++----
 src/gallium/drivers/radeon/r600_texture.c     |   27 +++++++++++++++++++++++--
 src/gallium/drivers/radeon/r600d_common.h     |    3 +++
 src/gallium/drivers/radeonsi/si_state.c       |   22 +++++++-------------
 6 files changed, 48 insertions(+), 61 deletions(-)

diff --git a/src/gallium/drivers/r600/evergreen_state.c 
b/src/gallium/drivers/r600/evergreen_state.c
index d0291ff..dca7c58 100644
--- a/src/gallium/drivers/r600/evergreen_state.c
+++ b/src/gallium/drivers/r600/evergreen_state.c
@@ -964,8 +964,6 @@ void evergreen_init_color_surface_rat(struct r600_context 
*rctx,
        util_range_add(&r600_resource(pipe_buffer)->valid_buffer_range,
                       0, pipe_buffer->width0);
 
-       surf->cb_color_cmask = surf->cb_color_base;
-       surf->cb_color_cmask_slice = 0;
        surf->cb_color_fmask = surf->cb_color_base;
        surf->cb_color_fmask_slice = 0;
 }
@@ -1133,9 +1131,6 @@ void evergreen_init_color_surface(struct r600_context 
*rctx,
        if (rtex->fmask.size) {
                color_info |= S_028C70_COMPRESSION(1);
        }
-       if (rtex->cmask.size) {
-               color_info |= S_028C70_FAST_CLEAR(1);
-       }
 
        base_offset = r600_resource_va(rctx->b.b.screen, pipe_tex);
 
@@ -1152,14 +1147,7 @@ void evergreen_init_color_surface(struct r600_context 
*rctx,
        } else {
                surf->cb_color_fmask = surf->cb_color_base;
        }
-       if (rtex->cmask.size) {
-               uint64_t va = r600_resource_va(rctx->b.b.screen, 
&rtex->cmask_buffer->b.b);
-               surf->cb_color_cmask = (va + rtex->cmask.offset) >> 8;
-       } else {
-               surf->cb_color_cmask = surf->cb_color_base;
-       }
        surf->cb_color_fmask_slice = 
S_028C88_TILE_MAX(rtex->fmask.slice_tile_max);
-       surf->cb_color_cmask_slice = 
S_028C80_TILE_MAX(rtex->cmask.slice_tile_max);
 
        surf->color_initialized = true;
 }
@@ -1547,6 +1535,8 @@ static void evergreen_emit_framebuffer_state(struct 
r600_context *rctx, struct r
        struct pipe_framebuffer_state *state = &rctx->framebuffer.state;
        unsigned nr_cbufs = state->nr_cbufs;
        unsigned i, tl, br;
+       struct r600_texture *tex = NULL;
+       struct r600_surface *cb = NULL;
 
        /* XXX support more colorbuffers once we need them */
        assert(nr_cbufs <= 8);
@@ -1555,10 +1545,9 @@ static void evergreen_emit_framebuffer_state(struct 
r600_context *rctx, struct r
 
        /* Colorbuffers. */
        for (i = 0; i < nr_cbufs; i++) {
-               struct r600_surface *cb = (struct r600_surface*)state->cbufs[i];
-               struct r600_texture *tex;
                unsigned reloc, cmask_reloc;
 
+               cb = (struct r600_surface*)state->cbufs[i];
                if (!cb) {
                        r600_write_context_reg(cs, R_028C70_CB_COLOR0_INFO + i 
* 0x3C,
                                               
S_028C70_FORMAT(V_028C70_COLOR_INVALID));
@@ -1587,11 +1576,11 @@ static void evergreen_emit_framebuffer_state(struct 
r600_context *rctx, struct r
                radeon_emit(cs, cb->cb_color_pitch);    /* 
R_028C64_CB_COLOR0_PITCH */
                radeon_emit(cs, cb->cb_color_slice);    /* 
R_028C68_CB_COLOR0_SLICE */
                radeon_emit(cs, cb->cb_color_view);     /* 
R_028C6C_CB_COLOR0_VIEW */
-               radeon_emit(cs, cb->cb_color_info);     /* 
R_028C70_CB_COLOR0_INFO */
+               radeon_emit(cs, cb->cb_color_info | tex->cb_color_info); /* 
R_028C70_CB_COLOR0_INFO */
                radeon_emit(cs, cb->cb_color_attrib);   /* 
R_028C74_CB_COLOR0_ATTRIB */
                radeon_emit(cs, cb->cb_color_dim);              /* 
R_028C78_CB_COLOR0_DIM */
-               radeon_emit(cs, cb->cb_color_cmask);    /* 
R_028C7C_CB_COLOR0_CMASK */
-               radeon_emit(cs, cb->cb_color_cmask_slice);      /* 
R_028C80_CB_COLOR0_CMASK_SLICE */
+               radeon_emit(cs, tex->cmask.base_address_reg);   /* 
R_028C7C_CB_COLOR0_CMASK */
+               radeon_emit(cs, tex->cmask.slice_tile_max);     /* 
R_028C80_CB_COLOR0_CMASK_SLICE */
                radeon_emit(cs, cb->cb_color_fmask);    /* 
R_028C84_CB_COLOR0_FMASK */
                radeon_emit(cs, cb->cb_color_fmask_slice); /* 
R_028C88_CB_COLOR0_FMASK_SLICE */
                radeon_emit(cs, tex->color_clear_value[0]); /* 
R_028C8C_CB_COLOR0_CLEAR_WORD0 */
@@ -1617,7 +1606,7 @@ static void evergreen_emit_framebuffer_state(struct 
r600_context *rctx, struct r
        /* set CB_COLOR1_INFO for possible dual-src blending */
        if (i == 1 && state->cbufs[0]) {
                r600_write_context_reg(cs, R_028C70_CB_COLOR0_INFO + 1 * 0x3C,
-                                      ((struct 
r600_surface*)state->cbufs[0])->cb_color_info);
+                                      cb->cb_color_info | tex->cb_color_info);
 
                if (!rctx->keep_tiling_flags) {
                        unsigned reloc = r600_context_bo_reloc(&rctx->b,
diff --git a/src/gallium/drivers/r600/r600_blit.c 
b/src/gallium/drivers/r600/r600_blit.c
index dc19b30..e0f3373 100644
--- a/src/gallium/drivers/r600/r600_blit.c
+++ b/src/gallium/drivers/r600/r600_blit.c
@@ -408,27 +408,6 @@ static void evergreen_set_clear_color(struct pipe_surface 
*cbuf,
        memcpy(clear_value, &uc, 2 * sizeof(uint32_t));
 }
 
-static void evergreen_check_alloc_cmask(struct pipe_context *ctx,
-                                        struct pipe_surface *cbuf)
-{
-        struct r600_context *rctx = (struct r600_context *)ctx;
-        struct r600_texture *tex = (struct r600_texture *)cbuf->texture;
-        struct r600_surface *surf = (struct r600_surface *)cbuf;
-
-        if (tex->cmask_buffer)
-                return;
-
-        r600_texture_init_cmask(&rctx->screen->b, tex);
-
-        /* update colorbuffer state bits */
-        if (tex->cmask_buffer != NULL) {
-                uint64_t va = r600_resource_va(rctx->b.b.screen, 
&tex->cmask_buffer->b.b);
-                surf->cb_color_cmask = va >> 8;
-                surf->cb_color_cmask_slice = 
S_028C80_TILE_MAX(tex->cmask.slice_tile_max);
-                surf->cb_color_info |= S_028C70_FAST_CLEAR(1);
-        }
-}
-
 static void r600_try_fast_color_clear(struct r600_context *rctx, unsigned 
*buffers,
                                      const union pipe_color_union *color)
 {
@@ -470,7 +449,7 @@ static void r600_try_fast_color_clear(struct r600_context 
*rctx, unsigned *buffe
                }
 
                /* ensure CMASK is enabled */
-               evergreen_check_alloc_cmask(&rctx->b.b, fb->cbufs[i]);
+               r600_texture_alloc_cmask_separate(&rctx->screen->b, tex);
                if (tex->cmask.size == 0) {
                        continue;
                }
diff --git a/src/gallium/drivers/radeon/r600_pipe_common.h 
b/src/gallium/drivers/radeon/r600_pipe_common.h
index 672097d..5808ec3 100644
--- a/src/gallium/drivers/radeon/r600_pipe_common.h
+++ b/src/gallium/drivers/radeon/r600_pipe_common.h
@@ -149,6 +149,7 @@ struct r600_cmask_info {
        unsigned size;
        unsigned alignment;
        unsigned slice_tile_max;
+       unsigned base_address_reg;
 };
 
 struct r600_texture {
@@ -166,6 +167,7 @@ struct r600_texture {
        struct r600_fmask_info          fmask;
        struct r600_cmask_info          cmask;
        struct r600_resource            *cmask_buffer;
+       unsigned                        cb_color_info; /* fast clear enable bit 
*/
        unsigned                        color_clear_value[2];
 
        /* Depth buffer compression and fast clear. */
@@ -197,8 +199,7 @@ struct r600_surface {
        unsigned cb_color_attrib;       /* EG and later */
        unsigned cb_color_fmask;        /* CB_COLORn_FMASK (EG and later) or 
CB_COLORn_FRAG (r600) */
        unsigned cb_color_fmask_slice;  /* EG and later */
-       unsigned cb_color_cmask;        /* CB_COLORn_CMASK (EG and later) or 
CB_COLORn_TILE (r600) */
-       unsigned cb_color_cmask_slice;  /* EG and later */
+       unsigned cb_color_cmask;        /* CB_COLORn_TILE (r600 only) */
        unsigned cb_color_mask;         /* R600 only */
        struct r600_resource *cb_buffer_fmask; /* Used for FMASK relocations. 
R600 only */
        struct r600_resource *cb_buffer_cmask; /* Used for CMASK relocations. 
R600 only */
@@ -425,8 +426,8 @@ void r600_texture_get_fmask_info(struct r600_common_screen 
*rscreen,
 void r600_texture_get_cmask_info(struct r600_common_screen *rscreen,
                                 struct r600_texture *rtex,
                                 struct r600_cmask_info *out);
-void r600_texture_init_cmask(struct r600_common_screen *rscreen,
-                            struct r600_texture *rtex);
+void r600_texture_alloc_cmask_separate(struct r600_common_screen *rscreen,
+                                      struct r600_texture *rtex);
 bool r600_init_flushed_depth_texture(struct pipe_context *ctx,
                                     struct pipe_resource *texture,
                                     struct r600_texture **staging);
diff --git a/src/gallium/drivers/radeon/r600_texture.c 
b/src/gallium/drivers/radeon/r600_texture.c
index 81f32c0..011efb0 100644
--- a/src/gallium/drivers/radeon/r600_texture.c
+++ b/src/gallium/drivers/radeon/r600_texture.c
@@ -442,11 +442,19 @@ static void r600_texture_allocate_cmask(struct 
r600_common_screen *rscreen,
 
        rtex->cmask.offset = align(rtex->size, rtex->cmask.alignment);
        rtex->size = rtex->cmask.offset + rtex->cmask.size;
+
+       if (rscreen->chip_class >= SI)
+               rtex->cb_color_info |= SI_S_028C70_FAST_CLEAR(1);
+       else
+               rtex->cb_color_info |= EG_S_028C70_FAST_CLEAR(1);
 }
 
-void r600_texture_init_cmask(struct r600_common_screen *rscreen,
-                            struct r600_texture *rtex)
+void r600_texture_alloc_cmask_separate(struct r600_common_screen *rscreen,
+                                      struct r600_texture *rtex)
 {
+       if (rtex->cmask_buffer)
+                return;
+
        assert(rtex->cmask.size == 0);
 
        r600_texture_get_cmask_info(rscreen, rtex, &rtex->cmask);
@@ -456,7 +464,17 @@ void r600_texture_init_cmask(struct r600_common_screen 
*rscreen,
                                   PIPE_USAGE_DEFAULT, rtex->cmask.size);
        if (rtex->cmask_buffer == NULL) {
                rtex->cmask.size = 0;
+               return;
        }
+
+       /* update colorbuffer state bits */
+       rtex->cmask.base_address_reg =
+               r600_resource_va(&rscreen->b, &rtex->cmask_buffer->b.b) >> 8;
+
+       if (rscreen->chip_class >= SI)
+               rtex->cb_color_info |= SI_S_028C70_FAST_CLEAR(1);
+       else
+               rtex->cb_color_info |= EG_S_028C70_FAST_CLEAR(1);
 }
 
 static unsigned si_texture_htile_alloc_size(struct r600_common_screen *rscreen,
@@ -567,6 +585,7 @@ r600_texture_create_object(struct pipe_screen *screen,
        struct r600_texture *rtex;
        struct r600_resource *resource;
        struct r600_common_screen *rscreen = (struct r600_common_screen*)screen;
+       uint64_t va;
 
        rtex = CALLOC_STRUCT(r600_texture);
        if (rtex == NULL)
@@ -633,6 +652,10 @@ r600_texture_create_object(struct pipe_screen *screen,
                                         rtex->cmask.offset, rtex->cmask.size, 
0xCCCCCCCC);
        }
 
+       /* Initialize the CMASK base register value. */
+       va = r600_resource_va(&rscreen->b, &rtex->resource.b.b);
+       rtex->cmask.base_address_reg = (va + rtex->cmask.offset) >> 8;
+
        if (rscreen->debug_flags & DBG_VM) {
                fprintf(stderr, "VM start=0x%"PRIu64"  end=0x%"PRIu64" | 
Texture %ix%ix%i, %i levels, %i samples, %s\n",
                        r600_resource_va(screen, &rtex->resource.b.b),
diff --git a/src/gallium/drivers/radeon/r600d_common.h 
b/src/gallium/drivers/radeon/r600d_common.h
index cd311c2..1172af0 100644
--- a/src/gallium/drivers/radeon/r600d_common.h
+++ b/src/gallium/drivers/radeon/r600d_common.h
@@ -189,6 +189,9 @@
 #define CM_R_028C18_PA_SC_AA_SAMPLE_LOCS_PIXEL_X0Y1_0 0x28c18
 #define CM_R_028C28_PA_SC_AA_SAMPLE_LOCS_PIXEL_X1Y1_0 0x28c28
 
+#define   EG_S_028C70_FAST_CLEAR(x)                       (((x) & 0x1) << 17)
+#define   SI_S_028C70_FAST_CLEAR(x)                       (((x) & 0x1) << 13)
+
 /*CIK+*/
 #define R_0300FC_CP_STRMOUT_CNTL                    0x0300FC
 
diff --git a/src/gallium/drivers/radeonsi/si_state.c 
b/src/gallium/drivers/radeonsi/si_state.c
index 6cb8984..b95e1e2 100644
--- a/src/gallium/drivers/radeonsi/si_state.c
+++ b/src/gallium/drivers/radeonsi/si_state.c
@@ -1655,10 +1655,6 @@ static void si_initialize_color_surface(struct 
si_context *sctx,
                }
        }
 
-       if (rtex->cmask.size) {
-               color_info |= S_028C70_FAST_CLEAR(1);
-       }
-
        offset += r600_resource_va(sctx->b.b.screen, surf->base.texture);
 
        surf->cb_color_base = offset >> 8;
@@ -1668,10 +1664,6 @@ static void si_initialize_color_surface(struct 
si_context *sctx,
        surf->cb_color_info = color_info;
        surf->cb_color_attrib = color_attrib;
 
-       if (rtex->cmask.size) {
-               surf->cb_color_cmask = (offset + rtex->cmask.offset) >> 8;
-               surf->cb_color_cmask_slice = 
S_028C80_TILE_MAX(rtex->cmask.slice_tile_max);
-       }
        if (rtex->fmask.size) {
                surf->cb_color_fmask = (offset + rtex->fmask.offset) >> 8;
                surf->cb_color_fmask_slice = 
S_028C88_TILE_MAX(rtex->fmask.slice_tile_max);
@@ -1908,12 +1900,12 @@ static void si_emit_framebuffer_state(struct si_context 
*sctx, struct r600_atom
        struct radeon_winsys_cs *cs = sctx->b.rings.gfx.cs;
        struct pipe_framebuffer_state *state = &sctx->framebuffer.state;
        unsigned i, nr_cbufs = state->nr_cbufs;
+       struct r600_texture *tex = NULL;
+       struct r600_surface *cb = NULL;
 
        /* Colorbuffers. */
        for (i = 0; i < nr_cbufs; i++) {
-               struct r600_surface *cb = (struct r600_surface*)state->cbufs[i];
-               struct r600_texture *tex;
-
+               cb = (struct r600_surface*)state->cbufs[i];
                if (!cb) {
                        r600_write_context_reg(cs, R_028C70_CB_COLOR0_INFO + i 
* 0x3C,
                                               
S_028C70_FORMAT(V_028C70_COLOR_INVALID));
@@ -1938,11 +1930,11 @@ static void si_emit_framebuffer_state(struct si_context 
*sctx, struct r600_atom
                radeon_emit(cs, cb->cb_color_pitch);    /* 
R_028C64_CB_COLOR0_PITCH */
                radeon_emit(cs, cb->cb_color_slice);    /* 
R_028C68_CB_COLOR0_SLICE */
                radeon_emit(cs, cb->cb_color_view);     /* 
R_028C6C_CB_COLOR0_VIEW */
-               radeon_emit(cs, cb->cb_color_info);     /* 
R_028C70_CB_COLOR0_INFO */
+               radeon_emit(cs, cb->cb_color_info | tex->cb_color_info); /* 
R_028C70_CB_COLOR0_INFO */
                radeon_emit(cs, cb->cb_color_attrib);   /* 
R_028C74_CB_COLOR0_ATTRIB */
                radeon_emit(cs, 0);                     /* R_028C78 unused */
-               radeon_emit(cs, cb->cb_color_cmask);    /* 
R_028C7C_CB_COLOR0_CMASK */
-               radeon_emit(cs, cb->cb_color_cmask_slice);      /* 
R_028C80_CB_COLOR0_CMASK_SLICE */
+               radeon_emit(cs, tex->cmask.base_address_reg);   /* 
R_028C7C_CB_COLOR0_CMASK */
+               radeon_emit(cs, tex->cmask.slice_tile_max);     /* 
R_028C80_CB_COLOR0_CMASK_SLICE */
                radeon_emit(cs, cb->cb_color_fmask);            /* 
R_028C84_CB_COLOR0_FMASK */
                radeon_emit(cs, cb->cb_color_fmask_slice);      /* 
R_028C88_CB_COLOR0_FMASK_SLICE */
                radeon_emit(cs, tex->color_clear_value[0]);     /* 
R_028C8C_CB_COLOR0_CLEAR_WORD0 */
@@ -1951,7 +1943,7 @@ static void si_emit_framebuffer_state(struct si_context 
*sctx, struct r600_atom
        /* set CB_COLOR1_INFO for possible dual-src blending */
        if (i == 1 && state->cbufs[0]) {
                r600_write_context_reg(cs, R_028C70_CB_COLOR0_INFO + 1 * 0x3C,
-                                      ((struct 
r600_surface*)state->cbufs[0])->cb_color_info);
+                                      cb->cb_color_info | tex->cb_color_info);
                i++;
        }
        for (; i < 8 ; i++) {

_______________________________________________
mesa-commit mailing list
[email protected]
http://lists.freedesktop.org/mailman/listinfo/mesa-commit

Reply via email to