Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for dedicated allocations and committed resource tracking #148

Merged
merged 15 commits into from
Jan 12, 2023

Conversation

janie177
Copy link
Member

@janie177 janie177 commented Dec 21, 2022

Changes

This PR adds the option to create dedicated allocations in the Vulkan allocator and CommittedResources in the Dx12 allocator. These types of allocations are managed by the driver, which allows it to do special optimizations (🧙‍♂️ magic).

Vulkan

In the Vulkan allocator, you must now pass an extra bool dedicated_allocation into the allocate function. Vulkan 1.1 is required for this to be available, though there is an extension for Vulkan 1.0 available (which I didn't integrate, but I could do that if we want to support it).

The visualizer now displays whether a memory block is backed by a dedicated allocation or not.

D3D12

In DirectX, dedicated allocations are hidden behind the CreateCommittedResource() call. It is not possible to access these allocations, so I've added a create_resource function to the dx12 allocator which will return a Resource object. You can decide whether you want this to be a Placed or Committed resource, and the rest is handled under the hood for you. When freeing a resource, you have to call the free_resource function on the allocator.

I have added a special section that displays the total amount of committed resources and their total size per memory type to the visualizer.

Testing

I have tested these changes in the dx12 and vulkan backends of the Breda framework. Performance on vulkan and dx12 increased by about 10-fold in our ray-tracing shaders when marking render targets as dedicated resources.

@janie177 janie177 requested review from Jasper-Bekkers and MarijnS95 and removed request for Jasper-Bekkers December 21, 2022 16:14
@janie177 janie177 marked this pull request as ready for review December 21, 2022 16:14
src/d3d12/mod.rs Outdated Show resolved Hide resolved
src/d3d12/mod.rs Outdated Show resolved Hide resolved
src/vulkan/mod.rs Outdated Show resolved Hide resolved
src/vulkan/mod.rs Outdated Show resolved Hide resolved
src/vulkan/visualizer.rs Outdated Show resolved Hide resolved
src/d3d12/mod.rs Outdated Show resolved Hide resolved
src/d3d12/visualizer.rs Outdated Show resolved Hide resolved
src/d3d12/visualizer.rs Outdated Show resolved Hide resolved
src/vulkan/mod.rs Outdated Show resolved Hide resolved
src/vulkan/mod.rs Outdated Show resolved Hide resolved
Remove old heap type information that was leftover from before an API change.
Implement several pull request suggestions, and fix a bug that would wrongly display dedicated block information in the vulkan visualizer.
…w an allocation should be managed.

Remove the BlockType enum that previously fulfilled the same task under the hood.
Comment on lines +18 to +30
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum AllocationScheme {
/// This allocation will be for a buffer, and it will be driver managed using vulkans DedicatedAllocation feature.
/// The driver will be able to perform optimizations in some cases with this type of allocation.
DedicatedBuffer { buffer: vk::Buffer },
/// This allocation will be for a image, and it will be driver managed using vulkans DedicatedAllocation feature.
/// The driver will be able to perform optimizations in some cases with this type of allocation.
DedicatedImage { image: vk::Image },
/// This allocation will be managed by the GPU allocator.
/// It is possible that the allocation will reside in an allocation block shared with other resources.
GpuAllocatorManaged,
}

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@MarijnS95 What do you think about this for the user exposed interface?
We can now also correctly pass the buffer and image when required for dedicated allocations. I got rid of the BlockType as that was essentially serving the same purpose, just with less configurability and under the hood.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Interface looks good, though I'd have reworded some of the comments:

Suggested change
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum AllocationScheme {
/// This allocation will be for a buffer, and it will be driver managed using vulkans DedicatedAllocation feature.
/// The driver will be able to perform optimizations in some cases with this type of allocation.
DedicatedBuffer { buffer: vk::Buffer },
/// This allocation will be for a image, and it will be driver managed using vulkans DedicatedAllocation feature.
/// The driver will be able to perform optimizations in some cases with this type of allocation.
DedicatedImage { image: vk::Image },
/// This allocation will be managed by the GPU allocator.
/// It is possible that the allocation will reside in an allocation block shared with other resources.
GpuAllocatorManaged,
}
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum AllocationScheme {
/// Perform a dedicated, driver-managed allocation for the given buffer, allowing
/// it to perform optimizations on this type of allocation.
DedicatedBuffer { buffer: vk::Buffer },
/// Perform a dedicated, driver-managed allocation for the given image, allowing
/// it to perform optimizations on this type of allocation.
DedicatedImage { image: vk::Image },
/// The memory for this resource will be allocated and managed by gpu-allocator.
/// It is possible that the allocation will reside in [`vk::Memory`] shared with other resources.
GpuAllocatorManaged,
}

@Jasper-Bekkers Jasper-Bekkers merged commit 5c422cf into main Jan 12, 2023
@@ -743,6 +794,131 @@ impl Allocator {
}
}
}

/// Create a resource according to the provided parameters.
/// Created resources should be freed at the end of their lifetime by calling [`Self::free_resource()`].
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we need a Drop destructor to call this or print a warning when it was not called?

Comment on lines +911 to +912
// Committed resources are implicitly dropped when their refcount reaches 0.
// We only have to change the allocation and size tracking.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Well you're explicitly dropping resource with ManuallyDrop right above... It's just that there's no allocation to clean up here.

buffer_device_address: bool,
allocation_scheme: &AllocationScheme,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a cheap Copy type, just pass-by-value. The user will likely ad-hoc create it anyway.

Comment on lines +22 to +25
DedicatedBuffer { buffer: vk::Buffer },
/// This allocation will be for a image, and it will be driver managed using vulkans DedicatedAllocation feature.
/// The driver will be able to perform optimizations in some cases with this type of allocation.
DedicatedImage { image: vk::Image },
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also feel free to just use a tuple-variant here, the name of the variant conveys the same name as the only named field here.

Box::new(allocator::FreeListAllocator::new(size))
};
let sub_allocator: Box<dyn allocator::SubAllocator> =
if !matches!(allocation_scheme, AllocationScheme::GpuAllocatorManaged)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just use == :)

@MarijnS95 MarijnS95 deleted the resource-creation-in-gpu-allocator branch January 16, 2023 14:28
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants