summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChia-I Wu <olvaffe@gmail.com>2010-01-20 13:24:42 +0800
committerChia-I Wu <olvaffe@gmail.com>2010-01-20 13:30:55 +0800
commitf291200a4bbc0b701cfe831bdeeb79f90efd866f (patch)
tree371e84da3fce5e2378133c928df48ea077ae1120
parent77c08003819e8e2c922271c859bceb2b9c9234b7 (diff)
st/egl_g3d: Do not reuse the pipe transfer in ximage.
A pipe transfer is supposed to be temporary. It should be created before X*PutImage and destroyed afterwards.
-rw-r--r--src/gallium/state_trackers/egl_g3d/x11/native_ximage.c40
1 files changed, 22 insertions, 18 deletions
diff --git a/src/gallium/state_trackers/egl_g3d/x11/native_ximage.c b/src/gallium/state_trackers/egl_g3d/x11/native_ximage.c
index d76107c47f1..dfa8df22234 100644
--- a/src/gallium/state_trackers/egl_g3d/x11/native_ximage.c
+++ b/src/gallium/state_trackers/egl_g3d/x11/native_ximage.c
@@ -66,7 +66,6 @@ struct ximage_buffer {
XImage *ximage;
struct pipe_texture *texture;
- struct pipe_transfer *transfer;
XShmSegmentInfo *shm_info;
boolean xshm_attached;
};
@@ -115,12 +114,7 @@ ximage_surface_free_buffer(struct native_surface *nsurf,
{
struct ximage_surface *xsurf = ximage_surface(nsurf);
struct ximage_buffer *xbuf = &xsurf->buffers[which];
- struct pipe_screen *screen = xsurf->xdpy->base.screen;
- if (xbuf->transfer) {
- screen->tex_transfer_destroy(xbuf->transfer);
- xbuf->transfer = NULL;
- }
pipe_texture_reference(&xbuf->texture, NULL);
if (xbuf->shm_info) {
@@ -193,13 +187,6 @@ ximage_surface_alloc_buffer(struct native_surface *nsurf,
xbuf->texture = screen->texture_create(screen, &templ);
}
- if (xbuf->texture) {
- xbuf->transfer = screen->get_tex_transfer(screen, xbuf->texture,
- 0, 0, 0, PIPE_TRANSFER_READ, 0, 0, xsurf->width, xsurf->height);
- if (!xbuf->transfer)
- pipe_texture_reference(&xbuf->texture, NULL);
- }
-
/* clean up the buffer if allocation failed */
if (!xbuf->texture)
ximage_surface_free_buffer(&xsurf->base, which);
@@ -214,13 +201,25 @@ ximage_surface_draw_buffer(struct native_surface *nsurf,
struct ximage_surface *xsurf = ximage_surface(nsurf);
struct ximage_buffer *xbuf = &xsurf->buffers[which];
struct pipe_screen *screen = xsurf->xdpy->base.screen;
+ struct pipe_transfer *transfer;
if (xsurf->type == XIMAGE_SURFACE_TYPE_PBUFFER)
return TRUE;
assert(xsurf->drawable && xbuf->ximage && xbuf->texture);
- xbuf->ximage->data = screen->transfer_map(screen, xbuf->transfer);
+ transfer = screen->get_tex_transfer(screen, xbuf->texture,
+ 0, 0, 0, PIPE_TRANSFER_READ, 0, 0, xsurf->width, xsurf->height);
+ if (!transfer)
+ return FALSE;
+
+ xbuf->ximage->bytes_per_line = transfer->stride;
+ xbuf->ximage->data = screen->transfer_map(screen, transfer);
+ if (!xbuf->ximage->data) {
+ screen->tex_transfer_destroy(transfer);
+ return FALSE;
+ }
+
if (xbuf->shm_info)
XShmPutImage(xsurf->xdpy->dpy, xsurf->drawable, xsurf->gc,
@@ -230,7 +229,13 @@ ximage_surface_draw_buffer(struct native_surface *nsurf,
xbuf->ximage, 0, 0, 0, 0, xsurf->width, xsurf->height);
xbuf->ximage->data = NULL;
- screen->transfer_unmap(screen, xbuf->transfer);
+ screen->transfer_unmap(screen, transfer);
+
+ /*
+ * softpipe allows the pipe transfer to be re-used, but we don't want to
+ * rely on that behavior.
+ */
+ screen->tex_transfer_destroy(transfer);
XSync(xsurf->xdpy->dpy, FALSE);
@@ -314,9 +319,8 @@ ximage_surface_validate(struct native_surface *nsurf, uint attachment_mask,
if (ximage_surface_alloc_buffer(&xsurf->base, att)) {
/* update ximage */
if (xbuf->ximage) {
- xbuf->ximage->width = xbuf->transfer->width;
- xbuf->ximage->height = xbuf->transfer->height;
- xbuf->ximage->bytes_per_line = xbuf->transfer->stride;
+ xbuf->ximage->width = xsurf->width;
+ xbuf->ximage->height = xsurf->height;
}
}
}