SPARK  0.1.0
A general purpose game engine written in C++.
Loading...
Searching...
No Matches
spark::render::vk::VulkanDescriptorSetLayout Class Referencefinal

Vulkan implementation of IDescriptorSetLayout. More...

#include <VulkanDescriptorSetLayout.h>

Inheritance diagram for spark::render::vk::VulkanDescriptorSetLayout:
spark::render::DescriptorSetLayout< VulkanDescriptorLayout, VulkanDescriptorSet > spark::render::Resource< VkDescriptorSetLayout > spark::render::IDescriptorSetLayout spark::render::IResource< VkDescriptorSetLayout >

Classes

struct  Impl
 

Public Member Functions

 VulkanDescriptorSetLayout (const VulkanDevice &device, std::vector< std::unique_ptr< VulkanDescriptorLayout > > &&descriptor_layouts, unsigned int space, ShaderStage stages, unsigned int pool_size=1024, unsigned int max_unbounded_array_size=104857)
 Initializes a VulkanDescriptorSetLayout.
 
 VulkanDescriptorSetLayout (const VulkanDescriptorSetLayout &other)=delete
 
 VulkanDescriptorSetLayout (VulkanDescriptorSetLayout &&other) noexcept=delete
 
VulkanDescriptorSetLayoutoperator= (const VulkanDescriptorSetLayout &other)=delete
 
VulkanDescriptorSetLayoutoperator= (VulkanDescriptorSetLayout &&other) noexcept=delete
 
unsigned poolSize () const noexcept
 Gets the size of each descriptor pool.
 
std::size_t pools () const noexcept
 Gets the number of active descriptor pools.
 
const VulkanDevicedevice () const noexcept
 Gets the parent VulkanDevice the pipeline layout has been created from.
 
std::vector< const VulkanDescriptorLayout * > descriptors () const noexcept override
 Gets the layouts of all descriptors in the IDescriptorSet.
 
const VulkanDescriptorLayoutdescriptor (unsigned binding) const override
 Gets the layout of a descriptor in the IDescriptorSet bound to a specific binding point.
 
unsigned space () const noexcept override
 Gets the space index of the IDescriptorSet.
 
ShaderStage shaderStage () const noexcept override
 Gets the shader stage the IDescriptorSet is used in.
 
unsigned uniforms () const noexcept override
 Gets the number of uniform/constant buffers in the IDescriptorSet.
 
unsigned storages () const noexcept override
 Gets the number of storage buffers in the IDescriptorSet.
 
unsigned images () const noexcept override
 Gets the number of images (textures) in the IDescriptorSet.
 
unsigned samplers () const noexcept override
 Gets the number of texel buffer descriptors in the IDescriptorSet.
 
unsigned buffers () const noexcept override
 Get the number of texel buffer descriptors in the IDescriptorSet.
 
unsigned staticSamplers () const noexcept override
 Gets the number of static/immutable samplers in the IDescriptorSet.
 
unsigned inputAttachments () const noexcept override
 Gets the number of input attachments in the IDescriptorSet.
 
std::unique_ptr< VulkanDescriptorSetallocate (const std::vector< DescriptorBinding > &bindings={}) const override
 Allocates a new IDescriptorSet or returns an unused descriptor set.
 
std::unique_ptr< VulkanDescriptorSetallocate (unsigned descriptors, const std::vector< DescriptorBinding > &bindings={}) const override
 Allocates a new IDescriptorSet or returns an unused descriptor set.
 
std::vector< std::unique_ptr< VulkanDescriptorSet > > allocateMultiple (unsigned descriptor_sets, const std::vector< std::vector< DescriptorBinding > > &bindings={}) const override
 Allocates an array of IDescriptorSet.
 
std::vector< std::unique_ptr< VulkanDescriptorSet > > allocateMultiple (unsigned descriptor_sets, const std::function< std::vector< DescriptorBinding >(unsigned)> &binding_factory) const override
 Allocates an array of IDescriptorSet.
 
std::vector< std::unique_ptr< VulkanDescriptorSet > > allocateMultiple (unsigned descriptor_sets, unsigned descriptors, const std::vector< std::vector< DescriptorBinding > > &bindings={}) const override
 Allocates an array of IDescriptorSet.
 
std::vector< std::unique_ptr< VulkanDescriptorSet > > allocateMultiple (unsigned descriptor_sets, unsigned descriptors, const std::function< std::vector< DescriptorBinding >(unsigned)> &binding_factory) const override
 Allocates an array of IDescriptorSet.
 
void free (const VulkanDescriptorSet &descriptor_set) const noexcept override
 
- Public Member Functions inherited from spark::render::DescriptorSetLayout< VulkanDescriptorLayout, VulkanDescriptorSet >
virtual void free (const descriptor_set_type &descriptor_set) const noexcept=0
 Marks a IDescriptorSet as unused, so that it can be handed out again instead of allocating a new one.
 
- Public Member Functions inherited from spark::render::IDescriptorSetLayout
std::vector< const IDescriptorLayout * > descriptors () const noexcept
 Gets the layouts of all descriptors in the IDescriptorSet.
 
virtual const IDescriptorLayoutdescriptor (unsigned int binding) const =0
 Gets the layout of a descriptor in the IDescriptorSet bound to a specific binding point.
 
std::unique_ptr< IDescriptorSetallocate (const std::vector< DescriptorBinding > &bindings={}) const
 Allocates a new IDescriptorSet or returns an unused descriptor set.
 
std::unique_ptr< IDescriptorSetallocate (unsigned int descriptors, const std::vector< DescriptorBinding > &bindings={}) const
 Allocates a new IDescriptorSet or returns an unused descriptor set.
 
std::vector< std::unique_ptr< IDescriptorSet > > allocateMultiple (unsigned int descriptors_sets, const std::vector< std::vector< DescriptorBinding > > &bindings={}) const noexcept
 Allocates an array of IDescriptorSet.
 
std::vector< std::unique_ptr< IDescriptorSet > > allocateMultiple (unsigned int descriptors_sets, const std::function< std::vector< DescriptorBinding >(unsigned)> &binding_factory) const noexcept
 Allocates an array of IDescriptorSet.
 
std::vector< std::unique_ptr< IDescriptorSet > > allocateMultiple (unsigned int descriptors_sets, unsigned int descriptors, const std::vector< std::vector< DescriptorBinding > > &bindings={}) const noexcept
 Allocates an array of IDescriptorSet.
 
std::vector< std::unique_ptr< IDescriptorSet > > allocateMultiple (unsigned int descriptors_sets, unsigned int descriptors, const std::function< std::vector< DescriptorBinding >(unsigned)> &binding_factory={}) const noexcept
 Allocates an array of IDescriptorSet.
 
void free (const IDescriptorSet &descriptor_set) const noexcept
 Marks a IDescriptorSet as unused, so that it can be handed out again instead of allocating a new one.
 
- Public Member Functions inherited from spark::render::Resource< VkDescriptorSetLayout >
 Resource (VkDescriptorSetLayout handle) noexcept
 Initializes the managed resource with the given handle.
 
 Resource (const Resource &other)=delete
 
 Resource (Resource &&other) noexcept=delete
 
Resourceoperator= (const Resource &other)=delete
 
Resourceoperator= (Resource &&other) noexcept=delete
 
const VkDescriptorSetLayout & handle () const final
 Gets the managed resource handle.
 

Additional Inherited Members

- Public Types inherited from spark::render::DescriptorSetLayout< VulkanDescriptorLayout, VulkanDescriptorSet >
using descriptor_layout_type
 
using descriptor_set_type
 
- Public Types inherited from spark::render::IResource< VkDescriptorSetLayout >
using handle_type
 
- Protected Member Functions inherited from spark::render::Resource< VkDescriptorSetLayout >
VkDescriptorSetLayout & handle () final
 Gets the managed resource handle.
 

Detailed Description

Vulkan implementation of IDescriptorSetLayout.

Constructor & Destructor Documentation

◆ VulkanDescriptorSetLayout()

spark::render::vk::VulkanDescriptorSetLayout::VulkanDescriptorSetLayout ( const VulkanDevice & device,
std::vector< std::unique_ptr< VulkanDescriptorLayout > > && descriptor_layouts,
unsigned int space,
ShaderStage stages,
unsigned int pool_size = 1024,
unsigned int max_unbounded_array_size = 104857 )
explicit

Initializes a VulkanDescriptorSetLayout.

Parameters
deviceThe parent VulkanDevice the pipeline layout has been created from.
descriptor_layoutsThe descriptor layouts that are part of this descriptor set layout.
spaceThe space (space id) of the descriptor set layout.
stagesThe ShaderStage the descriptor set layout is used in.
pool_sizeThe size of the descriptor pool.
max_unbounded_array_sizeThe maximum numbers of descriptors in an unbounded array.

Member Function Documentation

◆ allocate() [1/2]

std::unique_ptr< VulkanDescriptorSet > spark::render::vk::VulkanDescriptorSetLayout::allocate ( const std::vector< DescriptorBinding > & bindings = {}) const
nodiscardoverridevirtual

Allocates a new IDescriptorSet or returns an unused descriptor set.

Parameters
bindingsOptional list of descriptor bindings to initialize the IDescriptorSet with.
Returns
A std::unique_ptr to the allocated IDescriptorSet.

Allocating a new descriptor set may be an expensive operation. To improve performance, and prevent fragmentation, the descriptor set layout keeps track of created descriptor sets. It does this by never releasing them. Instead, when a IDescriptorSet instance gets destroyed, it should call IDescriptorSetLayout::free() in order to mark itself (i.e. its handle) as not being used any longer.

Before allocating a new descriptor set from a pool (which may even result in the creation of a new pool, if the existing pools are full), the layout tries to hand out descriptor sets that marked as unused. Descriptor sets are only deleted, if the whole layout instance and therefore the descriptor pools are deleted. ( The above does not apply to unbounded descriptor arrays. A unbounded descriptor array is one, for which IDescriptorLayout::descriptors() returns -1 (or 0xFFFFFFFF). They must be allocated by specifying the descriptors parameter. This parameter defines the number of descriptors to allocate in the array.

Note that descriptor sets, that contain an unbounded descriptor array must only contain one single descriptor (the one that identifies this array). Such descriptor sets are never cached. Instead, they are released when calling IDescriptorSetLayout::free(). It is a good practice to cache such descriptor sets as global descriptor tables once and never release them. They provide more flexibility than regular descriptor arrays, since they may be updated, even after they have been bound to a command buffer or from different threads. However, you must ensure yourself not to overwrite any descriptors that are currently in use. Because unbounded arrays are not cached, freeing and re-allocating such descriptor sets may leave the descriptor heap fragmented, which might cause the allocation to fail, if the heap is full.

Implements spark::render::DescriptorSetLayout< VulkanDescriptorLayout, VulkanDescriptorSet >.

◆ allocate() [2/2]

std::unique_ptr< VulkanDescriptorSet > spark::render::vk::VulkanDescriptorSetLayout::allocate ( unsigned descriptors,
const std::vector< DescriptorBinding > & bindings = {} ) const
nodiscardoverridevirtual

Allocates a new IDescriptorSet or returns an unused descriptor set.

Parameters
bindingsOptional list of descriptor bindings to initialize the IDescriptorSet with.
Returns
A std::unique_ptr to the allocated IDescriptorSet.

Allocating a new descriptor set may be an expensive operation. To improve performance, and prevent fragmentation, the descriptor set layout keeps track of created descriptor sets. It does this by never releasing them. Instead, when a IDescriptorSet instance gets destroyed, it should call IDescriptorSetLayout::free() in order to mark itself (i.e. its handle) as not being used any longer.

Before allocating a new descriptor set from a pool (which may even result in the creation of a new pool, if the existing pools are full), the layout tries to hand out descriptor sets that marked as unused. Descriptor sets are only deleted, if the whole layout instance and therefore the descriptor pools are deleted. ( The above does not apply to unbounded descriptor arrays. A unbounded descriptor array is one, for which IDescriptorLayout::descriptors() returns -1 (or 0xFFFFFFFF). They must be allocated by specifying the descriptors parameter. This parameter defines the number of descriptors to allocate in the array.

Note that descriptor sets, that contain an unbounded descriptor array must only contain one single descriptor (the one that identifies this array). Such descriptor sets are never cached. Instead, they are released when calling IDescriptorSetLayout::free(). It is a good practice to cache such descriptor sets as global descriptor tables once and never release them. They provide more flexibility than regular descriptor arrays, since they may be updated, even after they have been bound to a command buffer or from different threads. However, you must ensure yourself not to overwrite any descriptors that are currently in use. Because unbounded arrays are not cached, freeing and re-allocating such descriptor sets may leave the descriptor heap fragmented, which might cause the allocation to fail, if the heap is full.

Implements spark::render::DescriptorSetLayout< VulkanDescriptorLayout, VulkanDescriptorSet >.

◆ allocateMultiple() [1/4]

std::vector< std::unique_ptr< VulkanDescriptorSet > > spark::render::vk::VulkanDescriptorSetLayout::allocateMultiple ( unsigned descriptor_sets,
const std::function< std::vector< DescriptorBinding >(unsigned)> & binding_factory ) const
nodiscardoverridevirtual

Allocates an array of IDescriptorSet.

Parameters
descriptors_setsThe number of IDescriptorSet to allocate.
bindingsOptional list of descriptor bindings to initialize the IDescriptorSet with.
Returns
A std::vector containing std::unique_ptr to the newly allocated descriptor sets .

Implements spark::render::DescriptorSetLayout< VulkanDescriptorLayout, VulkanDescriptorSet >.

◆ allocateMultiple() [2/4]

std::vector< std::unique_ptr< VulkanDescriptorSet > > spark::render::vk::VulkanDescriptorSetLayout::allocateMultiple ( unsigned descriptor_sets,
const std::vector< std::vector< DescriptorBinding > > & bindings = {} ) const
nodiscardoverridevirtual

Allocates an array of IDescriptorSet.

Parameters
descriptors_setsThe number of IDescriptorSet to allocate.
bindingsOptional list of descriptor bindings to initialize the IDescriptorSet with.
Returns
A std::vector containing std::unique_ptr to the newly allocated descriptor sets .

Implements spark::render::DescriptorSetLayout< VulkanDescriptorLayout, VulkanDescriptorSet >.

◆ allocateMultiple() [3/4]

std::vector< std::unique_ptr< VulkanDescriptorSet > > spark::render::vk::VulkanDescriptorSetLayout::allocateMultiple ( unsigned descriptor_sets,
unsigned descriptors,
const std::function< std::vector< DescriptorBinding >(unsigned)> & binding_factory ) const
nodiscardoverridevirtual

Allocates an array of IDescriptorSet.

Parameters
descriptors_setsThe number of IDescriptorSet to allocate.
bindingsOptional list of descriptor bindings to initialize the IDescriptorSet with.
Returns
A std::vector containing std::unique_ptr to the newly allocated descriptor sets .

Implements spark::render::DescriptorSetLayout< VulkanDescriptorLayout, VulkanDescriptorSet >.

◆ allocateMultiple() [4/4]

std::vector< std::unique_ptr< VulkanDescriptorSet > > spark::render::vk::VulkanDescriptorSetLayout::allocateMultiple ( unsigned descriptor_sets,
unsigned descriptors,
const std::vector< std::vector< DescriptorBinding > > & bindings = {} ) const
nodiscardoverridevirtual

Allocates an array of IDescriptorSet.

Parameters
descriptors_setsThe number of IDescriptorSet to allocate.
bindingsOptional list of descriptor bindings to initialize the IDescriptorSet with.
Returns
A std::vector containing std::unique_ptr to the newly allocated descriptor sets .

Implements spark::render::DescriptorSetLayout< VulkanDescriptorLayout, VulkanDescriptorSet >.

◆ buffers()

unsigned spark::render::vk::VulkanDescriptorSetLayout::buffers ( ) const
nodiscardoverridevirtualnoexcept

Get the number of texel buffer descriptors in the IDescriptorSet.

Returns
The number of texel buffer descriptors in the IDescriptorSet.

Implements spark::render::IDescriptorSetLayout.

◆ descriptor()

const VulkanDescriptorLayout * spark::render::vk::VulkanDescriptorSetLayout::descriptor ( unsigned binding) const
nodiscardoverridevirtual

Gets the layout of a descriptor in the IDescriptorSet bound to a specific binding point.

Parameters
bindingThe binding point of the requested descriptor layout.
Returns
A pointer to the IDescriptorLayout describing the layout of the descriptor bound to binding.

Implements spark::render::DescriptorSetLayout< VulkanDescriptorLayout, VulkanDescriptorSet >.

◆ descriptors()

std::vector< const VulkanDescriptorLayout * > spark::render::vk::VulkanDescriptorSetLayout::descriptors ( ) const
nodiscardoverridevirtualnoexcept

Gets the layouts of all descriptors in the IDescriptorSet.

Returns
A std::vector containing pointers to IDescriptorLayout of all descriptors in the IDescriptorSet.

Implements spark::render::DescriptorSetLayout< VulkanDescriptorLayout, VulkanDescriptorSet >.

◆ device()

const VulkanDevice & spark::render::vk::VulkanDescriptorSetLayout::device ( ) const
nodiscardnoexcept

Gets the parent VulkanDevice the pipeline layout has been created from.

Returns
The parent VulkanDevice the pipeline layout has been created from.

◆ images()

unsigned spark::render::vk::VulkanDescriptorSetLayout::images ( ) const
nodiscardoverridevirtualnoexcept

Gets the number of images (textures) in the IDescriptorSet.

Returns
The number of images (textures) in the IDescriptorSet.

Implements spark::render::IDescriptorSetLayout.

◆ inputAttachments()

unsigned spark::render::vk::VulkanDescriptorSetLayout::inputAttachments ( ) const
nodiscardoverridevirtualnoexcept

Gets the number of input attachments in the IDescriptorSet.

Returns
The number of input attachments in the IDescriptorSet.

Implements spark::render::IDescriptorSetLayout.

◆ pools()

std::size_t spark::render::vk::VulkanDescriptorSetLayout::pools ( ) const
nodiscardnoexcept

Gets the number of active descriptor pools.

Returns
The number of active descriptor pools.

◆ poolSize()

unsigned spark::render::vk::VulkanDescriptorSetLayout::poolSize ( ) const
nodiscardnoexcept

Gets the size of each descriptor pool.

Returns
The size of one descriptor pool.

Descriptors are allocated from descriptor pools in Vulkan. Each descriptor pool has a number of descriptor sets it can hand out. Before allocating a new descriptor set the layout tries to find an unused descriptor set, that it can hand out. If there are no free descriptor sets, the layout tries to allocate a new one. This is only possible if the descriptor pool is not yet full, in which case a new pool needs to be created. All created pools are cached and destroyed, if the layout itself gets destroyed, causing all descriptor sets allocated from the layout to be invalidated.

In general, if the number of required descriptor sets can be pre-calculated, it should be used as a pool size. Otherwise there is a trade-off to be made, based on the frequency of which new descriptor sets are required. A small pool size is more memory efficient, but can have a significant runtime cost, as long as new allocations happen and no descriptor sets can be reused. A large pool size on the other hand is faster, whilst it may leave a large chunk of descriptor sets unallocated. Keep in mind, that the layout might not be the only active layout, hence a large portion of descriptor sets might end up not being used.

◆ samplers()

unsigned spark::render::vk::VulkanDescriptorSetLayout::samplers ( ) const
nodiscardoverridevirtualnoexcept

Gets the number of texel buffer descriptors in the IDescriptorSet.

Returns
The number of texel buffer descriptors in the IDescriptorSet.

Implements spark::render::IDescriptorSetLayout.

◆ shaderStage()

ShaderStage spark::render::vk::VulkanDescriptorSetLayout::shaderStage ( ) const
nodiscardoverridevirtualnoexcept

Gets the shader stage the IDescriptorSet is used in.

Returns
A ShaderStage representing the shader stage the IDescriptorSet is used in.

Implements spark::render::IDescriptorSetLayout.

◆ space()

unsigned spark::render::vk::VulkanDescriptorSetLayout::space ( ) const
nodiscardoverridevirtualnoexcept

Gets the space index of the IDescriptorSet.

Returns
The space index of the IDescriptorSet.
Note
This maps the space index in HLSL.

Implements spark::render::IDescriptorSetLayout.

◆ staticSamplers()

unsigned spark::render::vk::VulkanDescriptorSetLayout::staticSamplers ( ) const
nodiscardoverridevirtualnoexcept

Gets the number of static/immutable samplers in the IDescriptorSet.

Returns
The number of static/immutable samplers in the IDescriptorSet.

Implements spark::render::IDescriptorSetLayout.

◆ storages()

unsigned spark::render::vk::VulkanDescriptorSetLayout::storages ( ) const
nodiscardoverridevirtualnoexcept

Gets the number of storage buffers in the IDescriptorSet.

Returns
The number of storage buffers in the IDescriptorSet.

Implements spark::render::IDescriptorSetLayout.

◆ uniforms()

unsigned spark::render::vk::VulkanDescriptorSetLayout::uniforms ( ) const
nodiscardoverridevirtualnoexcept

Gets the number of uniform/constant buffers in the IDescriptorSet.

Returns
The number of uniform/constant buffers in the IDescriptorSet.

Implements spark::render::IDescriptorSetLayout.