Querying feature/extension support during layer setup
Complex layers often need to enable or disable additional API functionality (optional features and/or extensions) exposed by layers beneath, and it's nice to be application-like and robustly query what's supported beneath you and report nice errors rather than just speculatively trying to enable something and failing erratically if it's not supported.
I've been trying to work out how to do the following from inside a layer, and struggling a bit to work out what's allowed or not, as the layer/loader documentation skims over this a bit. Any guidance would be appreciated!
Q1: How does a layer query vkEnumerateInstanceVersion() before instance creation?
Use case: Often a layer will want to increase the API support version above what the application requests (e.g. app uses 1.0, but we want to use 1.2 to access timeline sems). Is it even worth trying to configure my layer, or should I just set the entire layer to passthrough?
Footnote: I know this isn't enough by itself, and you still need to query device API version, but it's the first check we'd normally do as it sets an upper bound on the device API version, and it means we can avoid init-ing instance extensions if the layer is going to no-op anyway.
Q2: How does a layer query instance extension availability before instance creation?
Use case: can I safely use/enable an instance extension that the layer needs?
An application would query vkEnumerateInstanceExtensionProperties() to get the enumeration of extensions from the loader, but a layer can't invoke the loader version directly. It's possible (is it?) for a layer to query by calling the chain GetProcAddr() version of the function during instance creation, but if another vendor's explicit layers are beneath you and follow the spec ...
When pLayerName parameter is NULL, only extensions provided by the Vulkan implementation or by implicitly enabled layers are returned.
... then it's possible that they enable extensions that a layer above them can't see in generic queries (with pLayerName=NULL), and the layer above has no way to know the name of the other explicit layers below to query them specifically because that's outside of our remit. It's "strange" to have a layered API with functionality like this that can side-step the layering.
Q4: How does a layer query device extension availability before device creation?
Basically a repeat of the problem above, but for device extensions. The way it's specified, it seems possible for explicit layers beneath our layer to hide their functionality because you can't query them without knowing their name.
Q5: Can a Vulkan layer tell if it's being loaded implicitly or explicitly?
The API spec seems to require a layer to do different things if implicit or explicit (e.g. see vkEnumerateInstance/DeviceExtensionProperties()), but I can't see a way for a layer to programmatically tell if its being loaded implicitly or explicitly.
You can monitor VkInstanceCreateInfo::ppEnabledLayerNames to see if you are in the explicit list, but that's too late for pre-instance functions like vkEnumerateInstanceExtensionProperties() to change their behavior.