Skip to content

Commit 7794b8d

Browse files
committed
[clang-format] Lex C++ only keywords as identifiers in C
Fix #128847
1 parent 80f34e2 commit 7794b8d

File tree

2 files changed

+34
-17
lines changed

2 files changed

+34
-17
lines changed

clang/lib/Format/Format.cpp

Lines changed: 25 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -3941,34 +3941,42 @@ tooling::Replacements sortUsingDeclarations(const FormatStyle &Style,
39413941
LangOptions getFormattingLangOpts(const FormatStyle &Style) {
39423942
LangOptions LangOpts;
39433943

3944-
FormatStyle::LanguageStandard LexingStd = Style.Standard;
3945-
if (LexingStd == FormatStyle::LS_Auto)
3946-
LexingStd = FormatStyle::LS_Latest;
3947-
if (LexingStd == FormatStyle::LS_Latest)
3944+
auto LexingStd = Style.Standard;
3945+
if (LexingStd == FormatStyle::LS_Auto || LexingStd == FormatStyle::LS_Latest)
39483946
LexingStd = FormatStyle::LS_Cpp20;
3949-
LangOpts.CPlusPlus = 1;
3950-
LangOpts.CPlusPlus11 = LexingStd >= FormatStyle::LS_Cpp11;
3951-
LangOpts.CPlusPlus14 = LexingStd >= FormatStyle::LS_Cpp14;
3952-
LangOpts.CPlusPlus17 = LexingStd >= FormatStyle::LS_Cpp17;
3953-
LangOpts.CPlusPlus20 = LexingStd >= FormatStyle::LS_Cpp20;
3954-
LangOpts.Char8 = LexingStd >= FormatStyle::LS_Cpp20;
3947+
3948+
const bool SinceCpp11 = LexingStd >= FormatStyle::LS_Cpp11;
3949+
const bool SinceCpp20 = LexingStd >= FormatStyle::LS_Cpp20;
3950+
3951+
switch (Style.Language) {
3952+
case FormatStyle::LK_C:
3953+
LangOpts.C17 = 1;
3954+
break;
3955+
case FormatStyle::LK_Cpp:
3956+
case FormatStyle::LK_ObjC:
3957+
LangOpts.CXXOperatorNames = 1;
3958+
LangOpts.CPlusPlus11 = SinceCpp11;
3959+
LangOpts.CPlusPlus14 = LexingStd >= FormatStyle::LS_Cpp14;
3960+
LangOpts.CPlusPlus17 = LexingStd >= FormatStyle::LS_Cpp17;
3961+
LangOpts.CPlusPlus20 = SinceCpp20;
3962+
[[fallthrough]];
3963+
default:
3964+
LangOpts.CPlusPlus = 1;
3965+
}
3966+
3967+
LangOpts.Char8 = SinceCpp20;
39553968
// Turning on digraphs in standards before C++0x is error-prone, because e.g.
39563969
// the sequence "<::" will be unconditionally treated as "[:".
39573970
// Cf. Lexer::LexTokenInternal.
3958-
LangOpts.Digraphs = LexingStd >= FormatStyle::LS_Cpp11;
3971+
LangOpts.Digraphs = SinceCpp11;
39593972

39603973
LangOpts.LineComment = 1;
3961-
3962-
const auto Language = Style.Language;
3963-
LangOpts.C17 = Language == FormatStyle::LK_C;
3964-
LangOpts.CXXOperatorNames =
3965-
Language == FormatStyle::LK_Cpp || Language == FormatStyle::LK_ObjC;
3966-
39673974
LangOpts.Bool = 1;
39683975
LangOpts.ObjC = 1;
39693976
LangOpts.MicrosoftExt = 1; // To get kw___try, kw___finally.
39703977
LangOpts.DeclSpecKeyword = 1; // To get __declspec.
39713978
LangOpts.C99 = 1; // To get kw_restrict for non-underscore-prefixed restrict.
3979+
39723980
return LangOpts;
39733981
}
39743982

clang/unittests/Format/TokenAnnotatorTest.cpp

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3705,6 +3705,15 @@ TEST_F(TokenAnnotatorTest, CppAltOperatorKeywords) {
37053705
EXPECT_TOKEN(Tokens[1], tok::identifier, TT_StartOfName);
37063706
}
37073707

3708+
TEST_F(TokenAnnotatorTest, CppOnlyKeywordInC) {
3709+
auto Tokens = annotate("int maximized = new & STATE_MAXIMIZED;",
3710+
getLLVMStyle(FormatStyle::LK_C));
3711+
ASSERT_EQ(Tokens.size(), 8u) << Tokens;
3712+
EXPECT_TOKEN(Tokens[3], tok::identifier, TT_Unknown); // Not tok::kw_new
3713+
EXPECT_TOKEN(Tokens[4], tok::amp, TT_BinaryOperator);
3714+
EXPECT_TOKEN(Tokens[3], tok::identifier, TT_Unknown); // Not TT_StartOfName
3715+
}
3716+
37083717
TEST_F(TokenAnnotatorTest, FunctionTryBlock) {
37093718
auto Tokens =
37103719
annotate("Foo::Foo(int x, int y) try\n"

0 commit comments

Comments
 (0)