https://github.com/TPPPP72 created https://github.com/llvm/llvm-project/pull/212743
This PR makes the following changes: 1. Adds a new diagnostic field, `err_ms_integer_literal_too_large`, to provide more precise diagnostics. 2. Rewrites the truncation logic for Microsoft integer literals to fix an assertion failure. Fix #212504, Fix #212731 >From 443fb82fe88f36ac54ff5bb26cb2706b29f7b0ee Mon Sep 17 00:00:00 2001 From: Shengxin Pei <[email protected]> Date: Wed, 29 Jul 2026 19:22:31 +0800 Subject: [PATCH] [Clang] Improve diagnostic of Microsoft interger literials and refactor its truncation logic --- .../clang/Basic/DiagnosticCommonKinds.td | 3 ++ clang/lib/Sema/SemaExpr.cpp | 16 +++++++++- clang/test/SemaCXX/ms_integer_suffix.cpp | 30 ++++++++++++++++++- 3 files changed, 47 insertions(+), 2 deletions(-) diff --git a/clang/include/clang/Basic/DiagnosticCommonKinds.td b/clang/include/clang/Basic/DiagnosticCommonKinds.td index f2ed2f4698b8d..baba1f065d5e0 100644 --- a/clang/include/clang/Basic/DiagnosticCommonKinds.td +++ b/clang/include/clang/Basic/DiagnosticCommonKinds.td @@ -246,6 +246,9 @@ def warn_c23_compat_bitint_suffix : Warning< def err_integer_literal_too_large : Error< "integer literal is too large to be represented in any %select{signed |}0" "integer type">; +def err_ms_integer_literal_too_large : Error< + "integer literal is too large to be represented in a %0-bit " + "%select{signed|unsigned}1 integer type">; def ext_integer_literal_too_large_for_signed : ExtWarn< "integer literal is too large to be represented in a signed integer type, " "interpreting as unsigned">, diff --git a/clang/lib/Sema/SemaExpr.cpp b/clang/lib/Sema/SemaExpr.cpp index ed3d27b5adc27..45a2723c3dc24 100644 --- a/clang/lib/Sema/SemaExpr.cpp +++ b/clang/lib/Sema/SemaExpr.cpp @@ -4092,7 +4092,7 @@ ExprResult Sema::ActOnNumericConstant(const Token &Tok, Scope *UDLScope) { !Context.getTargetInfo().hasInt128Type()) PP.Diag(Tok.getLocation(), diag::err_integer_literal_too_large) << Literal.isUnsigned; - BitsNeeded = Literal.MicrosoftInteger; + BitsNeeded = std::max<unsigned>(BitsNeeded, Literal.MicrosoftInteger); } llvm::APInt ResultVal(BitsNeeded, 0); @@ -4134,6 +4134,20 @@ ExprResult Sema::ActOnNumericConstant(const Token &Tok, Scope *UDLScope) { Ty = Context.getIntTypeForBitwidth(Width, /*Signed=*/!Literal.isUnsigned); } + + bool IsTooLarge = false; + if (Literal.isUnsigned) + IsTooLarge = ResultVal.getActiveBits() > Width; + else + IsTooLarge = ResultVal.getSignificantBits() > Width || + (ResultVal.getSignificantBits() == Width && + ResultVal.isSignBitSet()); + + if (IsTooLarge) + Diag(Tok.getLocation(), diag::err_ms_integer_literal_too_large) + << Width << Literal.isUnsigned; + + ResultVal = ResultVal.zextOrTrunc(Width); } // Bit-precise integer literals are automagically-sized based on the diff --git a/clang/test/SemaCXX/ms_integer_suffix.cpp b/clang/test/SemaCXX/ms_integer_suffix.cpp index aa2f13099d3b8..5dd77df093bdd 100644 --- a/clang/test/SemaCXX/ms_integer_suffix.cpp +++ b/clang/test/SemaCXX/ms_integer_suffix.cpp @@ -1,5 +1,4 @@ // RUN: %clang_cc1 -std=c++11 -fsyntax-only -fms-extensions -verify %s -// expected-no-diagnostics #ifdef __SIZEOF_INT8__ static_assert(sizeof(0i8) == __SIZEOF_INT8__, ""); @@ -18,3 +17,32 @@ static_assert(sizeof(0i32) == __SIZEOF_INT32__, ""); #ifdef __SIZEOF_INT64__ static_assert(sizeof(0i64) == __SIZEOF_INT64__, ""); #endif +namespace gh212504 { + static_assert(-127i8, ""); + static_assert(127i8, ""); + static_assert(128i8, ""); // expected-error {{integer literal is too large to be represented in a 8-bit signed integer type}} + static_assert(255ui8, ""); + static_assert(256ui8, ""); // expected-error {{integer literal is too large to be represented in a 8-bit unsigned integer type}} \ + // expected-error {{static assertion failed}} + + static_assert(-32767i16, ""); + static_assert(32767i16, ""); + static_assert(32768i16, ""); // expected-error {{integer literal is too large to be represented in a 16-bit signed integer type}} + static_assert(65535ui16, ""); + static_assert(65536ui16, ""); // expected-error {{integer literal is too large to be represented in a 16-bit unsigned integer type}} \ + // expected-error {{static assertion failed}} + + static_assert(-2147483647i32, ""); + static_assert(2147483647i32, ""); + static_assert(2147483648i32, ""); // expected-error {{integer literal is too large to be represented in a 32-bit signed integer type}} + static_assert(4294967295ui32, ""); + static_assert(4294967296ui32, ""); // expected-error {{integer literal is too large to be represented in a 32-bit unsigned integer type}} \ + // expected-error {{static assertion failed}} + + static_assert(-9223372036854775807i64, ""); + static_assert(9223372036854775807i64, ""); + static_assert(9223372036854775808i64, ""); // expected-error {{integer literal is too large to be represented in a 64-bit signed integer type}} + static_assert(18446744073709551615ui64, ""); + static_assert(18446744073709551616ui64, ""); // expected-error {{integer literal is too large to be represented in any integer type}} \ + // expected-error {{static assertion failed}} +} _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
