summaryrefslogtreecommitdiff
path: root/src/gallium
diff options
context:
space:
mode:
authorMichel Dänzer <daenzer@vmware.com>2009-02-18 16:43:02 +0100
committerMichel Dänzer <daenzer@vmware.com>2009-02-18 16:43:02 +0100
commit3bd7c5ceffc88a052c5e8e114df2f2c7549ddb4a (patch)
treebdb352609c3ef21875a2699428e26b8c8c930f73 /src/gallium
parent76d8951fd3adbb91b2f71d461eec0f304619ca0b (diff)
parentb89aa1d87ad6cebdbb3f2067863c600f50bf0ff1 (diff)
Merge branch 'gallium-texture-transfer'
Conflicts: src/gallium/drivers/softpipe/sp_tile_cache.c
Diffstat (limited to 'src/gallium')
-rw-r--r--src/gallium/auxiliary/draw/draw_pipe_aaline.c14
-rw-r--r--src/gallium/auxiliary/draw/draw_pipe_pstipple.c17
-rw-r--r--src/gallium/auxiliary/util/u_debug.c59
-rw-r--r--src/gallium/auxiliary/util/u_gen_mipmap.c125
-rw-r--r--src/gallium/auxiliary/util/u_rect.c112
-rw-r--r--src/gallium/auxiliary/util/u_tile.c127
-rw-r--r--src/gallium/auxiliary/util/u_tile.h30
-rw-r--r--src/gallium/drivers/i915simple/i915_screen.c90
-rw-r--r--src/gallium/drivers/i915simple/i915_screen.h19
-rw-r--r--src/gallium/drivers/i915simple/i915_state_emit.c6
-rw-r--r--src/gallium/drivers/i915simple/i915_surface.c79
-rw-r--r--src/gallium/drivers/i915simple/i915_texture.c4
-rw-r--r--src/gallium/drivers/softpipe/sp_context.c12
-rw-r--r--src/gallium/drivers/softpipe/sp_draw_arrays.c2
-rw-r--r--src/gallium/drivers/softpipe/sp_flush.c2
-rw-r--r--src/gallium/drivers/softpipe/sp_state.h4
-rw-r--r--src/gallium/drivers/softpipe/sp_texture.c114
-rw-r--r--src/gallium/drivers/softpipe/sp_texture.h15
-rw-r--r--src/gallium/drivers/softpipe/sp_tile_cache.c162
-rw-r--r--src/gallium/drivers/softpipe/sp_tile_cache.h4
-rw-r--r--src/gallium/include/pipe/p_defines.h10
-rw-r--r--src/gallium/include/pipe/p_inlines.h23
-rw-r--r--src/gallium/include/pipe/p_screen.h24
-rw-r--r--src/gallium/include/pipe/p_state.h28
-rw-r--r--src/gallium/state_trackers/g3dvl/vl_r16snorm_mc_buf.c18
-rw-r--r--src/gallium/winsys/xlib/xlib_brw_aub.c12
-rw-r--r--src/gallium/winsys/xlib/xlib_softpipe.c15
27 files changed, 642 insertions, 485 deletions
diff --git a/src/gallium/auxiliary/draw/draw_pipe_aaline.c b/src/gallium/auxiliary/draw/draw_pipe_aaline.c
index 20841bb5d6..80c9c918a9 100644
--- a/src/gallium/auxiliary/draw/draw_pipe_aaline.c
+++ b/src/gallium/auxiliary/draw/draw_pipe_aaline.c
@@ -410,7 +410,7 @@ aaline_create_texture(struct aaline_stage *aaline)
* texels which are zero. Special case the 1x1 and 2x2 levels.
*/
for (level = 0; level <= MAX_TEXTURE_LEVEL; level++) {
- struct pipe_surface *surface;
+ struct pipe_transfer *transfer;
const uint size = aaline->texture->width[level];
ubyte *data;
uint i, j;
@@ -419,9 +419,9 @@ aaline_create_texture(struct aaline_stage *aaline)
/* This texture is new, no need to flush.
*/
- surface = screen->get_tex_surface(screen, aaline->texture, 0, level, 0,
- PIPE_BUFFER_USAGE_CPU_WRITE);
- data = screen->surface_map(screen, surface, PIPE_BUFFER_USAGE_CPU_WRITE);
+ transfer = screen->get_tex_transfer(screen, aaline->texture, 0, level, 0,
+ PIPE_TRANSFER_WRITE, 0, 0, size, size);
+ data = screen->transfer_map(screen, transfer);
if (data == NULL)
return FALSE;
@@ -440,13 +440,13 @@ aaline_create_texture(struct aaline_stage *aaline)
else {
d = 255;
}
- data[i * surface->stride + j] = d;
+ data[i * transfer->stride + j] = d;
}
}
/* unmap */
- screen->surface_unmap(screen, surface);
- screen->tex_surface_release(screen, &surface);
+ screen->transfer_unmap(screen, transfer);
+ screen->tex_transfer_release(screen, &transfer);
}
return TRUE;
}
diff --git a/src/gallium/auxiliary/draw/draw_pipe_pstipple.c b/src/gallium/auxiliary/draw/draw_pipe_pstipple.c
index a0f9716dac..e68c824c86 100644
--- a/src/gallium/auxiliary/draw/draw_pipe_pstipple.c
+++ b/src/gallium/auxiliary/draw/draw_pipe_pstipple.c
@@ -372,7 +372,7 @@ pstip_update_texture(struct pstip_stage *pstip)
static const uint bit31 = 1 << 31;
struct pipe_context *pipe = pstip->pipe;
struct pipe_screen *screen = pipe->screen;
- struct pipe_surface *surface;
+ struct pipe_transfer *transfer;
const uint *stipple = pstip->state.stipple->stipple;
uint i, j;
ubyte *data;
@@ -381,10 +381,9 @@ pstip_update_texture(struct pstip_stage *pstip)
*/
pipe->flush( pipe, PIPE_FLUSH_TEXTURE_CACHE, NULL );
- surface = screen->get_tex_surface(screen, pstip->texture, 0, 0, 0,
- PIPE_BUFFER_USAGE_CPU_WRITE);
- data = screen->surface_map(screen, surface,
- PIPE_BUFFER_USAGE_CPU_WRITE);
+ transfer = screen->get_tex_transfer(screen, pstip->texture, 0, 0, 0,
+ PIPE_TRANSFER_WRITE, 0, 0, 32, 32);
+ data = screen->transfer_map(screen, transfer);
/*
* Load alpha texture.
@@ -396,18 +395,18 @@ pstip_update_texture(struct pstip_stage *pstip)
for (j = 0; j < 32; j++) {
if (stipple[i] & (bit31 >> j)) {
/* fragment "on" */
- data[i * surface->stride + j] = 0;
+ data[i * transfer->stride + j] = 0;
}
else {
/* fragment "off" */
- data[i * surface->stride + j] = 255;
+ data[i * transfer->stride + j] = 255;
}
}
}
/* unmap */
- screen->surface_unmap(screen, surface);
- screen->tex_surface_release(screen, &surface);
+ screen->transfer_unmap(screen, transfer);
+ screen->tex_transfer_release(screen, &transfer);
}
diff --git a/src/gallium/auxiliary/util/u_debug.c b/src/gallium/auxiliary/util/u_debug.c
index 43d424b1d6..7f2a113dea 100644
--- a/src/gallium/auxiliary/util/u_debug.c
+++ b/src/gallium/auxiliary/util/u_debug.c
@@ -643,34 +643,37 @@ void debug_dump_image(const char *prefix,
void debug_dump_surface(const char *prefix,
struct pipe_surface *surface)
{
- unsigned surface_usage;
+ struct pipe_texture *texture;
+ struct pipe_screen *screen;
+ struct pipe_transfer *transfer;
void *data;
if (!surface)
- goto error1;
+ return;
+
+ texture = surface->texture;
+ screen = texture->screen;
- /* XXX: force mappable surface */
- surface_usage = surface->usage;
- surface->usage |= PIPE_BUFFER_USAGE_CPU_READ;
+ transfer = screen->get_tex_transfer(screen, texture, surface->face,
+ surface->level, surface->zslice,
+ PIPE_TRANSFER_READ, 0, 0, surface->width,
+ surface->height);
- data = pipe_surface_map(surface,
- PIPE_BUFFER_USAGE_CPU_READ);
+ data = screen->transfer_map(screen, transfer);
if(!data)
- goto error2;
+ goto error;
debug_dump_image(prefix,
- surface->format,
- surface->block.size,
- surface->nblocksx,
- surface->nblocksy,
- surface->stride,
+ transfer->format,
+ transfer->block.size,
+ transfer->nblocksx,
+ transfer->nblocksy,
+ transfer->stride,
data);
- pipe_surface_unmap(surface);
-error2:
- surface->usage = surface_usage;
-error1:
- ;
+ screen->transfer_unmap(screen, transfer);
+error:
+ screen->tex_transfer_release(screen, &transfer);
}
@@ -710,8 +713,10 @@ debug_dump_surface_bmp(const char *filename,
struct pipe_surface *surface)
{
#ifndef PIPE_SUBSYSTEM_WINDOWS_MINIPORT
+ struct pipe_texture *texture;
+ struct pipe_screen *screen;
struct util_stream *stream;
- unsigned surface_usage;
+ struct pipe_transfer *transfer;
struct bmp_file_header bmfh;
struct bmp_info_header bmih;
float *rgba;
@@ -748,14 +753,18 @@ debug_dump_surface_bmp(const char *filename,
util_stream_write(stream, &bmfh, 14);
util_stream_write(stream, &bmih, 40);
+
+ texture = surface->texture;
+ screen = texture->screen;
- /* XXX: force mappable surface */
- surface_usage = surface->usage;
- surface->usage |= PIPE_BUFFER_USAGE_CPU_READ;
+ transfer = screen->get_tex_transfer(screen, texture, surface->face,
+ surface->level, surface->zslice,
+ PIPE_TRANSFER_READ, 0, 0, surface->width,
+ surface->height);
y = surface->height;
while(y--) {
- pipe_get_tile_rgba(surface,
+ pipe_get_tile_rgba(transfer,
0, y, surface->width, 1,
rgba);
for(x = 0; x < surface->width; ++x)
@@ -768,9 +777,9 @@ debug_dump_surface_bmp(const char *filename,
util_stream_write(stream, &pixel, 4);
}
}
-
- surface->usage = surface_usage;
+ screen->tex_transfer_release(screen, &transfer);
+
util_stream_close(stream);
error2:
FREE(rgba);
diff --git a/src/gallium/auxiliary/util/u_gen_mipmap.c b/src/gallium/auxiliary/util/u_gen_mipmap.c
index 7c20c7ce7b..90483fcb21 100644
--- a/src/gallium/auxiliary/util/u_gen_mipmap.c
+++ b/src/gallium/auxiliary/util/u_gen_mipmap.c
@@ -1116,31 +1116,30 @@ make_1d_mipmap(struct gen_mipmap_state *ctx,
for (dstLevel = baseLevel + 1; dstLevel <= lastLevel; dstLevel++) {
const uint srcLevel = dstLevel - 1;
- struct pipe_surface *srcSurf, *dstSurf;
+ struct pipe_transfer *srcTrans, *dstTrans;
void *srcMap, *dstMap;
- srcSurf = screen->get_tex_surface(screen, pt, face, srcLevel, zslice,
- PIPE_BUFFER_USAGE_CPU_READ);
-
- dstSurf = screen->get_tex_surface(screen, pt, face, dstLevel, zslice,
- PIPE_BUFFER_USAGE_CPU_WRITE);
-
- srcMap = ((ubyte *) pipe_surface_map(srcSurf,
- PIPE_BUFFER_USAGE_CPU_READ)
- + srcSurf->offset);
- dstMap = ((ubyte *) pipe_surface_map(dstSurf,
- PIPE_BUFFER_USAGE_CPU_WRITE)
- + dstSurf->offset);
+ srcTrans = screen->get_tex_transfer(screen, pt, face, srcLevel, zslice,
+ PIPE_TRANSFER_READ, 0, 0,
+ pt->width[srcLevel],
+ pt->height[srcLevel]);
+ dstTrans = screen->get_tex_transfer(screen, pt, face, dstLevel, zslice,
+ PIPE_TRANSFER_WRITE, 0, 0,
+ pt->width[dstLevel],
+ pt->height[dstLevel]);
+
+ srcMap = (ubyte *) screen->transfer_map(screen, srcTrans);
+ dstMap = (ubyte *) screen->transfer_map(screen, dstTrans);
reduce_1d(pt->format,
- srcSurf->width, srcMap,
- dstSurf->width, dstMap);
+ srcTrans->width, srcMap,
+ dstTrans->width, dstMap);
- pipe_surface_unmap(srcSurf);
- pipe_surface_unmap(dstSurf);
+ screen->transfer_unmap(screen, srcTrans);
+ screen->transfer_unmap(screen, dstTrans);
- pipe_surface_reference(&srcSurf, NULL);
- pipe_surface_reference(&dstSurf, NULL);
+ screen->tex_transfer_release(screen, &srcTrans);
+ screen->tex_transfer_release(screen, &dstTrans);
}
}
@@ -1160,32 +1159,32 @@ make_2d_mipmap(struct gen_mipmap_state *ctx,
for (dstLevel = baseLevel + 1; dstLevel <= lastLevel; dstLevel++) {
const uint srcLevel = dstLevel - 1;
- struct pipe_surface *srcSurf, *dstSurf;
+ struct pipe_transfer *srcTrans, *dstTrans;
ubyte *srcMap, *dstMap;
- srcSurf = screen->get_tex_surface(screen, pt, face, srcLevel, zslice,
- PIPE_BUFFER_USAGE_CPU_READ);
- dstSurf = screen->get_tex_surface(screen, pt, face, dstLevel, zslice,
- PIPE_BUFFER_USAGE_CPU_WRITE);
-
- srcMap = ((ubyte *) pipe_surface_map(srcSurf,
- PIPE_BUFFER_USAGE_CPU_READ)
- + srcSurf->offset);
- dstMap = ((ubyte *) pipe_surface_map(dstSurf,
- PIPE_BUFFER_USAGE_CPU_WRITE)
- + dstSurf->offset);
+ srcTrans = screen->get_tex_transfer(screen, pt, face, srcLevel, zslice,
+ PIPE_TRANSFER_READ, 0, 0,
+ pt->width[srcLevel],
+ pt->height[srcLevel]);
+ dstTrans = screen->get_tex_transfer(screen, pt, face, dstLevel, zslice,
+ PIPE_TRANSFER_WRITE, 0, 0,
+ pt->width[dstLevel],
+ pt->height[dstLevel]);
+
+ srcMap = (ubyte *) screen->transfer_map(screen, srcTrans);
+ dstMap = (ubyte *) screen->transfer_map(screen, dstTrans);
reduce_2d(pt->format,
- srcSurf->width, srcSurf->height,
- srcSurf->stride, srcMap,
- dstSurf->width, dstSurf->height,
- dstSurf->stride, dstMap);
+ srcTrans->width, srcTrans->height,
+ srcTrans->stride, srcMap,
+ dstTrans->width, dstTrans->height,
+ dstTrans->stride, dstMap);
- pipe_surface_unmap(srcSurf);
- pipe_surface_unmap(dstSurf);
+ screen->transfer_unmap(screen, srcTrans);
+ screen->transfer_unmap(screen, dstTrans);
- pipe_surface_reference(&srcSurf, NULL);
- pipe_surface_reference(&dstSurf, NULL);
+ screen->tex_transfer_release(screen, &srcTrans);
+ screen->tex_transfer_release(screen, &dstTrans);
}
}
@@ -1195,6 +1194,7 @@ make_3d_mipmap(struct gen_mipmap_state *ctx,
struct pipe_texture *pt,
uint face, uint baseLevel, uint lastLevel)
{
+#if 0
struct pipe_context *pipe = ctx->pipe;
struct pipe_screen *screen = pipe->screen;
uint dstLevel, zslice = 0;
@@ -1204,37 +1204,36 @@ make_3d_mipmap(struct gen_mipmap_state *ctx,
for (dstLevel = baseLevel + 1; dstLevel <= lastLevel; dstLevel++) {
const uint srcLevel = dstLevel - 1;
- struct pipe_surface *srcSurf, *dstSurf;
+ struct pipe_transfer *srcTrans, *dstTrans;
ubyte *srcMap, *dstMap;
- srcSurf = screen->get_tex_surface(screen, pt, face, srcLevel, zslice,
- PIPE_BUFFER_USAGE_CPU_READ);
- dstSurf = screen->get_tex_surface(screen, pt, face, dstLevel, zslice,
- PIPE_BUFFER_USAGE_CPU_WRITE);
-
- srcMap = ((ubyte *) pipe_surface_map(srcSurf,
- PIPE_BUFFER_USAGE_CPU_READ)
- + srcSurf->offset);
- dstMap = ((ubyte *) pipe_surface_map(dstSurf,
- PIPE_BUFFER_USAGE_CPU_WRITE)
- + dstSurf->offset);
+ srcTrans = screen->get_tex_transfer(screen, pt, face, srcLevel, zslice,
+ PIPE_TRANSFER_READ, 0, 0,
+ pt->width[srcLevel],
+ pt->height[srcLevel]);
+ dstTrans = screen->get_tex_transfer(screen, pt, face, dstLevel, zslice,
+ PIPE_TRANSFER_WRITE, 0, 0,
+ pt->width[dstLevel],
+ pt->height[dstLevel]);
+
+ srcMap = (ubyte *) screen->transfer_map(screen, srcTrans);
+ dstMap = (ubyte *) screen->transfer_map(screen, dstTrans);
-#if 0
reduce_3d(pt->format,
- srcSurf->width, srcSurf->height,
- srcSurf->stride, srcMap,
- dstSurf->width, dstSurf->height,
- dstSurf->stride, dstMap);
-#else
- (void) reduce_3d;
-#endif
+ srcTrans->width, srcTrans->height,
+ srcTrans->stride, srcMap,
+ dstTrans->width, dstTrans->height,
+ dstTrans->stride, dstMap);
- pipe_surface_unmap(srcSurf);
- pipe_surface_unmap(dstSurf);
+ screen->transfer_unmap(screen, srcTrans);
+ screen->transfer_unmap(screen, dstTrans);
- pipe_surface_reference(&srcSurf, NULL);
- pipe_surface_reference(&dstSurf, NULL);
+ screen->tex_transfer_release(screen, &srcTrans);
+ screen->tex_transfer_release(screen, &dstTrans);
}
+#else
+ (void) reduce_3d;
+#endif
}
diff --git a/src/gallium/auxiliary/util/u_rect.c b/src/gallium/auxiliary/util/u_rect.c
index fe81a685be..6e24e594e4 100644
--- a/src/gallium/auxiliary/util/u_rect.c
+++ b/src/gallium/auxiliary/util/u_rect.c
@@ -169,46 +169,35 @@ util_surface_copy(struct pipe_context *pipe,
unsigned w, unsigned h)
{
struct pipe_screen *screen = pipe->screen;
- struct pipe_surface *new_src = NULL, *new_dst = NULL;
+ struct pipe_transfer *src_trans, *dst_trans;
void *dst_map;
const void *src_map;
- assert(dst->block.size == src->block.size);
- assert(dst->block.width == src->block.width);
- assert(dst->block.height == src->block.height);
-
- if ((src->usage & PIPE_BUFFER_USAGE_CPU_READ) == 0) {
- /* Need to create new src surface which is CPU readable */
- assert(src->texture);
- if (!src->texture)
- return;
- new_src = screen->get_tex_surface(screen,
+ assert(src->texture && dst->texture);
+ if (!src->texture || !dst->texture)
+ return;
+ src_trans = screen->get_tex_transfer(screen,
src->texture,
src->face,
src->level,
src->zslice,
- PIPE_BUFFER_USAGE_CPU_READ);
- src = new_src;
- }
+ PIPE_TRANSFER_READ,
+ src_x, src_y, w, h);
- if ((dst->usage & PIPE_BUFFER_USAGE_CPU_WRITE) == 0) {
- /* Need to create new dst surface which is CPU writable */
- assert(dst->texture);
- if (!dst->texture)
- return;
- new_dst = screen->get_tex_surface(screen,
+ dst_trans = screen->get_tex_transfer(screen,
dst->texture,
dst->face,
dst->level,
dst->zslice,
- PIPE_BUFFER_USAGE_CPU_WRITE);
- dst = new_dst;
- }
+ PIPE_TRANSFER_WRITE,
+ dst_x, dst_y, w, h);
- src_map = pipe->screen->surface_map(screen,
- src, PIPE_BUFFER_USAGE_CPU_READ);
- dst_map = pipe->screen->surface_map(screen,
- dst, PIPE_BUFFER_USAGE_CPU_WRITE);
+ assert(dst_trans->block.size == src_trans->block.size);
+ assert(dst_trans->block.width == src_trans->block.width);
+ assert(dst_trans->block.height == src_trans->block.height);
+
+ src_map = pipe->screen->transfer_map(screen, src_trans);
+ dst_map = pipe->screen->transfer_map(screen, dst_trans);
assert(src_map);
assert(dst_map);
@@ -216,36 +205,25 @@ util_surface_copy(struct pipe_context *pipe,
if (src_map && dst_map) {
/* If do_flip, invert src_y position and pass negative src stride */
pipe_copy_rect(dst_map,
- &dst->block,
- dst->stride,
- dst_x, dst_y,
+ &dst_trans->block,
+ dst_trans->stride,
+ 0, 0,
w, h,
src_map,
- do_flip ? -(int) src->stride : src->stride,
- src_x,
- do_flip ? src_y + h - 1 : src_y);
+ do_flip ? -(int) src_trans->stride : src_trans->stride,
+ 0,
+ do_flip ? h - 1 : 0);
}
- pipe->screen->surface_unmap(pipe->screen, src);
- pipe->screen->surface_unmap(pipe->screen, dst);
+ pipe->screen->transfer_unmap(pipe->screen, src_trans);
+ pipe->screen->transfer_unmap(pipe->screen, dst_trans);
- if (new_src)
- screen->tex_surface_release(screen, &new_src);
- if (new_dst)
- screen->tex_surface_release(screen, &new_dst);
+ screen->tex_transfer_release(screen, &src_trans);
+ screen->tex_transfer_release(screen, &dst_trans);
}
-static void *
-get_pointer(struct pipe_surface *dst, void *dst_map, unsigned x, unsigned y)
-{
- return (char *)dst_map
- + y / dst->block.height * dst->stride
- + x / dst->block.width * dst->block.size;
-}
-
-
#define UBYTE_TO_USHORT(B) ((B) | ((B) << 8))
@@ -260,42 +238,38 @@ util_surface_fill(struct pipe_context *pipe,
unsigned width, unsigned height, unsigned value)
{
struct pipe_screen *screen = pipe->screen;
- struct pipe_surface *new_dst = NULL;
+ struct pipe_transfer *dst_trans;
void *dst_map;
- if ((dst->usage & PIPE_BUFFER_USAGE_CPU_WRITE) == 0) {
- /* Need to create new dst surface which is CPU writable */
- assert(dst->texture);
- if (!dst->texture)
- return;
- new_dst = screen->get_tex_surface(screen,
+ assert(dst->texture);
+ if (!dst->texture)
+ return;
+ dst_trans = screen->get_tex_transfer(screen,
dst->texture,
dst->face,
dst->level,
dst->zslice,
- PIPE_BUFFER_USAGE_CPU_WRITE);
- dst = new_dst;
- }
+ PIPE_TRANSFER_WRITE,
+ dstx, dsty, width, height);
- dst_map = pipe->screen->surface_map(screen,
- dst, PIPE_BUFFER_USAGE_CPU_WRITE);
+ dst_map = pipe->screen->transfer_map(screen, dst_trans);
assert(dst_map);
if (dst_map) {
- assert(dst->stride > 0);
+ assert(dst_trans->stride > 0);
- switch (dst->block.size) {
+ switch (dst_trans->block.size) {
case 1:
case 2:
case 4:
- pipe_fill_rect(dst_map, &dst->block, dst->stride,
- dstx, dsty, width, height, value);
+ pipe_fill_rect(dst_map, &dst_trans->block, dst_trans->stride,
+ 0, 0, width, height, value);
break;
case 8:
{
/* expand the 4-byte clear value to an 8-byte value */
- ushort *row = (ushort *) get_pointer(dst, dst_map, dstx, dsty);
+ ushort *row = (ushort *) dst_map;
ushort val0 = UBYTE_TO_USHORT((value >> 0) & 0xff);
ushort val1 = UBYTE_TO_USHORT((value >> 8) & 0xff);
ushort val2 = UBYTE_TO_USHORT((value >> 16) & 0xff);
@@ -312,7 +286,7 @@ util_surface_fill(struct pipe_context *pipe,
row[j*4+2] = val2;
row[j*4+3] = val3;
}
- row += dst->stride/2;
+ row += dst_trans->stride/2;
}
}
break;
@@ -322,8 +296,6 @@ util_surface_fill(struct pipe_context *pipe,
}
}
- pipe->screen->surface_unmap(pipe->screen, dst);
-
- if (new_dst)
- screen->tex_surface_release(screen, &new_dst);
+ pipe->screen->transfer_unmap(pipe->screen, dst_trans);
+ screen->tex_transfer_release(screen, &dst_trans);
}
diff --git a/src/gallium/auxiliary/util/u_tile.c b/src/gallium/auxiliary/util/u_tile.c
index 32f6b072a0..56f2f577cc 100644
--- a/src/gallium/auxiliary/util/u_tile.c
+++ b/src/gallium/auxiliary/util/u_tile.c
@@ -28,7 +28,6 @@
/**
* RGBA/float tile get/put functions.
* Usable both by drivers and state trackers.
- * Surfaces should already be in a mapped state.
*/
@@ -42,58 +41,58 @@
/**
- * Move raw block of pixels from surface to user memory.
- * This should be usable by any hw driver that has mappable surfaces.
+ * Move raw block of pixels from transfer object to user memory.
*/
void
-pipe_get_tile_raw(struct pipe_surface *ps,
+pipe_get_tile_raw(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
void *dst, int dst_stride)
{
+ struct pipe_screen *screen = pt->texture->screen;
const void *src;
if (dst_stride == 0)
- dst_stride = pf_get_nblocksx(&ps->block, w) * ps->block.size;
+ dst_stride = pf_get_nblocksx(&pt->block, w) * pt->block.size;
- if (pipe_clip_tile(x, y, &w, &h, ps))
+ if (pipe_clip_tile(x, y, &w, &h, pt))
return;
- src = pipe_surface_map(ps, PIPE_BUFFER_USAGE_CPU_READ);
+ src = screen->transfer_map(screen, pt);
assert(src);
if(!src)
return;
- pipe_copy_rect(dst, &ps->block, dst_stride, 0, 0, w, h, src, ps->stride, x, y);
+ pipe_copy_rect(dst, &pt->block, dst_stride, 0, 0, w, h, src, pt->stride, x, y);
- pipe_surface_unmap(ps);
+ screen->transfer_unmap(screen, pt);
}
/**
- * Move raw block of pixels from user memory to surface.
- * This should be usable by any hw driver that has mappable surfaces.
+ * Move raw block of pixels from user memory to transfer object.
*/
void
-pipe_put_tile_raw(struct pipe_surface *ps,
+pipe_put_tile_raw(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
const void *src, int src_stride)
{
+ struct pipe_screen *screen = pt->texture->screen;
void *dst;
if (src_stride == 0)
- src_stride = pf_get_nblocksx(&ps->block, w) * ps->block.size;
+ src_stride = pf_get_nblocksx(&pt->block, w) * pt->block.size;
- if (pipe_clip_tile(x, y, &w, &h, ps))
+ if (pipe_clip_tile(x, y, &w, &h, pt))
return;
- dst = pipe_surface_map(ps, PIPE_BUFFER_USAGE_CPU_WRITE);
+ dst = screen->transfer_map(screen, pt);
assert(dst);
if(!dst)
return;
- pipe_copy_rect(dst, &ps->block, ps->stride, x, y, w, h, src, src_stride, 0, 0);
+ pipe_copy_rect(dst, &pt->block, pt->stride, x, y, w, h, src, src_stride, 0, 0);
- pipe_surface_unmap(ps);
+ screen->transfer_unmap(screen, pt);
}
@@ -955,49 +954,49 @@ pipe_tile_raw_to_rgba(enum pipe_format format,
void
-pipe_get_tile_rgba(struct pipe_surface *ps,
+pipe_get_tile_rgba(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
float *p)
{
unsigned dst_stride = w * 4;
void *packed;
- if (pipe_clip_tile(x, y, &w, &h, ps))
+ if (pipe_clip_tile(x, y, &w, &h, pt))
return;
- packed = MALLOC(pf_get_nblocks(&ps->block, w, h) * ps->block.size);
+ packed = MALLOC(pf_get_nblocks(&pt->block, w, h) * pt->block.size);
if (!packed)
return;
- if(ps->format == PIPE_FORMAT_YCBCR || ps->format == PIPE_FORMAT_YCBCR_REV)
+ if(pt->format == PIPE_FORMAT_YCBCR || pt->format == PIPE_FORMAT_YCBCR_REV)
assert((x & 1) == 0);
- pipe_get_tile_raw(ps, x, y, w, h, packed, 0);
+ pipe_get_tile_raw(pt, x, y, w, h, packed, 0);
- pipe_tile_raw_to_rgba(ps->format, packed, w, h, p, dst_stride);
+ pipe_tile_raw_to_rgba(pt->format, packed, w, h, p, dst_stride);
FREE(packed);
}
void
-pipe_put_tile_rgba(struct pipe_surface *ps,
+pipe_put_tile_rgba(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
const float *p)
{
unsigned src_stride = w * 4;
void *packed;
- if (pipe_clip_tile(x, y, &w, &h, ps))
+ if (pipe_clip_tile(x, y, &w, &h, pt))
return;
- packed = MALLOC(pf_get_nblocks(&ps->block, w, h) * ps->block.size);
+ packed = MALLOC(pf_get_nblocks(&pt->block, w, h) * pt->block.size);
if (!packed)
return;
- switch (ps->format) {
+ switch (pt->format) {
case PIPE_FORMAT_A8R8G8B8_UNORM:
a8r8g8b8_put_tile_rgba((unsigned *) packed, w, h, p, src_stride);
break;
@@ -1054,7 +1053,7 @@ pipe_put_tile_rgba(struct pipe_surface *ps,
assert(0);
}
- pipe_put_tile_raw(ps, x, y, w, h, packed, 0);
+ pipe_put_tile_raw(pt, x, y, w, h, packed, 0);
FREE(packed);
}
@@ -1064,62 +1063,63 @@ pipe_put_tile_rgba(struct pipe_surface *ps,
* Get a block of Z values, converted to 32-bit range.
*/
void
-pipe_get_tile_z(struct pipe_surface *ps,
+pipe_get_tile_z(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
uint *z)
{
+ struct pipe_screen *screen = pt->texture->screen;
const uint dstStride = w;
ubyte *map;
uint *pDest = z;
uint i, j;
- if (pipe_clip_tile(x, y, &w, &h, ps))
+ if (pipe_clip_tile(x, y, &w, &h, pt))
return;
- map = (ubyte *)pipe_surface_map(ps, PIPE_BUFFER_USAGE_CPU_READ);
+ map = (ubyte *)screen->transfer_map(screen, pt);
if (!map) {
assert(0);
return;
}
- switch (ps->format) {
+ switch (pt->format) {
case PIPE_FORMAT_Z32_UNORM:
{
- const uint *pSrc
- = (const uint *)(map + y * ps->stride + x*4);
+ const uint *ptrc
+ = (const uint *)(map + y * pt->stride + x*4);
for (i = 0; i < h; i++) {
- memcpy(pDest, pSrc, 4 * w);
+ memcpy(pDest, ptrc, 4 * w);
pDest += dstStride;
- pSrc += ps->stride/4;
+ ptrc += pt->stride/4;
}
}
break;
case PIPE_FORMAT_S8Z24_UNORM:
case PIPE_FORMAT_X8Z24_UNORM:
{
- const uint *pSrc
- = (const uint *)(map + y * ps->stride + x*4);
+ const uint *ptrc
+ = (const uint *)(map + y * pt->stride + x*4);
for (i = 0; i < h; i++) {
for (j = 0; j < w; j++) {
/* convert 24-bit Z to 32-bit Z */
- pDest[j] = (pSrc[j] << 8) | (pSrc[j] & 0xff);
+ pDest[j] = (ptrc[j] << 8) | (ptrc[j] & 0xff);
}
pDest += dstStride;
- pSrc += ps->stride/4;
+ ptrc += pt->stride/4;
}
}
break;
case PIPE_FORMAT_Z16_UNORM:
{
- const ushort *pSrc
- = (const ushort *)(map + y * ps->stride + x*2);
+ const ushort *ptrc
+ = (const ushort *)(map + y * pt->stride + x*2);
for (i = 0; i < h; i++) {
for (j = 0; j < w; j++) {
/* convert 16-bit Z to 32-bit Z */
- pDest[j] = (pSrc[j] << 16) | pSrc[j];
+ pDest[j] = (ptrc[j] << 16) | ptrc[j];
}
pDest += dstStride;
- pSrc += ps->stride/2;
+ ptrc += pt->stride/2;
}
}
break;
@@ -1127,64 +1127,65 @@ pipe_get_tile_z(struct pipe_surface *ps,
assert(0);
}
- pipe_surface_unmap(ps);
+ screen->transfer_unmap(screen, pt);
}
void
-pipe_put_tile_z(struct pipe_surface *ps,
+pipe_put_tile_z(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
const uint *zSrc)
{
+ struct pipe_screen *screen = pt->texture->screen;
const uint srcStride = w;
- const uint *pSrc = zSrc;
+ const uint *ptrc = zSrc;
ubyte *map;
uint i, j;
- if (pipe_clip_tile(x, y, &w, &h, ps))
+ if (pipe_clip_tile(x, y, &w, &h, pt))
return;
- map = (ubyte *)pipe_surface_map(ps, PIPE_BUFFER_USAGE_CPU_WRITE);
+ map = (ubyte *)screen->transfer_map(screen, pt);
if (!map) {
assert(0);
return;
}
- switch (ps->format) {
+ switch (pt->format) {
case PIPE_FORMAT_Z32_UNORM:
{
- uint *pDest = (uint *) (map + y * ps->stride + x*4);
+ uint *pDest = (uint *) (map + y * pt->stride + x*4);
for (i = 0; i < h; i++) {
- memcpy(pDest, pSrc, 4 * w);
- pDest += ps->stride/4;
- pSrc += srcStride;
+ memcpy(pDest, ptrc, 4 * w);
+ pDest += pt->stride/4;
+ ptrc += srcStride;
}
}
break;
case PIPE_FORMAT_S8Z24_UNORM:
case PIPE_FORMAT_X8Z24_UNORM:
{
- uint *pDest = (uint *) (map + y * ps->stride + x*4);
+ uint *pDest = (uint *) (map + y * pt->stride + x*4);
for (i = 0; i < h; i++) {
for (j = 0; j < w; j++) {
/* convert 32-bit Z to 24-bit Z (0 stencil) */
- pDest[j] = pSrc[j] >> 8;
+ pDest[j] = ptrc[j] >> 8;
}
- pDest += ps->stride/4;
- pSrc += srcStride;
+ pDest += pt->stride/4;
+ ptrc += srcStride;
}
}
break;
case PIPE_FORMAT_Z16_UNORM:
{
- ushort *pDest = (ushort *) (map + y * ps->stride + x*2);
+ ushort *pDest = (ushort *) (map + y * pt->stride + x*2);
for (i = 0; i < h; i++) {
for (j = 0; j < w; j++) {
/* convert 32-bit Z to 16-bit Z */
- pDest[j] = pSrc[j] >> 16;
+ pDest[j] = ptrc[j] >> 16;
}
- pDest += ps->stride/2;
- pSrc += srcStride;
+ pDest += pt->stride/2;
+ ptrc += srcStride;
}
}
break;
@@ -1192,7 +1193,7 @@ pipe_put_tile_z(struct pipe_surface *ps,
assert(0);
}
- pipe_surface_unmap(ps);
+ screen->transfer_unmap(screen, pt);
}
diff --git a/src/gallium/auxiliary/util/u_tile.h b/src/gallium/auxiliary/util/u_tile.h
index a8ac805308..1453af38b8 100644
--- a/src/gallium/auxiliary/util/u_tile.h
+++ b/src/gallium/auxiliary/util/u_tile.h
@@ -30,24 +30,24 @@
#include "pipe/p_compiler.h"
-struct pipe_surface;
+struct pipe_transfer;
/**
- * Clip tile against surface dims.
+ * Clip tile against transfer dims.
* \return TRUE if tile is totally clipped, FALSE otherwise
*/
static INLINE boolean
-pipe_clip_tile(uint x, uint y, uint *w, uint *h, const struct pipe_surface *ps)
+pipe_clip_tile(uint x, uint y, uint *w, uint *h, const struct pipe_transfer *pt)
{
- if (x >= ps->width)
+ if (x >= pt->width)
return TRUE;
- if (y >= ps->height)
+ if (y >= pt->height)
return TRUE;
- if (x + *w > ps->width)
- *w = ps->width - x;
- if (y + *h > ps->height)
- *h = ps->height - y;
+ if (x + *w > pt->width)
+ *w = pt->width - x;
+ if (y + *h > pt->height)
+ *h = pt->height - y;
return FALSE;
}
@@ -56,34 +56,34 @@ extern "C" {
#endif
void
-pipe_get_tile_raw(struct pipe_surface *ps,
+pipe_get_tile_raw(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
void *p, int dst_stride);
void
-pipe_put_tile_raw(struct pipe_surface *ps,
+pipe_put_tile_raw(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
const void *p, int src_stride);
void
-pipe_get_tile_rgba(struct pipe_surface *ps,
+pipe_get_tile_rgba(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
float *p);
void
-pipe_put_tile_rgba(struct pipe_surface *ps,
+pipe_put_tile_rgba(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
const float *p);
void
-pipe_get_tile_z(struct pipe_surface *ps,
+pipe_get_tile_z(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
uint *z);
void
-pipe_put_tile_z(struct pipe_surface *ps,
+pipe_put_tile_z(struct pipe_transfer *pt,
uint x, uint y, uint w, uint h,
const uint *z);
diff --git a/src/gallium/drivers/i915simple/i915_screen.c b/src/gallium/drivers/i915simple/i915_screen.c
index 39e48105b3..b7bd3b3b74 100644
--- a/src/gallium/drivers/i915simple/i915_screen.c
+++ b/src/gallium/drivers/i915simple/i915_screen.c
@@ -204,17 +204,79 @@ i915_destroy_screen( struct pipe_screen *screen )
}
+static struct pipe_transfer*
+i915_get_tex_transfer(struct pipe_screen *screen,
+ struct pipe_texture *texture,
+ unsigned face, unsigned level, unsigned zslice,
+ enum pipe_transfer_usage usage, unsigned x, unsigned y,
+ unsigned w, unsigned h)
+{
+ struct i915_texture *tex = (struct i915_texture *)texture;
+ struct i915_transfer *trans;
+ unsigned offset; /* in bytes */
+
+ if (texture->target == PIPE_TEXTURE_CUBE) {
+ offset = tex->image_offset[level][face];
+ }
+ else if (texture->target == PIPE_TEXTURE_3D) {
+ offset = tex->image_offset[level][zslice];
+ }
+ else {
+ offset = tex->image_offset[level][0];
+ assert(face == 0);
+ assert(zslice == 0);
+ }
+
+ trans = CALLOC_STRUCT(i915_transfer);
+ if (trans) {
+ trans->base.refcount = 1;
+ pipe_texture_reference(&trans->base.texture, texture);
+ trans->base.format = trans->base.format;
+ trans->base.width = w;
+ trans->base.height = h;
+ trans->base.block = texture->block;
+ trans->base.nblocksx = texture->nblocksx[level];
+ trans->base.nblocksy = texture->nblocksy[level];
+ trans->base.stride = tex->stride;
+ trans->offset = offset;
+ trans->base.usage = usage;
+ }
+ return &trans->base;
+}
+
+static void
+i915_tex_transfer_release(struct pipe_screen *screen,
+ struct pipe_transfer **transfer)
+{
+ struct pipe_transfer *trans = *transfer;
+
+ if (--trans->refcount == 0) {
+ pipe_texture_reference(&trans->texture, NULL);
+ FREE(trans);
+ }
+
+ *transfer = NULL;
+}
+
static void *
-i915_surface_map( struct pipe_screen *screen,
- struct pipe_surface *surface,
- unsigned flags )
+i915_transfer_map( struct pipe_screen *screen,
+ struct pipe_transfer *transfer )
{
- struct i915_texture *tex = (struct i915_texture *)surface->texture;
- char *map = pipe_buffer_map( screen, tex->buffer, flags );
+ struct i915_texture *tex = (struct i915_texture *)transfer->texture;
+ char *map;
+ unsigned flags = 0;
+
+ if (transfer->usage != PIPE_TRANSFER_WRITE)
+ flags |= PIPE_BUFFER_USAGE_CPU_READ;
+
+ if (transfer->usage != PIPE_TRANSFER_READ)
+ flags |= PIPE_BUFFER_USAGE_CPU_WRITE;
+
+ map = pipe_buffer_map( screen, tex->buffer, flags );
if (map == NULL)
return NULL;
- if (surface->texture &&
+ if (transfer->texture &&
(flags & PIPE_BUFFER_USAGE_CPU_WRITE))
{
/* Do something to notify contexts of a texture change.
@@ -222,14 +284,16 @@ i915_surface_map( struct pipe_screen *screen,
/* i915_screen(screen)->timestamp++; */
}
- return map + surface->offset;
+ return map + i915_transfer(transfer)->offset +
+ transfer->y / transfer->block.height * transfer->stride +
+ transfer->x / transfer->block.width * transfer->block.size;
}
static void
-i915_surface_unmap(struct pipe_screen *screen,
- struct pipe_surface *surface)
+i915_transfer_unmap(struct pipe_screen *screen,
+ struct pipe_transfer *transfer)
{
- struct i915_texture *tex = (struct i915_texture *)surface->texture;
+ struct i915_texture *tex = (struct i915_texture *)transfer->texture;
pipe_buffer_unmap( screen, tex->buffer );
}
@@ -278,8 +342,10 @@ i915_create_screen(struct pipe_winsys *winsys, uint pci_id)
i915screen->screen.get_param = i915_get_param;
i915screen->screen.get_paramf = i915_get_paramf;
i915screen->screen.is_format_supported = i915_is_format_supported;
- i915screen->screen.surface_map = i915_surface_map;
- i915screen->screen.surface_unmap = i915_surface_unmap;
+ i915screen->screen.get_tex_transfer = i915_get_tex_transfer;
+ i915screen->screen.tex_transfer_release = i915_tex_transfer_release;
+ i915screen->screen.transfer_map = i915_transfer_map;
+ i915screen->screen.transfer_unmap = i915_transfer_unmap;
i915_init_screen_texture_functions(&i915screen->screen);
u_simple_screen_init(&i915screen->screen);
diff --git a/src/gallium/drivers/i915simple/i915_screen.h b/src/gallium/drivers/i915simple/i915_screen.h
index 73b0ff05ce..a371663453 100644
--- a/src/gallium/drivers/i915simple/i915_screen.h
+++ b/src/gallium/drivers/i915simple/i915_screen.h
@@ -50,13 +50,30 @@ struct i915_screen
};
-/** cast wrapper */
+/**
+ * Subclass of pipe_transfer
+ */
+struct i915_transfer
+{
+ struct pipe_transfer base;
+
+ unsigned offset;
+};
+
+
+/** cast wrappers */
static INLINE struct i915_screen *
i915_screen(struct pipe_screen *pscreen)
{
return (struct i915_screen *) pscreen;
}
+static INLINE struct i915_transfer *
+i915_transfer( struct pipe_transfer *transfer )
+{
+ return (struct i915_transfer *)transfer;
+}
+
extern struct pipe_screen *
i915_create_screen(struct pipe_winsys *winsys, uint pci_id);
diff --git a/src/gallium/drivers/i915simple/i915_state_emit.c b/src/gallium/drivers/i915simple/i915_state_emit.c
index 6558cf1c3e..26e03f5127 100644
--- a/src/gallium/drivers/i915simple/i915_state_emit.c
+++ b/src/gallium/drivers/i915simple/i915_state_emit.c
@@ -211,7 +211,6 @@ i915_emit_hardware_state(struct i915_context *i915 )
struct pipe_surface *depth_surface = i915->framebuffer.zsbuf;
if (cbuf_surface) {
- unsigned cpitch = cbuf_surface->stride;
unsigned ctile = BUF_3D_USE_FENCE;
struct i915_texture *tex = (struct i915_texture *)
cbuf_surface->texture;
@@ -225,7 +224,7 @@ i915_emit_hardware_state(struct i915_context *i915 )
OUT_BATCH(_3DSTATE_BUF_INFO_CMD);
OUT_BATCH(BUF_3D_ID_COLOR_BACK |
- BUF_3D_PITCH(cpitch) | /* pitch in bytes */
+ BUF_3D_PITCH(tex->stride) | /* pitch in bytes */
ctile);
OUT_RELOC(tex->buffer,
@@ -236,7 +235,6 @@ i915_emit_hardware_state(struct i915_context *i915 )
/* What happens if no zbuf??
*/
if (depth_surface) {
- unsigned zpitch = depth_surface->stride;
unsigned ztile = BUF_3D_USE_FENCE;
struct i915_texture *tex = (struct i915_texture *)
depth_surface->texture;
@@ -250,7 +248,7 @@ i915_emit_hardware_state(struct i915_context *i915 )
OUT_BATCH(_3DSTATE_BUF_INFO_CMD);
OUT_BATCH(BUF_3D_ID_DEPTH |
- BUF_3D_PITCH(zpitch) | /* pitch in bytes */
+ BUF_3D_PITCH(tex->stride) | /* pitch in bytes */
ztile);
OUT_RELOC(tex->buffer,
diff --git a/src/gallium/drivers/i915simple/i915_surface.c b/src/gallium/drivers/i915simple/i915_surface.c
index 94e2deaf61..7eec649906 100644
--- a/src/gallium/drivers/i915simple/i915_surface.c
+++ b/src/gallium/drivers/i915simple/i915_surface.c
@@ -47,44 +47,22 @@ i915_surface_copy(struct pipe_context *pipe,
struct pipe_surface *src,
unsigned srcx, unsigned srcy, unsigned width, unsigned height)
{
- assert( dst != src );
- assert( dst->block.size == src->block.size );
- assert( dst->block.width == src->block.height );
- assert( dst->block.height == src->block.height );
+ struct i915_texture *dst_tex = (struct i915_texture *)dst->texture;
+ struct i915_texture *src_tex = (struct i915_texture *)src->texture;
- if (0) {
- void *dst_map = pipe->screen->surface_map( pipe->screen,
- dst,
- PIPE_BUFFER_USAGE_CPU_WRITE );
-
- const void *src_map = pipe->screen->surface_map( pipe->screen,
- src,
- PIPE_BUFFER_USAGE_CPU_READ );
-
- pipe_copy_rect(dst_map,
- &dst->block,
- dst->stride,
- dstx, dsty,
- width, height,
- src_map,
- do_flip ? -(int) src->stride : src->stride,
- srcx, do_flip ? height - 1 - srcy : srcy);
+ assert( dst != src );
+ assert( dst_tex->base.block.size == src_tex->base.block.size );
+ assert( dst_tex->base.block.width == src_tex->base.block.height );
+ assert( dst_tex->base.block.height == src_tex->base.block.height );
+ assert( dst_tex->base.block.width == 1 );
+ assert( dst_tex->base.block.height == 1 );
- pipe->screen->surface_unmap(pipe->screen, src);
- pipe->screen->surface_unmap(pipe->screen, dst);
- }
- else {
- struct i915_texture *dst_tex = (struct i915_texture *)dst->texture;
- struct i915_texture *src_tex = (struct i915_texture *)src->texture;
- assert(dst->block.width == 1);
- assert(dst->block.height == 1);
- i915_copy_blit( i915_context(pipe),
- do_flip,
- dst->block.size,
- (unsigned short) src->stride, src_tex->buffer, src->offset,
- (unsigned short) dst->stride, dst_tex->buffer, dst->offset,
- (short) srcx, (short) srcy, (short) dstx, (short) dsty, (short) width, (short) height );
- }
+ i915_copy_blit( i915_context(pipe),
+ do_flip,
+ dst_tex->base.block.size,
+ (unsigned short) src_tex->stride, src_tex->buffer, src->offset,
+ (unsigned short) dst_tex->stride, dst_tex->buffer, dst->offset,
+ (short) srcx, (short) srcy, (short) dstx, (short) dsty, (short) width, (short) height );
}
@@ -94,27 +72,18 @@ i915_surface_fill(struct pipe_context *pipe,
unsigned dstx, unsigned dsty,
unsigned width, unsigned height, unsigned value)
{
- if (0) {
- void *dst_map = pipe->screen->surface_map( pipe->screen,
- dst,
- PIPE_BUFFER_USAGE_CPU_WRITE );
+ struct i915_texture *tex = (struct i915_texture *)dst->texture;
- pipe_fill_rect(dst_map, &dst->block, dst->stride, dstx, dsty, width, height, value);
+ assert(tex->base.block.width == 1);
+ assert(tex->base.block.height == 1);
- pipe->screen->surface_unmap(pipe->screen, dst);
- }
- else {
- struct i915_texture *tex = (struct i915_texture *)dst->texture;
- assert(dst->block.width == 1);
- assert(dst->block.height == 1);
- i915_fill_blit( i915_context(pipe),
- dst->block.size,
- (unsigned short) dst->stride,
- tex->buffer, dst->offset,
- (short) dstx, (short) dsty,
- (short) width, (short) height,
- value );
- }
+ i915_fill_blit( i915_context(pipe),
+ tex->base.block.size,
+ (unsigned short) tex->stride,
+ tex->buffer, dst->offset,
+ (short) dstx, (short) dsty,
+ (short) width, (short) height,
+ value );
}
diff --git a/src/gallium/drivers/i915simple/i915_texture.c b/src/gallium/drivers/i915simple/i915_texture.c
index b2ca3a2286..957726523f 100644
--- a/src/gallium/drivers/i915simple/i915_texture.c
+++ b/src/gallium/drivers/i915simple/i915_texture.c
@@ -686,10 +686,6 @@ i915_get_tex_surface(struct pipe_screen *screen,
ps->format = pt->format;
ps->width = pt->width[level];
ps->height = pt->height[level];
- ps->block = pt->block;
- ps->nblocksx = pt->nblocksx[level];
- ps->nblocksy = pt->nblocksy[level];
- ps->stride = tex->stride;
ps->offset = offset;
ps->usage = flags;
ps->status = PIPE_SURFACE_STATUS_DEFINED;
diff --git a/src/gallium/drivers/softpipe/sp_context.c b/src/gallium/drivers/softpipe/sp_context.c
index c2d882a819..ff5d1b54a4 100644
--- a/src/gallium/drivers/softpipe/sp_context.c
+++ b/src/gallium/drivers/softpipe/sp_context.c
@@ -53,15 +53,15 @@
* Map any drawing surfaces which aren't already mapped
*/
void
-softpipe_map_surfaces(struct softpipe_context *sp)
+softpipe_map_transfers(struct softpipe_context *sp)
{
unsigned i;
for (i = 0; i < sp->framebuffer.nr_cbufs; i++) {
- sp_tile_cache_map_surfaces(sp->cbuf_cache[i]);
+ sp_tile_cache_map_transfers(sp->cbuf_cache[i]);
}
- sp_tile_cache_map_surfaces(sp->zsbuf_cache);
+ sp_tile_cache_map_transfers(sp->zsbuf_cache);
}
@@ -69,7 +69,7 @@ softpipe_map_surfaces(struct softpipe_context *sp)
* Unmap any mapped drawing surfaces
*/
void
-softpipe_unmap_surfaces(struct softpipe_context *sp)
+softpipe_unmap_transfers(struct softpipe_context *sp)
{
uint i;
@@ -78,9 +78,9 @@ softpipe_unmap_surfaces(struct softpipe_context *sp)
sp_flush_tile_cache(sp, sp->zsbuf_cache);
for (i = 0; i < sp->framebuffer.nr_cbufs; i++) {
- sp_tile_cache_unmap_surfaces(sp->cbuf_cache[i]);
+ sp_tile_cache_unmap_transfers(sp->cbuf_cache[i]);
}
- sp_tile_cache_unmap_surfaces(sp->zsbuf_cache);
+ sp_tile_cache_unmap_transfers(sp->zsbuf_cache);
}
diff --git a/src/gallium/drivers/softpipe/sp_draw_arrays.c b/src/gallium/drivers/softpipe/sp_draw_arrays.c
index 7e3a25e34b..f117096bf7 100644
--- a/src/gallium/drivers/softpipe/sp_draw_arrays.c
+++ b/src/gallium/drivers/softpipe/sp_draw_arrays.c
@@ -134,7 +134,7 @@ softpipe_draw_range_elements(struct pipe_context *pipe,
if (sp->dirty)
softpipe_update_derived( sp );
- softpipe_map_surfaces(sp);
+ softpipe_map_transfers(sp);
softpipe_map_constant_buffers(sp);
/*
diff --git a/src/gallium/drivers/softpipe/sp_flush.c b/src/gallium/drivers/softpipe/sp_flush.c
index c21faf57f3..035f4b963e 100644
--- a/src/gallium/drivers/softpipe/sp_flush.c
+++ b/src/gallium/drivers/softpipe/sp_flush.c
@@ -70,7 +70,7 @@ softpipe_flush( struct pipe_context *pipe,
* that's called before swapbuffers because we don't always want
* to unmap surfaces when flushing.
*/
- softpipe_unmap_surfaces(softpipe);
+ softpipe_unmap_transfers(softpipe);
}
/* Enable to dump BMPs of the color/depth buffers each frame */
diff --git a/src/gallium/drivers/softpipe/sp_state.h b/src/gallium/drivers/softpipe/sp_state.h
index 3eff41ffa5..6f558e6da5 100644
--- a/src/gallium/drivers/softpipe/sp_state.h
+++ b/src/gallium/drivers/softpipe/sp_state.h
@@ -184,10 +184,10 @@ softpipe_set_edgeflags(struct pipe_context *pipe, const unsigned *edgeflags);
void
-softpipe_map_surfaces(struct softpipe_context *sp);
+softpipe_map_transfers(struct softpipe_context *sp);
void
-softpipe_unmap_surfaces(struct softpipe_context *sp);
+softpipe_unmap_transfers(struct softpipe_context *sp);
void
softpipe_map_texture_surfaces(struct softpipe_context *sp);
diff --git a/src/gallium/drivers/softpipe/sp_texture.c b/src/gallium/drivers/softpipe/sp_texture.c
index 3eed0d0d29..28a9784b16 100644
--- a/src/gallium/drivers/softpipe/sp_texture.c
+++ b/src/gallium/drivers/softpipe/sp_texture.c
@@ -215,12 +215,8 @@ softpipe_get_tex_surface(struct pipe_screen *screen,
ps->refcount = 1;
pipe_texture_reference(&ps->texture, pt);
ps->format = pt->format;
- ps->block = pt->block;
ps->width = pt->width[level];
ps->height = pt->height[level];
- ps->nblocksx = pt->nblocksx[level];
- ps->nblocksy = pt->nblocksy[level];
- ps->stride = spt->stride[level];
ps->offset = spt->level_offset[level];
ps->usage = usage;
@@ -249,8 +245,7 @@ softpipe_get_tex_surface(struct pipe_screen *screen,
if (pt->target == PIPE_TEXTURE_CUBE || pt->target == PIPE_TEXTURE_3D) {
ps->offset += ((pt->target == PIPE_TEXTURE_CUBE) ? face : zslice) *
- ps->nblocksy *
- ps->stride;
+ pt->nblocksy[level] * spt->stride[level];
}
else {
assert(face == 0);
@@ -279,21 +274,91 @@ softpipe_tex_surface_release(struct pipe_screen *screen,
}
+static struct pipe_transfer *
+softpipe_get_tex_transfer(struct pipe_screen *screen,
+ struct pipe_texture *texture,
+ unsigned face, unsigned level, unsigned zslice,
+ enum pipe_transfer_usage usage,
+ unsigned x, unsigned y, unsigned w, unsigned h)
+{
+ struct softpipe_texture *sptex = softpipe_texture(texture);
+ struct softpipe_transfer *spt;
+ struct pipe_transfer *pt;
+
+ assert(texture);
+ assert(level <= texture->last_level);
+
+ spt = CALLOC_STRUCT(softpipe_transfer);
+ pt = &spt->base;
+ if (spt) {
+ pt->refcount = 1;
+ pipe_texture_reference(&pt->texture, texture);
+ pt->format = texture->format;
+ pt->block = texture->block;
+ pt->x = x;
+ pt->y = y;
+ pt->width = w;
+ pt->height = h;
+ pt->nblocksx = texture->nblocksx[level];
+ pt->nblocksy = texture->nblocksy[level];
+ pt->stride = sptex->stride[level];
+ spt->offset = sptex->level_offset[level];
+ pt->usage = usage;
+ pt->face = face;
+ pt->level = level;
+ pt->zslice = zslice;
+
+ if (texture->target == PIPE_TEXTURE_CUBE ||
+ texture->target == PIPE_TEXTURE_3D) {
+ spt->offset += ((texture->target == PIPE_TEXTURE_CUBE) ? face :
+ zslice) * pt->nblocksy * pt->stride;
+ }
+ else {
+ assert(face == 0);
+ assert(zslice == 0);
+ }
+ }
+ return pt;
+}
+
+
+static void
+softpipe_tex_transfer_release(struct pipe_screen *screen,
+ struct pipe_transfer **t)
+{
+ struct softpipe_transfer *transfer = softpipe_transfer(*t);
+ /* Effectively do the texture_update work here - if texture images
+ * needed post-processing to put them into hardware layout, this is
+ * where it would happen. For softpipe, nothing to do.
+ */
+ assert (transfer->base.texture);
+ if (--transfer->base.refcount == 0) {
+ pipe_texture_reference(&transfer->base.texture, NULL);
+ FREE(transfer);
+ }
+ *t = NULL;
+}
+
+
static void *
-softpipe_surface_map( struct pipe_screen *screen,
- struct pipe_surface *surface,
- unsigned flags )
+softpipe_transfer_map( struct pipe_screen *screen,
+ struct pipe_transfer *transfer )
{
ubyte *map;
struct softpipe_texture *spt;
+ unsigned flags = 0;
- if (flags & ~surface->usage) {
- assert(0);
- return NULL;
+ assert(transfer->texture);
+ spt = softpipe_texture(transfer->texture);
+
+ if (transfer->usage != PIPE_TRANSFER_READ) {
+ flags |= PIPE_BUFFER_USAGE_CPU_WRITE;
+ }
+
+ if (transfer->usage != PIPE_TRANSFER_WRITE) {
+ flags |= PIPE_BUFFER_USAGE_CPU_READ;
}
- assert(surface->texture);
- spt = softpipe_texture(surface->texture);
map = pipe_buffer_map(screen, spt->buffer, flags);
if (map == NULL)
return NULL;
@@ -301,8 +366,7 @@ softpipe_surface_map( struct pipe_screen *screen,
/* May want to different things here depending on read/write nature
* of the map:
*/
- if (surface->texture &&
- (flags & PIPE_BUFFER_USAGE_CPU_WRITE))
+ if (transfer->texture && transfer->usage != PIPE_TRANSFER_READ)
{
/* Do something to notify sharing contexts of a texture change.
* In softpipe, that would mean flushing the texture cache.
@@ -310,18 +374,20 @@ softpipe_surface_map( struct pipe_screen *screen,
softpipe_screen(screen)->timestamp++;
}
- return map + surface->offset;
+ return map + softpipe_transfer(transfer)->offset +
+ transfer->y / transfer->block.height * transfer->stride +
+ transfer->x / transfer->block.width * transfer->block.size;
}
static void
-softpipe_surface_unmap(struct pipe_screen *screen,
- struct pipe_surface *surface)
+softpipe_transfer_unmap(struct pipe_screen *screen,
+ struct pipe_transfer *transfer)
{
struct softpipe_texture *spt;
- assert(surface->texture);
- spt = softpipe_texture(surface->texture);
+ assert(transfer->texture);
+ spt = softpipe_texture(transfer->texture);
pipe_buffer_unmap( screen, spt->buffer );
}
@@ -343,6 +409,8 @@ softpipe_init_screen_texture_funcs(struct pipe_screen *screen)
screen->get_tex_surface = softpipe_get_tex_surface;
screen->tex_surface_release = softpipe_tex_surface_release;
- screen->surface_map = softpipe_surface_map;
- screen->surface_unmap = softpipe_surface_unmap;
+ screen->get_tex_transfer = softpipe_get_tex_transfer;
+ screen->tex_transfer_release = softpipe_tex_transfer_release;
+ screen->transfer_map = softpipe_transfer_map;
+ screen->transfer_unmap = softpipe_transfer_unmap;
}
diff --git a/src/gallium/drivers/softpipe/sp_texture.h b/src/gallium/drivers/softpipe/sp_texture.h
index c1636920cd..893aa7d11d 100644
--- a/src/gallium/drivers/softpipe/sp_texture.h
+++ b/src/gallium/drivers/softpipe/sp_texture.h
@@ -51,14 +51,27 @@ struct softpipe_texture
boolean modified;
};
+struct softpipe_transfer
+{
+ struct pipe_transfer base;
+
+ unsigned long offset;
+};
+
-/** cast wrapper */
+/** cast wrappers */
static INLINE struct softpipe_texture *
softpipe_texture(struct pipe_texture *pt)
{
return (struct softpipe_texture *) pt;
}
+static INLINE struct softpipe_transfer *
+softpipe_transfer(struct pipe_transfer *pt)
+{
+ return (struct softpipe_transfer *) pt;
+}
+
extern void
softpipe_init_texture_funcs( struct softpipe_context *softpipe );
diff --git a/src/gallium/drivers/softpipe/sp_tile_cache.c b/src/gallium/drivers/softpipe/sp_tile_cache.c
index bd5a672f77..593360aab0 100644
--- a/src/gallium/drivers/softpipe/sp_tile_cache.c
+++ b/src/gallium/drivers/softpipe/sp_tile_cache.c
@@ -26,7 +26,7 @@
**************************************************************************/
/**
- * Framebuffer/surface tile caching.
+ * Texture tile caching.
*
* Author:
* Brian Paul
@@ -52,7 +52,8 @@ struct softpipe_tile_cache
{
struct pipe_screen *screen;
struct pipe_surface *surface; /**< the surface we're caching */
- void *surface_map;
+ struct pipe_transfer *transfer;
+ void *transfer_map;
struct pipe_texture *texture; /**< if caching a texture */
struct softpipe_cached_tile entries[NUM_ENTRIES];
uint clear_flags[(MAX_WIDTH / TILE_SIZE) * (MAX_HEIGHT / TILE_SIZE) / 32];
@@ -60,8 +61,8 @@ struct softpipe_tile_cache
uint clear_val;
boolean depth_stencil; /** Is the surface a depth/stencil format? */
- struct pipe_surface *tex_surf;
- void *tex_surf_map;
+ struct pipe_transfer *tex_trans;
+ void *tex_trans_map;
int tex_face, tex_level, tex_z;
struct softpipe_cached_tile tile; /**< scratch tile for clears */
@@ -131,16 +132,19 @@ sp_create_tile_cache( struct pipe_screen *screen )
void
sp_destroy_tile_cache(struct softpipe_tile_cache *tc)
{
+ struct pipe_screen *screen;
uint pos;
for (pos = 0; pos < NUM_ENTRIES; pos++) {
/*assert(tc->entries[pos].x < 0);*/
}
- if (tc->surface) {
- pipe_surface_reference(&tc->surface, NULL);
+ if (tc->transfer) {
+ screen = tc->transfer->texture->screen;
+ screen->tex_transfer_release(screen, &tc->transfer);
}
- if (tc->tex_surf) {
- pipe_surface_reference(&tc->tex_surf, NULL);
+ if (tc->tex_trans) {
+ screen = tc->tex_trans->texture->screen;
+ screen->tex_transfer_release(screen, &tc->tex_trans);
}
FREE( tc );
@@ -156,18 +160,29 @@ sp_tile_cache_set_surface(struct softpipe_tile_cache *tc,
{
assert(!tc->texture);
- if (tc->surface_map) {
- tc->screen->surface_unmap(tc->screen, tc->surface);
- tc->surface_map = NULL;
+ if (tc->transfer) {
+ struct pipe_screen *screen = tc->transfer->texture->screen;
+
+ if (ps == tc->surface)
+ return;
+
+ if (tc->transfer_map) {
+ tc->screen->transfer_unmap(tc->screen, tc->transfer);
+ tc->transfer_map = NULL;
+ }
+
+ screen->tex_transfer_release(screen, &tc->transfer);
}
- pipe_surface_reference(&tc->surface, ps);
+ tc->surface = ps;
+
+ if (ps) {
+ struct pipe_screen *screen = ps->texture->screen;
- if (tc->surface) {
- if (tc->surface_map) /* XXX: this is always NULL!? */
- tc->surface_map = tc->screen->surface_map(tc->screen, tc->surface,
- PIPE_BUFFER_USAGE_CPU_READ |
- PIPE_BUFFER_USAGE_CPU_WRITE);
+ tc->transfer = screen->get_tex_transfer(screen, ps->texture, ps->face,
+ ps->level, ps->zslice,
+ PIPE_TRANSFER_READ_WRITE,
+ 0, 0, ps->width, ps->height);
tc->depth_stencil = (ps->format == PIPE_FORMAT_S8Z24_UNORM ||
ps->format == PIPE_FORMAT_X8Z24_UNORM ||
@@ -181,7 +196,7 @@ sp_tile_cache_set_surface(struct softpipe_tile_cache *tc,
/**
- * Return the surface being cached.
+ * Return the transfer being cached.
*/
struct pipe_surface *
sp_tile_cache_get_surface(struct softpipe_tile_cache *tc)
@@ -191,30 +206,27 @@ sp_tile_cache_get_surface(struct softpipe_tile_cache *tc)
void
-sp_tile_cache_map_surfaces(struct softpipe_tile_cache *tc)
+sp_tile_cache_map_transfers(struct softpipe_tile_cache *tc)
{
- if (tc->surface && !tc->surface_map)
- tc->surface_map = tc->screen->surface_map(tc->screen, tc->surface,
- PIPE_BUFFER_USAGE_CPU_WRITE |
- PIPE_BUFFER_USAGE_CPU_READ);
-
- if (tc->tex_surf && !tc->tex_surf_map)
- tc->tex_surf_map = tc->screen->surface_map(tc->screen, tc->tex_surf,
- PIPE_BUFFER_USAGE_CPU_READ);
+ if (tc->transfer && !tc->transfer_map)
+ tc->transfer_map = tc->screen->transfer_map(tc->screen, tc->transfer);
+
+ if (tc->tex_trans && !tc->tex_trans_map)
+ tc->tex_trans_map = tc->screen->transfer_map(tc->screen, tc->tex_trans);
}
void
-sp_tile_cache_unmap_surfaces(struct softpipe_tile_cache *tc)
+sp_tile_cache_unmap_transfers(struct softpipe_tile_cache *tc)
{
- if (tc->surface_map) {
- tc->screen->surface_unmap(tc->screen, tc->surface);
- tc->surface_map = NULL;
+ if (tc->transfer_map) {
+ tc->screen->transfer_unmap(tc->screen, tc->transfer);
+ tc->transfer_map = NULL;
}
- if (tc->tex_surf_map) {
- tc->screen->surface_unmap(tc->screen, tc->tex_surf);
- tc->tex_surf_map = NULL;
+ if (tc->tex_trans_map) {
+ tc->screen->transfer_unmap(tc->screen, tc->tex_trans);
+ tc->tex_trans_map = NULL;
}
}
@@ -229,15 +241,20 @@ sp_tile_cache_set_texture(struct pipe_context *pipe,
{
uint i;
- assert(!tc->surface);
+ assert(!tc->transfer);
pipe_texture_reference(&tc->texture, texture);
- if (tc->tex_surf_map) {
- tc->screen->surface_unmap(tc->screen, tc->tex_surf);
- tc->tex_surf_map = NULL;
+ if (tc->transfer) {
+ struct pipe_screen *screen = tc->transfer->texture->screen;
+
+ if (tc->tex_trans_map) {
+ tc->screen->transfer_unmap(tc->screen, tc->tex_trans);
+ tc->tex_trans_map = NULL;
+ }
+
+ screen->tex_transfer_release(screen, &tc->tex_trans);
}
- pipe_surface_reference(&tc->tex_surf, NULL);
/* mark as entries as invalid/empty */
/* XXX we should try to avoid this when the teximage hasn't changed */
@@ -328,20 +345,20 @@ static void
sp_tile_cache_flush_clear(struct pipe_context *pipe,
struct softpipe_tile_cache *tc)
{
- struct pipe_surface *ps = tc->surface;
- const uint w = tc->surface->width;
- const uint h = tc->surface->height;
+ struct pipe_transfer *pt = tc->transfer;
+ 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, ps->format, tc->clear_val);
+ 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) {
if (is_clear_flag_set(tc->clear_flags, x, y)) {
- pipe_put_tile_raw(ps,
+ pipe_put_tile_raw(pt,
x, y, TILE_SIZE, TILE_SIZE,
tc->tile.data.color32, 0/*STRIDE*/);
@@ -359,28 +376,28 @@ sp_tile_cache_flush_clear(struct pipe_context *pipe,
/**
- * Flush the tile cache: write all dirty tiles back to the surface.
+ * Flush the tile cache: write all dirty tiles back to the transfer.
* any tiles "flagged" as cleared will be "really" cleared.
*/
void
sp_flush_tile_cache(struct softpipe_context *softpipe,
struct softpipe_tile_cache *tc)
{
- struct pipe_surface *ps = tc->surface;
+ struct pipe_transfer *pt = tc->transfer;
int inuse = 0, pos;
- if (ps) {
- /* caching a drawing surface */
+ if (pt) {
+ /* caching a drawing transfer */
for (pos = 0; pos < NUM_ENTRIES; pos++) {
struct softpipe_cached_tile *tile = tc->entries + pos;
if (tile->x >= 0) {
if (tc->depth_stencil) {
- pipe_put_tile_raw(ps,
+ pipe_put_tile_raw(pt,
tile->x, tile->y, TILE_SIZE, TILE_SIZE,
tile->data.depth32, 0/*STRIDE*/);
}
else {
- pipe_put_tile_rgba(ps,
+ pipe_put_tile_rgba(pt,
tile->x, tile->y, TILE_SIZE, TILE_SIZE,
(float *) tile->data.color);
}
@@ -415,7 +432,7 @@ struct softpipe_cached_tile *
sp_get_cached_tile(struct softpipe_context *softpipe,
struct softpipe_tile_cache *tc, int x, int y)
{
- struct pipe_surface *ps = tc->surface;
+ struct pipe_transfer *pt = tc->transfer;
/* tile pos in framebuffer: */
const int tile_x = x & ~(TILE_SIZE - 1);
@@ -431,12 +448,12 @@ sp_get_cached_tile(struct softpipe_context *softpipe,
if (tile->x != -1) {
/* put dirty tile back in framebuffer */
if (tc->depth_stencil) {
- pipe_put_tile_raw(ps,
+ pipe_put_tile_raw(pt,
tile->x, tile->y, TILE_SIZE, TILE_SIZE,
tile->data.depth32, 0/*STRIDE*/);
}
else {
- pipe_put_tile_rgba(ps,
+ pipe_put_tile_rgba(pt,
tile->x, tile->y, TILE_SIZE, TILE_SIZE,
(float *) tile->data.color);
}
@@ -448,22 +465,22 @@ sp_get_cached_tile(struct softpipe_context *softpipe,
if (is_clear_flag_set(tc->clear_flags, x, y)) {
/* don't get tile from framebuffer, just clear it */
if (tc->depth_stencil) {
- clear_tile(tile, ps->format, tc->clear_val);
+ clear_tile(tile, pt->format, tc->clear_val);
}
else {
- clear_tile_rgba(tile, ps->format, tc->clear_color);
+ clear_tile_rgba(tile, pt->format, tc->clear_color);
}
clear_clear_flag(tc->clear_flags, x, y);
}
else {
- /* get new tile data from surface */
+ /* get new tile data from transfer */
if (tc->depth_stencil) {
- pipe_get_tile_raw(ps,
+ pipe_get_tile_raw(pt,
tile->x, tile->y, TILE_SIZE, TILE_SIZE,
tile->data.depth32, 0/*STRIDE*/);
}
else {
- pipe_get_tile_rgba(ps,
+ pipe_get_tile_rgba(pt,
tile->x, tile->y, TILE_SIZE, TILE_SIZE,
(float *) tile->data.color);
}
@@ -531,28 +548,33 @@ sp_get_cached_tile_tex(struct softpipe_context *sp,
printf("miss at %u x=%d y=%d z=%d face=%d level=%d\n", pos,
x/TILE_SIZE, y/TILE_SIZE, z, face, level);
#endif
- /* check if we need to get a new surface */
- if (!tc->tex_surf ||
+ /* check if we need to get a new transfer */
+ if (!tc->tex_trans ||
tc->tex_face != face ||
tc->tex_level != level ||
tc->tex_z != z) {
- /* get new surface (view into texture) */
+ /* get new transfer (view into texture) */
+
+ if (tc->transfer) {
+ if (tc->tex_trans_map)
+ tc->screen->transfer_unmap(tc->screen, tc->tex_trans);
- if (tc->tex_surf_map)
- tc->screen->surface_unmap(tc->screen, tc->tex_surf);
+ screen->tex_transfer_release(screen, &tc->tex_trans);
+ }
- tc->tex_surf = screen->get_tex_surface(screen, tc->texture, face, level, z,
- PIPE_BUFFER_USAGE_CPU_READ);
- tc->tex_surf_map = screen->surface_map(screen, tc->tex_surf,
- PIPE_BUFFER_USAGE_CPU_READ);
+ tc->tex_trans = screen->get_tex_transfer(screen, tc->texture, face, level, z,
+ PIPE_TRANSFER_READ, 0, 0,
+ tc->texture->width[level],
+ tc->texture->height[level]);
+ tc->tex_trans_map = screen->transfer_map(screen, tc->tex_trans);
tc->tex_face = face;
tc->tex_level = level;
tc->tex_z = z;
}
- /* get tile from the surface (view into texture) */
- pipe_get_tile_rgba(tc->tex_surf,
+ /* get tile from the transfer (view into texture) */
+ pipe_get_tile_rgba(tc->tex_trans,
tile_x, tile_y, TILE_SIZE, TILE_SIZE,
(float *) tile->data.color);
tile->x = tile_x;
@@ -579,7 +601,7 @@ sp_tile_cache_clear(struct softpipe_tile_cache *tc, uint clearValue)
tc->clear_val = clearValue;
- switch (tc->surface->format) {
+ switch (tc->transfer->format) {
case PIPE_FORMAT_R8G8B8A8_UNORM:
r = (clearValue >> 24) & 0xff;
g = (clearValue >> 16) & 0xff;
diff --git a/src/gallium/drivers/softpipe/sp_tile_cache.h b/src/gallium/drivers/softpipe/sp_tile_cache.h
index a66bb50bcc..9ac3fdda94 100644
--- a/src/gallium/drivers/softpipe/sp_tile_cache.h
+++ b/src/gallium/drivers/softpipe/sp_tile_cache.h
@@ -74,10 +74,10 @@ extern struct pipe_surface *
sp_tile_cache_get_surface(struct softpipe_tile_cache *tc);
extern void
-sp_tile_cache_map_surfaces(struct softpipe_tile_cache *tc);
+sp_tile_cache_map_transfers(struct softpipe_tile_cache *tc);
extern void
-sp_tile_cache_unmap_surfaces(struct softpipe_tile_cache *tc);
+sp_tile_cache_unmap_transfers(struct softpipe_tile_cache *tc);
extern void
sp_tile_cache_set_texture(struct pipe_context *pipe,
diff --git a/src/gallium/include/pipe/p_defines.h b/src/gallium/include/pipe/p_defines.h
index 4f0b301f31..0d70348c11 100644
--- a/src/gallium/include/pipe/p_defines.h
+++ b/src/gallium/include/pipe/p_defines.h
@@ -194,6 +194,16 @@ enum pipe_texture_target {
/**
+ * Transfer object usage flags
+ */
+enum pipe_transfer_usage {
+ PIPE_TRANSFER_READ,
+ PIPE_TRANSFER_WRITE,
+ PIPE_TRANSFER_READ_WRITE //< Read/modify/write
+};
+
+
+/**
* Buffer usage flags
*/
#define PIPE_BUFFER_USAGE_CPU_READ (1 << 0)
diff --git a/src/gallium/include/pipe/p_inlines.h b/src/gallium/include/pipe/p_inlines.h
index 1219c817b4..76460d2724 100644
--- a/src/gallium/include/pipe/p_inlines.h
+++ b/src/gallium/include/pipe/p_inlines.h
@@ -38,29 +38,6 @@ extern "C" {
#endif
-/* XXX: these are a kludge. will fix when all surfaces are views into
- * textures, and free-floating winsys surfaces go away.
- */
-static INLINE void *
-pipe_surface_map( struct pipe_surface *surf, unsigned flags )
-{
- struct pipe_screen *screen;
- assert(surf->texture);
- screen = surf->texture->screen;
- return screen->surface_map( screen, surf, flags );
-}
-
-static INLINE void
-pipe_surface_unmap( struct pipe_surface *surf )
-{
- struct pipe_screen *screen;
- assert(surf->texture);
- screen = surf->texture->screen;
- screen->surface_unmap( screen, surf );
-}
-
-
-
/**
* Set 'ptr' to point to 'surf' and update reference counting.
* The old thing pointed to, if any, will be unreferenced first.
diff --git a/src/gallium/include/pipe/p_screen.h b/src/gallium/include/pipe/p_screen.h
index 17d1548253..341d1caea0 100644
--- a/src/gallium/include/pipe/p_screen.h
+++ b/src/gallium/include/pipe/p_screen.h
@@ -55,6 +55,7 @@ struct pipe_winsys;
struct pipe_buffer;
+
/**
* Gallium screen/adapter context. Basically everything
* hardware-specific that doesn't actually require a rendering
@@ -128,12 +129,25 @@ struct pipe_screen {
struct pipe_surface ** );
- void *(*surface_map)( struct pipe_screen *,
- struct pipe_surface *surface,
- unsigned flags );
+ /** Get a transfer object for transferring data to/from a texture */
+ struct pipe_transfer *(*get_tex_transfer)(struct pipe_screen *,
+ struct pipe_texture *texture,
+ unsigned face, unsigned level,
+ unsigned zslice,
+ enum pipe_transfer_usage usage,
+ unsigned x, unsigned y,
+ unsigned w, unsigned h);
+
+ /* Transfer objects allocated by the above must be released here:
+ */
+ void (*tex_transfer_release)( struct pipe_screen *,
+ struct pipe_transfer ** );
+
+ void *(*transfer_map)( struct pipe_screen *,
+ struct pipe_transfer *transfer );
- void (*surface_unmap)( struct pipe_screen *,
- struct pipe_surface *surface );
+ void (*transfer_unmap)( struct pipe_screen *,
+ struct pipe_transfer *transfer );
/**
diff --git a/src/gallium/include/pipe/p_state.h b/src/gallium/include/pipe/p_state.h
index 9dc541630c..a2e839da5c 100644
--- a/src/gallium/include/pipe/p_state.h
+++ b/src/gallium/include/pipe/p_state.h
@@ -280,10 +280,6 @@ struct pipe_surface
unsigned clear_value; /**< XXX may be temporary */
unsigned width; /**< logical width in pixels */
unsigned height; /**< logical height in pixels */
- struct pipe_format_block block;
- unsigned nblocksx; /**< allocated width in blocks */
- unsigned nblocksy; /**< allocated height in blocks */
- unsigned stride; /**< stride in bytes between rows of blocks */
unsigned layout; /**< PIPE_SURFACE_LAYOUT_x */
unsigned offset; /**< offset from start of buffer, in bytes */
unsigned refcount;
@@ -297,6 +293,30 @@ struct pipe_surface
/**
+ * Transfer object. For data transfer to/from a texture.
+ */
+struct pipe_transfer
+{
+ enum pipe_format format; /**< PIPE_FORMAT_x */
+ unsigned x; /**< x offset from start of texture image */
+ unsigned y; /**< y offset from start of texture image */
+ unsigned width; /**< logical width in pixels */
+ unsigned height; /**< logical height in pixels */
+ struct pipe_format_block block;
+ unsigned nblocksx; /**< allocated width in blocks */
+ unsigned nblocksy; /**< allocated height in blocks */
+ unsigned stride; /**< stride in bytes between rows of blocks */
+ unsigned refcount;
+ unsigned usage; /**< PIPE_TRANSFER_* */
+
+ struct pipe_texture *texture; /**< texture to transfer to/from */
+ unsigned face;
+ unsigned level;
+ unsigned zslice;
+};
+
+
+/**
* Texture object.
*/
struct pipe_texture
diff --git a/src/gallium/state_trackers/g3dvl/vl_r16snorm_mc_buf.c b/src/gallium/state_trackers/g3dvl/vl_r16snorm_mc_buf.c
index 2176bb86d8..7cd753f736 100644
--- a/src/gallium/state_trackers/g3dvl/vl_r16snorm_mc_buf.c
+++ b/src/gallium/state_trackers/g3dvl/vl_r16snorm_mc_buf.c
@@ -66,7 +66,7 @@ struct vlR16SnormBufferedMC
struct vlVertex2f zero_block[3];
unsigned int num_macroblocks;
struct vlMpeg2MacroBlock *macroblocks;
- struct pipe_surface *tex_surface[3];
+ struct pipe_transfer *tex_transfer[3];
short *texels[3];
struct pipe_context *pipe;
@@ -187,7 +187,7 @@ static inline int vlGrabBlocks
assert(mc);
assert(blocks);
- tex_pitch = mc->tex_surface[0]->stride / mc->tex_surface[0]->block.size;
+ tex_pitch = mc->tex_transfer[0]->stride / mc->tex_transfer[0]->block.size;
texels = mc->texels[0] + mbpy * tex_pitch + mbpx;
for (y = 0; y < 2; ++y)
@@ -235,7 +235,7 @@ static inline int vlGrabBlocks
for (tb = 0; tb < 2; ++tb)
{
- tex_pitch = mc->tex_surface[tb + 1]->stride / mc->tex_surface[tb + 1]->block.size;
+ tex_pitch = mc->tex_transfer[tb + 1]->stride / mc->tex_transfer[tb + 1]->block.size;
texels = mc->texels[tb + 1] + mbpy * tex_pitch + mbpx;
if ((coded_block_pattern >> (1 - tb)) & 1)
@@ -635,8 +635,8 @@ static int vlFlush
for (i = 0; i < 3; ++i)
{
- pipe_surface_unmap(mc->tex_surface[i]);
- pipe_surface_reference(&mc->tex_surface[i], NULL);
+ pipe->screen->transfer_unmap(pipe->screen, mc->tex_transfer[i]);
+ pipe->screen->tex_transfer_release(pipe->screen, &mc->tex_transfer[i]);
}
mc->render_target.cbufs[0] = pipe->screen->get_tex_surface
@@ -809,14 +809,16 @@ static int vlRenderMacroBlocksMpeg2R16SnormBuffered
for (i = 0; i < 3; ++i)
{
- mc->tex_surface[i] = mc->pipe->screen->get_tex_surface
+ mc->tex_transfer[i] = mc->pipe->screen->get_tex_transfer
(
mc->pipe->screen,
mc->textures.all[i],
- 0, 0, 0, PIPE_BUFFER_USAGE_CPU_WRITE | PIPE_BUFFER_USAGE_DISCARD
+ 0, 0, 0, PIPE_TRANSFER_WRITE, 0, 0,
+ surface->texture->width[0],
+ surface->texture->height[0]
);
- mc->texels[i] = pipe_surface_map(mc->tex_surface[i], PIPE_BUFFER_USAGE_CPU_WRITE | PIPE_BUFFER_USAGE_DISCARD);
+ mc->texels[i] = mc->pipe->screen->transfer_map(mc->pipe->screen, mc->tex_transfer[i]);
}
}
diff --git a/src/gallium/winsys/xlib/xlib_brw_aub.c b/src/gallium/winsys/xlib/xlib_brw_aub.c
index ce4b5f83ff..b6bd849ef2 100644
--- a/src/gallium/winsys/xlib/xlib_brw_aub.c
+++ b/src/gallium/winsys/xlib/xlib_brw_aub.c
@@ -36,6 +36,7 @@
#include "pipe/p_state.h"
#include "util/u_debug.h"
#include "util/u_memory.h"
+#include "softpipe/sp_texture.h"
struct brw_aubfile {
@@ -322,10 +323,10 @@ void brw_aub_dump_bmp( struct brw_aubfile *aubfile,
struct aub_dump_bmp db;
unsigned format;
- assert(surface->block.width == 1);
- assert(surface->block.height == 1);
+ assert(surface->texture->block.width == 1);
+ assert(surface->texture->block.height == 1);
- if (surface->block.size == 4)
+ if (surface->texture->block.size == 4)
format = 0x7;
else
format = 0x3;
@@ -334,8 +335,9 @@ void brw_aub_dump_bmp( struct brw_aubfile *aubfile,
db.xmin = 0;
db.ymin = 0;
db.format = format;
- db.bpp = surface->block.size * 8;
- db.pitch = surface->stride/surface->block.size;
+ db.bpp = surface->texture->block.size * 8;
+ db.pitch = softpipe_texture(surface->texture)->stride[surface->level] /
+ surface->texture->block.size;
db.xsize = surface->width;
db.ysize = surface->height;
db.addr = gtt_offset;
diff --git a/src/gallium/winsys/xlib/xlib_softpipe.c b/src/gallium/winsys/xlib/xlib_softpipe.c
index 586e1dfca5..d8aa4856dc 100644
--- a/src/gallium/winsys/xlib/xlib_softpipe.c
+++ b/src/gallium/winsys/xlib/xlib_softpipe.c
@@ -170,6 +170,8 @@ alloc_shm_ximage(struct xm_buffer *b, struct xmesa_buffer *xmb,
(void) XSetErrorHandler(old_handler);
return;
}
+
+ b->shm = 1;
}
@@ -230,8 +232,8 @@ xlib_softpipe_display_surface(struct xmesa_buffer *b,
struct pipe_surface *surf)
{
XImage *ximage;
- struct xm_buffer *xm_buf = xm_buffer(
- softpipe_texture(surf->texture)->buffer);
+ struct softpipe_texture *spt = softpipe_texture(surf->texture);
+ struct xm_buffer *xm_buf = xm_buffer(spt->buffer);
static boolean no_swap = 0;
static boolean firsttime = 1;
@@ -244,9 +246,10 @@ xlib_softpipe_display_surface(struct xmesa_buffer *b,
return;
if (XSHM_ENABLED(xm_buf) && (xm_buf->tempImage == NULL)) {
- assert(surf->block.width == 1);
- assert(surf->block.height == 1);
- alloc_shm_ximage(xm_buf, b, surf->stride/surf->block.size, surf->height);
+ assert(surf->texture->block.width == 1);
+ assert(surf->texture->block.height == 1);
+ alloc_shm_ximage(xm_buf, b, spt->stride[surf->level] /
+ surf->texture->block.size, surf->height);
}
ximage = (XSHM_ENABLED(xm_buf)) ? xm_buf->tempImage : b->tempImage;
@@ -264,7 +267,7 @@ xlib_softpipe_display_surface(struct xmesa_buffer *b,
/* update XImage's fields */
ximage->width = surf->width;
ximage->height = surf->height;
- ximage->bytes_per_line = surf->stride;
+ ximage->bytes_per_line = spt->stride[surf->level];
XPutImage(b->xm_visual->display, b->drawable, b->gc,
ximage, 0, 0, 0, 0, surf->width, surf->height);