AIGLX: Fix GLX_EXT_texture_from_pixmap fallback with EXA.

Use pScreen->GetImage to obtain the pixmap contents instead of dereferencing
pPixmap->devPrivate.ptr directly.
This commit is contained in:
Michel Dänzer 2008-01-19 13:17:45 +01:00
parent e9fa7c1c88
commit 94a21d757c

View File

@ -47,6 +47,8 @@
#include <xf86.h> #include <xf86.h>
#include <dri.h> #include <dri.h>
#include "servermd.h"
#define DRI_NEW_INTERFACE_ONLY #define DRI_NEW_INTERFACE_ONLY
#include "glxserver.h" #include "glxserver.h"
#include "glxutil.h" #include "glxutil.h"
@ -308,18 +310,20 @@ __glXDRIcontextForceCurrent(__GLXcontext *baseContext)
} }
static void static void
glxFillAlphaChannel (PixmapPtr pixmap, int x, int y, int width, int height) glxFillAlphaChannel (CARD32 *pixels, CARD32 rowstride, int width, int height)
{ {
int i; int i;
CARD32 *p, *end, *pixels = (CARD32 *)pixmap->devPrivate.ptr; CARD32 *p, *end;
CARD32 rowstride = pixmap->devKind / 4;
rowstride /= 4;
for (i = y; i < y + height; i++) for (i = 0; i < height; i++)
{ {
p = &pixels[i * rowstride + x]; p = pixels;
end = p + width; end = p + width;
while (p < end) while (p < end)
*p++ |= 0xFF000000; *p++ |= 0xFF000000;
pixels += rowstride;
} }
} }
@ -430,22 +434,31 @@ nooverride:
type = GL_UNSIGNED_SHORT_5_6_5; type = GL_UNSIGNED_SHORT_5_6_5;
} }
CALL_PixelStorei( GET_DISPATCH(), (GL_UNPACK_ROW_LENGTH,
pixmap->devKind / bpp) );
if (pRegion == NULL) if (pRegion == NULL)
{ {
if (!override && pixmap->drawable.depth == 24) void *data = NULL;
glxFillAlphaChannel(pixmap,
pixmap->drawable.x,
pixmap->drawable.y,
pixmap->drawable.width,
pixmap->drawable.height);
CALL_PixelStorei( GET_DISPATCH(), (GL_UNPACK_SKIP_PIXELS, if (!override) {
pixmap->drawable.x) ); unsigned pitch = PixmapBytePad(pixmap->drawable.width,
CALL_PixelStorei( GET_DISPATCH(), (GL_UNPACK_SKIP_ROWS, pixmap->drawable.depth);
pixmap->drawable.y) );
data = xalloc(pitch * pixmap->drawable.height);
pScreen->GetImage(&pixmap->drawable, 0 /*pixmap->drawable.x*/,
0 /*pixmap->drawable.y*/, pixmap->drawable.width,
pixmap->drawable.height, ZPixmap, ~0, data);
if (pixmap->drawable.depth == 24)
glxFillAlphaChannel(data,
pitch,
pixmap->drawable.width,
pixmap->drawable.height);
CALL_PixelStorei( GET_DISPATCH(), (GL_UNPACK_ROW_LENGTH,
pitch / bpp) );
CALL_PixelStorei( GET_DISPATCH(), (GL_UNPACK_SKIP_PIXELS, 0) );
CALL_PixelStorei( GET_DISPATCH(), (GL_UNPACK_SKIP_ROWS, 0) );
}
CALL_TexImage2D( GET_DISPATCH(), CALL_TexImage2D( GET_DISPATCH(),
(glxPixmap->target, (glxPixmap->target,
@ -456,26 +469,37 @@ nooverride:
0, 0,
format, format,
type, type,
override ? NULL : pixmap->devPrivate.ptr) ); data) );
xfree(data);
} else if (!override) { } else if (!override) {
int i, numRects; int i, numRects;
BoxPtr p; BoxPtr p;
numRects = REGION_NUM_RECTS (pRegion); numRects = REGION_NUM_RECTS (pRegion);
p = REGION_RECTS (pRegion); p = REGION_RECTS (pRegion);
CALL_PixelStorei( GET_DISPATCH(), (GL_UNPACK_SKIP_PIXELS, 0) );
CALL_PixelStorei( GET_DISPATCH(), (GL_UNPACK_SKIP_ROWS, 0) );
for (i = 0; i < numRects; i++) for (i = 0; i < numRects; i++)
{ {
unsigned pitch = PixmapBytePad(p[i].x2 - p[i].x1,
pixmap->drawable.depth);
void *data = xalloc(pitch * (p[i].y2 - p[i].y1));
pScreen->GetImage(&pixmap->drawable, /*pixmap->drawable.x +*/ p[i].x1,
/*pixmap->drawable.y*/ + p[i].y1, p[i].x2 - p[i].x1,
p[i].y2 - p[i].y1, ZPixmap, ~0, data);
if (pixmap->drawable.depth == 24) if (pixmap->drawable.depth == 24)
glxFillAlphaChannel(pixmap, glxFillAlphaChannel(data,
pixmap->drawable.x + p[i].x1, pitch,
pixmap->drawable.y + p[i].y1,
p[i].x2 - p[i].x1, p[i].x2 - p[i].x1,
p[i].y2 - p[i].y1); p[i].y2 - p[i].y1);
CALL_PixelStorei( GET_DISPATCH(), (GL_UNPACK_SKIP_PIXELS, CALL_PixelStorei( GET_DISPATCH(), (GL_UNPACK_ROW_LENGTH,
pixmap->drawable.x + p[i].x1) ); pitch / bpp) );
CALL_PixelStorei( GET_DISPATCH(), (GL_UNPACK_SKIP_ROWS,
pixmap->drawable.y + p[i].y1) );
CALL_TexSubImage2D( GET_DISPATCH(), CALL_TexSubImage2D( GET_DISPATCH(),
(glxPixmap->target, (glxPixmap->target,
@ -484,7 +508,9 @@ nooverride:
p[i].x2 - p[i].x1, p[i].y2 - p[i].y1, p[i].x2 - p[i].x1, p[i].y2 - p[i].y1,
format, format,
type, type,
pixmap->devPrivate.ptr) ); data) );
xfree(data);
} }
} }