Brain dump new resource update api
Author: flooohCreated Jul 8, 2026Updated Sep 15, 2026
Labelssokol-gfx
Write-Transient vs Copy-Src vs Copy-Dst resource usage
Replace the current .dynamic_update and .stream_update usages:
sg_buffer/image_usage {
// ...
.write_transient = true/false,
.copy_src = true/false,
.copy_dst = true/false,
};Write-Transient behaviour:
- can only be written once per resource and frame
- no random placement, data must be written from start, but less data can be written than resource size
- written data must be 'consumed' in the same frame (it won't survive into the next frame)
- depending on backend a sokol-gfx transient resource may not even have a unique backing resource, the data may be written into a unified staging buffer
write_transientusage can be combined withcopy_src, but notcopy_dst.
'Consuming' the transient-write data means:
- for buffers (but not images): can be bound directly as rendering/compute resource
- can the be source of a copy-operation (for images that's the only operation that makes sense)
Associated sokol-gfx functions:
sg_write_buffer(sg_buffer buf, const sg_range* data);sg_write_image(sg_image img, const sg_image_data* data);Copy behaviour:
Copy data on the GPU between resources with random source and destination locations. The only way to upload CPU-side data persistently and piece-wise into a GPU resource to first write the CPU-side data into a transient resource, and then do a copy-operation on the GPU (this pretty much mimicks the upload via staging buffer in modern 3D APIs).
Associated sokol-gfx functions:
sg_copy_buffer_to_buffer(&(sg_copy_buffer_to_buffer_desc){
.src = {
.buffer = ..., // must have .copy_src usage
.offset = ...,
},
.dst = {
.buffer = ..., // must have copy_dst usage
.offset = ...,
},
.size = ....,
});sg_copy_buffer_to_image(&(sg_copy_buffer_to_image_desc){
.src = {
.buffer = ..., // must have .copy_src usage
.offset = ...,
.range = { .ptr = ..., .size = ... }, // source data chunk
},
.dst = {
.image = ..., // must have .copy_dst usage
???
},
});sg_copy_image_to_image(&(sg_copy_image_to_image_desc){
.src = {
.image = ..., // must have .copy_src usage
???
},
.dst = {
.image = ..., // must have .copy_dst usage
???
},
});sg_copy_image_to_buffer(&(sg_copy_image_to_buffer_desc){
.src = {
.image = ..., // must have .copy_src usage
???
},
.dst = {
.buffer = ..., // must have copy_dst usage
.offset = ...,
},
});To be defined
- GPU vs CPU timelines...
- is are write operations allowed within passes? (ideally yes but they may be moved in front of all render commands in the frame)
- are copy operations allowed in passes? copy operations must be able to consume a former write operation, the output of a former pass, and in compute passes ideally the result of a former dispatch within the same pass... possible on all backend APIs or needs more restrictions?
- read operations? (GPU => CPU)
- should the be an
sg_clear_buffer()andsg_clear_image()?
Source: floooh/sokol