26 uint32_t availableExtCount = 0;
27 qboolean vk_khr_swapchain_extension_available =
false;
28 VK_VERIFY(vkEnumerateDeviceExtensionProperties(*physicalDevice,
NULL, &availableExtCount,
NULL));
30 if (availableExtCount > 0)
32 VkExtensionProperties *extensions = (VkExtensionProperties *)malloc(availableExtCount *
sizeof(VkExtensionProperties));
33 VK_VERIFY(vkEnumerateDeviceExtensionProperties(*physicalDevice,
NULL, &availableExtCount, extensions));
35 for (uint32_t
i = 0;
i < availableExtCount; ++
i)
37 vk_khr_swapchain_extension_available |= strcmp(extensions[
i].extensionName, VK_KHR_SWAPCHAIN_EXTENSION_NAME) == 0;
44 return vk_khr_swapchain_extension_available;
50 VkPhysicalDeviceProperties deviceProperties;
51 VkPhysicalDeviceFeatures deviceFeatures;
52 uint32_t queueFamilyCount = 0;
56 vkGetPhysicalDeviceProperties(devices[
i], &deviceProperties);
57 vkGetPhysicalDeviceFeatures(devices[
i], &deviceFeatures);
58 vkGetPhysicalDeviceQueueFamilyProperties(devices[
i], &queueFamilyCount,
NULL);
60 if (queueFamilyCount == 0)
65 qboolean bestProperties = deviceProperties.deviceType == VK_PHYSICAL_DEVICE_TYPE_DISCRETE_GPU;
66 if (preferredIdx ==
i || (bestProperties && preferredIdx < 0) ||
count == 1)
68 uint32_t formatCount = 0;
69 uint32_t presentModesCount = 0;
75 if (!extSupported || !deviceFeatures.samplerAnisotropy || !deviceFeatures.fillModeNonSolid)
82 if (formatCount == 0 || presentModesCount == 0)
85 VkQueueFamilyProperties *queueFamilies = (VkQueueFamilyProperties *)malloc(queueFamilyCount *
sizeof(VkQueueFamilyProperties));
86 vkGetPhysicalDeviceQueueFamilyProperties(devices[
i], &queueFamilyCount, queueFamilies);
89 for (uint32_t
j = 0;
j < queueFamilyCount; ++
j)
92 VkBool32 presentSupported;
101 if (
vk_device.
gfxFamilyIndex < 0 && queueFamilies[
j].queueCount > 0 && (queueFamilies[
j].queueFlags & VK_QUEUE_GRAPHICS_BIT))
106 if (
vk_device.
transferFamilyIndex < 0 && queueFamilies[
j].queueCount > 0 && !(queueFamilies[
j].queueFlags & VK_QUEUE_GRAPHICS_BIT) && (queueFamilies[
j].queueFlags & VK_QUEUE_TRANSFER_BIT))
134 uint32_t physicalDeviceCount = 0;
137 if (physicalDeviceCount == 0)
145 VkPhysicalDevice *physicalDevices = (VkPhysicalDevice *)malloc(physicalDeviceCount *
sizeof(VkPhysicalDevice));
148 getBestPhysicalDevice(physicalDevices, preferredDeviceIdx < physicalDeviceCount ? preferredDeviceIdx : -1, physicalDeviceCount);
149 free(physicalDevices);
164 uint32_t numQueues = 1;
165 float queuePriority = 1.f;
166 VkDeviceQueueCreateInfo queueCreateInfo[3];
167 queueCreateInfo[0].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO;
168 queueCreateInfo[0].pNext =
NULL;
169 queueCreateInfo[0].flags = 0;
171 queueCreateInfo[0].queueCount = 1;
172 queueCreateInfo[0].pQueuePriorities = &queuePriority;
173 queueCreateInfo[1].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO;
174 queueCreateInfo[1].pNext =
NULL;
175 queueCreateInfo[1].flags = 0;
176 queueCreateInfo[1].queueFamilyIndex = 0;
177 queueCreateInfo[1].queueCount = 1;
178 queueCreateInfo[1].pQueuePriorities = &queuePriority;
179 queueCreateInfo[2].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO;
180 queueCreateInfo[2].pNext =
NULL;
181 queueCreateInfo[2].flags = 0;
182 queueCreateInfo[2].queueFamilyIndex = 0;
183 queueCreateInfo[2].queueCount = 1;
184 queueCreateInfo[2].pQueuePriorities = &queuePriority;
186 VkPhysicalDeviceFeatures wantedDeviceFeatures = {
204 const char *deviceExtensions[] = { VK_KHR_SWAPCHAIN_EXTENSION_NAME };
206 VkDeviceCreateInfo deviceCreateInfo = {
207 .sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO,
208 .pEnabledFeatures = &wantedDeviceFeatures,
209 .ppEnabledExtensionNames = deviceExtensions,
210 .enabledExtensionCount = 1,
211 .enabledLayerCount = 0,
212 .ppEnabledLayerNames =
NULL,
213 .queueCreateInfoCount = numQueues,
214 .pQueueCreateInfos = queueCreateInfo
217 #if VK_HEADER_VERSION > 101
218 const char *validationLayers[] = {
"VK_LAYER_KHRONOS_validation" };
220 const char *validationLayers[] = {
"VK_LAYER_LUNARG_standard_validation" };
225 deviceCreateInfo.enabledLayerCount =
sizeof(validationLayers)/
sizeof(validationLayers[0]);
226 deviceCreateInfo.ppEnabledLayerNames = validationLayers;
235 #define DEVTYPESTR(r) case VK_ ##r: return "VK_"#r
239 DEVTYPESTR(PHYSICAL_DEVICE_TYPE_INTEGRATED_GPU);
240 DEVTYPESTR(PHYSICAL_DEVICE_TYPE_DISCRETE_GPU);
243 default:
return "<unknown>";
246 return "UNKNOWN DEVICE";
254 case 0x1002:
return "AMD";
255 case 0x1010:
return "ImgTec";
256 case 0x10DE:
return "NVIDIA";
257 case 0x13B5:
return "ARM";
258 case 0x5143:
return "Qualcomm";
259 case 0x8086:
return "Intel";
260 default:
return "unknown";
273 if (res != VK_SUCCESS)
287 #if defined(_DEBUG) || defined(ENABLE_DEBUG_LABELS)
291 VkDebugUtilsObjectNameInfoEXT oNameInf = {
292 .sType = VK_STRUCTURE_TYPE_DEBUG_UTILS_OBJECT_NAME_INFO_EXT,
294 .objectType = objType,
296 .pObjectName = objName
302 void QVk_DebugSetObjectTag(uint64_t obj, VkObjectType objType, uint64_t tagName,
size_t tagSize,
const void *tagData)
304 VkDebugUtilsObjectTagInfoEXT oTagInf = {
305 .sType = VK_STRUCTURE_TYPE_DEBUG_UTILS_OBJECT_TAG_INFO_EXT,
307 .objectType = objType,
317 void QVk_DebugLabelBegin(
const VkCommandBuffer *cmdBuffer,
const char *labelName,
const float r,
const float g,
const float b)
319 VkDebugUtilsLabelEXT labelInfo = {
320 .sType = VK_STRUCTURE_TYPE_DEBUG_UTILS_LABEL_EXT,
322 .pLabelName = labelName,
323 .color = {
r, g, b, 1.f }
334 void QVk_DebugLabelInsert(
const VkCommandBuffer *cmdBuffer,
const char *labelName,
const float r,
const float g,
const float b)
336 VkDebugUtilsLabelEXT labelInfo = {
337 .sType = VK_STRUCTURE_TYPE_DEBUG_UTILS_LABEL_EXT,
339 .pLabelName = labelName,
340 .color = {
r, g, b, 1.f }