mirror of
https://github.com/baldurk/renderdoc.git
synced 2026-05-06 01:50:38 +00:00
Prepare for actually serialising pNext pointers in structs
* Any struct with a pNext pointer gets a Deserialise function, to clean
up any dynamically allocated chains.
* The mechanism is as follows:
- On writing, walk the pNext chain (assuming there is one) and skip
any structs we don't care to serialise.
- When we reach a struct we do want to serialise, save a nullable (i.e
optional) VkStructureType* for it, then recurse and serialise the
nullable casted struct.
- If there is no pNext (or none we care about) we serialise a NULL
VkStructureType*
- On reading, we serialise the VkStructureType*. If it's NULL, rename
it to look like a void *pNext = NULL.
- If it's not NULL, use the structure type to serialise a nullable
struct of the right type, and recurse.
* The pNext chain is dynamically allocated, which is why it gets cleaned
up in the Deserialise() function.
This commit is contained in:
@@ -271,6 +271,24 @@ void AppendModifiedChainedStruct(byte *&tempMem, VkStruct *outputStruct,
|
||||
nextChainTail = (VkGenericStruct *)outputStruct;
|
||||
}
|
||||
|
||||
template <typename VkStruct>
|
||||
const VkGenericStruct *FindNextStruct(const VkStruct *haystack, VkStructureType needle)
|
||||
{
|
||||
if(!haystack)
|
||||
return NULL;
|
||||
|
||||
const VkGenericStruct *next = (const VkGenericStruct *)haystack->pNext;
|
||||
while(next)
|
||||
{
|
||||
if(next->sType == needle)
|
||||
return next;
|
||||
|
||||
next = next->pNext;
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
enum class MemoryScope : uint8_t
|
||||
{
|
||||
InitialContents,
|
||||
@@ -602,7 +620,9 @@ DECLARE_REFLECTION_STRUCT(VkBindImageMemoryInfoKHR);
|
||||
|
||||
DECLARE_DESERIALISE_TYPE(VkDeviceCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkBufferCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkBufferViewCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkImageCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkImageViewCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkBindSparseInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkSubmitInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkDescriptorSetAllocateInfo);
|
||||
@@ -610,15 +630,32 @@ DECLARE_DESERIALISE_TYPE(VkFramebufferCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkRenderPassCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkRenderPassBeginInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkCommandBufferBeginInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkCommandPoolCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkCommandBufferAllocateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkPipelineCacheCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkPipelineLayoutCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkShaderModuleCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkGraphicsPipelineCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkComputePipelineCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkDescriptorPoolCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkQueryPoolCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkSemaphoreCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkEventCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkFenceCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkSamplerCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkMemoryAllocateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkMemoryBarrier);
|
||||
DECLARE_DESERIALISE_TYPE(VkBufferMemoryBarrier);
|
||||
DECLARE_DESERIALISE_TYPE(VkImageMemoryBarrier);
|
||||
DECLARE_DESERIALISE_TYPE(VkWriteDescriptorSet);
|
||||
DECLARE_DESERIALISE_TYPE(VkCopyDescriptorSet);
|
||||
DECLARE_DESERIALISE_TYPE(VkDescriptorSetLayoutCreateInfo);
|
||||
DECLARE_DESERIALISE_TYPE(VkDescriptorUpdateTemplateCreateInfoKHR);
|
||||
DECLARE_DESERIALISE_TYPE(VkMappedMemoryRange);
|
||||
DECLARE_DESERIALISE_TYPE(VkSwapchainCreateInfoKHR);
|
||||
DECLARE_DESERIALISE_TYPE(VkDebugMarkerMarkerInfoEXT);
|
||||
DECLARE_DESERIALISE_TYPE(VkBindBufferMemoryInfoKHR);
|
||||
DECLARE_DESERIALISE_TYPE(VkBindImageMemoryInfoKHR);
|
||||
|
||||
DECLARE_REFLECTION_ENUM(VkFlagWithNoBits);
|
||||
DECLARE_REFLECTION_ENUM(VkQueueFlagBits);
|
||||
|
||||
@@ -119,80 +119,156 @@ void DoSerialiseViaResourceId(SerialiserType &ser, type &el)
|
||||
|
||||
SERIALISE_VK_HANDLES();
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkGenericStruct &el)
|
||||
{
|
||||
SERIALISE_MEMBER(sType);
|
||||
SERIALISE_MEMBER_OPT(pNext);
|
||||
|
||||
RDCERR("Unexpected VkGenericStruct being serialised!");
|
||||
|
||||
// here we'd switch on sType to serialise the rest of the members
|
||||
}
|
||||
// pNext structure type dispatch
|
||||
#define HANDLE_PNEXT() \
|
||||
/* we can ignore all external memory extension structs entirely. We don't need to */ \
|
||||
/* serialise or replay it as we won't actually use external memory and will just create */ \
|
||||
/* normal memory to replay with. */ \
|
||||
\
|
||||
/* VK_NV_external_memory / VK_NV_external_memory_win32 */ \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_EXPORT_MEMORY_ALLOCATE_INFO_NV) \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_EXTERNAL_MEMORY_IMAGE_CREATE_INFO_NV) \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_IMPORT_MEMORY_WIN32_HANDLE_INFO_NV) \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_EXPORT_MEMORY_WIN32_HANDLE_INFO_NV) \
|
||||
\
|
||||
/* VK_NV_win32_keyed_mutex */ \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_WIN32_KEYED_MUTEX_ACQUIRE_RELEASE_INFO_NV) \
|
||||
\
|
||||
/* VK_KHR_external_memory / ..._fd / .._win32 */ \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_EXPORT_MEMORY_ALLOCATE_INFO_KHR) \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_EXTERNAL_MEMORY_IMAGE_CREATE_INFO_KHR) \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_EXTERNAL_MEMORY_BUFFER_CREATE_INFO_KHR) \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_IMPORT_MEMORY_WIN32_HANDLE_INFO_KHR) \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_EXPORT_MEMORY_WIN32_HANDLE_INFO_KHR) \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_IMPORT_MEMORY_FD_INFO_KHR) \
|
||||
\
|
||||
/* VK_KHR_external_semaphore / .._fd / ..._win32 */ \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_EXPORT_SEMAPHORE_CREATE_INFO_KHR) \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_EXPORT_SEMAPHORE_WIN32_HANDLE_INFO_KHR) \
|
||||
\
|
||||
/* we don't create real swapchains on replay, so we can ignore surface counters */ \
|
||||
/* VK_EXT_display_control */ \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_SWAPCHAIN_COUNTER_CREATE_INFO_EXT) \
|
||||
\
|
||||
/* for now we don't serialise dedicated memory on replay as it's only a performance */ \
|
||||
/* hint, and is only required in conjunction with shared memory (which we don't */ \
|
||||
/* replay). In future it might be helpful to serialise this for informational purposes. */ \
|
||||
\
|
||||
/* VK_NV_dedicated_allocation */ \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_DEDICATED_ALLOCATION_MEMORY_ALLOCATE_INFO_NV) \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_DEDICATED_ALLOCATION_IMAGE_CREATE_INFO_NV) \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_DEDICATED_ALLOCATION_BUFFER_CREATE_INFO_NV) \
|
||||
\
|
||||
/* VK_KHR_dedicated_allocation */ \
|
||||
PNEXT_IGNORE(VK_STRUCTURE_TYPE_MEMORY_DEDICATED_ALLOCATE_INFO_KHR)
|
||||
|
||||
template <typename SerialiserType>
|
||||
static void SerialiseNext(SerialiserType &ser, VkStructureType &sType, const void *&pNext)
|
||||
{
|
||||
// this is the parent sType, serialised here for convenience
|
||||
ser.Serialise("sType", sType);
|
||||
|
||||
// we just serialise a dummy pointer to preserve it here.
|
||||
VkGenericStruct *dummy = NULL;
|
||||
ser.SerialiseNullable("pNext", dummy);
|
||||
|
||||
if(ser.IsReading())
|
||||
{
|
||||
// default to a NULL pNext
|
||||
pNext = NULL;
|
||||
}
|
||||
else
|
||||
{
|
||||
if(pNext == NULL)
|
||||
return;
|
||||
|
||||
// serialise a nullable next type, to tell us the type of object that's serialised. This is
|
||||
// hidden as it doesn't correspond to the actual pNext, it's just metadata to help us launch the
|
||||
// serialisation.
|
||||
VkStructureType *nextType = NULL;
|
||||
ser.SerialiseNullable("pNext", nextType);
|
||||
|
||||
// most common case - no pNext serialised. Bail immediately
|
||||
if(nextType == NULL)
|
||||
{
|
||||
// fixup the structured data, set the type to void*
|
||||
ser.TypedAs("void *");
|
||||
return;
|
||||
}
|
||||
|
||||
// hide and rename the pNextType if we got something - we'll want the pNext below to be the only
|
||||
// thing user-facing.
|
||||
ser.Named("pNextType").Hidden();
|
||||
|
||||
// any pNext structs that we ignore should not be present on reading - print an error
|
||||
#define PNEXT_IGNORE(StructType) \
|
||||
case StructType: RDCERR("Serialised ignore struct %s", ToStr(*nextType).c_str()); break;
|
||||
|
||||
// if we come across a struct we should process, then serialise a pointer to it.
|
||||
#define PNEXT_STRUCT(StructType, StructName) \
|
||||
case StructType: \
|
||||
{ \
|
||||
StructName *nextStruct = NULL; \
|
||||
ser.SerialiseNullable("pNext", nextStruct); \
|
||||
pNext = nextStruct; \
|
||||
break; \
|
||||
}
|
||||
|
||||
// this serialises the pNext with the right type, as nullable. We already know from above that
|
||||
// there IS something here, so the nullable is redundant but convenient
|
||||
switch(*nextType)
|
||||
{
|
||||
HANDLE_PNEXT();
|
||||
default:
|
||||
{
|
||||
RDCERR("Unexpected/unhandled next structure type %s", ToStr(*nextType).c_str());
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// delete the type itself. Any pNext we serialised is saved in the pNext pointer and will be
|
||||
// deleted in DeserialiseNext()
|
||||
delete nextType;
|
||||
|
||||
// note, we don't have to serialise more of the chain - this is recursive, if there was more of
|
||||
// the pNext chain it would be done recursively above
|
||||
}
|
||||
else // ser.IsWriting()
|
||||
{
|
||||
// any pNext structs that we ignore, just break and keep walking the chain
|
||||
#undef PNEXT_IGNORE
|
||||
#define PNEXT_IGNORE(StructType) \
|
||||
case StructType: break;
|
||||
|
||||
// if we come across a struct we should process, then serialise a pointer to its type (to tell the
|
||||
// reading serialisation what struct is coming up), then a pointer to it.
|
||||
// We don't have to go any further, the act of serialising this struct will walk the chain further,
|
||||
// so we can return immediately.
|
||||
#undef PNEXT_STRUCT
|
||||
#define PNEXT_STRUCT(StructType, StructName) \
|
||||
case StructType: \
|
||||
{ \
|
||||
VkStructureType *nextType = &next->sType; \
|
||||
ser.SerialiseNullable("pNextType", nextType); \
|
||||
StructName *actual = (StructName *)next; \
|
||||
ser.SerialiseNullable("pNext", actual); \
|
||||
return; \
|
||||
}
|
||||
|
||||
// walk the pNext chain, skipping any structs we don't care about serialising.
|
||||
VkGenericStruct *next = (VkGenericStruct *)pNext;
|
||||
|
||||
while(next)
|
||||
{
|
||||
// we can ignore this entirely, we don't need to serialise or replay it as we won't
|
||||
// actually use external memory. Unwrapping, if necessary, happens elsewhere
|
||||
if(next->sType == VK_STRUCTURE_TYPE_EXPORT_MEMORY_ALLOCATE_INFO_NV ||
|
||||
next->sType == VK_STRUCTURE_TYPE_EXTERNAL_MEMORY_IMAGE_CREATE_INFO_NV ||
|
||||
next->sType == VK_STRUCTURE_TYPE_IMPORT_MEMORY_WIN32_HANDLE_INFO_NV ||
|
||||
next->sType == VK_STRUCTURE_TYPE_EXPORT_MEMORY_WIN32_HANDLE_INFO_NV ||
|
||||
next->sType == VK_STRUCTURE_TYPE_WIN32_KEYED_MUTEX_ACQUIRE_RELEASE_INFO_NV ||
|
||||
|
||||
next->sType == VK_STRUCTURE_TYPE_EXPORT_MEMORY_ALLOCATE_INFO_KHR ||
|
||||
next->sType == VK_STRUCTURE_TYPE_EXTERNAL_MEMORY_IMAGE_CREATE_INFO_KHR ||
|
||||
next->sType == VK_STRUCTURE_TYPE_EXTERNAL_MEMORY_BUFFER_CREATE_INFO_KHR ||
|
||||
next->sType == VK_STRUCTURE_TYPE_IMPORT_MEMORY_WIN32_HANDLE_INFO_KHR ||
|
||||
next->sType == VK_STRUCTURE_TYPE_EXPORT_MEMORY_WIN32_HANDLE_INFO_KHR ||
|
||||
next->sType == VK_STRUCTURE_TYPE_IMPORT_MEMORY_FD_INFO_KHR ||
|
||||
next->sType == VK_STRUCTURE_TYPE_EXPORT_SEMAPHORE_CREATE_INFO_KHR ||
|
||||
next->sType == VK_STRUCTURE_TYPE_EXPORT_SEMAPHORE_WIN32_HANDLE_INFO_KHR)
|
||||
switch(next->sType)
|
||||
{
|
||||
// do nothing
|
||||
}
|
||||
// likewise we don't create real swapchains, so we can ignore surface counters
|
||||
else if(next->sType == VK_STRUCTURE_TYPE_SWAPCHAIN_COUNTER_CREATE_INFO_EXT)
|
||||
{
|
||||
// do nothing
|
||||
}
|
||||
// for now we don't serialise dedicated memory on replay as it's only a performance hint,
|
||||
// and is only required in conjunction with shared memory (which we don't replay). In future
|
||||
// it might be helpful to serialise this for informational purposes.
|
||||
else if(next->sType == VK_STRUCTURE_TYPE_DEDICATED_ALLOCATION_MEMORY_ALLOCATE_INFO_NV ||
|
||||
next->sType == VK_STRUCTURE_TYPE_DEDICATED_ALLOCATION_IMAGE_CREATE_INFO_NV ||
|
||||
next->sType == VK_STRUCTURE_TYPE_DEDICATED_ALLOCATION_BUFFER_CREATE_INFO_NV ||
|
||||
next->sType == VK_STRUCTURE_TYPE_MEMORY_DEDICATED_ALLOCATE_INFO_KHR)
|
||||
{
|
||||
// do nothing
|
||||
}
|
||||
else
|
||||
{
|
||||
RDCERR("Unrecognised extension structure type %d", next->sType);
|
||||
HANDLE_PNEXT();
|
||||
default:
|
||||
{
|
||||
RDCERR("Unrecognised extension structure type %s", ToStr(next->sType).c_str());
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// walk to the next item if we didn't serialise the current one
|
||||
next = (VkGenericStruct *)next->pNext;
|
||||
}
|
||||
|
||||
// if we got here, either pNext was NULL (common) or we skipped the whole chain. Serialise a
|
||||
// NULL structure type to indicate that.
|
||||
VkStructureType *dummy = NULL;
|
||||
ser.SerialiseNullable("pNext", dummy);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -204,6 +280,17 @@ static void SerialiseNext(SerialiserType &ser, VkStructureType &sType, void *&pN
|
||||
pNext = (void *)tmpNext;
|
||||
}
|
||||
|
||||
static inline void DeserialiseNext(const void *pNext)
|
||||
{
|
||||
if(pNext == NULL)
|
||||
return;
|
||||
|
||||
// walk the chain, deserialising from the tail back
|
||||
const VkGenericStruct *gen = (const VkGenericStruct *)pNext;
|
||||
DeserialiseNext(gen->pNext);
|
||||
delete gen;
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkAllocationCallbacks &el)
|
||||
{
|
||||
@@ -479,9 +566,12 @@ void DoSerialise(SerialiserType &ser, VkDeviceCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkDeviceCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
for(uint32_t i = 0; i < el.queueCreateInfoCount; i++)
|
||||
{
|
||||
DeserialiseNext(el.pQueueCreateInfos[i].pNext);
|
||||
delete[] el.pQueueCreateInfos[i].pQueuePriorities;
|
||||
}
|
||||
delete[] el.pQueueCreateInfos;
|
||||
delete[] el.ppEnabledExtensionNames;
|
||||
delete[] el.ppEnabledLayerNames;
|
||||
@@ -516,7 +606,7 @@ void DoSerialise(SerialiserType &ser, VkBufferCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkBufferCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
delete[] el.pQueueFamilyIndices;
|
||||
}
|
||||
|
||||
@@ -533,6 +623,12 @@ void DoSerialise(SerialiserType &ser, VkBufferViewCreateInfo &el)
|
||||
SERIALISE_MEMBER(range);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkBufferViewCreateInfo &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkImageCreateInfo &el)
|
||||
{
|
||||
@@ -569,7 +665,7 @@ void DoSerialise(SerialiserType &ser, VkImageCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkImageCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
delete[] el.pQueueFamilyIndices;
|
||||
}
|
||||
|
||||
@@ -595,6 +691,12 @@ void DoSerialise(SerialiserType &ser, VkImageViewCreateInfo &el)
|
||||
SERIALISE_MEMBER(subresourceRange);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkImageViewCreateInfo &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkSparseMemoryBind &el)
|
||||
{
|
||||
@@ -663,7 +765,7 @@ void DoSerialise(SerialiserType &ser, VkBindSparseInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkBindSparseInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
delete[] el.pWaitSemaphores;
|
||||
for(uint32_t i = 0; i < el.bufferBindCount; i++)
|
||||
delete[] el.pBufferBinds[i].pBinds;
|
||||
@@ -706,7 +808,7 @@ void DoSerialise(SerialiserType &ser, VkSubmitInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkSubmitInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
delete[] el.pWaitSemaphores;
|
||||
delete[] el.pCommandBuffers;
|
||||
delete[] el.pSignalSemaphores;
|
||||
@@ -730,7 +832,7 @@ void DoSerialise(SerialiserType &ser, VkFramebufferCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkFramebufferCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
delete[] el.pAttachments;
|
||||
}
|
||||
|
||||
@@ -804,7 +906,7 @@ void DoSerialise(SerialiserType &ser, VkRenderPassCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkRenderPassCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
delete[] el.pAttachments;
|
||||
for(uint32_t i = 0; i < el.subpassCount; i++)
|
||||
{
|
||||
@@ -835,7 +937,7 @@ void DoSerialise(SerialiserType &ser, VkRenderPassBeginInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkRenderPassBeginInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
delete[] el.pClearValues;
|
||||
}
|
||||
|
||||
@@ -1008,6 +1110,12 @@ void DoSerialise(SerialiserType &ser, VkCommandPoolCreateInfo &el)
|
||||
SERIALISE_MEMBER(queueFamilyIndex);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkCommandPoolCreateInfo &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkCommandBufferAllocateInfo &el)
|
||||
{
|
||||
@@ -1019,6 +1127,12 @@ void DoSerialise(SerialiserType &ser, VkCommandBufferAllocateInfo &el)
|
||||
SERIALISE_MEMBER(commandBufferCount);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkCommandBufferAllocateInfo &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkCommandBufferInheritanceInfo &el)
|
||||
{
|
||||
@@ -1046,7 +1160,9 @@ void DoSerialise(SerialiserType &ser, VkCommandBufferBeginInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkCommandBufferBeginInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
if(el.pInheritanceInfo)
|
||||
DeserialiseNext(el.pInheritanceInfo->pNext);
|
||||
delete el.pInheritanceInfo;
|
||||
}
|
||||
|
||||
@@ -1074,6 +1190,12 @@ void DoSerialise(SerialiserType &ser, VkQueryPoolCreateInfo &el)
|
||||
SERIALISE_MEMBER_TYPED(VkQueryPipelineStatisticFlagBits, pipelineStatistics);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkQueryPoolCreateInfo &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkSemaphoreCreateInfo &el)
|
||||
{
|
||||
@@ -1083,6 +1205,12 @@ void DoSerialise(SerialiserType &ser, VkSemaphoreCreateInfo &el)
|
||||
SERIALISE_MEMBER_TYPED(VkFlagWithNoBits, flags);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkSemaphoreCreateInfo &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkEventCreateInfo &el)
|
||||
{
|
||||
@@ -1092,6 +1220,12 @@ void DoSerialise(SerialiserType &ser, VkEventCreateInfo &el)
|
||||
SERIALISE_MEMBER_TYPED(VkFlagWithNoBits, flags);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkEventCreateInfo &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkFenceCreateInfo &el)
|
||||
{
|
||||
@@ -1101,6 +1235,12 @@ void DoSerialise(SerialiserType &ser, VkFenceCreateInfo &el)
|
||||
SERIALISE_MEMBER_TYPED(VkFenceCreateFlagBits, flags);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkFenceCreateInfo &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkSamplerCreateInfo &el)
|
||||
{
|
||||
@@ -1125,6 +1265,12 @@ void DoSerialise(SerialiserType &ser, VkSamplerCreateInfo &el)
|
||||
SERIALISE_MEMBER(unnormalizedCoordinates);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkSamplerCreateInfo &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkPipelineShaderStageCreateInfo &el)
|
||||
{
|
||||
@@ -1193,7 +1339,7 @@ void DoSerialise(SerialiserType &ser, VkPipelineCacheCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkPipelineCacheCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
FreeAlignedBuffer((byte *)el.pInitialData);
|
||||
}
|
||||
|
||||
@@ -1213,7 +1359,7 @@ void DoSerialise(SerialiserType &ser, VkPipelineLayoutCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkPipelineLayoutCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
delete[] el.pSetLayouts;
|
||||
delete[] el.pPushConstantRanges;
|
||||
}
|
||||
@@ -1246,7 +1392,7 @@ void DoSerialise(SerialiserType &ser, VkShaderModuleCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkShaderModuleCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
FreeAlignedBuffer((byte *)el.pCode);
|
||||
}
|
||||
|
||||
@@ -1287,6 +1433,12 @@ void DoSerialise(SerialiserType &ser, VkMemoryAllocateInfo &el)
|
||||
SERIALISE_MEMBER(memoryTypeIndex);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkMemoryAllocateInfo &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkMemoryBarrier &el)
|
||||
{
|
||||
@@ -1297,6 +1449,12 @@ void DoSerialise(SerialiserType &ser, VkMemoryBarrier &el)
|
||||
SERIALISE_MEMBER_TYPED(VkAccessFlagBits, dstAccessMask);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkMemoryBarrier &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkBufferMemoryBarrier &el)
|
||||
{
|
||||
@@ -1318,6 +1476,12 @@ void DoSerialise(SerialiserType &ser, VkBufferMemoryBarrier &el)
|
||||
SERIALISE_MEMBER(size);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkBufferMemoryBarrier &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkImageMemoryBarrier &el)
|
||||
{
|
||||
@@ -1340,6 +1504,12 @@ void DoSerialise(SerialiserType &ser, VkImageMemoryBarrier &el)
|
||||
SERIALISE_MEMBER(subresourceRange);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkImageMemoryBarrier &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkGraphicsPipelineCreateInfo &el)
|
||||
{
|
||||
@@ -1370,27 +1540,27 @@ void DoSerialise(SerialiserType &ser, VkGraphicsPipelineCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkGraphicsPipelineCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
if(el.pVertexInputState)
|
||||
{
|
||||
RDCASSERT(el.pVertexInputState->pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pVertexInputState->pNext);
|
||||
delete[] el.pVertexInputState->pVertexBindingDescriptions;
|
||||
delete[] el.pVertexInputState->pVertexAttributeDescriptions;
|
||||
delete el.pVertexInputState;
|
||||
}
|
||||
if(el.pInputAssemblyState)
|
||||
{
|
||||
RDCASSERT(el.pInputAssemblyState->pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pInputAssemblyState->pNext);
|
||||
delete el.pInputAssemblyState;
|
||||
}
|
||||
if(el.pTessellationState)
|
||||
{
|
||||
RDCASSERT(el.pTessellationState->pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pTessellationState->pNext);
|
||||
delete el.pTessellationState;
|
||||
}
|
||||
if(el.pViewportState)
|
||||
{
|
||||
RDCASSERT(el.pViewportState->pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pViewportState->pNext);
|
||||
if(el.pViewportState->pViewports)
|
||||
delete[] el.pViewportState->pViewports;
|
||||
if(el.pViewportState->pScissors)
|
||||
@@ -1399,36 +1569,36 @@ void Deserialise(const VkGraphicsPipelineCreateInfo &el)
|
||||
}
|
||||
if(el.pRasterizationState)
|
||||
{
|
||||
RDCASSERT(el.pRasterizationState->pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pRasterizationState->pNext);
|
||||
delete el.pRasterizationState;
|
||||
}
|
||||
if(el.pMultisampleState)
|
||||
{
|
||||
RDCASSERT(el.pMultisampleState->pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pMultisampleState->pNext);
|
||||
delete el.pMultisampleState->pSampleMask;
|
||||
delete el.pMultisampleState;
|
||||
}
|
||||
if(el.pDepthStencilState)
|
||||
{
|
||||
RDCASSERT(el.pDepthStencilState->pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pDepthStencilState->pNext);
|
||||
delete el.pDepthStencilState;
|
||||
}
|
||||
if(el.pColorBlendState)
|
||||
{
|
||||
RDCASSERT(el.pColorBlendState->pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pColorBlendState->pNext);
|
||||
delete[] el.pColorBlendState->pAttachments;
|
||||
delete el.pColorBlendState;
|
||||
}
|
||||
if(el.pDynamicState)
|
||||
{
|
||||
RDCASSERT(el.pDynamicState->pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pDynamicState->pNext);
|
||||
if(el.pDynamicState->pDynamicStates)
|
||||
delete[] el.pDynamicState->pDynamicStates;
|
||||
delete el.pDynamicState;
|
||||
}
|
||||
for(uint32_t i = 0; i < el.stageCount; i++)
|
||||
{
|
||||
RDCASSERT(el.pStages[i].pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pStages[i].pNext);
|
||||
if(el.pStages[i].pSpecializationInfo)
|
||||
{
|
||||
FreeAlignedBuffer((byte *)el.pStages[i].pSpecializationInfo->pData);
|
||||
@@ -1455,8 +1625,8 @@ void DoSerialise(SerialiserType &ser, VkComputePipelineCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkComputePipelineCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
RDCASSERT(el.stage.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
DeserialiseNext(el.stage.pNext);
|
||||
if(el.stage.pSpecializationInfo)
|
||||
{
|
||||
FreeAlignedBuffer((byte *)(el.stage.pSpecializationInfo->pData));
|
||||
@@ -1487,7 +1657,7 @@ void DoSerialise(SerialiserType &ser, VkDescriptorPoolCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkDescriptorPoolCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
delete[] el.pPoolSizes;
|
||||
}
|
||||
|
||||
@@ -1505,7 +1675,7 @@ void DoSerialise(SerialiserType &ser, VkDescriptorSetAllocateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkDescriptorSetAllocateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
delete[] el.pSetLayouts;
|
||||
}
|
||||
|
||||
@@ -1627,7 +1797,7 @@ void DoSerialise(SerialiserType &ser, VkWriteDescriptorSet &el)
|
||||
template <>
|
||||
void Deserialise(const VkWriteDescriptorSet &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
if(el.pImageInfo)
|
||||
delete[] el.pImageInfo;
|
||||
if(el.pBufferInfo)
|
||||
@@ -1655,6 +1825,12 @@ void DoSerialise(SerialiserType &ser, VkCopyDescriptorSet &el)
|
||||
SERIALISE_MEMBER(descriptorCount);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkCopyDescriptorSet &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
};
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkPushConstantRange &el)
|
||||
{
|
||||
@@ -1687,7 +1863,7 @@ void DoSerialise(SerialiserType &ser, VkDescriptorSetLayoutCreateInfo &el)
|
||||
template <>
|
||||
void Deserialise(const VkDescriptorSetLayoutCreateInfo &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
for(uint32_t i = 0; i < el.bindingCount; i++)
|
||||
if(el.pBindings[i].pImmutableSamplers)
|
||||
delete[] el.pBindings[i].pImmutableSamplers;
|
||||
@@ -1714,6 +1890,12 @@ void DoSerialise(SerialiserType &ser, VkMappedMemoryRange &el)
|
||||
SERIALISE_MEMBER(size);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkMappedMemoryRange &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkBufferImageCopy &el)
|
||||
{
|
||||
@@ -1880,6 +2062,12 @@ void DoSerialise(SerialiserType &ser, VkSwapchainCreateInfoKHR &el)
|
||||
SERIALISE_MEMBER_EMPTY(oldSwapchain);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkSwapchainCreateInfoKHR &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkDebugMarkerMarkerInfoEXT &el)
|
||||
{
|
||||
@@ -1890,6 +2078,12 @@ void DoSerialise(SerialiserType &ser, VkDebugMarkerMarkerInfoEXT &el)
|
||||
SERIALISE_MEMBER(color);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkDebugMarkerMarkerInfoEXT &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
// this isn't a real vulkan type, it's our own "anything that could be in a descriptor"
|
||||
// structure that
|
||||
template <typename SerialiserType>
|
||||
@@ -1976,7 +2170,7 @@ void DoSerialise(SerialiserType &ser, VkDescriptorUpdateTemplateCreateInfoKHR &e
|
||||
template <>
|
||||
void Deserialise(const VkDescriptorUpdateTemplateCreateInfoKHR &el)
|
||||
{
|
||||
RDCASSERT(el.pNext == NULL); // otherwise delete
|
||||
DeserialiseNext(el.pNext);
|
||||
delete[] el.pDescriptorUpdateEntries;
|
||||
}
|
||||
|
||||
@@ -1991,6 +2185,12 @@ void DoSerialise(SerialiserType &ser, VkBindBufferMemoryInfoKHR &el)
|
||||
SERIALISE_MEMBER(memoryOffset);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkBindBufferMemoryInfoKHR &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
template <typename SerialiserType>
|
||||
void DoSerialise(SerialiserType &ser, VkBindImageMemoryInfoKHR &el)
|
||||
{
|
||||
@@ -2002,6 +2202,12 @@ void DoSerialise(SerialiserType &ser, VkBindImageMemoryInfoKHR &el)
|
||||
SERIALISE_MEMBER(memoryOffset);
|
||||
}
|
||||
|
||||
template <>
|
||||
void Deserialise(const VkBindImageMemoryInfoKHR &el)
|
||||
{
|
||||
DeserialiseNext(el.pNext);
|
||||
}
|
||||
|
||||
INSTANTIATE_SERIALISE_TYPE(VkOffset2D);
|
||||
INSTANTIATE_SERIALISE_TYPE(VkExtent2D);
|
||||
INSTANTIATE_SERIALISE_TYPE(VkMemoryType);
|
||||
|
||||
Reference in New Issue
Block a user