0
$\begingroup$

Glsl does not support string / char data types, but obviously debugPrintfEXT works and takes some form of string. How are these handled in glsl?

Ideally I would like to forward the input, such that I can very easily limit when debugPrintfEXT is called, something like this

layout(pushconstant) uniform DebugSettings
{
    bool Enabled;
}

debugPrintLimited(string s)
{
    bool isCenter = gl_LaunchIDEXT.x == gl_LaunchSizeEXT.x / 2
        && gl_LaunchIDEXT.y == gl_LaunchSizeEXT.y / 2
    if(DebugSettings.Enabled && isCenter)
    {
        debugPrintfEXT(s);
    }
}

Obviously the string here is not correct, but glsl has to handle the strings put into debugPrintfEXT somehow, so I would like to forward whatever they use, if at all possible.

$\endgroup$

1 Answer 1

1
$\begingroup$

They get help from the compiler. The line #extension GL_EXT_debug_printf : enable tells the compiler to look for and process debugPrintf statements inside the shader it then parses them out, modifies them, adds its own instructions, creates buffers... Basically they can do whatever they need to make it work.

You could forward just the variables but that would be pretty limited. And , unfortunately the printf would end up being very generic.

Another choice would be to write a macro that expands to a call to the printf with a bool wrapper around it. Basically the macro would expand to the if statement that is need to gate the call without using a function call, and have the printf inside of its body. I haven't tried this in GLSL myself but it seems very doable. GLSL's macro language is pretty powerful. I've seen some crazy long macro's put together with long code segments passed as strings.

Updated the code to the version that worked from the comment:

#ifdef DEBUG 
#define printf( condition, message, value ) if( condition ){ \
       debugPrintfEXT( message, value ); \
     } 
#define printfDbg(message, value) if(isCenter() && pSettings.PrintDebugEnabled){ \
     debugPrintfEXT(message, value);\
  } 
#else 
#define printf( condition, message, value ) 
#define printfDbg(message, value) 
#endif

...

printf( x==40.0 && y==20.0, "at 20,40 color is %1fv4.", color );

Unfortunately glsl doesn't support variadic macros so this has to be specific to 1 value or 2 values ect.

Maybe a macro for 1,2,3 variable outputs like printf1, printf2, and printf3.

Also the glsl language version can effect macro behavior but since the code is using debugprintf then it probably won't be an issue.

Finally you may want to just preprocess this through the compiler a few times until you get the syntax just right.

$\endgroup$
1
  • $\begingroup$ Not quite as nice with the lack of variadic macros, but a lot better than retyping the condition every time. Just for completeness, this is the syntax that got it working for me (with isCenter() and pSettings` coming from my program, of course: #ifdef DEBUG #define printf( condition, message, value ) if( condition ){ \ debugPrintfEXT( message, value ); \ } #define printfDbg(message, value) if(isCenter() && pSettings.PrintDebugEnabled){ \ debugPrintfEXT(message, value);\ } #else #define printf( condition, message, value ) #define printfDbg(message, value) #endif $\endgroup$
    – Tare
    Sep 16, 2023 at 7:36

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.