llvmpipe: Simplify tile clears. Use pipe_fill_rect instead of scratch tile.
authorJosé Fonseca <jfonseca@vmware.com>
Fri, 21 Aug 2009 07:55:50 +0000 (08:55 +0100)
committerJosé Fonseca <jfonseca@vmware.com>
Sat, 29 Aug 2009 08:21:38 +0000 (09:21 +0100)
src/gallium/drivers/llvmpipe/lp_clear.c
src/gallium/drivers/llvmpipe/lp_tile_cache.c
src/gallium/drivers/llvmpipe/lp_tile_cache.h

index c3e62e823d29971a26e2dd68ee30bad711bfde13..7f0fb1f215604426d4eab06b620360bed5edf6e8 100644 (file)
@@ -75,7 +75,6 @@ llvmpipe_clear(struct pipe_context *pipe, unsigned buffers, const float *rgba,
    }
 
    if (buffers & PIPE_CLEAR_DEPTHSTENCIL) {
-      static const float zero[4] = { 0.0F, 0.0F, 0.0F, 0.0F };
       struct pipe_surface *ps = llvmpipe->framebuffer.zsbuf;
 
       cv = util_pack_z_stencil(ps->format, depth, stencil);
index 2aa3d091710e2a6f807fde810c8c89ab549d37d6..074d2dabb432f412185f57ee86919793b9e35b4c 100644 (file)
@@ -36,6 +36,7 @@
 #include "util/u_memory.h"
 #include "util/u_math.h"
 #include "util/u_tile.h"
+#include "util/u_rect.h"
 #include "lp_context.h"
 #include "lp_surface.h"
 #include "lp_texture.h"
@@ -197,51 +198,23 @@ lp_tile_cache_unmap_transfers(struct llvmpipe_tile_cache *tc)
 
 
 /**
- * Set pixels in a tile to the given clear color/value, float.
+ * Set a tile to a solid color.
  */
 static void
-clear_tile_rgba(struct llvmpipe_cached_tile *tile,
-                enum pipe_format format,
-                const float clear_value[4])
+clear_tile(struct llvmpipe_cached_tile *tile,
+           uint8_t clear_color[4])
 {
-   if (clear_value[0] == 0.0 &&
-       clear_value[1] == 0.0 &&
-       clear_value[2] == 0.0 &&
-       clear_value[3] == 0.0) {
-      memset(tile->data.color, 0, sizeof(tile->data.color));
+   if (clear_color[0] == clear_color[1] &&
+       clear_color[1] == clear_color[2] &&
+       clear_color[2] == clear_color[3]) {
+      memset(tile->color, clear_color[0], TILE_SIZE * TILE_SIZE * 4);
    }
    else {
-      uint8_t c[4];
-      uint x, y, i;
-      for (i = 0; i < 4; ++i)
-         c[i] = float_to_ubyte(clear_value[i]);
+      uint x, y, chan;
       for (y = 0; y < TILE_SIZE; y++)
          for (x = 0; x < TILE_SIZE; x++)
-            for (i = 0; i < 4; ++i)
-               TILE_PIXEL(tile->data.color, x, y, i) = c[i];
-   }
-}
-
-
-/**
- * Set a tile to a solid value/color.
- */
-static void
-clear_tile(struct llvmpipe_cached_tile *tile,
-           enum pipe_format format,
-           uint clear_value)
-{
-   uint i, j;
-
-   if (clear_value == 0) {
-      memset(tile->data.any, 0, 4 * TILE_SIZE * TILE_SIZE);
-   }
-   else {
-      for (i = 0; i < TILE_SIZE; i++) {
-         for (j = 0; j < TILE_SIZE; j++) {
-            tile->data.color32[i][j] = clear_value;
-         }
-      }
+            for (chan = 0; chan < 4; ++chan)
+               TILE_PIXEL(tile->color, x, y, chan) = clear_color[chan];
    }
 }
 
@@ -253,23 +226,33 @@ static void
 lp_tile_cache_flush_clear(struct llvmpipe_tile_cache *tc)
 {
    struct pipe_transfer *pt = tc->transfer;
+   struct pipe_screen *screen = pt->texture->screen;
    const uint w = tc->transfer->width;
    const uint h = tc->transfer->height;
    uint x, y;
    uint numCleared = 0;
 
-   /* clear the scratch tile to the clear value */
-   clear_tile(&tc->tile, pt->format, tc->clear_val);
-
    /* push the tile to all positions marked as clear */
    for (y = 0; y < h; y += TILE_SIZE) {
       for (x = 0; x < w; x += TILE_SIZE) {
          union tile_address addr = tile_address(x, y, 0, 0, 0);
 
          if (is_clear_flag_set(tc->clear_flags, addr)) {
-            pipe_put_tile_raw(pt,
-                              x, y, TILE_SIZE, TILE_SIZE,
-                              tc->tile.data.color32, 0/*STRIDE*/);
+            unsigned tw = TILE_SIZE;
+            unsigned th = TILE_SIZE;
+            void *dst;
+
+            if (pipe_clip_tile(x, y, &tw, &th, pt))
+               continue;
+
+            dst = screen->transfer_map(screen, pt);
+            assert(dst);
+            if(!dst)
+               continue;
+
+            pipe_fill_rect(dst, &pt->block, pt->stride,
+                           x, y, tw,  th,
+                           tc->clear_val);
 
             /* do this? */
             clear_clear_flag(tc->clear_flags, addr);
@@ -302,7 +285,7 @@ lp_flush_tile_cache(struct llvmpipe_tile_cache *tc)
             lp_put_tile_rgba_soa(pt,
                                  tile->addr.bits.x * TILE_SIZE,
                                  tile->addr.bits.y * TILE_SIZE,
-                                 tile->data.color);
+                                 tile->color);
             tile->addr.bits.invalid = 1;  /* mark as empty */
             inuse++;
          }
@@ -348,14 +331,14 @@ lp_find_cached_tile(struct llvmpipe_tile_cache *tc,
          lp_put_tile_rgba_soa(pt,
                               tile->addr.bits.x * TILE_SIZE,
                               tile->addr.bits.y * TILE_SIZE,
-                              tile->data.color);
+                              tile->color);
       }
 
       tile->addr = addr;
 
       if (is_clear_flag_set(tc->clear_flags, addr)) {
          /* don't get tile from framebuffer, just clear it */
-         clear_tile_rgba(tile, pt->format, tc->clear_color);
+         clear_tile(tile, tc->clear_color);
          clear_clear_flag(tc->clear_flags, addr);
       }
       else {
@@ -363,13 +346,13 @@ lp_find_cached_tile(struct llvmpipe_tile_cache *tc,
          lp_get_tile_rgba_soa(pt,
                               tile->addr.bits.x * TILE_SIZE,
                               tile->addr.bits.y * TILE_SIZE,
-                              tile->data.color);
+                              tile->color);
       }
    }
 
    tc->last_tile = tile;
 
-   return tile->data.color;
+   return tile->color;
 }
 
 
@@ -402,12 +385,11 @@ void
 lp_tile_cache_clear(struct llvmpipe_tile_cache *tc, const float *rgba,
                     uint clearValue)
 {
+   unsigned chan;
    uint pos;
 
-   tc->clear_color[0] = rgba[0];
-   tc->clear_color[1] = rgba[1];
-   tc->clear_color[2] = rgba[2];
-   tc->clear_color[3] = rgba[3];
+   for(chan = 0; chan < 4; ++chan)
+      tc->clear_color[chan] = float_to_ubyte(rgba[chan]);
 
    tc->clear_val = clearValue;
 
index f0c3feef9cae3d543594c9aa744a9d6900cc0eb2..f1869b0d2bfd9fee400b6ace52c9f63d910c5ff4 100644 (file)
@@ -58,14 +58,8 @@ union tile_address {
 struct llvmpipe_cached_tile
 {
    union tile_address addr;
-   union {
-
-      /** color in SOA format */
-      uint8_t ALIGN16_ATTRIB color[TILE_SIZE*TILE_SIZE*NUM_CHANNELS];
-
-      uint color32[TILE_SIZE][TILE_SIZE];
-      ubyte any[1];
-   } data;
+   /** color in SOA format */
+   uint8_t ALIGN16_ATTRIB color[TILE_SIZE*TILE_SIZE*NUM_CHANNELS];
 };
 
 #define NUM_ENTRIES 50
@@ -88,15 +82,13 @@ struct llvmpipe_tile_cache
 
    struct llvmpipe_cached_tile entries[NUM_ENTRIES];
    uint clear_flags[(MAX_WIDTH / TILE_SIZE) * (MAX_HEIGHT / TILE_SIZE) / 32];
-   float clear_color[4];  /**< for color bufs */
+   uint8_t clear_color[4];  /**< for color bufs */
    uint clear_val;        /**< for z+stencil, or packed color clear value */
 
    struct pipe_transfer *tex_trans;
    void *tex_trans_map;
    int tex_face, tex_level, tex_z;
 
-   struct llvmpipe_cached_tile tile;  /**< scratch tile for clears */
-
    struct llvmpipe_cached_tile *last_tile;  /**< most recently retrieved tile */
 };
 
@@ -159,7 +151,7 @@ lp_get_cached_tile(struct llvmpipe_tile_cache *tc,
    union tile_address addr = tile_address( x, y, 0, 0, 0 );
 
    if (tc->last_tile->addr.value == addr.value)
-      return &tc->last_tile->data.color;
+      return &tc->last_tile->color;
 
    return lp_find_cached_tile( tc, addr );
 }