As the “get” part of the function suggests, it’s a function that queries something in the implementation, not one that allows you to tell it what to do.
It should similarly be obvious by Vulkan’s (rather strict) naming conversions that the VkDeviceQueueCreateInfo structure should not take a structure named VkPhysicalDeviceFloatControlsProperties as one of its extension structures.
If shaderDenormFlushToZeroFloat32 is true, then this means that denormalized floats can be flushed to zero. It doesn’t say they will be.
If you want to ensure that denormalized floats are not flushed, then you must first see if the implementation even allows that. This requires the shaderDenormPreserveFloat32 feature. If the implementation provides this functionality, then you can decorate your shader entrypoint with DenormPreserve to ensure preserving denormalized floats.
I don’t know what the Vulkan-GLSL equivalent to this is, so I don’t know how to turn it on from GLSL.
In my opinion, since shaderDenormFlushToZeroFloat32 is false, so the output value should be a denormalized float, not zero. But I print out output value which is zero, that conflicts with shaderDenormFlushToZeroFloat32 is false
No, it doesn’t. Vulkan’s naming convensions are very strict and very simple. If it’s a Vk<NameOfObject><OtherStuff> struct, its extension structs will be named Vk<NameOfObject><DifferentOtherStuff> too. VkPhysicalDeviceFloatControlsProperties is taken by exactly one function: vkGetPhysicalDeviceProperties2.
You cannot pass VkPhysicalDeviceFloatControlsProperties to VkDeviceCreateInfo. Well, you can, but it won’t actually do anything and if you’re using validation layers, you’ll get an error.
… I don’t know how to explain it any better than that. If something doesn’t say that X happens, then you don’t know if X will happen. That something can happen does not mean that it will.
The word “can” means “is able to”, not “will definitely happen”. I can eat a whole pizza. That does not mean I will do so whenever I am presented with a whole pizza.
If the standard says that a thing will definitely happen, then it will use the word “must”. Note that in the standard, “can” and “must” are in bold-face to make it clear that they are intentionally making such a distinction between what implementations “can” and “must” do.
If the implementation specifies shaderDenormFlushToZeroFloat32 , this still means the default behavior is used (which is whatever the implementation wants). However, you have the ability to require denormalized to be flushed to zero for all operations within a shader.
Similarly, shaderDenormPreserveFloat32 being set means that the implementation may preserve denormalized values, but you can also force it to do so within a shader.
These are not queries about what the implementation will do to denormalized values; it’s a statement about your ability to force a shader to handle denormalized values. Some implementations cannot handle denormalized floats at all, so they do not support denormalization preservation. Some implementations (in theory) always handle denormalized values and do not flush them at all, so they do not support flushing behavior. And some implementations may sometimes preserve and sometimes flush, but don’t let you pick which happens.