Skip to content

Commit

Permalink
Merge pull request #2291 from billhollings/dyn-alloc-descriptors
Browse files Browse the repository at this point in the history
Support dynamically allocating descriptors when pool is exhausted.
  • Loading branch information
billhollings authored Jul 28, 2024
2 parents accc727 + ddd5bf4 commit c2bca92
Show file tree
Hide file tree
Showing 7 changed files with 110 additions and 83 deletions.
13 changes: 0 additions & 13 deletions Docs/MoltenVK_Configuration_Parameters.md
Original file line number Diff line number Diff line change
Expand Up @@ -324,19 +324,6 @@ You can also use the `MVK_CONFIG_ACTIVITY_PERFORMANCE_LOGGING_STYLE` and
`MVK_CONFIG_PERFORMANCE_LOGGING_FRAME_COUNT` parameters to configure when to log the performance statistics collected by this parameter.


---------------------------------------
#### MVK_CONFIG_PREALLOCATE_DESCRIPTORS

##### Type: Boolean
##### Default: `1`

Controls whether **MoltenVK** should preallocate memory in each `VkDescriptorPool` according
to the values of the `VkDescriptorPoolSize` parameters. Doing so may improve descriptor set
allocation performance and memory stability at a cost of preallocated application memory.
If this setting is disabled, the descriptors required for a descriptor set will be individually
dynamically allocated in application memory when the descriptor set itself is allocated.


---------------------------------------
#### MVK_CONFIG_PREFILL_METAL_COMMAND_BUFFERS

Expand Down
5 changes: 5 additions & 0 deletions Docs/Whats_New.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,11 @@ MoltenVK 1.2.11

Released TBD

- Support dynamically allocating descriptors when pool is exhausted.
- Deprecate `MVKConfiguration::preallocateDescriptors` and `MVK_CONFIG_PREALLOCATE_DESCRIPTORS` environment variable.
- `vkAllocateDescriptorSets()`: Per Vulkan spec, if any descriptor set allocation
fails, populate all descriptor set pointers with `VK_NULL_HANDLE`. In addition,
return `VK_ERROR_FRAGMENTED_POOL` if failure was due to pool fragmentation.
- Fix rendering issue with render pass that immediately follows a kernel dispatch.
- Ensure all MoltenVK config info set by `VK_EXT_layer_settings` is used.

Expand Down
2 changes: 1 addition & 1 deletion MoltenVK/MoltenVK/API/mvk_private_api.h
Original file line number Diff line number Diff line change
Expand Up @@ -225,7 +225,7 @@ typedef struct {
MVKConfigAutoGPUCaptureScope autoGPUCaptureScope; /**< MVK_CONFIG_AUTO_GPU_CAPTURE_SCOPE */
const char* autoGPUCaptureOutputFilepath; /**< MVK_CONFIG_AUTO_GPU_CAPTURE_OUTPUT_FILE */
VkBool32 texture1DAs2D; /**< MVK_CONFIG_TEXTURE_1D_AS_2D */
VkBool32 preallocateDescriptors; /**< MVK_CONFIG_PREALLOCATE_DESCRIPTORS */
VkBool32 preallocateDescriptors; /**< Obsolete, deprecated, and ignored. */
VkBool32 useCommandPooling; /**< MVK_CONFIG_USE_COMMAND_POOLING */
VkBool32 useMTLHeap; /**< MVK_CONFIG_USE_MTLHEAP */
MVKConfigActivityPerformanceLoggingStyle activityPerformanceLoggingStyle; /**< MVK_CONFIG_ACTIVITY_PERFORMANCE_LOGGING_STYLE */
Expand Down
16 changes: 9 additions & 7 deletions MoltenVK/MoltenVK/GPUObjects/MVKDescriptorSet.h
Original file line number Diff line number Diff line change
Expand Up @@ -217,12 +217,13 @@ class MVKDescriptorSet : public MVKVulkanAPIDeviceObject {
void setBufferSize(uint32_t descIdx, uint32_t value);

MVKDescriptorPool* _pool;
MVKDescriptorSetLayout* _layout;
MVKDescriptorSetLayout* _layout = nullptr;
MVKMTLBufferAllocation* _bufferSizesBuffer = nullptr;
MVKSmallVector<MVKDescriptor*> _descriptors;
MVKMetalArgumentBuffer _argumentBuffer;
MVKMTLBufferAllocation* _bufferSizesBuffer = nullptr;
uint32_t _dynamicOffsetDescriptorCount;
uint32_t _variableDescriptorCount;
uint32_t _dynamicOffsetDescriptorCount = 0;
uint32_t _variableDescriptorCount = 0;
bool _allDescriptorsAreFromPool = true;
};


Expand All @@ -242,9 +243,11 @@ class MVKDescriptorTypePool : public MVKBaseObject {
protected:
friend class MVKDescriptorPool;

VkResult allocateDescriptor(MVKDescriptor** pMVKDesc, MVKDescriptorPool* pool);
VkResult allocateDescriptor(VkDescriptorType descType, MVKDescriptor** pMVKDesc, bool& dynamicAllocation, MVKDescriptorPool* pool);
void freeDescriptor(MVKDescriptor* mvkDesc, MVKDescriptorPool* pool);
void reset();
size_t size() { return _availability.size(); }
size_t getRemainingDescriptorCount();

MVKSmallVector<DescriptorClass> _descriptors;
MVKBitArray _availability;
Expand Down Expand Up @@ -286,15 +289,14 @@ class MVKDescriptorPool : public MVKVulkanAPIDeviceObject {
void propagateDebugName() override {}
VkResult allocateDescriptorSet(MVKDescriptorSetLayout* mvkDSL, uint32_t variableDescriptorCount, VkDescriptorSet* pVKDS);
void freeDescriptorSet(MVKDescriptorSet* mvkDS, bool isPoolReset);
VkResult allocateDescriptor(VkDescriptorType descriptorType, MVKDescriptor** pMVKDesc);
VkResult allocateDescriptor(VkDescriptorType descriptorType, MVKDescriptor** pMVKDesc, bool& dynamicAllocation);
void freeDescriptor(MVKDescriptor* mvkDesc);
void initMetalArgumentBuffer(const VkDescriptorPoolCreateInfo* pCreateInfo);
NSUInteger getMetalArgumentBufferEncodedResourceStorageSize(NSUInteger bufferCount, NSUInteger textureCount, NSUInteger samplerCount);
MTLArgumentDescriptor* getMTLArgumentDescriptor(MTLDataType resourceType, NSUInteger argIndex, NSUInteger count);
size_t getPoolSize(const VkDescriptorPoolCreateInfo* pCreateInfo, VkDescriptorType descriptorType);
std::string getLogDescription();

bool _hasPooledDescriptors;
MVKSmallVector<MVKDescriptorSet> _descriptorSets;
MVKBitArray _descriptorSetAvailablility;
id<MTLBuffer> _metalArgumentBuffer;
Expand Down
Loading

0 comments on commit c2bca92

Please sign in to comment.