[Mesa-dev] [PATCH 01/17] swrast: Directly map the stencil buffer in read_stencil_pixels.
Eric Anholt
eric at anholt.net
Tue Nov 1 16:17:26 PDT 2011
This avoids going through the wrapper that has to rewrite the data for
packed depth/stencil. This isn't done in _swrast_read_stencil_span
because we don't want to map/unmap for each span.
v2: Move the unpack code to format_unpack.c.
---
src/mesa/main/format_unpack.c | 58 +++++++++++++++++++++++++++++++++++++++++
src/mesa/main/format_unpack.h | 4 +++
src/mesa/swrast/s_readpix.c | 16 ++++++++---
3 files changed, 74 insertions(+), 4 deletions(-)
diff --git a/src/mesa/main/format_unpack.c b/src/mesa/main/format_unpack.c
index fbda031..6295238 100644
--- a/src/mesa/main/format_unpack.c
+++ b/src/mesa/main/format_unpack.c
@@ -1480,4 +1480,62 @@ _mesa_unpack_uint_z_row(gl_format format, GLuint n,
}
}
+static void
+unpack_ubyte_s_S8(const void *src, GLubyte *dst, GLuint n)
+{
+ memcpy(dst, src, n);
+}
+static void
+unpack_ubyte_s_Z24_S8(const void *src, GLubyte *dst, GLuint n)
+{
+ int i;
+ const GLuint *src32 = src;
+
+ for (i = 0; i < n; i++)
+ dst[i] = src32[i] & 0xff;
+}
+
+static void
+unpack_ubyte_s_S8_Z24(const void *src, GLubyte *dst, GLuint n)
+{
+ int i;
+ const GLuint *src32 = src;
+
+ for (i = 0; i < n; i++)
+ dst[i] = src32[i] >> 24;
+}
+
+static void
+unpack_ubyte_s_Z32_FLOAT_X24S8(const void *src, GLubyte *dst, GLuint n)
+{
+ int i;
+ const GLuint *src32 = src;
+
+ for (i = 0; i < n; i++)
+ dst[i] = src32[i * 2 + 1] & 0xff;
+}
+
+void
+_mesa_unpack_ubyte_stencil_row(gl_format format, GLuint n,
+ const void *src, GLubyte *dst)
+{
+ switch (format) {
+ case MESA_FORMAT_S8:
+ unpack_ubyte_s_S8(src, dst, n);
+ break;
+ case MESA_FORMAT_Z24_S8:
+ unpack_ubyte_s_Z24_S8(src, dst, n);
+ break;
+ case MESA_FORMAT_S8_Z24:
+ unpack_ubyte_s_S8_Z24(src, dst, n);
+ break;
+ case MESA_FORMAT_Z32_FLOAT_X24S8:
+ unpack_ubyte_s_Z32_FLOAT_X24S8(src, dst, n);
+ break;
+ default:
+ _mesa_problem(NULL, "bad format %s in _mesa_unpack_ubyte_s_row",
+ _mesa_get_format_name(format));
+ return;
+ }
+}
diff --git a/src/mesa/main/format_unpack.h b/src/mesa/main/format_unpack.h
index c37727d..2e00047 100644
--- a/src/mesa/main/format_unpack.h
+++ b/src/mesa/main/format_unpack.h
@@ -45,5 +45,9 @@ void
_mesa_unpack_uint_z_row(gl_format format, GLuint n,
const void *src, GLuint *dst);
+void
+_mesa_unpack_ubyte_stencil_row(gl_format format, GLuint n,
+ const void *src, GLubyte *dst);
+
#endif /* FORMAT_UNPACK_H */
diff --git a/src/mesa/swrast/s_readpix.c b/src/mesa/swrast/s_readpix.c
index 187c27e..6351ec1 100644
--- a/src/mesa/swrast/s_readpix.c
+++ b/src/mesa/swrast/s_readpix.c
@@ -142,8 +142,10 @@ read_stencil_pixels( struct gl_context *ctx,
const struct gl_pixelstore_attrib *packing )
{
struct gl_framebuffer *fb = ctx->ReadBuffer;
- struct gl_renderbuffer *rb = fb->_StencilBuffer;
+ struct gl_renderbuffer *rb = fb->Attachment[BUFFER_STENCIL].Renderbuffer;
GLint j;
+ GLubyte *map;
+ GLint stride;
if (!rb)
return;
@@ -151,18 +153,24 @@ read_stencil_pixels( struct gl_context *ctx,
/* width should never be > MAX_WIDTH since we did clipping earlier */
ASSERT(width <= MAX_WIDTH);
+ ctx->Driver.MapRenderbuffer(ctx, rb, x, y, width, height, GL_MAP_READ_BIT,
+ &map, &stride);
+
/* process image row by row */
- for (j=0;j<height;j++,y++) {
+ for (j = 0; j < height; j++) {
GLvoid *dest;
GLstencil stencil[MAX_WIDTH];
- _swrast_read_stencil_span(ctx, rb, width, x, y, stencil);
-
+ _mesa_unpack_ubyte_stencil_row(rb->Format, width, map, stencil);
dest = _mesa_image_address2d(packing, pixels, width, height,
GL_STENCIL_INDEX, type, j, 0);
_mesa_pack_stencil_span(ctx, width, type, dest, stencil, packing);
+
+ map += stride;
}
+
+ ctx->Driver.UnmapRenderbuffer(ctx, rb);
}
--
1.7.7
More information about the mesa-dev
mailing list