https://gcc.gnu.org/bugzilla/show_bug.cgi?id=112296
--- Comment #12 from joseph at codesourcery dot com <joseph at codesourcery dot com> --- I agree that the side effects of an argument to __builtin_constant_p must be discarded, for the original macro use case to work properly. There are various constructs with __builtin_* names that, although they look like function calls, in fact have syntactic or semantic differences from what can be done with a normal function call. In the cases of syntactic differences, they are actually keywords and handled specially in the parsers. That's probably not relevant here, because the issue is semantics of the call (argument not evaluated) rather than the syntax, but it does illustrate how it's reasonable to have special handling for some __builtin_* construct when needed for its semantics.