vk-bootstrap icon indicating copy to clipboard operation
vk-bootstrap copied to clipboard

It is not clear how to activate device extensions

Open ferserc1 opened this issue 1 year ago • 1 comments

It is not clear at all from the documentation how to enable device extensions.

Specifically, with MoltenVK, the API 1.3 is not currently available, but most of the extensions, including Dynamic Rendering, are available.

The following code works correctly as long as the validation layers are not enabled:

    VkPhysicalDeviceVulkan13Features features13 = {};
    features13.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_3_FEATURES;
    features13.dynamicRendering = true;
    
    vkb::PhysicalDeviceSelector selector { _vkbInstance };
    vkb::PhysicalDevice physicalDevice = selector
        .set_minimum_version(1, 2)  // Set 1.2 API
        .set_required_features_13(features13)  // Enable 1.3 core feature
        .set_surface(_surface)
        .select()
        .value();
    
    vkb::DeviceBuilder deviceBuilder{ physicalDevice };
    vkb::Device vkbDevice = deviceBuilder.build().value();

That is, using Vulkan version 1.2 and passing features of version 1.3, the device is created correctly and we can use the functions of the extension. But if we activate the validation layers the above code fails, because it's not correct to enable a 1.3 core feature using version 1.2:

pCreateInfo->pNext includes a pointer to a VkStructureType (VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_3_FEATURES) which was added in VK_API_VERSION_1_3 but the current effective API version is 1.2.283 (0x0040211b). The Vulkan spec states: Each pNext member of any structure (including this one) in the pNext chain must be either NULL or a pointer to a valid struct for extending VkDeviceCreateInfo

From the documentation I have been able to deduce that the correct way to activate the extension is this:

    vkb::PhysicalDeviceSelector selector { _vkbInstance };
    vkb::PhysicalDevice physicalDevice = selector
        .set_minimum_version(1, 2)
        .add_required_extension(VK_KHR_DYNAMIC_RENDERING_EXTENSION_NAME)
        .add_required_extension(VK_KHR_SYNCHRONIZATION_2_EXTENSION_NAME)
        .set_surface(_surface)
        .select()
        .value();
    
    physicalDevice.enable_extension_if_present(VK_KHR_DYNAMIC_RENDERING_EXTENSION_NAME);
    physicalDevice.enable_extension_if_present(VK_KHR_SYNCHRONIZATION_2_EXTENSION_NAME);

But the above code does not activate the extensions.

I have tested creating the device and loading the extension functions manually, without using vk-bootstrap, and it works without problems. I don't know if the problem is that the documentation doesn't explain the correct way to load the extensions or if it's a bug.

ferserc1 avatar Nov 06 '24 15:11 ferserc1

Did you set the instance apiVersion to 1.3? That is alos a requirement.

There certainly could be a bug in the extension enablement - how else are you checking that the extensions were in fact enabled? Loading function pointers and checking for null isn't necessarily the best way to do it. (if you do, be sure to use vkGetDeviceProcAddr). I would suggest looking at the list of extensions passed into vkCreateDevice - if those contain the ones you want and the device is successfully created, then that would be how I validate success.

charles-lunarg avatar Nov 16 '24 16:11 charles-lunarg