diff options
author | Marek Olšák <[email protected]> | 2012-10-08 04:06:42 +0200 |
---|---|---|
committer | Marek Olšák <[email protected]> | 2012-10-11 21:12:16 +0200 |
commit | 369e46888904c6d379b8b477d9242cff1608e30e (patch) | |
tree | 528b10f900f23af3acd22a0edcf50fde0eeee86e /src/gallium/drivers/r300 | |
parent | ec4c74a9dc10039d97ad24c4f16bd2400517991d (diff) |
gallium: unify transfer functions
"get_transfer + transfer_map" becomes "transfer_map".
"transfer_unmap + transfer_destroy" becomes "transfer_unmap".
transfer_map must create and return the transfer object and transfer_unmap
must destroy it.
transfer_map is successful if the returned buffer pointer is not NULL.
If transfer_map fails, the pointer to the transfer object remains unchanged
(i.e. doesn't have to be NULL).
Acked-by: Brian Paul <[email protected]>
Diffstat (limited to 'src/gallium/drivers/r300')
-rw-r--r-- | src/gallium/drivers/r300/r300_resource.c | 2 | ||||
-rw-r--r-- | src/gallium/drivers/r300/r300_screen_buffer.c | 80 | ||||
-rw-r--r-- | src/gallium/drivers/r300/r300_texture.c | 2 | ||||
-rw-r--r-- | src/gallium/drivers/r300/r300_transfer.c | 105 | ||||
-rw-r--r-- | src/gallium/drivers/r300/r300_transfer.h | 15 |
5 files changed, 80 insertions, 124 deletions
diff --git a/src/gallium/drivers/r300/r300_resource.c b/src/gallium/drivers/r300/r300_resource.c index 46399fb2397..701fd249d30 100644 --- a/src/gallium/drivers/r300/r300_resource.c +++ b/src/gallium/drivers/r300/r300_resource.c @@ -40,11 +40,9 @@ r300_resource_create(struct pipe_screen *screen, void r300_init_resource_functions(struct r300_context *r300) { - r300->context.get_transfer = u_get_transfer_vtbl; r300->context.transfer_map = u_transfer_map_vtbl; r300->context.transfer_flush_region = u_default_transfer_flush_region; r300->context.transfer_unmap = u_transfer_unmap_vtbl; - r300->context.transfer_destroy = u_transfer_destroy_vtbl; r300->context.transfer_inline_write = u_default_transfer_inline_write; r300->context.create_surface = r300_create_surface; r300->context.surface_destroy = r300_surface_destroy; diff --git a/src/gallium/drivers/r300/r300_screen_buffer.c b/src/gallium/drivers/r300/r300_screen_buffer.c index f652bf72b0c..37a7c77010a 100644 --- a/src/gallium/drivers/r300/r300_screen_buffer.c +++ b/src/gallium/drivers/r300/r300_screen_buffer.c @@ -63,79 +63,63 @@ static void r300_buffer_destroy(struct pipe_screen *screen, FREE(rbuf); } -static struct pipe_transfer* -r300_buffer_get_transfer(struct pipe_context *context, - struct pipe_resource *resource, - unsigned level, - unsigned usage, - const struct pipe_box *box) -{ - struct r300_context *r300 = r300_context(context); - struct pipe_transfer *transfer = - util_slab_alloc(&r300->pool_transfers); - - transfer->resource = resource; - transfer->level = level; - transfer->usage = usage; - transfer->box = *box; - transfer->stride = 0; - transfer->layer_stride = 0; - transfer->data = NULL; - - /* Note strides are zero, this is ok for buffers, but not for - * textures 2d & higher at least. - */ - return transfer; -} - -static void r300_buffer_transfer_destroy(struct pipe_context *pipe, - struct pipe_transfer *transfer) -{ - struct r300_context *r300 = r300_context(pipe); - util_slab_free(&r300->pool_transfers, transfer); -} - static void * -r300_buffer_transfer_map( struct pipe_context *pipe, - struct pipe_transfer *transfer ) +r300_buffer_transfer_map( struct pipe_context *context, + struct pipe_resource *resource, + unsigned level, + unsigned usage, + const struct pipe_box *box, + struct pipe_transfer **ptransfer ) { - struct r300_context *r300 = r300_context(pipe); - struct r300_screen *r300screen = r300_screen(pipe->screen); - struct radeon_winsys *rws = r300screen->rws; - struct r300_resource *rbuf = r300_resource(transfer->resource); + struct r300_context *r300 = r300_context(context); + struct radeon_winsys *rws = r300->screen->rws; + struct r300_resource *rbuf = r300_resource(resource); + struct pipe_transfer *transfer; uint8_t *map; - enum pipe_transfer_usage usage; - if (rbuf->malloced_buffer) - return (uint8_t *) rbuf->malloced_buffer + transfer->box.x; + transfer = util_slab_alloc(&r300->pool_transfers); + transfer->resource = resource; + transfer->level = level; + transfer->usage = usage; + transfer->box = *box; + transfer->stride = 0; + transfer->layer_stride = 0; + transfer->data = NULL; + + if (rbuf->malloced_buffer) { + *ptransfer = transfer; + return (uint8_t *) rbuf->malloced_buffer + box->x; + } /* Buffers are never used for write, therefore mapping for read can be * unsynchronized. */ - usage = transfer->usage; if (!(usage & PIPE_TRANSFER_WRITE)) { usage |= PIPE_TRANSFER_UNSYNCHRONIZED; } map = rws->buffer_map(rbuf->cs_buf, r300->cs, usage); - if (map == NULL) + if (map == NULL) { + util_slab_free(&r300->pool_transfers, transfer); return NULL; + } - return map + transfer->box.x; + *ptransfer = transfer; + return map + box->x; } static void r300_buffer_transfer_unmap( struct pipe_context *pipe, - struct pipe_transfer *transfer ) + struct pipe_transfer *transfer ) { - /* no-op */ + struct r300_context *r300 = r300_context(pipe); + + util_slab_free(&r300->pool_transfers, transfer); } static const struct u_resource_vtbl r300_buffer_vtbl = { NULL, /* get_handle */ r300_buffer_destroy, /* resource_destroy */ - r300_buffer_get_transfer, /* get_transfer */ - r300_buffer_transfer_destroy, /* transfer_destroy */ r300_buffer_transfer_map, /* transfer_map */ NULL, /* transfer_flush_region */ r300_buffer_transfer_unmap, /* transfer_unmap */ diff --git a/src/gallium/drivers/r300/r300_texture.c b/src/gallium/drivers/r300/r300_texture.c index 39cca78ebce..7f74538deea 100644 --- a/src/gallium/drivers/r300/r300_texture.c +++ b/src/gallium/drivers/r300/r300_texture.c @@ -937,8 +937,6 @@ static const struct u_resource_vtbl r300_texture_vtbl = { NULL, /* get_handle */ r300_texture_destroy, /* resource_destroy */ - r300_texture_get_transfer, /* get_transfer */ - r300_texture_transfer_destroy, /* transfer_destroy */ r300_texture_transfer_map, /* transfer_map */ NULL, /* transfer_flush_region */ r300_texture_transfer_unmap, /* transfer_unmap */ diff --git a/src/gallium/drivers/r300/r300_transfer.c b/src/gallium/drivers/r300/r300_transfer.c index 9140bb191cf..fbae2df52b9 100644 --- a/src/gallium/drivers/r300/r300_transfer.c +++ b/src/gallium/drivers/r300/r300_transfer.c @@ -76,18 +76,21 @@ static void r300_copy_into_tiled_texture(struct pipe_context *ctx, r300_flush(ctx, 0, NULL); } -struct pipe_transfer* -r300_texture_get_transfer(struct pipe_context *ctx, +void * +r300_texture_transfer_map(struct pipe_context *ctx, struct pipe_resource *texture, unsigned level, unsigned usage, - const struct pipe_box *box) + const struct pipe_box *box, + struct pipe_transfer **transfer) { struct r300_context *r300 = r300_context(ctx); struct r300_resource *tex = r300_resource(texture); struct r300_transfer *trans; struct pipe_resource base; boolean referenced_cs, referenced_hw; + enum pipe_format format = tex->b.b.format; + char *map; referenced_cs = r300->rws->cs_is_buffer_referenced(r300->cs, tex->cs_buf, RADEON_USAGE_READWRITE); @@ -101,7 +104,7 @@ r300_texture_get_transfer(struct pipe_context *ctx, trans = CALLOC_STRUCT(r300_transfer); if (trans) { /* Initialize the transfer object. */ - pipe_resource_reference(&trans->transfer.resource, texture); + trans->transfer.resource = texture; trans->transfer.level = level; trans->transfer.usage = usage; trans->transfer.box = *box; @@ -161,15 +164,8 @@ r300_texture_get_transfer(struct pipe_context *ctx, &base)); if (!trans->linear_texture) { - /* For linear textures, it's safe to fallback to - * an unpipelined transfer. */ - if (!tex->tex.microtile && !tex->tex.macrotile[level]) { - goto unpipelined; - } - - /* Otherwise, go to hell. */ fprintf(stderr, - "r300: Failed to create a transfer object, praise.\n"); + "r300: Failed to create a transfer object.\n"); FREE(trans); return NULL; } @@ -190,64 +186,43 @@ r300_texture_get_transfer(struct pipe_context *ctx, /* Always referenced in the blit. */ r300_flush(ctx, 0, NULL); } - return &trans->transfer; - } - - unpipelined: - /* Unpipelined transfer. */ - trans->transfer.stride = tex->tex.stride_in_bytes[level]; - trans->offset = r300_texture_get_offset(tex, level, box->z); - - if (referenced_cs && - !(usage & PIPE_TRANSFER_UNSYNCHRONIZED)) - r300_flush(ctx, 0, NULL); - return &trans->transfer; - } - return NULL; -} + } else { + /* Unpipelined transfer. */ + trans->transfer.stride = tex->tex.stride_in_bytes[level]; + trans->offset = r300_texture_get_offset(tex, level, box->z); -void r300_texture_transfer_destroy(struct pipe_context *ctx, - struct pipe_transfer *trans) -{ - struct r300_transfer *r300transfer = r300_transfer(trans); - - if (r300transfer->linear_texture) { - if (trans->usage & PIPE_TRANSFER_WRITE) { - r300_copy_into_tiled_texture(ctx, r300transfer); + if (referenced_cs && + !(usage & PIPE_TRANSFER_UNSYNCHRONIZED)) { + r300_flush(ctx, 0, NULL); + } } - - pipe_resource_reference( - (struct pipe_resource**)&r300transfer->linear_texture, NULL); } - pipe_resource_reference(&trans->resource, NULL); - FREE(trans); -} -void* r300_texture_transfer_map(struct pipe_context *ctx, - struct pipe_transfer *transfer) -{ - struct r300_context *r300 = r300_context(ctx); - struct r300_transfer *r300transfer = r300_transfer(transfer); - struct r300_resource *tex = r300_resource(transfer->resource); - char *map; - enum pipe_format format = tex->b.b.format; - - if (r300transfer->linear_texture) { + if (trans->linear_texture) { /* The detiled texture is of the same size as the region being mapped * (no offset needed). */ - return r300->rws->buffer_map(r300transfer->linear_texture->cs_buf, - r300->cs, transfer->usage); + map = r300->rws->buffer_map(trans->linear_texture->cs_buf, + r300->cs, usage); + if (!map) { + pipe_resource_reference( + (struct pipe_resource**)&trans->linear_texture, NULL); + FREE(trans); + return NULL; + } + *transfer = &trans->transfer; + return map; } else { /* Tiling is disabled. */ - map = r300->rws->buffer_map(tex->cs_buf, r300->cs, transfer->usage); - + map = r300->rws->buffer_map(tex->cs_buf, r300->cs, usage); if (!map) { + FREE(trans); return NULL; } - return map + r300_transfer(transfer)->offset + - transfer->box.y / util_format_get_blockheight(format) * transfer->stride + - transfer->box.x / util_format_get_blockwidth(format) * util_format_get_blocksize(format); + *transfer = &trans->transfer; + return map + trans->offset + + box->y / util_format_get_blockheight(format) * trans->transfer.stride + + box->x / util_format_get_blockwidth(format) * util_format_get_blocksize(format); } } @@ -255,12 +230,20 @@ void r300_texture_transfer_unmap(struct pipe_context *ctx, struct pipe_transfer *transfer) { struct radeon_winsys *rws = r300_context(ctx)->rws; - struct r300_transfer *r300transfer = r300_transfer(transfer); + struct r300_transfer *trans = r300_transfer(transfer); struct r300_resource *tex = r300_resource(transfer->resource); - if (r300transfer->linear_texture) { - rws->buffer_unmap(r300transfer->linear_texture->cs_buf); + if (trans->linear_texture) { + rws->buffer_unmap(trans->linear_texture->cs_buf); + + if (transfer->usage & PIPE_TRANSFER_WRITE) { + r300_copy_into_tiled_texture(ctx, trans); + } + + pipe_resource_reference( + (struct pipe_resource**)&trans->linear_texture, NULL); } else { rws->buffer_unmap(tex->cs_buf); } + FREE(transfer); } diff --git a/src/gallium/drivers/r300/r300_transfer.h b/src/gallium/drivers/r300/r300_transfer.h index 7977ef516f2..45477ae6d0d 100644 --- a/src/gallium/drivers/r300/r300_transfer.h +++ b/src/gallium/drivers/r300/r300_transfer.h @@ -28,20 +28,13 @@ struct r300_context; -struct pipe_transfer* -r300_texture_get_transfer(struct pipe_context *ctx, +void * +r300_texture_transfer_map(struct pipe_context *ctx, struct pipe_resource *texture, unsigned level, unsigned usage, - const struct pipe_box *box); - -void -r300_texture_transfer_destroy(struct pipe_context *ctx, - struct pipe_transfer *trans); - -void* -r300_texture_transfer_map(struct pipe_context *ctx, - struct pipe_transfer *transfer); + const struct pipe_box *box, + struct pipe_transfer **transfer); void r300_texture_transfer_unmap(struct pipe_context *ctx, |