[lex.name]/3.2 says that an identifier like _min
, i.e. starting with an underscore,
[...] is reserved to the implementation for use as a name in the global namespace.
The wording doesn't say that you can't use the identifier in the global namespace scope, but that you must ensure that the implementation can do so. If you #define
it as a macro and then include a standard library header, then the implementation can't reliably use the name in the global namespace scope.
So it seems clearly UB to me if you include (transitively) a standard library header after the #define
and before a corresponding #undef
. It doesn't seem however to be the intention to generally make these #define
UB. As long as no standard library header is affected during preprocessing, it seems to be fine. See also comments under the answer.
An interpretation along the lines above, i.e. UB if a standard library header would see the macro definition, is also given by Richard Smith (C++ standard editor) in a comment on Clang's -Wreserved-identifier
warning here, although qualified with "I think".
There is indeed a code example using #define _x
in [diff.cpp03.lex]/2 of the standard which is implied to be (at least by itself) well-defined, although it is in a non-normative section of the standard.