Skip to content

Commit

Permalink
vulkan: Add device feature queries (#88)
Browse files Browse the repository at this point in the history
  • Loading branch information
TheSpydog authored and flibitijibibo committed Aug 23, 2024
1 parent 2dbf25e commit d22efe9
Showing 1 changed file with 87 additions and 35 deletions.
122 changes: 87 additions & 35 deletions src/gpu/vulkan/SDL_gpu_vulkan.c
Original file line number Diff line number Diff line change
Expand Up @@ -302,12 +302,6 @@ static VkPrimitiveTopology SDLToVK_PrimitiveType[] = {
VK_PRIMITIVE_TOPOLOGY_TRIANGLE_STRIP
};

static VkPolygonMode SDLToVK_PolygonMode[] = {
VK_POLYGON_MODE_FILL,
VK_POLYGON_MODE_LINE,
VK_POLYGON_MODE_POINT
};

static VkCullModeFlags SDLToVK_CullMode[] = {
VK_CULL_MODE_NONE,
VK_CULL_MODE_FRONT_BIT,
Expand Down Expand Up @@ -1288,12 +1282,15 @@ struct VulkanRenderer
Uint8 integratedMemoryNotification;
Uint8 outOfDeviceLocalMemoryWarning;
Uint8 outofBARMemoryWarning;
Uint8 fillModeOnlyWarning;

SDL_bool debugMode;
SDL_bool preferLowPower;
VulkanExtensions supports;
SDL_bool supportsDebugUtils;
SDL_bool supportsColorspace;
SDL_bool supportsFillModeNonSolid;
SDL_bool supportsMultiDrawIndirect;

VulkanMemoryAllocator *memoryAllocator;
VkPhysicalDeviceMemoryProperties memoryProperties;
Expand Down Expand Up @@ -1479,6 +1476,25 @@ static inline VkSampleCountFlagBits VULKAN_INTERNAL_GetMaxMultiSampleCount(
return SDL_min(multiSampleCount, maxSupported);
}

static inline VkPolygonMode SDLToVK_PolygonMode(
VulkanRenderer *renderer,
SDL_GpuFillMode mode)
{
if (mode == SDL_GPU_FILLMODE_FILL) {
return VK_POLYGON_MODE_FILL; /* always available! */
}

if (renderer->supportsFillModeNonSolid && mode == SDL_GPU_FILLMODE_LINE) {
return VK_POLYGON_MODE_LINE;
}

if (!renderer->fillModeOnlyWarning) {
SDL_LogInfo(SDL_LOG_CATEGORY_APPLICATION, "Unsupported fill mode requested, using FILL!");
renderer->fillModeOnlyWarning = 1;
}
return VK_POLYGON_MODE_FILL;
}

/* Memory Management */

/* Vulkan: Memory Allocation */
Expand Down Expand Up @@ -5235,15 +5251,29 @@ static void VULKAN_DrawPrimitivesIndirect(
VulkanCommandBuffer *vulkanCommandBuffer = (VulkanCommandBuffer *)commandBuffer;
VulkanRenderer *renderer = (VulkanRenderer *)vulkanCommandBuffer->renderer;
VulkanBuffer *vulkanBuffer = ((VulkanBufferContainer *)buffer)->activeBufferHandle->vulkanBuffer;
Uint32 i;

VULKAN_INTERNAL_BindGraphicsDescriptorSets(renderer, vulkanCommandBuffer);

renderer->vkCmdDrawIndirect(
vulkanCommandBuffer->commandBuffer,
vulkanBuffer->buffer,
offsetInBytes,
drawCount,
stride);
if (renderer->supportsMultiDrawIndirect) {
/* Real multi-draw! */
renderer->vkCmdDrawIndirect(
vulkanCommandBuffer->commandBuffer,
vulkanBuffer->buffer,
offsetInBytes,
drawCount,
stride);
} else {
/* Fake multi-draw... */
for (i = 0; i < drawCount; i += 1) {
renderer->vkCmdDrawIndirect(
vulkanCommandBuffer->commandBuffer,
vulkanBuffer->buffer,
offsetInBytes + (stride * i),
1,
stride);
}
}

VULKAN_INTERNAL_TrackBuffer(vulkanCommandBuffer, vulkanBuffer);
}
Expand All @@ -5258,15 +5288,29 @@ static void VULKAN_DrawIndexedPrimitivesIndirect(
VulkanCommandBuffer *vulkanCommandBuffer = (VulkanCommandBuffer *)commandBuffer;
VulkanRenderer *renderer = (VulkanRenderer *)vulkanCommandBuffer->renderer;
VulkanBuffer *vulkanBuffer = ((VulkanBufferContainer *)buffer)->activeBufferHandle->vulkanBuffer;
Uint32 i;

VULKAN_INTERNAL_BindGraphicsDescriptorSets(renderer, vulkanCommandBuffer);

renderer->vkCmdDrawIndexedIndirect(
vulkanCommandBuffer->commandBuffer,
vulkanBuffer->buffer,
offsetInBytes,
drawCount,
stride);
if (renderer->supportsMultiDrawIndirect) {
/* Real multi-draw! */
renderer->vkCmdDrawIndexedIndirect(
vulkanCommandBuffer->commandBuffer,
vulkanBuffer->buffer,
offsetInBytes,
drawCount,
stride);
} else {
/* Fake multi-draw... */
for (i = 0; i < drawCount; i += 1) {
renderer->vkCmdDrawIndexedIndirect(
vulkanCommandBuffer->commandBuffer,
vulkanBuffer->buffer,
offsetInBytes + (stride * i),
1,
stride);
}
}

VULKAN_INTERNAL_TrackBuffer(vulkanCommandBuffer, vulkanBuffer);
}
Expand Down Expand Up @@ -6326,7 +6370,9 @@ static SDL_GpuGraphicsPipeline *VULKAN_CreateGraphicsPipeline(
rasterizationStateCreateInfo.flags = 0;
rasterizationStateCreateInfo.depthClampEnable = VK_FALSE;
rasterizationStateCreateInfo.rasterizerDiscardEnable = VK_FALSE;
rasterizationStateCreateInfo.polygonMode = SDLToVK_PolygonMode[pipelineCreateInfo->rasterizerState.fillMode];
rasterizationStateCreateInfo.polygonMode = SDLToVK_PolygonMode(
renderer,
pipelineCreateInfo->rasterizerState.fillMode);
rasterizationStateCreateInfo.cullMode = SDLToVK_CullMode[pipelineCreateInfo->rasterizerState.cullMode];
rasterizationStateCreateInfo.frontFace = SDLToVK_FrontFace[pipelineCreateInfo->rasterizerState.frontFace];
rasterizationStateCreateInfo.depthBiasEnable =
Expand Down Expand Up @@ -11233,7 +11279,8 @@ static Uint8 VULKAN_INTERNAL_CreateLogicalDevice(
{
VkResult vulkanResult;
VkDeviceCreateInfo deviceCreateInfo;
VkPhysicalDeviceFeatures deviceFeatures;
VkPhysicalDeviceFeatures desiredDeviceFeatures;
VkPhysicalDeviceFeatures haveDeviceFeatures;
VkPhysicalDevicePortabilitySubsetFeaturesKHR portabilityFeatures;
const char **deviceExtensions;

Expand All @@ -11248,13 +11295,27 @@ static Uint8 VULKAN_INTERNAL_CreateLogicalDevice(
queueCreateInfo.queueCount = 1;
queueCreateInfo.pQueuePriorities = &queuePriority;

/* check feature support */

renderer->vkGetPhysicalDeviceFeatures(
renderer->physicalDevice,
&haveDeviceFeatures);

/* specifying used device features */

SDL_zero(deviceFeatures);
deviceFeatures.fillModeNonSolid = VK_TRUE;
deviceFeatures.samplerAnisotropy = VK_TRUE;
deviceFeatures.multiDrawIndirect = VK_TRUE;
deviceFeatures.independentBlend = VK_TRUE;
SDL_zero(desiredDeviceFeatures);
desiredDeviceFeatures.independentBlend = VK_TRUE;
desiredDeviceFeatures.samplerAnisotropy = VK_TRUE;

if (haveDeviceFeatures.fillModeNonSolid) {
desiredDeviceFeatures.fillModeNonSolid = VK_TRUE;
renderer->supportsFillModeNonSolid = SDL_TRUE;
}

if (haveDeviceFeatures.multiDrawIndirect) {
desiredDeviceFeatures.multiDrawIndirect = VK_TRUE;
renderer->supportsMultiDrawIndirect = SDL_TRUE;
}

/* creating the logical device */

Expand Down Expand Up @@ -11293,7 +11354,7 @@ static Uint8 VULKAN_INTERNAL_CreateLogicalDevice(
deviceCreateInfo.enabledExtensionCount);
CreateDeviceExtensionArray(&renderer->supports, deviceExtensions);
deviceCreateInfo.ppEnabledExtensionNames = deviceExtensions;
deviceCreateInfo.pEnabledFeatures = &deviceFeatures;
deviceCreateInfo.pEnabledFeatures = &desiredDeviceFeatures;

vulkanResult = renderer->vkCreateDevice(
renderer->physicalDevice,
Expand Down Expand Up @@ -11476,9 +11537,6 @@ static SDL_GpuDevice *VULKAN_CreateDevice(SDL_bool debugMode, SDL_bool preferLow
/* Variables: Image Format Detection */
VkImageFormatProperties imageFormatProperties;

/* Variables: Device Feature Checks */
VkPhysicalDeviceFeatures physicalDeviceFeatures;

if (SDL_Vulkan_LoadLibrary(NULL) < 0) {
SDL_assert(!"This should have failed in PrepareDevice first!");
return NULL;
Expand Down Expand Up @@ -11702,12 +11760,6 @@ static SDL_GpuDevice *VULKAN_CreateDevice(SDL_bool debugMode, SDL_bool preferLow
renderer->allocationsToDefrag = SDL_malloc(
renderer->allocationsToDefragCapacity * sizeof(VulkanMemoryAllocation *));

/* Support checks */

renderer->vkGetPhysicalDeviceFeatures(
renderer->physicalDevice,
&physicalDeviceFeatures);

return result;
}

Expand Down

0 comments on commit d22efe9

Please sign in to comment.