1 #include "pipe/p_context.h"
2 #include "util/u_surface.h"
3 #include "util/u_inlines.h"
4 #include "util/u_transfer.h"
5 #include "util/u_memory.h"
6 
u_default_buffer_subdata(struct pipe_context * pipe,struct pipe_resource * resource,unsigned usage,unsigned offset,unsigned size,const void * data)7 void u_default_buffer_subdata(struct pipe_context *pipe,
8                               struct pipe_resource *resource,
9                               unsigned usage, unsigned offset,
10                               unsigned size, const void *data)
11 {
12    struct pipe_transfer *transfer = NULL;
13    struct pipe_box box;
14    uint8_t *map = NULL;
15 
16    assert(!(usage & PIPE_TRANSFER_READ));
17 
18    /* the write flag is implicit by the nature of buffer_subdata */
19    usage |= PIPE_TRANSFER_WRITE;
20 
21    /* buffer_subdata implicitly discards the rewritten buffer range */
22    if (offset == 0 && size == resource->width0) {
23       usage |= PIPE_TRANSFER_DISCARD_WHOLE_RESOURCE;
24    } else {
25       usage |= PIPE_TRANSFER_DISCARD_RANGE;
26    }
27 
28    u_box_1d(offset, size, &box);
29 
30    map = pipe->transfer_map(pipe, resource, 0, usage, &box, &transfer);
31    if (!map)
32       return;
33 
34    memcpy(map, data, size);
35    pipe_transfer_unmap(pipe, transfer);
36 }
37 
u_default_texture_subdata(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)38 void u_default_texture_subdata(struct pipe_context *pipe,
39                                struct pipe_resource *resource,
40                                unsigned level,
41                                unsigned usage,
42                                const struct pipe_box *box,
43                                const void *data,
44                                unsigned stride,
45                                unsigned layer_stride)
46 {
47    struct pipe_transfer *transfer = NULL;
48    const uint8_t *src_data = data;
49    uint8_t *map = NULL;
50 
51    assert(!(usage & PIPE_TRANSFER_READ));
52 
53    /* the write flag is implicit by the nature of texture_subdata */
54    usage |= PIPE_TRANSFER_WRITE;
55 
56    /* texture_subdata implicitly discards the rewritten buffer range */
57    usage |= PIPE_TRANSFER_DISCARD_RANGE;
58 
59    map = pipe->transfer_map(pipe,
60                             resource,
61                             level,
62                             usage,
63                             box, &transfer);
64    if (!map)
65       return;
66 
67    util_copy_box(map,
68                  resource->format,
69                  transfer->stride, /* bytes */
70                  transfer->layer_stride, /* bytes */
71                  0, 0, 0,
72                  box->width,
73                  box->height,
74                  box->depth,
75                  src_data,
76                  stride,       /* bytes */
77                  layer_stride, /* bytes */
78                  0, 0, 0);
79 
80    pipe_transfer_unmap(pipe, transfer);
81 }
82 
83 
u_default_resource_get_handle(UNUSED struct pipe_screen * screen,UNUSED struct pipe_resource * resource,UNUSED struct winsys_handle * handle)84 boolean u_default_resource_get_handle(UNUSED struct pipe_screen *screen,
85                                       UNUSED struct pipe_resource *resource,
86                                       UNUSED struct winsys_handle *handle)
87 {
88    return FALSE;
89 }
90 
91 
92 
u_default_transfer_flush_region(UNUSED struct pipe_context * pipe,UNUSED struct pipe_transfer * transfer,UNUSED const struct pipe_box * box)93 void u_default_transfer_flush_region(UNUSED struct pipe_context *pipe,
94                                      UNUSED struct pipe_transfer *transfer,
95                                      UNUSED const struct pipe_box *box)
96 {
97    /* This is a no-op implementation, nothing to do.
98     */
99 }
100 
u_default_transfer_unmap(UNUSED struct pipe_context * pipe,UNUSED struct pipe_transfer * transfer)101 void u_default_transfer_unmap(UNUSED struct pipe_context *pipe,
102                               UNUSED struct pipe_transfer *transfer)
103 {
104 }
105 
106 
107 static inline struct u_resource *
u_resource(struct pipe_resource * res)108 u_resource( struct pipe_resource *res )
109 {
110    return (struct u_resource *)res;
111 }
112 
u_resource_get_handle_vtbl(struct pipe_screen * screen,UNUSED struct pipe_context * ctx,struct pipe_resource * resource,struct winsys_handle * handle,UNUSED unsigned usage)113 boolean u_resource_get_handle_vtbl(struct pipe_screen *screen,
114                                    UNUSED struct pipe_context *ctx,
115                                    struct pipe_resource *resource,
116                                    struct winsys_handle *handle,
117                                    UNUSED unsigned usage)
118 {
119    struct u_resource *ur = u_resource(resource);
120    return ur->vtbl->resource_get_handle(screen, resource, handle);
121 }
122 
u_resource_destroy_vtbl(struct pipe_screen * screen,struct pipe_resource * resource)123 void u_resource_destroy_vtbl(struct pipe_screen *screen,
124                              struct pipe_resource *resource)
125 {
126    struct u_resource *ur = u_resource(resource);
127    ur->vtbl->resource_destroy(screen, resource);
128 }
129 
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)130 void *u_transfer_map_vtbl(struct pipe_context *context,
131                           struct pipe_resource *resource,
132                           unsigned level,
133                           unsigned usage,
134                           const struct pipe_box *box,
135                           struct pipe_transfer **transfer)
136 {
137    struct u_resource *ur = u_resource(resource);
138    return ur->vtbl->transfer_map(context, resource, level, usage, box,
139                                  transfer);
140 }
141 
u_transfer_flush_region_vtbl(struct pipe_context * pipe,struct pipe_transfer * transfer,const struct pipe_box * box)142 void u_transfer_flush_region_vtbl( struct pipe_context *pipe,
143                                    struct pipe_transfer *transfer,
144                                    const struct pipe_box *box)
145 {
146    struct u_resource *ur = u_resource(transfer->resource);
147    ur->vtbl->transfer_flush_region(pipe, transfer, box);
148 }
149 
u_transfer_unmap_vtbl(struct pipe_context * pipe,struct pipe_transfer * transfer)150 void u_transfer_unmap_vtbl( struct pipe_context *pipe,
151                             struct pipe_transfer *transfer )
152 {
153    struct u_resource *ur = u_resource(transfer->resource);
154    ur->vtbl->transfer_unmap(pipe, transfer);
155 }
156