summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBrian <[email protected]>2008-02-11 10:59:40 -0700
committerBrian <[email protected]>2008-02-11 10:59:40 -0700
commitb61b1a295b13a0ff2cf98c8d07e62147d71c08b9 (patch)
treeac65a17d8ea7e4c4294d4caabbe13ad0007032b8
parent3d0fd8a6cf294d58df2d2ec4139192416a1a4078 (diff)
gallium: take pitch/stride into account in mipmap generation
-rw-r--r--src/mesa/main/mipmap.c85
-rw-r--r--src/mesa/main/mipmap.h2
-rw-r--r--src/mesa/state_tracker/st_gen_mipmap.c3
3 files changed, 57 insertions, 33 deletions
diff --git a/src/mesa/main/mipmap.c b/src/mesa/main/mipmap.c
index 721a227bb53..d3d19589518 100644
--- a/src/mesa/main/mipmap.c
+++ b/src/mesa/main/mipmap.c
@@ -447,23 +447,29 @@ make_1d_mipmap(GLenum datatype, GLuint comps, GLint border,
/**
- * XXX need to use the tex image's row stride!
+ * Strides are in bytes. If zero, it'll be computed as width * bpp.
*/
static void
make_2d_mipmap(GLenum datatype, GLuint comps, GLint border,
- GLint srcWidth, GLint srcHeight, const GLubyte *srcPtr,
- GLint dstWidth, GLint dstHeight, GLubyte *dstPtr)
+ GLint srcWidth, GLint srcHeight,
+ GLint srcRowStride, const GLubyte *srcPtr,
+ GLint dstWidth, GLint dstHeight,
+ GLint dstRowStride, GLubyte *dstPtr)
{
const GLint bpt = bytes_per_pixel(datatype, comps);
const GLint srcWidthNB = srcWidth - 2 * border; /* sizes w/out border */
const GLint dstWidthNB = dstWidth - 2 * border;
const GLint dstHeightNB = dstHeight - 2 * border;
- const GLint srcRowStride = bpt * srcWidth;
- const GLint dstRowStride = bpt * dstWidth;
const GLubyte *srcA, *srcB;
GLubyte *dst;
GLint row;
+ if (!srcRowStride)
+ srcRowStride = bpt * srcWidth;
+
+ if (!dstRowStride)
+ dstRowStride = bpt * dstWidth;
+
/* Compute src and dst pointers, skipping any border */
srcA = srcPtr + border * ((srcWidth + 1) * bpt);
if (srcHeight > 1)
@@ -535,8 +541,10 @@ make_2d_mipmap(GLenum datatype, GLuint comps, GLint border,
static void
make_3d_mipmap(GLenum datatype, GLuint comps, GLint border,
GLint srcWidth, GLint srcHeight, GLint srcDepth,
+ GLint srcRowStride,
const GLubyte *srcPtr,
GLint dstWidth, GLint dstHeight, GLint dstDepth,
+ GLint dstRowStride,
GLubyte *dstPtr)
{
const GLint bpt = bytes_per_pixel(datatype, comps);
@@ -548,7 +556,6 @@ make_3d_mipmap(GLenum datatype, GLuint comps, GLint border,
GLvoid *tmpRowA, *tmpRowB;
GLint img, row;
GLint bytesPerSrcImage, bytesPerDstImage;
- GLint bytesPerSrcRow, bytesPerDstRow;
GLint srcImageOffset, srcRowOffset;
(void) srcDepthNB; /* silence warnings */
@@ -566,8 +573,10 @@ make_3d_mipmap(GLenum datatype, GLuint comps, GLint border,
bytesPerSrcImage = srcWidth * srcHeight * bpt;
bytesPerDstImage = dstWidth * dstHeight * bpt;
- bytesPerSrcRow = srcWidth * bpt;
- bytesPerDstRow = dstWidth * bpt;
+ if (!srcRowStride)
+ srcRowStride = srcWidth * bpt;
+ if (!dstRowStride)
+ dstRowStride = dstWidth * bpt;
/* Offset between adjacent src images to be averaged together */
srcImageOffset = (srcDepth == dstDepth) ? 0 : bytesPerSrcImage;
@@ -591,13 +600,13 @@ make_3d_mipmap(GLenum datatype, GLuint comps, GLint border,
for (img = 0; img < dstDepthNB; img++) {
/* first source image pointer, skipping border */
const GLubyte *imgSrcA = srcPtr
- + (bytesPerSrcImage + bytesPerSrcRow + border) * bpt * border
+ + (bytesPerSrcImage + srcRowStride + border) * bpt * border
+ img * (bytesPerSrcImage + srcImageOffset);
/* second source image pointer, skipping border */
const GLubyte *imgSrcB = imgSrcA + srcImageOffset;
/* address of the dest image, skipping border */
GLubyte *imgDst = dstPtr
- + (bytesPerDstImage + bytesPerDstRow + border) * bpt * border
+ + (bytesPerDstImage + dstRowStride + border) * bpt * border
+ img * bytesPerDstImage;
/* setup the four source row pointers and the dest row pointer */
@@ -618,11 +627,11 @@ make_3d_mipmap(GLenum datatype, GLuint comps, GLint border,
do_row(datatype, comps, srcWidthNB, tmpRowA, tmpRowB,
dstWidthNB, dstImgRow);
/* advance to next rows */
- srcImgARowA += bytesPerSrcRow + srcRowOffset;
- srcImgARowB += bytesPerSrcRow + srcRowOffset;
- srcImgBRowA += bytesPerSrcRow + srcRowOffset;
- srcImgBRowB += bytesPerSrcRow + srcRowOffset;
- dstImgRow += bytesPerDstRow;
+ srcImgARowA += srcRowStride + srcRowOffset;
+ srcImgARowB += srcRowStride + srcRowOffset;
+ srcImgBRowA += srcRowStride + srcRowOffset;
+ srcImgBRowB += srcRowStride + srcRowOffset;
+ dstImgRow += dstRowStride;
}
}
@@ -632,12 +641,14 @@ make_3d_mipmap(GLenum datatype, GLuint comps, GLint border,
/* Luckily we can leverage the make_2d_mipmap() function here! */
if (border > 0) {
/* do front border image */
- make_2d_mipmap(datatype, comps, 1, srcWidth, srcHeight, srcPtr,
- dstWidth, dstHeight, dstPtr);
+ make_2d_mipmap(datatype, comps, 1, srcWidth, srcHeight, 0, srcPtr,
+ dstWidth, dstHeight, 0, dstPtr);
/* do back border image */
make_2d_mipmap(datatype, comps, 1, srcWidth, srcHeight,
+ 0,
srcPtr + bytesPerSrcImage * (srcDepth - 1),
dstWidth, dstHeight,
+ 0,
dstPtr + bytesPerDstImage * (dstDepth - 1));
/* do four remaining border edges that span the image slices */
if (srcDepth == dstDepth) {
@@ -653,9 +664,9 @@ make_3d_mipmap(GLenum datatype, GLuint comps, GLint border,
/* do border along [img][row=dstHeight-1][col=0] */
src = srcPtr + (img * 2 + 1) * bytesPerSrcImage
- + (srcHeight - 1) * bytesPerSrcRow;
+ + (srcHeight - 1) * srcRowStride;
dst = dstPtr + (img + 1) * bytesPerDstImage
- + (dstHeight - 1) * bytesPerDstRow;
+ + (dstHeight - 1) * dstRowStride;
MEMCPY(dst, src, bpt);
/* do border along [img][row=0][col=dstWidth-1] */
@@ -687,9 +698,9 @@ make_3d_mipmap(GLenum datatype, GLuint comps, GLint border,
/* do border along [img][row=dstHeight-1][col=0] */
src = srcPtr + (img * 2 + 1) * bytesPerSrcImage
- + (srcHeight - 1) * bytesPerSrcRow;
+ + (srcHeight - 1) * srcRowStride;
dst = dstPtr + (img + 1) * bytesPerDstImage
- + (dstHeight - 1) * bytesPerDstRow;
+ + (dstHeight - 1) * dstRowStride;
do_row(datatype, comps, 1, src, src + srcImageOffset, 1, dst);
/* do border along [img][row=0][col=dstWidth-1] */
@@ -755,8 +766,11 @@ make_1d_stack_mipmap(GLenum datatype, GLuint comps, GLint border,
*/
static void
make_2d_stack_mipmap(GLenum datatype, GLuint comps, GLint border,
- GLint srcWidth, GLint srcHeight, const GLubyte *srcPtr,
+ GLint srcWidth, GLint srcHeight,
+ GLint srcRowStride,
+ const GLubyte *srcPtr,
GLint dstWidth, GLint dstHeight, GLint dstDepth,
+ GLint dstRowStride,
GLubyte *dstPtr)
{
const GLint bpt = bytes_per_pixel(datatype, comps);
@@ -764,13 +778,17 @@ make_2d_stack_mipmap(GLenum datatype, GLuint comps, GLint border,
const GLint dstWidthNB = dstWidth - 2 * border;
const GLint dstHeightNB = dstHeight - 2 * border;
const GLint dstDepthNB = dstDepth - 2 * border;
- const GLint srcRowStride = bpt * srcWidth;
- const GLint dstRowStride = bpt * dstWidth;
const GLubyte *srcA, *srcB;
GLubyte *dst;
GLint layer;
GLint row;
+ if (!srcRowStride)
+ srcRowStride = bpt * srcWidth;
+
+ if (!dstRowStride)
+ dstRowStride = bpt * dstWidth;
+
/* Compute src and dst pointers, skipping any border */
srcA = srcPtr + border * ((srcWidth + 1) * bpt);
if (srcHeight > 1)
@@ -849,8 +867,10 @@ _mesa_generate_mipmap_level(GLenum target,
GLenum datatype, GLuint comps,
GLint border,
GLint srcWidth, GLint srcHeight, GLint srcDepth,
+ GLint srcRowStride,
const GLubyte *srcData,
GLint dstWidth, GLint dstHeight, GLint dstDepth,
+ GLint dstRowStride,
GLubyte *dstData)
{
switch (target) {
@@ -867,13 +887,13 @@ _mesa_generate_mipmap_level(GLenum target,
case GL_TEXTURE_CUBE_MAP_POSITIVE_Z_ARB:
case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z_ARB:
make_2d_mipmap(datatype, comps, border,
- srcWidth, srcHeight, srcData,
- dstWidth, dstHeight, dstData);
+ srcWidth, srcHeight, srcRowStride, srcData,
+ dstWidth, dstHeight, dstRowStride, dstData);
break;
case GL_TEXTURE_3D:
make_3d_mipmap(datatype, comps, border,
- srcWidth, srcHeight, srcDepth, srcData,
- dstWidth, dstHeight, dstDepth, dstData);
+ srcWidth, srcHeight, srcDepth, srcRowStride, srcData,
+ dstWidth, dstHeight, dstDepth, dstRowStride, dstData);
break;
case GL_TEXTURE_1D_ARRAY_EXT:
make_1d_stack_mipmap(datatype, comps, border,
@@ -882,8 +902,8 @@ _mesa_generate_mipmap_level(GLenum target,
break;
case GL_TEXTURE_2D_ARRAY_EXT:
make_2d_stack_mipmap(datatype, comps, border,
- srcWidth, srcHeight, srcData,
- dstWidth, dstHeight, dstDepth, dstData);
+ srcWidth, srcHeight, srcRowStride, srcData,
+ dstWidth, dstHeight, dstDepth, dstRowStride, dstData);
break;
case GL_TEXTURE_RECTANGLE_NV:
/* no mipmaps, do nothing */
@@ -1110,9 +1130,10 @@ _mesa_generate_mipmap(GLcontext *ctx, GLenum target,
dstData = (GLubyte *) dstImage->Data;
}
+ /* Note, 0 indicates default row strides */
_mesa_generate_mipmap_level(target, datatype, comps, border,
- srcWidth, srcHeight, srcDepth, srcData,
- dstWidth, dstHeight, dstDepth, dstData);
+ srcWidth, srcHeight, srcDepth, 0, srcData,
+ dstWidth, dstHeight, dstDepth, 0, dstData);
if (dstImage->IsCompressed) {
GLubyte *temp;
diff --git a/src/mesa/main/mipmap.h b/src/mesa/main/mipmap.h
index b6491f55073..44ecdddb277 100644
--- a/src/mesa/main/mipmap.h
+++ b/src/mesa/main/mipmap.h
@@ -34,8 +34,10 @@ _mesa_generate_mipmap_level(GLenum target,
GLenum datatype, GLuint comps,
GLint border,
GLint srcWidth, GLint srcHeight, GLint srcDepth,
+ GLint srcRowStride,
const GLubyte *srcData,
GLint dstWidth, GLint dstHeight, GLint dstDepth,
+ GLint dstRowStride,
GLubyte *dstData);
diff --git a/src/mesa/state_tracker/st_gen_mipmap.c b/src/mesa/state_tracker/st_gen_mipmap.c
index f6af37cfac3..c152c599056 100644
--- a/src/mesa/state_tracker/st_gen_mipmap.c
+++ b/src/mesa/state_tracker/st_gen_mipmap.c
@@ -352,12 +352,13 @@ fallback_generate_mipmap(GLcontext *ctx, GLenum target,
PIPE_BUFFER_USAGE_CPU_WRITE)
+ dstSurf->offset;
- /* XXX need to take stride/pitch info into account... */
_mesa_generate_mipmap_level(target, datatype, comps,
0 /*border*/,
pt->width[srcLevel], pt->height[srcLevel], pt->depth[srcLevel],
+ srcSurf->pitch * srcSurf->cpp, /* stride in bytes */
srcData,
pt->width[dstLevel], pt->height[dstLevel], pt->depth[dstLevel],
+ dstSurf->pitch * dstSurf->cpp, /* stride in bytes */
dstData);
ws->buffer_unmap(ws, srcSurf->buffer);