Author: Aaron Ballman Date: 2025-04-08T14:25:59-04:00 New Revision: 9ba1a3fcb53936f20533585df283b3734ae8c4ef
URL: https://github.com/llvm/llvm-project/commit/9ba1a3fcb53936f20533585df283b3734ae8c4ef DIFF: https://github.com/llvm/llvm-project/commit/9ba1a3fcb53936f20533585df283b3734ae8c4ef.diff LOG: Reject invalid integer constants in unevaluated preprocessor operands (#134884) Clang was previously accepting invalid code like: ``` #if 1 ? 1 : 999999999999999999999 #endif ``` because the integer constant (which is too large to fit into any standard or extended integer type) was in an unevaluated branch of the conditional operator. Similar invalid code involving || or && was also accepted and is now rejected. Fixes #134658 Added: clang/test/Preprocessor/constants.c Modified: clang/docs/ReleaseNotes.rst clang/lib/Lex/PPExpressions.cpp Removed: ################################################################################ diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index e671183522565..90d72975e6572 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -354,6 +354,14 @@ Bug Fixes in This Version - Defining an integer literal suffix (e.g., ``LL``) before including ``<stdint.h>`` in a freestanding build no longer causes invalid token pasting when using the ``INTn_C`` macros. (#GH85995) +- Clang no longer accepts invalid integer constants which are too large to fit + into any (standard or extended) integer type when the constant is unevaluated. + Merely forming the token is sufficient to render the program invalid. Code + like this was previously accepted and is now rejected (#GH134658): + .. code-block:: c + + #if 1 ? 1 : 999999999999999999999 + #endif Bug Fixes to Compiler Builtins ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ diff --git a/clang/lib/Lex/PPExpressions.cpp b/clang/lib/Lex/PPExpressions.cpp index b031571907441..48835121b40e9 100644 --- a/clang/lib/Lex/PPExpressions.cpp +++ b/clang/lib/Lex/PPExpressions.cpp @@ -345,9 +345,7 @@ static bool EvaluateValue(PPValue &Result, Token &PeekTok, DefinedTracker &DT, // Parse the integer literal into Result. if (Literal.GetIntegerValue(Result.Val)) { // Overflow parsing integer literal. - if (ValueLive) - PP.Diag(PeekTok, diag::err_integer_literal_too_large) - << /* Unsigned */ 1; + PP.Diag(PeekTok, diag::err_integer_literal_too_large) << /* Unsigned */ 1; Result.Val.setIsUnsigned(true); } else { // Set the signedness of the result to match whether there was a U suffix diff --git a/clang/test/Preprocessor/constants.c b/clang/test/Preprocessor/constants.c new file mode 100644 index 0000000000000..d6241a4f1ceee --- /dev/null +++ b/clang/test/Preprocessor/constants.c @@ -0,0 +1,40 @@ +// RUN: %clang_cc1 -E -verify %s + +// C++ [lex.icon]p4 and C 6.4.4.1p2 + 6.4.4.2p7 both require C and C++ to +// validate the integer constant value when converting a preprocessing token +// into a token for semantic analysis, even within the preprocessor itself. + +// Plain integer constant. +#if 999999999999999999999 // expected-error {{integer literal is too large to be represented in any integer type}} +#endif + +// These cases were previously incorrectly accepted. See GH134658. + +// Integer constant in an unevaluated branch of a conditional. +#if 1 ? 1 : 999999999999999999999 // expected-error {{integer literal is too large to be represented in any integer type}} +#endif + +// Integer constant in an unevaluated operand of a logical operator. +#if 0 && 999999999999999999999 // expected-error {{integer literal is too large to be represented in any integer type}} +#endif + +#if 1 || 999999999999999999999 // expected-error {{integer literal is too large to be represented in any integer type}} +#endif + +// Make sure we also catch it in an elif condition. +#if 0 +#elif 1 || 999999999999999999999 // expected-error {{integer literal is too large to be represented in any integer type}} +#endif + +// However, if the block is skipped entirely, then it doesn't matter how +// invalid the constant value is. +#if 0 +int x = 999999999999999999999; + +#if 999999999999999999999 +#endif + +#if 0 && 999999999999999999999 +#endif + +#endif _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits