|
|
@ -190,6 +190,7 @@ static VkFormat RefreshToVK_SurfaceFormat[] =
|
|
|
|
VK_FORMAT_BC1_RGBA_UNORM_BLOCK, /* BC1 */
|
|
|
|
VK_FORMAT_BC1_RGBA_UNORM_BLOCK, /* BC1 */
|
|
|
|
VK_FORMAT_BC2_UNORM_BLOCK, /* BC3 */
|
|
|
|
VK_FORMAT_BC2_UNORM_BLOCK, /* BC3 */
|
|
|
|
VK_FORMAT_BC3_UNORM_BLOCK, /* BC5 */
|
|
|
|
VK_FORMAT_BC3_UNORM_BLOCK, /* BC5 */
|
|
|
|
|
|
|
|
VK_FORMAT_BC7_UNORM_BLOCK, /* BC7 */
|
|
|
|
VK_FORMAT_R8G8_SNORM, /* R8G8_SNORM */
|
|
|
|
VK_FORMAT_R8G8_SNORM, /* R8G8_SNORM */
|
|
|
|
VK_FORMAT_R8G8B8A8_SNORM, /* R8G8B8A8_SNORM */
|
|
|
|
VK_FORMAT_R8G8B8A8_SNORM, /* R8G8B8A8_SNORM */
|
|
|
|
VK_FORMAT_A2R10G10B10_UNORM_PACK32, /* A2R10G10B10 */
|
|
|
|
VK_FORMAT_A2R10G10B10_UNORM_PACK32, /* A2R10G10B10 */
|
|
|
@ -912,6 +913,7 @@ static inline void DescriptorSetLayoutHashTable_Insert(
|
|
|
|
|
|
|
|
|
|
|
|
typedef struct RenderPassColorTargetDescription
|
|
|
|
typedef struct RenderPassColorTargetDescription
|
|
|
|
{
|
|
|
|
{
|
|
|
|
|
|
|
|
VkFormat format;
|
|
|
|
Refresh_Vec4 clearColor;
|
|
|
|
Refresh_Vec4 clearColor;
|
|
|
|
Refresh_LoadOp loadOp;
|
|
|
|
Refresh_LoadOp loadOp;
|
|
|
|
Refresh_StoreOp storeOp;
|
|
|
|
Refresh_StoreOp storeOp;
|
|
|
@ -919,6 +921,7 @@ typedef struct RenderPassColorTargetDescription
|
|
|
|
|
|
|
|
|
|
|
|
typedef struct RenderPassDepthStencilTargetDescription
|
|
|
|
typedef struct RenderPassDepthStencilTargetDescription
|
|
|
|
{
|
|
|
|
{
|
|
|
|
|
|
|
|
VkFormat format;
|
|
|
|
Refresh_LoadOp loadOp;
|
|
|
|
Refresh_LoadOp loadOp;
|
|
|
|
Refresh_StoreOp storeOp;
|
|
|
|
Refresh_StoreOp storeOp;
|
|
|
|
Refresh_LoadOp stencilLoadOp;
|
|
|
|
Refresh_LoadOp stencilLoadOp;
|
|
|
@ -958,6 +961,11 @@ static inline uint8_t RenderPassHash_Compare(
|
|
|
|
|
|
|
|
|
|
|
|
for (i = 0; i < a->colorAttachmentCount; i += 1)
|
|
|
|
for (i = 0; i < a->colorAttachmentCount; i += 1)
|
|
|
|
{
|
|
|
|
{
|
|
|
|
|
|
|
|
if (a->colorTargetDescriptions[i].format != b->colorTargetDescriptions[i].format)
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
if ( a->colorTargetDescriptions[i].clearColor.x != b->colorTargetDescriptions[i].clearColor.x ||
|
|
|
|
if ( a->colorTargetDescriptions[i].clearColor.x != b->colorTargetDescriptions[i].clearColor.x ||
|
|
|
|
a->colorTargetDescriptions[i].clearColor.y != b->colorTargetDescriptions[i].clearColor.y ||
|
|
|
|
a->colorTargetDescriptions[i].clearColor.y != b->colorTargetDescriptions[i].clearColor.y ||
|
|
|
|
a->colorTargetDescriptions[i].clearColor.z != b->colorTargetDescriptions[i].clearColor.z ||
|
|
|
|
a->colorTargetDescriptions[i].clearColor.z != b->colorTargetDescriptions[i].clearColor.z ||
|
|
|
@ -977,6 +985,11 @@ static inline uint8_t RenderPassHash_Compare(
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (a->depthStencilTargetDescription.format != b->depthStencilTargetDescription.format)
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
if (a->depthStencilTargetDescription.loadOp != b->depthStencilTargetDescription.loadOp)
|
|
|
|
if (a->depthStencilTargetDescription.loadOp != b->depthStencilTargetDescription.loadOp)
|
|
|
|
{
|
|
|
|
{
|
|
|
|
return 0;
|
|
|
|
return 0;
|
|
|
@ -1674,6 +1687,10 @@ typedef struct VulkanRenderer
|
|
|
|
|
|
|
|
|
|
|
|
VkDeviceSize minUBOAlignment;
|
|
|
|
VkDeviceSize minUBOAlignment;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/* Some drivers don't support D16 for some reason. Fun! */
|
|
|
|
|
|
|
|
VkFormat D16Format;
|
|
|
|
|
|
|
|
VkFormat D16S8Format;
|
|
|
|
|
|
|
|
|
|
|
|
VulkanTexture **texturesToDestroy;
|
|
|
|
VulkanTexture **texturesToDestroy;
|
|
|
|
uint32_t texturesToDestroyCount;
|
|
|
|
uint32_t texturesToDestroyCount;
|
|
|
|
uint32_t texturesToDestroyCapacity;
|
|
|
|
uint32_t texturesToDestroyCapacity;
|
|
|
@ -1782,6 +1799,40 @@ static inline void LogVulkanResultAsWarn(
|
|
|
|
|
|
|
|
|
|
|
|
/* Utility */
|
|
|
|
/* Utility */
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
static inline VkFormat RefreshToVK_DepthFormat(
|
|
|
|
|
|
|
|
VulkanRenderer* renderer,
|
|
|
|
|
|
|
|
Refresh_TextureFormat format
|
|
|
|
|
|
|
|
) {
|
|
|
|
|
|
|
|
switch (format)
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
case REFRESH_TEXTUREFORMAT_D16_UNORM:
|
|
|
|
|
|
|
|
return renderer->D16Format;
|
|
|
|
|
|
|
|
case REFRESH_TEXTUREFORMAT_D16_UNORM_S8_UINT:
|
|
|
|
|
|
|
|
return renderer->D16S8Format;
|
|
|
|
|
|
|
|
case REFRESH_TEXTUREFORMAT_D32_SFLOAT:
|
|
|
|
|
|
|
|
return VK_FORMAT_D32_SFLOAT;
|
|
|
|
|
|
|
|
case REFRESH_TEXTUREFORMAT_D32_SFLOAT_S8_UINT:
|
|
|
|
|
|
|
|
return VK_FORMAT_D32_SFLOAT_S8_UINT;
|
|
|
|
|
|
|
|
default:
|
|
|
|
|
|
|
|
return VK_FORMAT_UNDEFINED;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
static inline uint8_t IsRefreshDepthFormat(Refresh_TextureFormat format)
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
switch (format)
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
case REFRESH_TEXTUREFORMAT_D16_UNORM:
|
|
|
|
|
|
|
|
case REFRESH_TEXTUREFORMAT_D32_SFLOAT:
|
|
|
|
|
|
|
|
case REFRESH_TEXTUREFORMAT_D16_UNORM_S8_UINT:
|
|
|
|
|
|
|
|
case REFRESH_TEXTUREFORMAT_D32_SFLOAT_S8_UINT:
|
|
|
|
|
|
|
|
return 1;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
default:
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
static inline uint8_t IsDepthFormat(VkFormat format)
|
|
|
|
static inline uint8_t IsDepthFormat(VkFormat format)
|
|
|
|
{
|
|
|
|
{
|
|
|
|
switch(format)
|
|
|
|
switch(format)
|
|
|
@ -1817,6 +1868,7 @@ static inline uint32_t VULKAN_INTERNAL_BytesPerPixel(VkFormat format)
|
|
|
|
case VK_FORMAT_R32G32B32A32_SFLOAT:
|
|
|
|
case VK_FORMAT_R32G32B32A32_SFLOAT:
|
|
|
|
case VK_FORMAT_BC2_UNORM_BLOCK:
|
|
|
|
case VK_FORMAT_BC2_UNORM_BLOCK:
|
|
|
|
case VK_FORMAT_BC3_UNORM_BLOCK:
|
|
|
|
case VK_FORMAT_BC3_UNORM_BLOCK:
|
|
|
|
|
|
|
|
case VK_FORMAT_BC7_UNORM_BLOCK:
|
|
|
|
return 16;
|
|
|
|
return 16;
|
|
|
|
|
|
|
|
|
|
|
|
case VK_FORMAT_R8G8B8A8_UNORM:
|
|
|
|
case VK_FORMAT_R8G8B8A8_UNORM:
|
|
|
@ -1857,6 +1909,40 @@ static inline uint32_t VULKAN_INTERNAL_BytesPerPixel(VkFormat format)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
static inline uint32_t VULKAN_INTERNAL_GetTextureBlockSize(
|
|
|
|
|
|
|
|
VkFormat format
|
|
|
|
|
|
|
|
) {
|
|
|
|
|
|
|
|
switch (format)
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
case VK_FORMAT_BC1_RGBA_UNORM_BLOCK:
|
|
|
|
|
|
|
|
case VK_FORMAT_BC2_UNORM_BLOCK:
|
|
|
|
|
|
|
|
case VK_FORMAT_BC3_UNORM_BLOCK:
|
|
|
|
|
|
|
|
case VK_FORMAT_BC7_UNORM_BLOCK:
|
|
|
|
|
|
|
|
return 4;
|
|
|
|
|
|
|
|
case VK_FORMAT_R8G8B8A8_UNORM:
|
|
|
|
|
|
|
|
case VK_FORMAT_B8G8R8A8_UNORM:
|
|
|
|
|
|
|
|
case VK_FORMAT_R5G6B5_UNORM_PACK16:
|
|
|
|
|
|
|
|
case VK_FORMAT_A1R5G5B5_UNORM_PACK16:
|
|
|
|
|
|
|
|
case VK_FORMAT_B4G4R4A4_UNORM_PACK16:
|
|
|
|
|
|
|
|
case VK_FORMAT_R8G8_SNORM:
|
|
|
|
|
|
|
|
case VK_FORMAT_R8G8B8A8_SNORM:
|
|
|
|
|
|
|
|
case VK_FORMAT_A2R10G10B10_UNORM_PACK32:
|
|
|
|
|
|
|
|
case VK_FORMAT_R16G16_UNORM:
|
|
|
|
|
|
|
|
case VK_FORMAT_R16G16B16A16_UNORM:
|
|
|
|
|
|
|
|
case VK_FORMAT_R8_UNORM:
|
|
|
|
|
|
|
|
case VK_FORMAT_R32_SFLOAT:
|
|
|
|
|
|
|
|
case VK_FORMAT_R32G32_SFLOAT:
|
|
|
|
|
|
|
|
case VK_FORMAT_R32G32B32A32_SFLOAT:
|
|
|
|
|
|
|
|
case VK_FORMAT_R16_SFLOAT:
|
|
|
|
|
|
|
|
case VK_FORMAT_R16G16_SFLOAT:
|
|
|
|
|
|
|
|
case VK_FORMAT_R16G16B16A16_SFLOAT:
|
|
|
|
|
|
|
|
return 1;
|
|
|
|
|
|
|
|
default:
|
|
|
|
|
|
|
|
Refresh_LogError("Unrecognized texture format!");
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
static inline VkDeviceSize VULKAN_INTERNAL_BytesPerImage(
|
|
|
|
static inline VkDeviceSize VULKAN_INTERNAL_BytesPerImage(
|
|
|
|
uint32_t width,
|
|
|
|
uint32_t width,
|
|
|
|
uint32_t height,
|
|
|
|
uint32_t height,
|
|
|
@ -1864,12 +1950,12 @@ static inline VkDeviceSize VULKAN_INTERNAL_BytesPerImage(
|
|
|
|
) {
|
|
|
|
) {
|
|
|
|
uint32_t blocksPerRow = width;
|
|
|
|
uint32_t blocksPerRow = width;
|
|
|
|
uint32_t blocksPerColumn = height;
|
|
|
|
uint32_t blocksPerColumn = height;
|
|
|
|
|
|
|
|
uint32_t blockSize = VULKAN_INTERNAL_GetTextureBlockSize(format);
|
|
|
|
|
|
|
|
|
|
|
|
if (format == VK_FORMAT_BC1_RGBA_UNORM_BLOCK ||
|
|
|
|
if (blockSize > 1)
|
|
|
|
format == VK_FORMAT_BC3_UNORM_BLOCK ||
|
|
|
|
|
|
|
|
format == VK_FORMAT_BC5_UNORM_BLOCK)
|
|
|
|
|
|
|
|
{
|
|
|
|
{
|
|
|
|
blocksPerRow = (width + 3) / 4;
|
|
|
|
blocksPerRow = (width + blockSize - 1) / blockSize;
|
|
|
|
|
|
|
|
blocksPerColumn = (height + blockSize - 1) / blockSize;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
return blocksPerRow * blocksPerColumn * VULKAN_INTERNAL_BytesPerPixel(format);
|
|
|
|
return blocksPerRow * blocksPerColumn * VULKAN_INTERNAL_BytesPerPixel(format);
|
|
|
@ -5614,9 +5700,10 @@ static VkRenderPass VULKAN_INTERNAL_CreateTransientRenderPass(
|
|
|
|
if (attachmentInfo.hasDepthStencilAttachment)
|
|
|
|
if (attachmentInfo.hasDepthStencilAttachment)
|
|
|
|
{
|
|
|
|
{
|
|
|
|
attachmentDescriptions[attachmentDescriptionCount].flags = 0;
|
|
|
|
attachmentDescriptions[attachmentDescriptionCount].flags = 0;
|
|
|
|
attachmentDescriptions[attachmentDescriptionCount].format = RefreshToVK_SurfaceFormat[
|
|
|
|
attachmentDescriptions[attachmentDescriptionCount].format = RefreshToVK_DepthFormat(
|
|
|
|
|
|
|
|
renderer,
|
|
|
|
attachmentInfo.depthStencilFormat
|
|
|
|
attachmentInfo.depthStencilFormat
|
|
|
|
];
|
|
|
|
);
|
|
|
|
attachmentDescriptions[attachmentDescriptionCount].samples =
|
|
|
|
attachmentDescriptions[attachmentDescriptionCount].samples =
|
|
|
|
VK_SAMPLE_COUNT_1_BIT; /* FIXME: do these take multisamples? */
|
|
|
|
VK_SAMPLE_COUNT_1_BIT; /* FIXME: do these take multisamples? */
|
|
|
|
attachmentDescriptions[attachmentDescriptionCount].loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
|
|
|
|
attachmentDescriptions[attachmentDescriptionCount].loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
|
|
|
@ -6313,7 +6400,16 @@ static Refresh_Texture* VULKAN_CreateTexture(
|
|
|
|
VK_IMAGE_USAGE_TRANSFER_SRC_BIT
|
|
|
|
VK_IMAGE_USAGE_TRANSFER_SRC_BIT
|
|
|
|
);
|
|
|
|
);
|
|
|
|
VkImageAspectFlags imageAspectFlags;
|
|
|
|
VkImageAspectFlags imageAspectFlags;
|
|
|
|
VkFormat format = RefreshToVK_SurfaceFormat[textureCreateInfo->format];
|
|
|
|
VkFormat format;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (IsRefreshDepthFormat(textureCreateInfo->format))
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
format = RefreshToVK_DepthFormat(renderer, textureCreateInfo->format);
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
else
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
format = RefreshToVK_SurfaceFormat[textureCreateInfo->format];
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
if (textureCreateInfo->usageFlags & REFRESH_TEXTUREUSAGE_SAMPLER_BIT)
|
|
|
|
if (textureCreateInfo->usageFlags & REFRESH_TEXTUREUSAGE_SAMPLER_BIT)
|
|
|
|
{
|
|
|
|
{
|
|
|
@ -6507,6 +6603,9 @@ static void VULKAN_SetTextureData(
|
|
|
|
VulkanTransferBuffer *transferBuffer;
|
|
|
|
VulkanTransferBuffer *transferBuffer;
|
|
|
|
VkBufferImageCopy imageCopy;
|
|
|
|
VkBufferImageCopy imageCopy;
|
|
|
|
uint8_t *stagingBufferPointer;
|
|
|
|
uint8_t *stagingBufferPointer;
|
|
|
|
|
|
|
|
uint32_t blockSize = VULKAN_INTERNAL_GetTextureBlockSize(vulkanTexture->format);
|
|
|
|
|
|
|
|
uint32_t bufferRowLength;
|
|
|
|
|
|
|
|
uint32_t bufferImageHeight;
|
|
|
|
|
|
|
|
|
|
|
|
if (vulkanCommandBuffer->renderPassInProgress)
|
|
|
|
if (vulkanCommandBuffer->renderPassInProgress)
|
|
|
|
{
|
|
|
|
{
|
|
|
@ -6555,6 +6654,9 @@ static void VULKAN_SetTextureData(
|
|
|
|
&vulkanTexture->resourceAccessType
|
|
|
|
&vulkanTexture->resourceAccessType
|
|
|
|
);
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
bufferRowLength = SDL_max(blockSize, textureSlice->rectangle.w);
|
|
|
|
|
|
|
|
bufferImageHeight = SDL_max(blockSize, textureSlice->rectangle.h);
|
|
|
|
|
|
|
|
|
|
|
|
imageCopy.imageExtent.width = textureSlice->rectangle.w;
|
|
|
|
imageCopy.imageExtent.width = textureSlice->rectangle.w;
|
|
|
|
imageCopy.imageExtent.height = textureSlice->rectangle.h;
|
|
|
|
imageCopy.imageExtent.height = textureSlice->rectangle.h;
|
|
|
|
imageCopy.imageExtent.depth = 1;
|
|
|
|
imageCopy.imageExtent.depth = 1;
|
|
|
@ -6566,8 +6668,8 @@ static void VULKAN_SetTextureData(
|
|
|
|
imageCopy.imageSubresource.layerCount = 1;
|
|
|
|
imageCopy.imageSubresource.layerCount = 1;
|
|
|
|
imageCopy.imageSubresource.mipLevel = textureSlice->level;
|
|
|
|
imageCopy.imageSubresource.mipLevel = textureSlice->level;
|
|
|
|
imageCopy.bufferOffset = transferBuffer->offset;
|
|
|
|
imageCopy.bufferOffset = transferBuffer->offset;
|
|
|
|
imageCopy.bufferRowLength = 0;
|
|
|
|
imageCopy.bufferRowLength = bufferRowLength;
|
|
|
|
imageCopy.bufferImageHeight = 0;
|
|
|
|
imageCopy.bufferImageHeight = bufferImageHeight;
|
|
|
|
|
|
|
|
|
|
|
|
renderer->vkCmdCopyBufferToImage(
|
|
|
|
renderer->vkCmdCopyBufferToImage(
|
|
|
|
vulkanCommandBuffer->commandBuffer,
|
|
|
|
vulkanCommandBuffer->commandBuffer,
|
|
|
@ -6692,6 +6794,24 @@ static void VULKAN_SetTextureDataYUV(
|
|
|
|
&imageCopy
|
|
|
|
&imageCopy
|
|
|
|
);
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (tex->usageFlags & VK_IMAGE_USAGE_SAMPLED_BIT)
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
/* TODO: is it worth it to only transition the specific subresource? */
|
|
|
|
|
|
|
|
VULKAN_INTERNAL_ImageMemoryBarrier(
|
|
|
|
|
|
|
|
renderer,
|
|
|
|
|
|
|
|
vulkanCommandBuffer->commandBuffer,
|
|
|
|
|
|
|
|
RESOURCE_ACCESS_ANY_SHADER_READ_SAMPLED_IMAGE,
|
|
|
|
|
|
|
|
VK_IMAGE_ASPECT_COLOR_BIT,
|
|
|
|
|
|
|
|
0,
|
|
|
|
|
|
|
|
tex->layerCount,
|
|
|
|
|
|
|
|
0,
|
|
|
|
|
|
|
|
tex->levelCount,
|
|
|
|
|
|
|
|
0,
|
|
|
|
|
|
|
|
tex->image,
|
|
|
|
|
|
|
|
&tex->resourceAccessType
|
|
|
|
|
|
|
|
);
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
VULKAN_INTERNAL_TrackTexture(renderer, vulkanCommandBuffer, tex);
|
|
|
|
VULKAN_INTERNAL_TrackTexture(renderer, vulkanCommandBuffer, tex);
|
|
|
|
|
|
|
|
|
|
|
|
/* These apply to both U and V */
|
|
|
|
/* These apply to both U and V */
|
|
|
@ -6736,6 +6856,24 @@ static void VULKAN_SetTextureDataYUV(
|
|
|
|
&imageCopy
|
|
|
|
&imageCopy
|
|
|
|
);
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (tex->usageFlags & VK_IMAGE_USAGE_SAMPLED_BIT)
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
/* TODO: is it worth it to only transition the specific subresource? */
|
|
|
|
|
|
|
|
VULKAN_INTERNAL_ImageMemoryBarrier(
|
|
|
|
|
|
|
|
renderer,
|
|
|
|
|
|
|
|
vulkanCommandBuffer->commandBuffer,
|
|
|
|
|
|
|
|
RESOURCE_ACCESS_ANY_SHADER_READ_SAMPLED_IMAGE,
|
|
|
|
|
|
|
|
VK_IMAGE_ASPECT_COLOR_BIT,
|
|
|
|
|
|
|
|
0,
|
|
|
|
|
|
|
|
tex->layerCount,
|
|
|
|
|
|
|
|
0,
|
|
|
|
|
|
|
|
tex->levelCount,
|
|
|
|
|
|
|
|
0,
|
|
|
|
|
|
|
|
tex->image,
|
|
|
|
|
|
|
|
&tex->resourceAccessType
|
|
|
|
|
|
|
|
);
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
VULKAN_INTERNAL_TrackTexture(renderer, vulkanCommandBuffer, tex);
|
|
|
|
VULKAN_INTERNAL_TrackTexture(renderer, vulkanCommandBuffer, tex);
|
|
|
|
|
|
|
|
|
|
|
|
/* V */
|
|
|
|
/* V */
|
|
|
@ -6775,11 +6913,9 @@ static void VULKAN_SetTextureDataYUV(
|
|
|
|
|
|
|
|
|
|
|
|
transferBuffer->offset += yDataLength + uvDataLength;
|
|
|
|
transferBuffer->offset += yDataLength + uvDataLength;
|
|
|
|
|
|
|
|
|
|
|
|
VULKAN_INTERNAL_TrackTexture(renderer, vulkanCommandBuffer, tex);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/* FIXME: don't we have to do this for every image? */
|
|
|
|
|
|
|
|
if (tex->usageFlags & VK_IMAGE_USAGE_SAMPLED_BIT)
|
|
|
|
if (tex->usageFlags & VK_IMAGE_USAGE_SAMPLED_BIT)
|
|
|
|
{
|
|
|
|
{
|
|
|
|
|
|
|
|
/* TODO: is it worth it to only transition the specific subresource? */
|
|
|
|
VULKAN_INTERNAL_ImageMemoryBarrier(
|
|
|
|
VULKAN_INTERNAL_ImageMemoryBarrier(
|
|
|
|
renderer,
|
|
|
|
renderer,
|
|
|
|
vulkanCommandBuffer->commandBuffer,
|
|
|
|
vulkanCommandBuffer->commandBuffer,
|
|
|
@ -6794,6 +6930,8 @@ static void VULKAN_SetTextureDataYUV(
|
|
|
|
&tex->resourceAccessType
|
|
|
|
&tex->resourceAccessType
|
|
|
|
);
|
|
|
|
);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
VULKAN_INTERNAL_TrackTexture(renderer, vulkanCommandBuffer, tex);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
static void VULKAN_INTERNAL_BlitImage(
|
|
|
|
static void VULKAN_INTERNAL_BlitImage(
|
|
|
@ -6858,8 +6996,8 @@ static void VULKAN_INTERNAL_BlitImage(
|
|
|
|
blit.dstOffsets[1].y = destinationTextureSlice->rectangle.y + destinationTextureSlice->rectangle.h;
|
|
|
|
blit.dstOffsets[1].y = destinationTextureSlice->rectangle.y + destinationTextureSlice->rectangle.h;
|
|
|
|
blit.dstOffsets[1].z = 1;
|
|
|
|
blit.dstOffsets[1].z = 1;
|
|
|
|
|
|
|
|
|
|
|
|
blit.dstSubresource.mipLevel = sourceTextureSlice->level;
|
|
|
|
blit.dstSubresource.mipLevel = destinationTextureSlice->level;
|
|
|
|
blit.dstSubresource.baseArrayLayer = sourceTextureSlice->layer;
|
|
|
|
blit.dstSubresource.baseArrayLayer = destinationTextureSlice->layer;
|
|
|
|
blit.dstSubresource.layerCount = 1;
|
|
|
|
blit.dstSubresource.layerCount = 1;
|
|
|
|
blit.dstSubresource.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT;
|
|
|
|
blit.dstSubresource.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT;
|
|
|
|
|
|
|
|
|
|
|
@ -7656,6 +7794,7 @@ static VkRenderPass VULKAN_INTERNAL_FetchRenderPass(
|
|
|
|
|
|
|
|
|
|
|
|
for (i = 0; i < colorAttachmentCount; i += 1)
|
|
|
|
for (i = 0; i < colorAttachmentCount; i += 1)
|
|
|
|
{
|
|
|
|
{
|
|
|
|
|
|
|
|
hash.colorTargetDescriptions[i].format = ((VulkanTexture*) colorAttachmentInfos[i].texture)->format;
|
|
|
|
hash.colorTargetDescriptions[i].clearColor = colorAttachmentInfos[i].clearColor;
|
|
|
|
hash.colorTargetDescriptions[i].clearColor = colorAttachmentInfos[i].clearColor;
|
|
|
|
hash.colorTargetDescriptions[i].loadOp = colorAttachmentInfos[i].loadOp;
|
|
|
|
hash.colorTargetDescriptions[i].loadOp = colorAttachmentInfos[i].loadOp;
|
|
|
|
hash.colorTargetDescriptions[i].storeOp = colorAttachmentInfos[i].storeOp;
|
|
|
|
hash.colorTargetDescriptions[i].storeOp = colorAttachmentInfos[i].storeOp;
|
|
|
@ -7665,6 +7804,7 @@ static VkRenderPass VULKAN_INTERNAL_FetchRenderPass(
|
|
|
|
|
|
|
|
|
|
|
|
if (depthStencilAttachmentInfo == NULL)
|
|
|
|
if (depthStencilAttachmentInfo == NULL)
|
|
|
|
{
|
|
|
|
{
|
|
|
|
|
|
|
|
hash.depthStencilTargetDescription.format = 0;
|
|
|
|
hash.depthStencilTargetDescription.loadOp = REFRESH_LOADOP_DONT_CARE;
|
|
|
|
hash.depthStencilTargetDescription.loadOp = REFRESH_LOADOP_DONT_CARE;
|
|
|
|
hash.depthStencilTargetDescription.storeOp = REFRESH_STOREOP_DONT_CARE;
|
|
|
|
hash.depthStencilTargetDescription.storeOp = REFRESH_STOREOP_DONT_CARE;
|
|
|
|
hash.depthStencilTargetDescription.stencilLoadOp = REFRESH_LOADOP_DONT_CARE;
|
|
|
|
hash.depthStencilTargetDescription.stencilLoadOp = REFRESH_LOADOP_DONT_CARE;
|
|
|
@ -7672,6 +7812,7 @@ static VkRenderPass VULKAN_INTERNAL_FetchRenderPass(
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
else
|
|
|
|
{
|
|
|
|
{
|
|
|
|
|
|
|
|
hash.depthStencilTargetDescription.format = ((VulkanTexture*) depthStencilAttachmentInfo->texture)->format;
|
|
|
|
hash.depthStencilTargetDescription.loadOp = depthStencilAttachmentInfo->loadOp;
|
|
|
|
hash.depthStencilTargetDescription.loadOp = depthStencilAttachmentInfo->loadOp;
|
|
|
|
hash.depthStencilTargetDescription.storeOp = depthStencilAttachmentInfo->storeOp;
|
|
|
|
hash.depthStencilTargetDescription.storeOp = depthStencilAttachmentInfo->storeOp;
|
|
|
|
hash.depthStencilTargetDescription.stencilLoadOp = depthStencilAttachmentInfo->stencilLoadOp;
|
|
|
|
hash.depthStencilTargetDescription.stencilLoadOp = depthStencilAttachmentInfo->stencilLoadOp;
|
|
|
@ -8000,6 +8141,8 @@ static void VULKAN_BeginRenderPass(
|
|
|
|
|
|
|
|
|
|
|
|
if (depthStencilAttachmentInfo != NULL)
|
|
|
|
if (depthStencilAttachmentInfo != NULL)
|
|
|
|
{
|
|
|
|
{
|
|
|
|
|
|
|
|
texture = (VulkanTexture*) depthStencilAttachmentInfo->texture;
|
|
|
|
|
|
|
|
|
|
|
|
if (texture->dimensions.width < framebufferWidth)
|
|
|
|
if (texture->dimensions.width < framebufferWidth)
|
|
|
|
{
|
|
|
|
{
|
|
|
|
framebufferWidth = texture->dimensions.width;
|
|
|
|
framebufferWidth = texture->dimensions.width;
|
|
|
@ -9363,9 +9506,9 @@ static void VULKAN_Submit(
|
|
|
|
|
|
|
|
|
|
|
|
/* Mark command buffers as submitted */
|
|
|
|
/* Mark command buffers as submitted */
|
|
|
|
|
|
|
|
|
|
|
|
if (renderer->submittedCommandBufferCount + commandBufferCount >= renderer->submittedCommandBufferCapacity)
|
|
|
|
if (renderer->submittedCommandBufferCount + 1 >= renderer->submittedCommandBufferCapacity)
|
|
|
|
{
|
|
|
|
{
|
|
|
|
renderer->submittedCommandBufferCapacity = renderer->submittedCommandBufferCount + commandBufferCount;
|
|
|
|
renderer->submittedCommandBufferCapacity = renderer->submittedCommandBufferCount + 1;
|
|
|
|
|
|
|
|
|
|
|
|
renderer->submittedCommandBuffers = SDL_realloc(
|
|
|
|
renderer->submittedCommandBuffers = SDL_realloc(
|
|
|
|
renderer->submittedCommandBuffers,
|
|
|
|
renderer->submittedCommandBuffers,
|
|
|
@ -9373,12 +9516,9 @@ static void VULKAN_Submit(
|
|
|
|
);
|
|
|
|
);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
for (i = 0; i < commandBufferCount; i += 1)
|
|
|
|
((VulkanCommandBuffer*)pCommandBuffers[i])->submitted = 1;
|
|
|
|
{
|
|
|
|
renderer->submittedCommandBuffers[renderer->submittedCommandBufferCount] = (VulkanCommandBuffer*) pCommandBuffers[i];
|
|
|
|
((VulkanCommandBuffer*)pCommandBuffers[i])->submitted = 1;
|
|
|
|
renderer->submittedCommandBufferCount += 1;
|
|
|
|
renderer->submittedCommandBuffers[renderer->submittedCommandBufferCount] = (VulkanCommandBuffer*) pCommandBuffers[i];
|
|
|
|
|
|
|
|
renderer->submittedCommandBufferCount += 1;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/* Present, if applicable */
|
|
|
|
/* Present, if applicable */
|
|
|
|
|
|
|
|
|
|
|
@ -10132,6 +10272,9 @@ static Refresh_Device* VULKAN_CreateDevice(
|
|
|
|
VkDescriptorPoolSize poolSizes[4];
|
|
|
|
VkDescriptorPoolSize poolSizes[4];
|
|
|
|
VkDescriptorSetAllocateInfo descriptorAllocateInfo;
|
|
|
|
VkDescriptorSetAllocateInfo descriptorAllocateInfo;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/* Variables: Image Format Detection */
|
|
|
|
|
|
|
|
VkImageFormatProperties imageFormatProperties;
|
|
|
|
|
|
|
|
|
|
|
|
VULKAN_INTERNAL_LoadEntryPoints(renderer);
|
|
|
|
VULKAN_INTERNAL_LoadEntryPoints(renderer);
|
|
|
|
|
|
|
|
|
|
|
|
renderer->presentMode = presentationParameters->presentMode;
|
|
|
|
renderer->presentMode = presentationParameters->presentMode;
|
|
|
@ -10571,12 +10714,53 @@ static Refresh_Device* VULKAN_CreateDevice(
|
|
|
|
renderer->renderTargetHashArray.capacity = 0;
|
|
|
|
renderer->renderTargetHashArray.capacity = 0;
|
|
|
|
|
|
|
|
|
|
|
|
/* Initialize transfer buffer pool */
|
|
|
|
/* Initialize transfer buffer pool */
|
|
|
|
|
|
|
|
|
|
|
|
renderer->transferBufferPool.lock = SDL_CreateMutex();
|
|
|
|
renderer->transferBufferPool.lock = SDL_CreateMutex();
|
|
|
|
|
|
|
|
|
|
|
|
renderer->transferBufferPool.availableBufferCapacity = 4;
|
|
|
|
renderer->transferBufferPool.availableBufferCapacity = 4;
|
|
|
|
renderer->transferBufferPool.availableBufferCount = 0;
|
|
|
|
renderer->transferBufferPool.availableBufferCount = 0;
|
|
|
|
renderer->transferBufferPool.availableBuffers = SDL_malloc(renderer->transferBufferPool.availableBufferCapacity * sizeof(VulkanTransferBuffer*));
|
|
|
|
renderer->transferBufferPool.availableBuffers = SDL_malloc(renderer->transferBufferPool.availableBufferCapacity * sizeof(VulkanTransferBuffer*));
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/* Some drivers don't support D16, so we have to fall back to D32. */
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
vulkanResult = renderer->vkGetPhysicalDeviceImageFormatProperties(
|
|
|
|
|
|
|
|
renderer->physicalDevice,
|
|
|
|
|
|
|
|
VK_FORMAT_D16_UNORM,
|
|
|
|
|
|
|
|
VK_IMAGE_TYPE_2D,
|
|
|
|
|
|
|
|
VK_IMAGE_TILING_OPTIMAL,
|
|
|
|
|
|
|
|
VK_IMAGE_ASPECT_DEPTH_BIT,
|
|
|
|
|
|
|
|
0,
|
|
|
|
|
|
|
|
&imageFormatProperties
|
|
|
|
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (vulkanResult == VK_ERROR_FORMAT_NOT_SUPPORTED)
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
renderer->D16Format = VK_FORMAT_D32_SFLOAT;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
else
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
renderer->D16Format = VK_FORMAT_D16_UNORM;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
vulkanResult = renderer->vkGetPhysicalDeviceImageFormatProperties(
|
|
|
|
|
|
|
|
renderer->physicalDevice,
|
|
|
|
|
|
|
|
VK_FORMAT_D16_UNORM_S8_UINT,
|
|
|
|
|
|
|
|
VK_IMAGE_TYPE_2D,
|
|
|
|
|
|
|
|
VK_IMAGE_TILING_OPTIMAL,
|
|
|
|
|
|
|
|
VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT,
|
|
|
|
|
|
|
|
0,
|
|
|
|
|
|
|
|
&imageFormatProperties
|
|
|
|
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (vulkanResult == VK_ERROR_FORMAT_NOT_SUPPORTED)
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
renderer->D16S8Format = VK_FORMAT_D32_SFLOAT_S8_UINT;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
else
|
|
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
renderer->D16S8Format = VK_FORMAT_D16_UNORM_S8_UINT;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/* Deferred destroy storage */
|
|
|
|
/* Deferred destroy storage */
|
|
|
|
|
|
|
|
|
|
|
|
renderer->texturesToDestroyCapacity = 16;
|
|
|
|
renderer->texturesToDestroyCapacity = 16;
|
|
|
|