Skip to content

Commit

Permalink
Support partial buffer locks
Browse files Browse the repository at this point in the history
  • Loading branch information
RobDangerous committed Oct 1, 2024
1 parent d637ced commit f5dba58
Show file tree
Hide file tree
Showing 9 changed files with 97 additions and 23 deletions.
71 changes: 62 additions & 9 deletions Backends/Graphics5/Direct3D12/Sources/kope/direct3d12/buffer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -14,26 +14,79 @@ void kope_d3d12_buffer_destroy(kope_g5_buffer *buffer) {
buffer->d3d12.resource->Release();
}

void *kope_d3d12_buffer_try_to_lock(kope_g5_buffer *buffer) {
void *kope_d3d12_buffer_try_to_lock_all(kope_g5_buffer *buffer) {
if (check_for_fence(buffer->d3d12.device->d3d12.execution_fence, buffer->d3d12.latest_execution_index)) {
void *data = NULL;
buffer->d3d12.resource->Map(0, NULL, &data);
return data;
buffer->d3d12.locked_data_offset = 0;
buffer->d3d12.locked_data_size = UINT64_MAX;

buffer->d3d12.resource->Map(0, NULL, &buffer->d3d12.locked_data);
return buffer->d3d12.locked_data;
}
else {
return NULL;
}
}

void *kope_d3d12_buffer_lock(kope_g5_buffer *buffer) {
void *kope_d3d12_buffer_lock_all(kope_g5_buffer *buffer) {
wait_for_fence(buffer->d3d12.device, buffer->d3d12.device->d3d12.execution_fence, buffer->d3d12.device->d3d12.execution_event,
buffer->d3d12.latest_execution_index);

void *data = NULL;
buffer->d3d12.resource->Map(0, NULL, &data);
return data;
buffer->d3d12.locked_data_offset = 0;
buffer->d3d12.locked_data_size = UINT64_MAX;

buffer->d3d12.resource->Map(0, NULL, &buffer->d3d12.locked_data);
return buffer->d3d12.locked_data;
}

void *kope_d3d12_buffer_try_to_lock(kope_g5_buffer *buffer, uint64_t offset, uint64_t size) {
if (check_for_fence(buffer->d3d12.device->d3d12.execution_fence, buffer->d3d12.latest_execution_index)) {
D3D12_RANGE read_range;
D3D12_RANGE *read_range_pointer = NULL;

if (buffer->d3d12.cpu_read) {
read_range.Begin = offset;
read_range.End = offset + size;
read_range_pointer = &read_range;
}

buffer->d3d12.locked_data_offset = offset;
buffer->d3d12.locked_data_size = size;

buffer->d3d12.resource->Map(0, read_range_pointer, &buffer->d3d12.locked_data);
return buffer->d3d12.locked_data;
}
else {
return NULL;
}
}

void *kope_d3d12_buffer_lock(kope_g5_buffer *buffer, uint64_t offset, uint64_t size) {
wait_for_fence(buffer->d3d12.device, buffer->d3d12.device->d3d12.execution_fence, buffer->d3d12.device->d3d12.execution_event,
buffer->d3d12.latest_execution_index);
D3D12_RANGE read_range;
D3D12_RANGE *read_range_pointer = NULL;

if (buffer->d3d12.cpu_read) {
read_range.Begin = offset;
read_range.End = offset + size;
read_range_pointer = &read_range;
}

buffer->d3d12.locked_data_offset = offset;
buffer->d3d12.locked_data_size = size;

buffer->d3d12.resource->Map(0, read_range_pointer, &buffer->d3d12.locked_data);
return buffer->d3d12.locked_data;
}

void kope_d3d12_buffer_unlock(kope_g5_buffer *buffer) {
buffer->d3d12.resource->Unmap(0, NULL); // doesn't actually do anything in D3D12, just helps with debugging
D3D12_RANGE written;
D3D12_RANGE *written_pointer = NULL;

if (buffer->d3d12.cpu_write && buffer->d3d12.locked_data_size < UINT64_MAX) {
written.Begin = buffer->d3d12.locked_data_offset;
written.End = buffer->d3d12.locked_data_offset + buffer->d3d12.locked_data_size;
}

buffer->d3d12.resource->Unmap(0, written_pointer);
}
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,13 @@ void kope_d3d12_buffer_set_name(kope_g5_buffer *buffer, const char *name);

void kope_d3d12_buffer_destroy(kope_g5_buffer *buffer);

void *kope_d3d12_buffer_try_to_lock(kope_g5_buffer *buffer);
void *kope_d3d12_buffer_try_to_lock_all(kope_g5_buffer *buffer);

void *kope_d3d12_buffer_lock(kope_g5_buffer *buffer);
void *kope_d3d12_buffer_lock_all(kope_g5_buffer *buffer);

void *kope_d3d12_buffer_try_to_lock(kope_g5_buffer *buffer, uint64_t offset, uint64_t size);

void *kope_d3d12_buffer_lock(kope_g5_buffer *buffer, uint64_t offset, uint64_t size);

void kope_d3d12_buffer_unlock(kope_g5_buffer *buffer);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,12 @@ typedef struct kope_d3d12_buffer {
uint32_t resource_state;
size_t size;

bool cpu_accessible;
void *locked_data;
uint64_t locked_data_offset;
uint64_t locked_data_size;

bool cpu_write;
bool cpu_read;
uint64_t latest_execution_index;
} kope_d3d12_buffer;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -571,7 +571,7 @@ void kope_d3d12_command_list_prepare_raytracing_hierarchy(kope_g5_command_list *

void kope_d3d12_command_list_update_raytracing_hierarchy(kope_g5_command_list *list, kinc_matrix4x4_t *volume_transforms, uint32_t volumes_count,
kope_g5_raytracing_hierarchy *hierarchy) {
D3D12_RAYTRACING_INSTANCE_DESC *descs = (D3D12_RAYTRACING_INSTANCE_DESC *)kope_g5_buffer_lock(&hierarchy->d3d12.instances);
D3D12_RAYTRACING_INSTANCE_DESC *descs = (D3D12_RAYTRACING_INSTANCE_DESC *)kope_g5_buffer_lock_all(&hierarchy->d3d12.instances);

for (uint32_t volume_index = 0; volume_index < hierarchy->d3d12.volumes_count; ++volume_index) {
descs[volume_index].Transform[0][0] = volume_transforms[volume_index].m[0];
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -160,7 +160,7 @@ void kope_d3d12_descriptor_set_prepare_cbv_buffer(kope_g5_command_list *list, ko
buffer->d3d12.resource_state = D3D12_RESOURCE_STATE_VERTEX_AND_CONSTANT_BUFFER;
}

if (buffer->d3d12.cpu_accessible) {
if (buffer->d3d12.cpu_read || buffer->d3d12.cpu_write) {
kope_d3d12_command_list_queue_buffer_access(list, buffer);
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -261,8 +261,8 @@ void kope_d3d12_device_create_buffer(kope_g5_device *device, const kope_g5_buffe

buffer->d3d12.latest_execution_index = 0;

buffer->d3d12.cpu_accessible =
(parameters->usage_flags & KOPE_G5_BUFFER_USAGE_CPU_READ) != 0 || (parameters->usage_flags & KOPE_G5_BUFFER_USAGE_CPU_WRITE) != 0;
buffer->d3d12.cpu_read = (parameters->usage_flags & KOPE_G5_BUFFER_USAGE_CPU_READ) != 0;
buffer->d3d12.cpu_write = (parameters->usage_flags & KOPE_G5_BUFFER_USAGE_CPU_WRITE) != 0;

kinc_microsoft_affirm(device->d3d12.device->CreateCommittedResource(
&props, D3D12_HEAP_FLAG_NONE, &desc, (D3D12_RESOURCE_STATES)buffer->d3d12.resource_state, NULL, IID_GRAPHICS_PPV_ARGS(&buffer->d3d12.resource)));
Expand Down Expand Up @@ -705,7 +705,7 @@ void kope_d3d12_device_create_raytracing_hierarchy(kope_g5_device *device, kope_
instances_params.usage_flags = KOPE_G5_BUFFER_USAGE_CPU_WRITE;
kope_g5_device_create_buffer(device, &instances_params, &hierarchy->d3d12.instances);

D3D12_RAYTRACING_INSTANCE_DESC *descs = (D3D12_RAYTRACING_INSTANCE_DESC *)kope_g5_buffer_lock(&hierarchy->d3d12.instances);
D3D12_RAYTRACING_INSTANCE_DESC *descs = (D3D12_RAYTRACING_INSTANCE_DESC *)kope_g5_buffer_lock_all(&hierarchy->d3d12.instances);
for (uint32_t volume_index = 0; volume_index < hierarchy->d3d12.volumes_count; ++volume_index) {
memset(&descs[volume_index], 0, sizeof(D3D12_RAYTRACING_INSTANCE_DESC));
descs[volume_index].InstanceID = volume_index;
Expand Down
16 changes: 12 additions & 4 deletions Sources/kope/graphics5/buffer.c
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,20 @@ void kope_g5_buffer_destroy(kope_g5_buffer *buffer) {
KOPE_G5_CALL1(buffer_destroy, buffer);
}

void *kope_g5_buffer_try_to_lock(kope_g5_buffer *buffer) {
return KOPE_G5_CALL1(buffer_try_to_lock, buffer);
void *kope_g5_buffer_try_to_lock_all(kope_g5_buffer *buffer) {
return KOPE_G5_CALL1(buffer_try_to_lock_all, buffer);
}

void *kope_g5_buffer_lock(kope_g5_buffer *buffer) {
return KOPE_G5_CALL1(buffer_lock, buffer);
void *kope_g5_buffer_lock_all(kope_g5_buffer *buffer) {
return KOPE_G5_CALL1(buffer_lock_all, buffer);
}

void *kope_g5_buffer_try_to_lock(kope_g5_buffer *buffer, uint64_t offset, uint64_t size) {
return KOPE_G5_CALL3(buffer_try_to_lock, buffer, offset, size);
}

void *kope_g5_buffer_lock(kope_g5_buffer *buffer, uint64_t offset, uint64_t size) {
return KOPE_G5_CALL3(buffer_lock, buffer, offset, size);
}

void kope_g5_buffer_unlock(kope_g5_buffer *buffer) {
Expand Down
6 changes: 4 additions & 2 deletions Sources/kope/graphics5/buffer.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,8 +28,10 @@ typedef struct kope_g5_buffer {

void kope_g5_buffer_set_name(kope_g5_buffer *buffer, const char *name);
void kope_g5_buffer_destroy(kope_g5_buffer *buffer);
void *kope_g5_buffer_try_to_lock(kope_g5_buffer *buffer);
void *kope_g5_buffer_lock(kope_g5_buffer *buffer);
void *kope_g5_buffer_try_to_lock_all(kope_g5_buffer *buffer);
void *kope_g5_buffer_lock_all(kope_g5_buffer *buffer);
void *kope_g5_buffer_try_to_lock(kope_g5_buffer *buffer, uint64_t offset, uint64_t size);
void *kope_g5_buffer_lock(kope_g5_buffer *buffer, uint64_t offset, uint64_t size);
void kope_g5_buffer_unlock(kope_g5_buffer *buffer);

#ifdef __cplusplus
Expand Down
2 changes: 2 additions & 0 deletions Sources/kope/graphics5/device.h
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,8 @@ typedef struct kope_g5_texture_parameters {

KOPE_FUNC void kope_g5_device_create_texture(kope_g5_device *device, const kope_g5_texture_parameters *parameters, kope_g5_texture *texture);

#define KOPE_G5_MAX_FRAMEBUFFERS 3

KOPE_FUNC kope_g5_texture *kope_g5_device_get_framebuffer(kope_g5_device *device);

typedef enum kope_g5_address_mode { KOPE_G5_ADDRESS_MODE_CLAMP_TO_EDGE, KOPE_G5_ADDRESS_MODE_REPEAT, KOPE_G5_ADDRESS_MODE_MIRROR_REPEAT } kope_g5_address_mode;
Expand Down

0 comments on commit f5dba58

Please sign in to comment.