X-Git-Url: https://git.libre-soc.org/?a=blobdiff_plain;f=src%2Fgallium%2Fauxiliary%2Futil%2Fu_transfer.c;h=adae84bbfab791a7f2d1825e7745956fbebef74f;hb=6691ba1fe8e54c6ce5c6b4424c8096a351fda932;hp=bedace3b1dcdb2c3f18404685b4ccfe2e5bbd187;hpb=1318848f782cce716d6376ca13aebf68b728e24c;p=mesa.git diff --git a/src/gallium/auxiliary/util/u_transfer.c b/src/gallium/auxiliary/util/u_transfer.c index bedace3b1dc..adae84bbfab 100644 --- a/src/gallium/auxiliary/util/u_transfer.c +++ b/src/gallium/auxiliary/util/u_transfer.c @@ -1,5 +1,5 @@ #include "pipe/p_context.h" -#include "util/u_rect.h" +#include "util/u_surface.h" #include "util/u_inlines.h" #include "util/u_transfer.h" #include "util/u_memory.h" @@ -8,53 +8,68 @@ * pointer. XXX: strides?? */ void u_default_transfer_inline_write( struct pipe_context *pipe, - struct pipe_resource *resource, - struct pipe_subresource sr, - unsigned usage, - const struct pipe_box *box, - const void *data, - unsigned stride, - unsigned slice_stride) + struct pipe_resource *resource, + unsigned level, + unsigned usage, + const struct pipe_box *box, + const void *data, + unsigned stride, + unsigned layer_stride) { struct pipe_transfer *transfer = NULL; uint8_t *map = NULL; - transfer = pipe->get_transfer(pipe, - resource, - sr, - usage, - box ); - if (transfer == NULL) - goto out; - - map = pipe_transfer_map(pipe, transfer); - if (map == NULL) - goto out; - - assert(box->depth == 1); /* XXX: fix me */ - - util_copy_rect(map, - resource->format, - transfer->stride, /* bytes? */ - 0, 0, - box->width, - box->height, - data, - box->width, /* bytes? texels? */ - 0, 0); - -out: - if (map) - pipe_transfer_unmap(pipe, transfer); - - if (transfer) - pipe_transfer_destroy(pipe, transfer); + assert(!(usage & PIPE_TRANSFER_READ)); + + /* the write flag is implicit by the nature of transfer_inline_write */ + usage |= PIPE_TRANSFER_WRITE; + + /* transfer_inline_write implicitly discards the rewritten buffer range */ + if (resource->target == PIPE_BUFFER && + box->x == 0 && box->width == resource->width0) { + usage |= PIPE_TRANSFER_DISCARD_WHOLE_RESOURCE; + } else { + usage |= PIPE_TRANSFER_DISCARD_RANGE; + } + + map = pipe->transfer_map(pipe, + resource, + level, + usage, + box, &transfer); + if (!map) + return; + + if (resource->target == PIPE_BUFFER) { + assert(box->height == 1); + assert(box->depth == 1); + + memcpy(map, data, box->width); + } + else { + const uint8_t *src_data = data; + + util_copy_box(map, + resource->format, + transfer->stride, /* bytes */ + transfer->layer_stride, /* bytes */ + 0, 0, 0, + box->width, + box->height, + box->depth, + src_data, + stride, /* bytes */ + layer_stride, /* bytes */ + 0, 0, 0); + } + + pipe_transfer_unmap(pipe, transfer); } boolean u_default_resource_get_handle(struct pipe_screen *screen, - struct pipe_resource *resource, - struct winsys_handle *handle) + struct pipe_resource *resource, + struct winsys_handle *handle) { return FALSE; } @@ -62,49 +77,87 @@ boolean u_default_resource_get_handle(struct pipe_screen *screen, void u_default_transfer_flush_region( struct pipe_context *pipe, - struct pipe_transfer *transfer, - const struct pipe_box *box) + struct pipe_transfer *transfer, + const struct pipe_box *box) { /* This is a no-op implementation, nothing to do. */ } -unsigned u_default_is_resource_referenced( struct pipe_context *pipe, - struct pipe_resource *resource, - unsigned face, unsigned level) +void u_default_transfer_unmap( struct pipe_context *pipe, + struct pipe_transfer *transfer ) { - return 0; } -struct pipe_transfer * u_default_get_transfer(struct pipe_context *context, - struct pipe_resource *resource, - struct pipe_subresource sr, - unsigned usage, - const struct pipe_box *box) + +static inline struct u_resource * +u_resource( struct pipe_resource *res ) { - struct pipe_transfer *transfer = CALLOC_STRUCT(pipe_transfer); - if (transfer == NULL) - return NULL; + return (struct u_resource *)res; +} - transfer->resource = resource; - transfer->sr = sr; - transfer->usage = usage; - transfer->box = *box; +boolean u_resource_get_handle_vtbl(struct pipe_screen *screen, + struct pipe_resource *resource, + struct winsys_handle *handle) +{ + struct u_resource *ur = u_resource(resource); + return ur->vtbl->resource_get_handle(screen, resource, handle); +} - /* Note strides are zero, this is ok for buffers, but not for - * textures 2d & higher at least. - */ - return transfer; +void u_resource_destroy_vtbl(struct pipe_screen *screen, + struct pipe_resource *resource) +{ + struct u_resource *ur = u_resource(resource); + ur->vtbl->resource_destroy(screen, resource); } -void u_default_transfer_unmap( struct pipe_context *pipe, - struct pipe_transfer *transfer ) +void *u_transfer_map_vtbl(struct pipe_context *context, + struct pipe_resource *resource, + unsigned level, + unsigned usage, + const struct pipe_box *box, + struct pipe_transfer **transfer) { + struct u_resource *ur = u_resource(resource); + return ur->vtbl->transfer_map(context, resource, level, usage, box, + transfer); } -void u_default_transfer_destroy(struct pipe_context *pipe, - struct pipe_transfer *transfer) +void u_transfer_flush_region_vtbl( struct pipe_context *pipe, + struct pipe_transfer *transfer, + const struct pipe_box *box) { - FREE(transfer); + struct u_resource *ur = u_resource(transfer->resource); + ur->vtbl->transfer_flush_region(pipe, transfer, box); } +void u_transfer_unmap_vtbl( struct pipe_context *pipe, + struct pipe_transfer *transfer ) +{ + struct u_resource *ur = u_resource(transfer->resource); + ur->vtbl->transfer_unmap(pipe, transfer); +} + +void u_transfer_inline_write_vtbl( struct pipe_context *pipe, + struct pipe_resource *resource, + unsigned level, + unsigned usage, + const struct pipe_box *box, + const void *data, + unsigned stride, + unsigned layer_stride) +{ + struct u_resource *ur = u_resource(resource); + ur->vtbl->transfer_inline_write(pipe, + resource, + level, + usage, + box, + data, + stride, + layer_stride); +} + + + +