Project setup
Vulkan Memory Allocator comes in form of a "stb-style" single header file. You don't need to build it as a separate library project. You can add this file directly to your project and submit it to code repository next to your other source files.
"Single header" doesn't mean that everything is contained in C/C++ declarations, like it tends to be in case of inline functions or C++ templates. It means that implementation is bundled with interface in a single file and needs to be extracted using preprocessor macro. If you don't do it properly, you will get linker errors.
To do it properly:
- Include "vk_mem_alloc.h" file in each CPP file where you want to use the library. This includes declarations of all members of the library.
- In exactly one CPP file define following macro before this include. It enables also internal definitions.
#define VMA_IMPLEMENTATION
It may be a good idea to create dedicated CPP file just for this purpose.
This library includes header <vulkan/vulkan.h>
, which in turn includes <windows.h>
on Windows. If you need some specific macros defined before including these headers (like WIN32_LEAN_AND_MEAN
or WINVER
for Windows, VK_USE_PLATFORM_WIN32_KHR
for Vulkan), you must define them before every #include
of this library.
This library is written in C++, but has C-compatible interface. Thus you can include and use vk_mem_alloc.h in C or C++ code, but full implementation with VMA_IMPLEMENTATION
macro must be compiled as C++, NOT as C. Some features of C++14 used. STL containers, RTTI, or C++ exceptions are not used.
Initialization
At program startup:
- Initialize Vulkan to have
VkPhysicalDevice
, VkDevice
and VkInstance
object.
- Fill VmaAllocatorCreateInfo structure and create VmaAllocator object by calling vmaCreateAllocator().
Only members physicalDevice
, device
, instance
are required. However, you should inform the library which Vulkan version do you use by setting VmaAllocatorCreateInfo::vulkanApiVersion and which extensions did you enable by setting VmaAllocatorCreateInfo::flags (like VMA_ALLOCATOR_CREATE_BUFFER_DEVICE_ADDRESS_BIT for VK_KHR_buffer_device_address). Otherwise, VMA would use only features of Vulkan 1.0 core with no extensions.
You may need to configure importing Vulkan functions. There are 3 ways to do this:
- If you link with Vulkan static library (e.g. "vulkan-1.lib" on Windows):
- You don't need to do anything.
- VMA will use these, as macro
VMA_STATIC_VULKAN_FUNCTIONS
is defined to 1 by default.
- If you want VMA to fetch pointers to Vulkan functions dynamically using
vkGetInstanceProcAddr
, vkGetDeviceProcAddr
(this is the option presented in the example below):
- If you fetch pointers to all Vulkan functions in a custom way, e.g. using some loader like Volk:
- Define
VMA_STATIC_VULKAN_FUNCTIONS
and VMA_DYNAMIC_VULKAN_FUNCTIONS
to 0.
- Pass these pointers via structure VmaVulkanFunctions.
allocatorCreateInfo.
device = device;
allocatorCreateInfo.
instance = instance;
VMA_CALL_PRE VkResult VMA_CALL_POST vmaCreateAllocator(const VmaAllocatorCreateInfo *VMA_NOT_NULL pCreateInfo, VmaAllocator VMA_NULLABLE *VMA_NOT_NULL pAllocator)
Creates VmaAllocator object.
Description of a Allocator to be created.
Definition: vk_mem_alloc.h:1001
const VmaVulkanFunctions *VMA_NULLABLE pVulkanFunctions
Pointers to Vulkan functions.
Definition: vk_mem_alloc.h:1049
VkInstance VMA_NOT_NULL instance
Handle to Vulkan instance object.
Definition: vk_mem_alloc.h:1054
VkDevice VMA_NOT_NULL device
Vulkan device.
Definition: vk_mem_alloc.h:1009
VkPhysicalDevice VMA_NOT_NULL physicalDevice
Vulkan physical device.
Definition: vk_mem_alloc.h:1006
uint32_t vulkanApiVersion
Optional.
Definition: vk_mem_alloc.h:1063
Represents main object of this library initialized.
Pointers to some Vulkan functions - a subset used by the library.
Definition: vk_mem_alloc.h:954
PFN_vkGetInstanceProcAddr VMA_NULLABLE vkGetInstanceProcAddr
Required when using VMA_DYNAMIC_VULKAN_FUNCTIONS.
Definition: vk_mem_alloc.h:956
PFN_vkGetDeviceProcAddr VMA_NULLABLE vkGetDeviceProcAddr
Required when using VMA_DYNAMIC_VULKAN_FUNCTIONS.
Definition: vk_mem_alloc.h:958
#define vkGetInstanceProcAddr
Definition: vulkan.h:4777
#define vkGetDeviceProcAddr
Definition: vulkan.h:4757
Resource allocation
When you want to create a buffer or image:
- Fill
VkBufferCreateInfo
/ VkImageCreateInfo
structure.
- Fill VmaAllocationCreateInfo structure.
- Call vmaCreateBuffer() / vmaCreateImage() to get
VkBuffer
/VkImage
with memory already allocated and bound to it, plus VmaAllocation objects that represents its underlying memory.
VkBuffer buffer;
vmaCreateBuffer(allocator, &bufferInfo, &allocInfo, &buffer, &allocation,
nullptr);
VMA_CALL_PRE VkResult VMA_CALL_POST vmaCreateBuffer(VmaAllocator VMA_NOT_NULL allocator, const VkBufferCreateInfo *VMA_NOT_NULL pBufferCreateInfo, const VmaAllocationCreateInfo *VMA_NOT_NULL pAllocationCreateInfo, VkBuffer VMA_NULLABLE_NON_DISPATCHABLE *VMA_NOT_NULL pBuffer, VmaAllocation VMA_NULLABLE *VMA_NOT_NULL pAllocation, VmaAllocationInfo *VMA_NULLABLE pAllocationInfo)
Creates a new VkBuffer, allocates and binds memory for it.
@ VMA_MEMORY_USAGE_AUTO
Selects best memory type automatically.
Definition: vk_mem_alloc.h:492
Definition: vulkan.h:2611
VkDeviceSize size
Definition: vulkan.h:2615
VkBufferUsageFlags usage
Definition: vulkan.h:2616
Parameters of new VmaAllocation.
Definition: vk_mem_alloc.h:1222
VmaMemoryUsage usage
Intended usage of memory.
Definition: vk_mem_alloc.h:1230
Represents single memory allocation.
@ VK_BUFFER_USAGE_TRANSFER_DST_BIT
Definition: vulkan.h:393
@ VK_BUFFER_USAGE_VERTEX_BUFFER_BIT
Definition: vulkan.h:399
@ VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO
Definition: vulkan.h:1110
Don't forget to destroy your objects when no longer needed:
VMA_CALL_PRE void VMA_CALL_POST vmaDestroyBuffer(VmaAllocator VMA_NOT_NULL allocator, VkBuffer VMA_NULLABLE_NON_DISPATCHABLE buffer, VmaAllocation VMA_NULLABLE allocation)
Destroys Vulkan buffer and frees allocated memory.
VMA_CALL_PRE void VMA_CALL_POST vmaDestroyAllocator(VmaAllocator VMA_NULLABLE allocator)
Destroys allocator object.