• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2020 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6 // vma_allocator_wrapper.cpp:
7 //    Hides VMA functions so we can use separate warning sets.
8 //
9 
10 #include "vk_mem_alloc_wrapper.h"
11 
12 #include <vk_mem_alloc.h>
13 
14 namespace vma
15 {
16 #define VALIDATE_BLOCK_CREATE_FLAG_BITS(x)                                                 \
17     static_assert(static_cast<uint32_t>(x) ==                                              \
18                       static_cast<uint32_t>(VMA_VIRTUAL_BLOCK_CREATE_##x##_ALGORITHM_BIT), \
19                   "VMA enum mismatch")
20 VALIDATE_BLOCK_CREATE_FLAG_BITS(LINEAR);
21 
InitAllocator(VkPhysicalDevice physicalDevice,VkDevice device,VkInstance instance,uint32_t apiVersion,VkDeviceSize preferredLargeHeapBlockSize,VmaAllocator * pAllocator)22 VkResult InitAllocator(VkPhysicalDevice physicalDevice,
23                        VkDevice device,
24                        VkInstance instance,
25                        uint32_t apiVersion,
26                        VkDeviceSize preferredLargeHeapBlockSize,
27                        VmaAllocator *pAllocator)
28 {
29     VmaVulkanFunctions funcs                  = {};
30     funcs.vkGetPhysicalDeviceProperties       = vkGetPhysicalDeviceProperties;
31     funcs.vkGetPhysicalDeviceMemoryProperties = vkGetPhysicalDeviceMemoryProperties;
32     funcs.vkAllocateMemory                    = vkAllocateMemory;
33     funcs.vkFreeMemory                        = vkFreeMemory;
34     funcs.vkMapMemory                         = vkMapMemory;
35     funcs.vkUnmapMemory                       = vkUnmapMemory;
36     funcs.vkFlushMappedMemoryRanges           = vkFlushMappedMemoryRanges;
37     funcs.vkInvalidateMappedMemoryRanges      = vkInvalidateMappedMemoryRanges;
38     funcs.vkBindBufferMemory                  = vkBindBufferMemory;
39     funcs.vkBindImageMemory                   = vkBindImageMemory;
40     funcs.vkGetBufferMemoryRequirements       = vkGetBufferMemoryRequirements;
41     funcs.vkGetImageMemoryRequirements        = vkGetImageMemoryRequirements;
42     funcs.vkCreateBuffer                      = vkCreateBuffer;
43     funcs.vkDestroyBuffer                     = vkDestroyBuffer;
44     funcs.vkCreateImage                       = vkCreateImage;
45     funcs.vkDestroyImage                      = vkDestroyImage;
46     funcs.vkCmdCopyBuffer                     = vkCmdCopyBuffer;
47     {
48         funcs.vkGetBufferMemoryRequirements2KHR       = vkGetBufferMemoryRequirements2;
49         funcs.vkGetImageMemoryRequirements2KHR        = vkGetImageMemoryRequirements2;
50         funcs.vkBindBufferMemory2KHR                  = vkBindBufferMemory2;
51         funcs.vkBindImageMemory2KHR                   = vkBindImageMemory2;
52         funcs.vkGetPhysicalDeviceMemoryProperties2KHR = vkGetPhysicalDeviceMemoryProperties2;
53     }
54 
55     VmaAllocatorCreateInfo allocatorInfo      = {};
56     allocatorInfo.physicalDevice              = physicalDevice;
57     allocatorInfo.device                      = device;
58     allocatorInfo.instance                    = instance;
59     allocatorInfo.pVulkanFunctions            = &funcs;
60     allocatorInfo.vulkanApiVersion            = apiVersion;
61     allocatorInfo.preferredLargeHeapBlockSize = preferredLargeHeapBlockSize;
62 
63     return vmaCreateAllocator(&allocatorInfo, pAllocator);
64 }
65 
DestroyAllocator(VmaAllocator allocator)66 void DestroyAllocator(VmaAllocator allocator)
67 {
68     vmaDestroyAllocator(allocator);
69 }
70 
FreeMemory(VmaAllocator allocator,VmaAllocation allocation)71 void FreeMemory(VmaAllocator allocator, VmaAllocation allocation)
72 {
73     vmaFreeMemory(allocator, allocation);
74 }
75 
CreateBuffer(VmaAllocator allocator,const VkBufferCreateInfo * pBufferCreateInfo,VkMemoryPropertyFlags requiredFlags,VkMemoryPropertyFlags preferredFlags,bool persistentlyMapped,uint32_t * pMemoryTypeIndexOut,VkBuffer * pBuffer,VmaAllocation * pAllocation)76 VkResult CreateBuffer(VmaAllocator allocator,
77                       const VkBufferCreateInfo *pBufferCreateInfo,
78                       VkMemoryPropertyFlags requiredFlags,
79                       VkMemoryPropertyFlags preferredFlags,
80                       bool persistentlyMapped,
81                       uint32_t *pMemoryTypeIndexOut,
82                       VkBuffer *pBuffer,
83                       VmaAllocation *pAllocation)
84 {
85     VkResult result;
86     VmaAllocationCreateInfo allocationCreateInfo = {};
87     allocationCreateInfo.requiredFlags           = requiredFlags;
88     allocationCreateInfo.preferredFlags          = preferredFlags;
89     allocationCreateInfo.flags       = (persistentlyMapped) ? VMA_ALLOCATION_CREATE_MAPPED_BIT : 0;
90     VmaAllocationInfo allocationInfo = {};
91 
92     result = vmaCreateBuffer(allocator, pBufferCreateInfo, &allocationCreateInfo, pBuffer,
93                              pAllocation, &allocationInfo);
94     *pMemoryTypeIndexOut = allocationInfo.memoryType;
95 
96     return result;
97 }
98 
AllocateAndBindMemoryForImage(VmaAllocator allocator,VkImage * pImage,VkMemoryPropertyFlags requiredFlags,VkMemoryPropertyFlags preferredFlags,uint32_t memoryTypeBits,bool allocateDedicatedMemory,VmaAllocation * pAllocationOut,uint32_t * pMemoryTypeIndexOut,VkDeviceSize * sizeOut)99 VkResult AllocateAndBindMemoryForImage(VmaAllocator allocator,
100                                        VkImage *pImage,
101                                        VkMemoryPropertyFlags requiredFlags,
102                                        VkMemoryPropertyFlags preferredFlags,
103                                        uint32_t memoryTypeBits,
104                                        bool allocateDedicatedMemory,
105                                        VmaAllocation *pAllocationOut,
106                                        uint32_t *pMemoryTypeIndexOut,
107                                        VkDeviceSize *sizeOut)
108 {
109     VkResult result;
110     VmaAllocationCreateInfo allocationCreateInfo = {};
111     allocationCreateInfo.requiredFlags           = requiredFlags;
112     allocationCreateInfo.preferredFlags          = preferredFlags;
113     allocationCreateInfo.memoryTypeBits          = memoryTypeBits;
114     allocationCreateInfo.flags =
115         allocateDedicatedMemory ? VMA_ALLOCATION_CREATE_DEDICATED_MEMORY_BIT : 0;
116     VmaAllocationInfo allocationInfo = {};
117 
118     result = vmaAllocateMemoryForImage(allocator, *pImage, &allocationCreateInfo, pAllocationOut,
119                                        &allocationInfo);
120     if (result == VK_SUCCESS)
121     {
122         // If binding was unsuccessful, we should free the allocation.
123         result = vmaBindImageMemory(allocator, *pAllocationOut, *pImage);
124         if (result != VK_SUCCESS)
125         {
126             vmaFreeMemory(allocator, *pAllocationOut);
127             *pAllocationOut = VK_NULL_HANDLE;
128             return result;
129         }
130 
131         *pMemoryTypeIndexOut = allocationInfo.memoryType;
132         *sizeOut             = allocationInfo.size;
133     }
134 
135     return result;
136 }
137 
FindMemoryTypeIndexForBufferInfo(VmaAllocator allocator,const VkBufferCreateInfo * pBufferCreateInfo,VkMemoryPropertyFlags requiredFlags,VkMemoryPropertyFlags preferredFlags,bool persistentlyMappedBuffers,uint32_t * pMemoryTypeIndexOut)138 VkResult FindMemoryTypeIndexForBufferInfo(VmaAllocator allocator,
139                                           const VkBufferCreateInfo *pBufferCreateInfo,
140                                           VkMemoryPropertyFlags requiredFlags,
141                                           VkMemoryPropertyFlags preferredFlags,
142                                           bool persistentlyMappedBuffers,
143                                           uint32_t *pMemoryTypeIndexOut)
144 {
145     VmaAllocationCreateInfo allocationCreateInfo = {};
146     allocationCreateInfo.requiredFlags           = requiredFlags;
147     allocationCreateInfo.preferredFlags          = preferredFlags;
148     allocationCreateInfo.flags = (persistentlyMappedBuffers) ? VMA_ALLOCATION_CREATE_MAPPED_BIT : 0;
149 
150     return vmaFindMemoryTypeIndexForBufferInfo(allocator, pBufferCreateInfo, &allocationCreateInfo,
151                                                pMemoryTypeIndexOut);
152 }
153 
FindMemoryTypeIndexForImageInfo(VmaAllocator allocator,const VkImageCreateInfo * pImageCreateInfo,VkMemoryPropertyFlags requiredFlags,VkMemoryPropertyFlags preferredFlags,bool allocateDedicatedMemory,uint32_t * pMemoryTypeIndexOut)154 VkResult FindMemoryTypeIndexForImageInfo(VmaAllocator allocator,
155                                          const VkImageCreateInfo *pImageCreateInfo,
156                                          VkMemoryPropertyFlags requiredFlags,
157                                          VkMemoryPropertyFlags preferredFlags,
158                                          bool allocateDedicatedMemory,
159                                          uint32_t *pMemoryTypeIndexOut)
160 {
161     VmaAllocationCreateInfo allocationCreateInfo = {};
162     allocationCreateInfo.requiredFlags           = requiredFlags;
163     allocationCreateInfo.preferredFlags          = preferredFlags;
164     allocationCreateInfo.flags =
165         allocateDedicatedMemory ? VMA_ALLOCATION_CREATE_DEDICATED_MEMORY_BIT : 0;
166 
167     return vmaFindMemoryTypeIndexForImageInfo(allocator, pImageCreateInfo, &allocationCreateInfo,
168                                               pMemoryTypeIndexOut);
169 }
170 
GetMemoryTypeProperties(VmaAllocator allocator,uint32_t memoryTypeIndex,VkMemoryPropertyFlags * pFlags)171 void GetMemoryTypeProperties(VmaAllocator allocator,
172                              uint32_t memoryTypeIndex,
173                              VkMemoryPropertyFlags *pFlags)
174 {
175     vmaGetMemoryTypeProperties(allocator, memoryTypeIndex, pFlags);
176 }
177 
MapMemory(VmaAllocator allocator,VmaAllocation allocation,void ** ppData)178 VkResult MapMemory(VmaAllocator allocator, VmaAllocation allocation, void **ppData)
179 {
180     return vmaMapMemory(allocator, allocation, ppData);
181 }
182 
UnmapMemory(VmaAllocator allocator,VmaAllocation allocation)183 void UnmapMemory(VmaAllocator allocator, VmaAllocation allocation)
184 {
185     return vmaUnmapMemory(allocator, allocation);
186 }
187 
FlushAllocation(VmaAllocator allocator,VmaAllocation allocation,VkDeviceSize offset,VkDeviceSize size)188 void FlushAllocation(VmaAllocator allocator,
189                      VmaAllocation allocation,
190                      VkDeviceSize offset,
191                      VkDeviceSize size)
192 {
193     vmaFlushAllocation(allocator, allocation, offset, size);
194 }
195 
InvalidateAllocation(VmaAllocator allocator,VmaAllocation allocation,VkDeviceSize offset,VkDeviceSize size)196 void InvalidateAllocation(VmaAllocator allocator,
197                           VmaAllocation allocation,
198                           VkDeviceSize offset,
199                           VkDeviceSize size)
200 {
201     vmaInvalidateAllocation(allocator, allocation, offset, size);
202 }
203 
BuildStatsString(VmaAllocator allocator,char ** statsString,VkBool32 detailedMap)204 void BuildStatsString(VmaAllocator allocator, char **statsString, VkBool32 detailedMap)
205 {
206     vmaBuildStatsString(allocator, statsString, detailedMap);
207 }
208 
FreeStatsString(VmaAllocator allocator,char * statsString)209 void FreeStatsString(VmaAllocator allocator, char *statsString)
210 {
211     vmaFreeStatsString(allocator, statsString);
212 }
213 
214 // VmaVirtualBlock implementation
CreateVirtualBlock(VkDeviceSize size,VirtualBlockCreateFlags flags,VmaVirtualBlock * pVirtualBlock)215 VkResult CreateVirtualBlock(VkDeviceSize size,
216                             VirtualBlockCreateFlags flags,
217                             VmaVirtualBlock *pVirtualBlock)
218 {
219     VmaVirtualBlockCreateInfo virtualBlockCreateInfo = {};
220     virtualBlockCreateInfo.size                      = size;
221     virtualBlockCreateInfo.flags                     = (VmaVirtualBlockCreateFlagBits)flags;
222     return vmaCreateVirtualBlock(&virtualBlockCreateInfo, pVirtualBlock);
223 }
224 
DestroyVirtualBlock(VmaVirtualBlock virtualBlock)225 void DestroyVirtualBlock(VmaVirtualBlock virtualBlock)
226 {
227     vmaDestroyVirtualBlock(virtualBlock);
228 }
229 
VirtualAllocate(VmaVirtualBlock virtualBlock,VkDeviceSize size,VkDeviceSize alignment,VmaVirtualAllocation * pAllocation,VkDeviceSize * pOffset)230 VkResult VirtualAllocate(VmaVirtualBlock virtualBlock,
231                          VkDeviceSize size,
232                          VkDeviceSize alignment,
233                          VmaVirtualAllocation *pAllocation,
234                          VkDeviceSize *pOffset)
235 {
236     VmaVirtualAllocationCreateInfo createInfo = {};
237     createInfo.size                           = size;
238     createInfo.alignment                      = alignment;
239     createInfo.flags                          = 0;
240     return vmaVirtualAllocate(virtualBlock, &createInfo, pAllocation, pOffset);
241 }
242 
VirtualFree(VmaVirtualBlock virtualBlock,VmaVirtualAllocation allocation,VkDeviceSize offset)243 void VirtualFree(VmaVirtualBlock virtualBlock, VmaVirtualAllocation allocation, VkDeviceSize offset)
244 {
245     vmaVirtualFree(virtualBlock, allocation);
246 }
247 
IsVirtualBlockEmpty(VmaVirtualBlock virtualBlock)248 VkBool32 IsVirtualBlockEmpty(VmaVirtualBlock virtualBlock)
249 {
250     return vmaIsVirtualBlockEmpty(virtualBlock);
251 }
252 
GetVirtualAllocationInfo(VmaVirtualBlock virtualBlock,VmaVirtualAllocation allocation,VkDeviceSize offset,VkDeviceSize * sizeOut,void ** pUserDataOut)253 void GetVirtualAllocationInfo(VmaVirtualBlock virtualBlock,
254                               VmaVirtualAllocation allocation,
255                               VkDeviceSize offset,
256                               VkDeviceSize *sizeOut,
257                               void **pUserDataOut)
258 {
259     VmaVirtualAllocationInfo virtualAllocInfo = {};
260     vmaGetVirtualAllocationInfo(virtualBlock, allocation, &virtualAllocInfo);
261     *sizeOut      = virtualAllocInfo.size;
262     *pUserDataOut = virtualAllocInfo.pUserData;
263 }
264 
ClearVirtualBlock(VmaVirtualBlock virtualBlock)265 void ClearVirtualBlock(VmaVirtualBlock virtualBlock)
266 {
267     vmaClearVirtualBlock(virtualBlock);
268 }
269 
SetVirtualAllocationUserData(VmaVirtualBlock virtualBlock,VmaVirtualAllocation allocation,VkDeviceSize offset,void * pUserData)270 void SetVirtualAllocationUserData(VmaVirtualBlock virtualBlock,
271                                   VmaVirtualAllocation allocation,
272                                   VkDeviceSize offset,
273                                   void *pUserData)
274 {
275     vmaSetVirtualAllocationUserData(virtualBlock, allocation, pUserData);
276 }
277 
CalculateVirtualBlockStats(VmaVirtualBlock virtualBlock,StatInfo * pStatInfo)278 void CalculateVirtualBlockStats(VmaVirtualBlock virtualBlock, StatInfo *pStatInfo)
279 {
280     vmaCalculateVirtualBlockStatistics(virtualBlock,
281                                        reinterpret_cast<VmaDetailedStatistics *>(pStatInfo));
282 }
283 
BuildVirtualBlockStatsString(VmaVirtualBlock virtualBlock,char ** ppStatsString,VkBool32 detailedMap)284 void BuildVirtualBlockStatsString(VmaVirtualBlock virtualBlock,
285                                   char **ppStatsString,
286                                   VkBool32 detailedMap)
287 {
288     vmaBuildVirtualBlockStatsString(virtualBlock, ppStatsString, detailedMap);
289 }
290 
FreeVirtualBlockStatsString(VmaVirtualBlock virtualBlock,char * pStatsString)291 void FreeVirtualBlockStatsString(VmaVirtualBlock virtualBlock, char *pStatsString)
292 {
293     vmaFreeVirtualBlockStatsString(virtualBlock, pStatsString);
294 }
295 }  // namespace vma
296