diff --git a/src/xrt/auxiliary/vk/vk_helpers.c b/src/xrt/auxiliary/vk/vk_helpers.c index 528836797..0ba9a1023 100644 --- a/src/xrt/auxiliary/vk/vk_helpers.c +++ b/src/xrt/auxiliary/vk/vk_helpers.c @@ -1231,7 +1231,7 @@ vk_check_extension(struct vk_bundle *vk, VkExtensionProperties *props, uint32_t } static void -fill_in_has_extensions(struct vk_bundle *vk, const char **device_extensions, uint32_t device_extension_count) +fill_in_has_extensions(struct vk_bundle *vk, const char *const *device_extensions, uint32_t device_extension_count) { // beginning of GENERATED extension code - do not modify - used by scripts // Reset before filling out. @@ -1299,12 +1299,9 @@ vk_get_device_ext_props(struct vk_bundle *vk, static bool vk_build_device_extensions(struct vk_bundle *vk, VkPhysicalDevice physical_device, - const char *const *required_device_extensions, - uint32_t required_device_extension_count, - const char *const *optional_device_extensions, - uint32_t optional_device_extension_count, - const char ***out_device_extensions, - uint32_t *out_device_extension_count) + struct u_string_list *required_device_ext_list, + struct u_string_list *optional_device_ext_list, + struct u_string_list **out_device_ext_list) { VkExtensionProperties *props = NULL; uint32_t prop_count = 0; @@ -1312,27 +1309,35 @@ vk_build_device_extensions(struct vk_bundle *vk, return false; } - uint32_t max_exts = required_device_extension_count + optional_device_extension_count; + uint32_t required_device_ext_count = u_string_list_get_size(required_device_ext_list); + const char *const *required_device_exts = u_string_list_get_data(required_device_ext_list); - const char **device_extensions = U_TYPED_ARRAY_CALLOC(const char *, max_exts); - - for (uint32_t i = 0; i < required_device_extension_count; i++) { - const char *ext = required_device_extensions[i]; + // error out if we don't support one of the required extensions + for (uint32_t i = 0; i < required_device_ext_count; i++) { + const char *ext = required_device_exts[i]; if (!vk_check_extension(vk, props, prop_count, ext)) { U_LOG_E("VkPhysicalDevice does not support required extension %s", ext); free(props); return false; } U_LOG_T("Using required device ext %s", ext); - device_extensions[i] = ext; } - uint32_t device_extension_count = required_device_extension_count; - for (uint32_t i = 0; i < optional_device_extension_count; i++) { - const char *ext = optional_device_extensions[i]; + + *out_device_ext_list = u_string_list_create_from_list(required_device_ext_list); + + + uint32_t optional_device_ext_count = u_string_list_get_size(optional_device_ext_list); + const char *const *optional_device_exts = u_string_list_get_data(optional_device_ext_list); + + for (uint32_t i = 0; i < optional_device_ext_count; i++) { + const char *ext = optional_device_exts[i]; if (vk_check_extension(vk, props, prop_count, ext)) { U_LOG_D("Using optional device ext %s", ext); - device_extensions[device_extension_count++] = ext; + int added = u_string_list_append_unique(*out_device_ext_list, ext); + if (added == 0) { + U_LOG_W("Duplicate device extension %s not added twice", ext); + } } else { U_LOG_T("NOT using optional device ext %s", ext); continue; @@ -1340,12 +1345,11 @@ vk_build_device_extensions(struct vk_bundle *vk, } // Fill this out here. - fill_in_has_extensions(vk, device_extensions, device_extension_count); + fill_in_has_extensions(vk, u_string_list_get_data(*out_device_ext_list), + u_string_list_get_size(*out_device_ext_list)); free(props); - *out_device_extensions = device_extensions; - *out_device_extension_count = device_extension_count; return true; } @@ -1455,10 +1459,8 @@ vk_create_device(struct vk_bundle *vk, int forced_index, bool only_compute, VkQueueGlobalPriorityEXT global_priority, - const char *const *required_device_extensions, - size_t required_device_extension_count, - const char *const *optional_device_extensions, - size_t optional_device_extension_count, + struct u_string_list *required_device_ext_list, + struct u_string_list *optional_device_ext_list, const struct vk_device_features *optional_device_features) { VkResult ret; @@ -1468,11 +1470,9 @@ vk_create_device(struct vk_bundle *vk, return ret; } - const char **device_extensions; - uint32_t device_extension_count; - if (!vk_build_device_extensions(vk, vk->physical_device, required_device_extensions, - required_device_extension_count, optional_device_extensions, - optional_device_extension_count, &device_extensions, &device_extension_count)) { + struct u_string_list *device_ext_list = NULL; + if (!vk_build_device_extensions(vk, vk->physical_device, required_device_ext_list, optional_device_ext_list, + &device_ext_list)) { return VK_ERROR_EXTENSION_NOT_PRESENT; } @@ -1548,8 +1548,8 @@ vk_create_device(struct vk_bundle *vk, .sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO, .queueCreateInfoCount = 1, .pQueueCreateInfos = &queue_create_info, - .enabledExtensionCount = device_extension_count, - .ppEnabledExtensionNames = device_extensions, + .enabledExtensionCount = u_string_list_get_size(device_ext_list), + .ppEnabledExtensionNames = u_string_list_get_data(device_ext_list), .pEnabledFeatures = &enabled_features, }; @@ -1568,7 +1568,7 @@ vk_create_device(struct vk_bundle *vk, ret = vk->vkCreateDevice(vk->physical_device, &device_create_info, NULL, &vk->device); - free(device_extensions); + u_string_list_destroy(&device_ext_list); if (ret != VK_SUCCESS) { VK_DEBUG(vk, "vkCreateDevice: %s (%d)", vk_result_string(ret), ret); diff --git a/src/xrt/auxiliary/vk/vk_helpers.h b/src/xrt/auxiliary/vk/vk_helpers.h index dc8decaea..d9ba39d4c 100644 --- a/src/xrt/auxiliary/vk/vk_helpers.h +++ b/src/xrt/auxiliary/vk/vk_helpers.h @@ -22,6 +22,7 @@ #include "xrt/xrt_vulkan_includes.h" #include "xrt/xrt_handles.h" #include "util/u_logging.h" +#include "util/u_string_list.h" #include "os/os_threading.h" #ifdef __cplusplus @@ -433,10 +434,8 @@ vk_create_device(struct vk_bundle *vk, int forced_index, bool only_compute, VkQueueGlobalPriorityEXT global_priorty, - const char *const *required_device_extensions, - size_t required_device_extension_count, - const char *const *optional_device_extensions, - size_t optional_device_extension_count, + struct u_string_list *required_device_ext_list, + struct u_string_list *optional_device_ext_list, const struct vk_device_features *optional_device_features); /*! diff --git a/src/xrt/compositor/main/comp_compositor.c b/src/xrt/compositor/main/comp_compositor.c index 0103ddf7e..08ebbf43a 100644 --- a/src/xrt/compositor/main/comp_compositor.c +++ b/src/xrt/compositor/main/comp_compositor.c @@ -893,17 +893,26 @@ compositor_check_vulkan_caps(struct comp_compositor *c) bool use_compute = c->settings.use_compute; + struct u_string_list *required_device_ext_list = + u_string_list_create_with_capacity(ARRAY_SIZE(required_device_extensions)); + append_all(c, required_device_ext_list, required_device_extensions, ARRAY_SIZE(required_device_extensions)); + + struct u_string_list *optional_device_ext_list = + u_string_list_create_with_capacity(ARRAY_SIZE(optional_device_extensions)); + append_all(c, optional_device_ext_list, optional_device_extensions, ARRAY_SIZE(optional_device_extensions)); + // follow same device selection logic as subsequent calls - ret = vk_create_device( // - temp_vk, // - c->settings.selected_gpu_index, // - use_compute, // compute_only - VK_QUEUE_GLOBAL_PRIORITY_MEDIUM_EXT, // global_priority - required_device_extensions, // - ARRAY_SIZE(required_device_extensions), // - optional_device_extensions, // - ARRAY_SIZE(optional_device_extensions), // - NULL); // optional_device_features + ret = vk_create_device( // + temp_vk, // + c->settings.selected_gpu_index, // + use_compute, // compute_only + VK_QUEUE_GLOBAL_PRIORITY_MEDIUM_EXT, // global_priority + required_device_ext_list, // + optional_device_ext_list, // + NULL); // optional_device_features + + u_string_list_destroy(&required_device_ext_list); + u_string_list_destroy(&optional_device_ext_list); if (ret != VK_SUCCESS) { CVK_ERROR(c, "vk_create_device", "Failed to create VkDevice.", ret); diff --git a/src/xrt/compositor/util/comp_vulkan.c b/src/xrt/compositor/util/comp_vulkan.c index d8ebae506..9683e53ee 100644 --- a/src/xrt/compositor/util/comp_vulkan.c +++ b/src/xrt/compositor/util/comp_vulkan.c @@ -166,16 +166,14 @@ create_device(struct vk_bundle *vk, const struct comp_vulkan_arguments *vk_args) // No other way then to try to see if realtime is available. for (size_t i = 0; i < ARRAY_SIZE(prios); i++) { - ret = vk_create_device( // - vk, // - vk_args->selected_gpu_index, // - only_compute_queue, // compute_only - prios[i], // global_priority - u_string_list_get_data(vk_args->required_device_extensions), // - u_string_list_get_size(vk_args->required_device_extensions), // - u_string_list_get_data(vk_args->optional_device_extensions), // - u_string_list_get_size(vk_args->optional_device_extensions), // - &device_features); // optional_device_features + ret = vk_create_device( // + vk, // + vk_args->selected_gpu_index, // + only_compute_queue, // compute_only + prios[i], // global_priority + vk_args->required_device_extensions, // + vk_args->optional_device_extensions, // + &device_features); // optional_device_features // All ok! if (ret == VK_SUCCESS) {