|
|
@@ -502,6 +502,24 @@ Error RenderingDeviceDriverVulkan::_initialize_device_extensions() {
|
|
|
_register_requested_device_extension(VK_KHR_SHADER_NON_SEMANTIC_INFO_EXTENSION_NAME, true);
|
|
|
}
|
|
|
|
|
|
+#if defined(VK_TRACK_DEVICE_MEMORY)
|
|
|
+ _register_requested_device_extension(VK_EXT_DEVICE_MEMORY_REPORT_EXTENSION_NAME, false);
|
|
|
+#endif
|
|
|
+ _register_requested_device_extension(VK_EXT_DEVICE_FAULT_EXTENSION_NAME, false);
|
|
|
+
|
|
|
+ {
|
|
|
+ // Debug marker extensions.
|
|
|
+ // Should be last element in the array.
|
|
|
+#ifdef DEV_ENABLED
|
|
|
+ bool want_debug_markers = true;
|
|
|
+#else
|
|
|
+ bool want_debug_markers = OS::get_singleton()->is_stdout_verbose();
|
|
|
+#endif
|
|
|
+ if (want_debug_markers) {
|
|
|
+ _register_requested_device_extension(VK_EXT_DEBUG_MARKER_EXTENSION_NAME, false);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
uint32_t device_extension_count = 0;
|
|
|
VkResult err = vkEnumerateDeviceExtensionProperties(physical_device, nullptr, &device_extension_count, nullptr);
|
|
|
ERR_FAIL_COND_V(err != VK_SUCCESS, ERR_CANT_CREATE);
|
|
|
@@ -745,6 +763,15 @@ Error RenderingDeviceDriverVulkan::_check_device_capabilities() {
|
|
|
if (enabled_device_extension_names.has(VK_EXT_PIPELINE_CREATION_CACHE_CONTROL_EXTENSION_NAME)) {
|
|
|
pipeline_cache_control_support = pipeline_cache_control_features.pipelineCreationCacheControl;
|
|
|
}
|
|
|
+
|
|
|
+ if (enabled_device_extension_names.has(VK_EXT_DEVICE_FAULT_EXTENSION_NAME)) {
|
|
|
+ device_fault_support = true;
|
|
|
+ }
|
|
|
+#if defined(VK_TRACK_DEVICE_MEMORY)
|
|
|
+ if (enabled_device_extension_names.has(VK_EXT_DEVICE_MEMORY_REPORT_EXTENSION_NAME)) {
|
|
|
+ device_memory_report_support = true;
|
|
|
+ }
|
|
|
+#endif
|
|
|
}
|
|
|
|
|
|
if (functions.GetPhysicalDeviceProperties2 != nullptr) {
|
|
|
@@ -913,6 +940,26 @@ Error RenderingDeviceDriverVulkan::_initialize_device(const LocalVector<VkDevice
|
|
|
create_info_next = &pipeline_cache_control_features;
|
|
|
}
|
|
|
|
|
|
+ VkPhysicalDeviceFaultFeaturesEXT device_fault_features = {};
|
|
|
+ if (device_fault_support) {
|
|
|
+ device_fault_features.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FAULT_FEATURES_EXT;
|
|
|
+ device_fault_features.pNext = create_info_next;
|
|
|
+ create_info_next = &device_fault_features;
|
|
|
+ }
|
|
|
+
|
|
|
+#if defined(VK_TRACK_DEVICE_MEMORY)
|
|
|
+ VkDeviceDeviceMemoryReportCreateInfoEXT memory_report_info = {};
|
|
|
+ if (device_memory_report_support) {
|
|
|
+ memory_report_info.sType = VK_STRUCTURE_TYPE_DEVICE_DEVICE_MEMORY_REPORT_CREATE_INFO_EXT;
|
|
|
+ memory_report_info.pfnUserCallback = RenderingContextDriverVulkan::memory_report_callback;
|
|
|
+ memory_report_info.pNext = create_info_next;
|
|
|
+ memory_report_info.flags = 0;
|
|
|
+ memory_report_info.pUserData = this;
|
|
|
+
|
|
|
+ create_info_next = &memory_report_info;
|
|
|
+ }
|
|
|
+#endif
|
|
|
+
|
|
|
VkPhysicalDeviceVulkan11Features vulkan_1_1_features = {};
|
|
|
VkPhysicalDevice16BitStorageFeaturesKHR storage_features = {};
|
|
|
VkPhysicalDeviceMultiviewFeatures multiview_features = {};
|
|
|
@@ -968,7 +1015,7 @@ Error RenderingDeviceDriverVulkan::_initialize_device(const LocalVector<VkDevice
|
|
|
bool device_created = VulkanHooks::get_singleton()->create_vulkan_device(&create_info, &vk_device);
|
|
|
ERR_FAIL_COND_V(!device_created, ERR_CANT_CREATE);
|
|
|
} else {
|
|
|
- VkResult err = vkCreateDevice(physical_device, &create_info, nullptr, &vk_device);
|
|
|
+ VkResult err = vkCreateDevice(physical_device, &create_info, VKC::get_allocation_callbacks(VK_OBJECT_TYPE_DEVICE), &vk_device);
|
|
|
ERR_FAIL_COND_V(err != VK_SUCCESS, ERR_CANT_CREATE);
|
|
|
}
|
|
|
|
|
|
@@ -989,6 +1036,19 @@ Error RenderingDeviceDriverVulkan::_initialize_device(const LocalVector<VkDevice
|
|
|
if (enabled_device_extension_names.has(VK_KHR_CREATE_RENDERPASS_2_EXTENSION_NAME)) {
|
|
|
device_functions.CreateRenderPass2KHR = PFN_vkCreateRenderPass2KHR(functions.GetDeviceProcAddr(vk_device, "vkCreateRenderPass2KHR"));
|
|
|
}
|
|
|
+
|
|
|
+ // Debug marker extensions.
|
|
|
+ if (enabled_device_extension_names.has(VK_EXT_DEBUG_MARKER_EXTENSION_NAME)) {
|
|
|
+ device_functions.CmdDebugMarkerBeginEXT = (PFN_vkCmdDebugMarkerBeginEXT)functions.GetDeviceProcAddr(vk_device, "vkCmdDebugMarkerBeginEXT");
|
|
|
+ device_functions.CmdDebugMarkerEndEXT = (PFN_vkCmdDebugMarkerEndEXT)functions.GetDeviceProcAddr(vk_device, "vkCmdDebugMarkerEndEXT");
|
|
|
+ device_functions.CmdDebugMarkerInsertEXT = (PFN_vkCmdDebugMarkerInsertEXT)functions.GetDeviceProcAddr(vk_device, "vkCmdDebugMarkerInsertEXT");
|
|
|
+ device_functions.DebugMarkerSetObjectNameEXT = (PFN_vkDebugMarkerSetObjectNameEXT)functions.GetDeviceProcAddr(vk_device, "vkDebugMarkerSetObjectNameEXT");
|
|
|
+ }
|
|
|
+
|
|
|
+ // Debug device fault extension.
|
|
|
+ if (device_fault_support) {
|
|
|
+ device_functions.GetDeviceFaultInfoEXT = (PFN_vkGetDeviceFaultInfoEXT)functions.GetDeviceProcAddr(vk_device, "vkGetDeviceFaultInfoEXT");
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
return OK;
|
|
|
@@ -1148,17 +1208,102 @@ bool RenderingDeviceDriverVulkan::_recreate_image_semaphore(CommandQueue *p_comm
|
|
|
VkSemaphore semaphore;
|
|
|
VkSemaphoreCreateInfo create_info = {};
|
|
|
create_info.sType = VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO;
|
|
|
- VkResult err = vkCreateSemaphore(vk_device, &create_info, nullptr, &semaphore);
|
|
|
+ VkResult err = vkCreateSemaphore(vk_device, &create_info, VKC::get_allocation_callbacks(VK_OBJECT_TYPE_SEMAPHORE), &semaphore);
|
|
|
ERR_FAIL_COND_V(err != VK_SUCCESS, false);
|
|
|
|
|
|
// Indicate the semaphore is free again and destroy the previous one before storing the new one.
|
|
|
- vkDestroySemaphore(vk_device, p_command_queue->image_semaphores[p_semaphore_index], nullptr);
|
|
|
+ vkDestroySemaphore(vk_device, p_command_queue->image_semaphores[p_semaphore_index], VKC::get_allocation_callbacks(VK_OBJECT_TYPE_SEMAPHORE));
|
|
|
|
|
|
p_command_queue->image_semaphores[p_semaphore_index] = semaphore;
|
|
|
p_command_queue->free_image_semaphores.push_back(p_semaphore_index);
|
|
|
|
|
|
return true;
|
|
|
}
|
|
|
+// Debug marker extensions.
|
|
|
+VkDebugReportObjectTypeEXT RenderingDeviceDriverVulkan::_convert_to_debug_report_objectType(VkObjectType p_object_type) {
|
|
|
+ switch (p_object_type) {
|
|
|
+ case VK_OBJECT_TYPE_UNKNOWN:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT;
|
|
|
+ case VK_OBJECT_TYPE_INSTANCE:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_INSTANCE_EXT;
|
|
|
+ case VK_OBJECT_TYPE_PHYSICAL_DEVICE:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_PHYSICAL_DEVICE_EXT;
|
|
|
+ case VK_OBJECT_TYPE_DEVICE:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_DEVICE_EXT;
|
|
|
+ case VK_OBJECT_TYPE_QUEUE:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_QUEUE_EXT;
|
|
|
+ case VK_OBJECT_TYPE_SEMAPHORE:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_SEMAPHORE_EXT;
|
|
|
+ case VK_OBJECT_TYPE_COMMAND_BUFFER:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_COMMAND_BUFFER_EXT;
|
|
|
+ case VK_OBJECT_TYPE_FENCE:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_FENCE_EXT;
|
|
|
+ case VK_OBJECT_TYPE_DEVICE_MEMORY:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_DEVICE_MEMORY_EXT;
|
|
|
+ case VK_OBJECT_TYPE_BUFFER:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_BUFFER_EXT;
|
|
|
+ case VK_OBJECT_TYPE_IMAGE:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT;
|
|
|
+ case VK_OBJECT_TYPE_EVENT:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_EVENT_EXT;
|
|
|
+ case VK_OBJECT_TYPE_QUERY_POOL:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_QUERY_POOL_EXT;
|
|
|
+ case VK_OBJECT_TYPE_BUFFER_VIEW:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_BUFFER_VIEW_EXT;
|
|
|
+ case VK_OBJECT_TYPE_IMAGE_VIEW:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_VIEW_EXT;
|
|
|
+ case VK_OBJECT_TYPE_SHADER_MODULE:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_SHADER_MODULE_EXT;
|
|
|
+ case VK_OBJECT_TYPE_PIPELINE_CACHE:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_PIPELINE_CACHE_EXT;
|
|
|
+ case VK_OBJECT_TYPE_PIPELINE_LAYOUT:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_PIPELINE_LAYOUT_EXT;
|
|
|
+ case VK_OBJECT_TYPE_RENDER_PASS:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_RENDER_PASS_EXT;
|
|
|
+ case VK_OBJECT_TYPE_PIPELINE:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_PIPELINE_EXT;
|
|
|
+ case VK_OBJECT_TYPE_DESCRIPTOR_SET_LAYOUT:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_DESCRIPTOR_SET_LAYOUT_EXT;
|
|
|
+ case VK_OBJECT_TYPE_SAMPLER:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_SAMPLER_EXT;
|
|
|
+ case VK_OBJECT_TYPE_DESCRIPTOR_POOL:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_DESCRIPTOR_POOL_EXT;
|
|
|
+ case VK_OBJECT_TYPE_DESCRIPTOR_SET:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_DESCRIPTOR_SET_EXT;
|
|
|
+ case VK_OBJECT_TYPE_FRAMEBUFFER:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_FRAMEBUFFER_EXT;
|
|
|
+ case VK_OBJECT_TYPE_COMMAND_POOL:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_COMMAND_POOL_EXT;
|
|
|
+ case VK_OBJECT_TYPE_SAMPLER_YCBCR_CONVERSION:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_SAMPLER_YCBCR_CONVERSION_EXT;
|
|
|
+ case VK_OBJECT_TYPE_DESCRIPTOR_UPDATE_TEMPLATE:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_DESCRIPTOR_UPDATE_TEMPLATE_EXT;
|
|
|
+ case VK_OBJECT_TYPE_SURFACE_KHR:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_SURFACE_KHR_EXT;
|
|
|
+ case VK_OBJECT_TYPE_SWAPCHAIN_KHR:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_SWAPCHAIN_KHR_EXT;
|
|
|
+ case VK_OBJECT_TYPE_DISPLAY_KHR:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_DISPLAY_KHR_EXT;
|
|
|
+ case VK_OBJECT_TYPE_DISPLAY_MODE_KHR:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_DISPLAY_MODE_KHR_EXT;
|
|
|
+ case VK_OBJECT_TYPE_DEBUG_REPORT_CALLBACK_EXT:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_DEBUG_REPORT_CALLBACK_EXT_EXT;
|
|
|
+ case VK_OBJECT_TYPE_CU_MODULE_NVX:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_CU_MODULE_NVX_EXT;
|
|
|
+ case VK_OBJECT_TYPE_CU_FUNCTION_NVX:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_CU_FUNCTION_NVX_EXT;
|
|
|
+ case VK_OBJECT_TYPE_ACCELERATION_STRUCTURE_KHR:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_ACCELERATION_STRUCTURE_KHR_EXT;
|
|
|
+ case VK_OBJECT_TYPE_VALIDATION_CACHE_EXT:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_VALIDATION_CACHE_EXT_EXT;
|
|
|
+ case VK_OBJECT_TYPE_ACCELERATION_STRUCTURE_NV:
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_ACCELERATION_STRUCTURE_NV_EXT;
|
|
|
+ default:
|
|
|
+ break;
|
|
|
+ }
|
|
|
+
|
|
|
+ return VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT;
|
|
|
+}
|
|
|
|
|
|
void RenderingDeviceDriverVulkan::_set_object_name(VkObjectType p_object_type, uint64_t p_object_handle, String p_object_name) {
|
|
|
const RenderingContextDriverVulkan::Functions &functions = context_driver->functions_get();
|
|
|
@@ -1171,6 +1316,16 @@ void RenderingDeviceDriverVulkan::_set_object_name(VkObjectType p_object_type, u
|
|
|
name_info.objectHandle = p_object_handle;
|
|
|
name_info.pObjectName = obj_data.get_data();
|
|
|
functions.SetDebugUtilsObjectNameEXT(vk_device, &name_info);
|
|
|
+ } else if (functions.DebugMarkerSetObjectNameEXT != nullptr) {
|
|
|
+ // Debug marker extensions.
|
|
|
+ CharString obj_data = p_object_name.utf8();
|
|
|
+ VkDebugMarkerObjectNameInfoEXT name_info;
|
|
|
+ name_info.sType = VK_STRUCTURE_TYPE_DEBUG_UTILS_OBJECT_NAME_INFO_EXT;
|
|
|
+ name_info.pNext = nullptr;
|
|
|
+ name_info.objectType = _convert_to_debug_report_objectType(p_object_type);
|
|
|
+ name_info.object = p_object_handle;
|
|
|
+ name_info.pObjectName = obj_data.get_data();
|
|
|
+ functions.DebugMarkerSetObjectNameEXT(vk_device, &name_info);
|
|
|
}
|
|
|
}
|
|
|
|
|
|
@@ -1211,6 +1366,7 @@ Error RenderingDeviceDriverVulkan::initialize(uint32_t p_device_index, uint32_t
|
|
|
ERR_FAIL_COND_V(err != OK, err);
|
|
|
|
|
|
max_descriptor_sets_per_pool = GLOBAL_GET("rendering/rendering_device/vulkan/max_descriptors_per_pool");
|
|
|
+ breadcrumb_buffer = buffer_create(sizeof(uint32_t), BufferUsageBits::BUFFER_USAGE_TRANSFER_TO_BIT, MemoryAllocationType::MEMORY_ALLOCATION_TYPE_CPU);
|
|
|
|
|
|
return OK;
|
|
|
}
|
|
|
@@ -1279,11 +1435,10 @@ RDD::BufferID RenderingDeviceDriverVulkan::buffer_create(uint64_t p_size, BitFie
|
|
|
// Looks like a readback buffer: GPU copies from VRAM, then CPU maps and reads.
|
|
|
alloc_create_info.flags = VMA_ALLOCATION_CREATE_HOST_ACCESS_RANDOM_BIT;
|
|
|
}
|
|
|
- alloc_create_info.usage = VMA_MEMORY_USAGE_AUTO_PREFER_HOST;
|
|
|
alloc_create_info.requiredFlags = (VK_MEMORY_PROPERTY_HOST_COHERENT_BIT | VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT);
|
|
|
} break;
|
|
|
case MEMORY_ALLOCATION_TYPE_GPU: {
|
|
|
- alloc_create_info.usage = VMA_MEMORY_USAGE_AUTO_PREFER_DEVICE;
|
|
|
+ alloc_create_info.preferredFlags = VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT;
|
|
|
if (p_size <= SMALL_ALLOCATION_MAX_SIZE) {
|
|
|
uint32_t mem_type_index = 0;
|
|
|
vmaFindMemoryTypeIndexForBufferInfo(allocator, &create_info, &alloc_create_info, &mem_type_index);
|
|
|
@@ -1295,11 +1450,15 @@ RDD::BufferID RenderingDeviceDriverVulkan::buffer_create(uint64_t p_size, BitFie
|
|
|
VkBuffer vk_buffer = VK_NULL_HANDLE;
|
|
|
VmaAllocation allocation = nullptr;
|
|
|
VmaAllocationInfo alloc_info = {};
|
|
|
- VkResult err = vmaCreateBuffer(allocator, &create_info, &alloc_create_info, &vk_buffer, &allocation, &alloc_info);
|
|
|
+
|
|
|
+ VkResult err = vkCreateBuffer(vk_device, &create_info, VKC::get_allocation_callbacks(VK_OBJECT_TYPE_BUFFER), &vk_buffer);
|
|
|
ERR_FAIL_COND_V_MSG(err, BufferID(), "Can't create buffer of size: " + itos(p_size) + ", error " + itos(err) + ".");
|
|
|
+ err = vmaAllocateMemoryForBuffer(allocator, vk_buffer, &alloc_create_info, &allocation, &alloc_info);
|
|
|
+ ERR_FAIL_COND_V_MSG(err, BufferID(), "Can't allocate memory for buffer of size: " + itos(p_size) + ", error " + itos(err) + ".");
|
|
|
+ err = vmaBindBufferMemory2(allocator, allocation, 0, vk_buffer, NULL);
|
|
|
+ ERR_FAIL_COND_V_MSG(err, BufferID(), "Can't bind memory to buffer of size: " + itos(p_size) + ", error " + itos(err) + ".");
|
|
|
|
|
|
// Bookkeep.
|
|
|
-
|
|
|
BufferInfo *buf_info = VersatileResource::allocate<BufferInfo>(resources_allocator);
|
|
|
buf_info->vk_buffer = vk_buffer;
|
|
|
buf_info->allocation.handle = allocation;
|
|
|