Search code examples
c++glslvulkanspir-v

Is it allowed to use a VkBool32 as a push constant?


I am trying to create a VkBool32 in my C++ code:

VkBool32 myBool = VK_FALSE;

and push it to GLSL via a push constant:

vkCmdPushConstants(..., sizeof(myBool), &myBool);

which is recieved by a bool inside a uniform storage class:

layout(push_constant) uniform PushConstants
{
    bool myBool;
} pushConts;

First tests seem to work and have the intended behaviour. But is this permitted by the Vulkan Spec?


Solution

  • Using bools for push constants is fine. There is nothing in the specs that prohibits this and I'v been using it in a few examples too.

    If you take a look at the human-readable SPIR-V output you'll see that they're converted to 32 bit integers and thus are aligned to 32 bit:

    GLSL

    layout (push_constant) uniform PushConsts {
        bool calculateNormals;
    } pushConsts;
    

    SPIR-V

     430(PushConsts):             TypeStruct 40(int)
                 431:             TypePointer PushConstant 430(PushConsts)
     432(pushConsts):    431(ptr) Variable PushConstant
                 433:             TypePointer PushConstant 40(int)
    

    So if you e.g. would pass a struct containing multiple booleans you'd have to properly align (pad) on the CPU side before passing as a push constant.

    As for the SPIR-V side of things, the official spec is always a good starting point and also contains details on how push constants are handled and how they differ.