[clang-format] Don't use PPIndentWidth inside multi-line macros
Differential Revision: https://reviews.llvm.org/D137181
This commit is contained in:
@@ -5095,8 +5095,9 @@ bool TokenAnnotator::canBreakBefore(const AnnotatedLine &Line,
|
||||
}
|
||||
|
||||
void TokenAnnotator::printDebugInfo(const AnnotatedLine &Line) const {
|
||||
llvm::errs() << "AnnotatedTokens(L=" << Line.Level << ", T=" << Line.Type
|
||||
<< ", C=" << Line.IsContinuation << "):\n";
|
||||
llvm::errs() << "AnnotatedTokens(L=" << Line.Level << ", P=" << Line.PPLevel
|
||||
<< ", T=" << Line.Type << ", C=" << Line.IsContinuation
|
||||
<< "):\n";
|
||||
const FormatToken *Tok = Line.First;
|
||||
while (Tok) {
|
||||
llvm::errs() << " M=" << Tok->MustBreakBefore
|
||||
|
||||
@@ -38,6 +38,7 @@ class AnnotatedLine {
|
||||
public:
|
||||
AnnotatedLine(const UnwrappedLine &Line)
|
||||
: First(Line.Tokens.front().Tok), Level(Line.Level),
|
||||
PPLevel(Line.PPLevel),
|
||||
MatchingOpeningBlockLineIndex(Line.MatchingOpeningBlockLineIndex),
|
||||
MatchingClosingBlockLineIndex(Line.MatchingClosingBlockLineIndex),
|
||||
InPPDirective(Line.InPPDirective),
|
||||
@@ -129,6 +130,7 @@ public:
|
||||
|
||||
LineType Type;
|
||||
unsigned Level;
|
||||
unsigned PPLevel;
|
||||
size_t MatchingOpeningBlockLineIndex;
|
||||
size_t MatchingClosingBlockLineIndex;
|
||||
bool InPPDirective;
|
||||
|
||||
@@ -60,12 +60,17 @@ public:
|
||||
// Update the indent level cache size so that we can rely on it
|
||||
// having the right size in adjustToUnmodifiedline.
|
||||
skipLine(Line, /*UnknownIndent=*/true);
|
||||
if (Line.InPPDirective ||
|
||||
(Style.IndentPPDirectives == FormatStyle::PPDIS_BeforeHash &&
|
||||
Line.Type == LT_CommentAbovePPDirective)) {
|
||||
unsigned IndentWidth =
|
||||
if (Style.IndentPPDirectives != FormatStyle::PPDIS_None &&
|
||||
(Line.InPPDirective ||
|
||||
(Style.IndentPPDirectives == FormatStyle::PPDIS_BeforeHash &&
|
||||
Line.Type == LT_CommentAbovePPDirective))) {
|
||||
unsigned PPIndentWidth =
|
||||
(Style.PPIndentWidth >= 0) ? Style.PPIndentWidth : Style.IndentWidth;
|
||||
Indent = Line.Level * IndentWidth + AdditionalIndent;
|
||||
Indent = Line.InMacroBody
|
||||
? Line.PPLevel * PPIndentWidth +
|
||||
(Line.Level - Line.PPLevel) * Style.IndentWidth
|
||||
: Line.Level * PPIndentWidth;
|
||||
Indent += AdditionalIndent;
|
||||
} else {
|
||||
Indent = getIndent(Line.Level);
|
||||
}
|
||||
|
||||
@@ -197,6 +197,7 @@ public:
|
||||
PreBlockLine = std::move(Parser.Line);
|
||||
Parser.Line = std::make_unique<UnwrappedLine>();
|
||||
Parser.Line->Level = PreBlockLine->Level;
|
||||
Parser.Line->PPLevel = PreBlockLine->PPLevel;
|
||||
Parser.Line->InPPDirective = PreBlockLine->InPPDirective;
|
||||
Parser.Line->InMacroBody = PreBlockLine->InMacroBody;
|
||||
}
|
||||
@@ -833,6 +834,9 @@ bool UnwrappedLineParser::mightFitOnOneLine(
|
||||
delete SavedToken.Tok;
|
||||
}
|
||||
|
||||
// If these change PPLevel needs to be used for get correct indentation.
|
||||
assert(!Line.InMacroBody);
|
||||
assert(!Line.InPPDirective);
|
||||
return Line.Level * Style.IndentWidth + Length <= ColumnLimit;
|
||||
}
|
||||
|
||||
@@ -1270,6 +1274,9 @@ void UnwrappedLineParser::parsePPDefine() {
|
||||
Line->Level += PPBranchLevel + 1;
|
||||
addUnwrappedLine();
|
||||
++Line->Level;
|
||||
|
||||
Line->PPLevel = PPBranchLevel + (IncludeGuard == IG_Defined ? 0 : 1);
|
||||
assert((int)Line->PPLevel >= 0);
|
||||
Line->InMacroBody = true;
|
||||
|
||||
// Errors during a preprocessor directive can only affect the layout of the
|
||||
|
||||
@@ -44,6 +44,10 @@ struct UnwrappedLine {
|
||||
/// The indent level of the \c UnwrappedLine.
|
||||
unsigned Level;
|
||||
|
||||
/// The \c PPBranchLevel (adjusted for header guards) if this line is a
|
||||
/// \c InMacroBody line, and 0 otherwise.
|
||||
unsigned PPLevel;
|
||||
|
||||
/// Whether this \c UnwrappedLine is part of a preprocessor directive.
|
||||
bool InPPDirective;
|
||||
/// Whether this \c UnwrappedLine is part of a pramga directive.
|
||||
@@ -357,7 +361,7 @@ struct UnwrappedLineNode {
|
||||
};
|
||||
|
||||
inline UnwrappedLine::UnwrappedLine()
|
||||
: Level(0), InPPDirective(false), InPragmaDirective(false),
|
||||
: Level(0), PPLevel(0), InPPDirective(false), InPragmaDirective(false),
|
||||
InMacroBody(false), MustBeDeclaration(false),
|
||||
MatchingOpeningBlockLineIndex(kInvalidIndex) {}
|
||||
|
||||
|
||||
@@ -5059,6 +5059,213 @@ TEST_F(FormatTest, IndentsPPDirectiveWithPPIndentWidth) {
|
||||
" int y = 0;\n"
|
||||
"}",
|
||||
style);
|
||||
|
||||
style.IndentPPDirectives = FormatStyle::PPDIS_None;
|
||||
verifyFormat("#ifdef foo\n"
|
||||
"#define bar() \\\n"
|
||||
" if (A) { \\\n"
|
||||
" B(); \\\n"
|
||||
" } \\\n"
|
||||
" C();\n"
|
||||
"#endif",
|
||||
style);
|
||||
verifyFormat("if (emacs) {\n"
|
||||
"#ifdef is\n"
|
||||
"#define lit \\\n"
|
||||
" if (af) { \\\n"
|
||||
" return duh(); \\\n"
|
||||
" }\n"
|
||||
"#endif\n"
|
||||
"}",
|
||||
style);
|
||||
verifyFormat("#if abc\n"
|
||||
"#ifdef foo\n"
|
||||
"#define bar() \\\n"
|
||||
" if (A) { \\\n"
|
||||
" if (B) { \\\n"
|
||||
" C(); \\\n"
|
||||
" } \\\n"
|
||||
" } \\\n"
|
||||
" D();\n"
|
||||
"#endif\n"
|
||||
"#endif",
|
||||
style);
|
||||
verifyFormat("#ifndef foo\n"
|
||||
"#define foo\n"
|
||||
"if (emacs) {\n"
|
||||
"#ifdef is\n"
|
||||
"#define lit \\\n"
|
||||
" if (af) { \\\n"
|
||||
" return duh(); \\\n"
|
||||
" }\n"
|
||||
"#endif\n"
|
||||
"}\n"
|
||||
"#endif",
|
||||
style);
|
||||
verifyFormat("#if 1\n"
|
||||
"#define X \\\n"
|
||||
" { \\\n"
|
||||
" x; \\\n"
|
||||
" x; \\\n"
|
||||
" }\n"
|
||||
"#endif",
|
||||
style);
|
||||
verifyFormat("#define X \\\n"
|
||||
" { \\\n"
|
||||
" x; \\\n"
|
||||
" x; \\\n"
|
||||
" }",
|
||||
style);
|
||||
|
||||
style.PPIndentWidth = 2;
|
||||
verifyFormat("#ifdef foo\n"
|
||||
"#define bar() \\\n"
|
||||
" if (A) { \\\n"
|
||||
" B(); \\\n"
|
||||
" } \\\n"
|
||||
" C();\n"
|
||||
"#endif",
|
||||
style);
|
||||
style.IndentWidth = 8;
|
||||
verifyFormat("#ifdef foo\n"
|
||||
"#define bar() \\\n"
|
||||
" if (A) { \\\n"
|
||||
" B(); \\\n"
|
||||
" } \\\n"
|
||||
" C();\n"
|
||||
"#endif",
|
||||
style);
|
||||
|
||||
style.IndentWidth = 1;
|
||||
style.PPIndentWidth = 4;
|
||||
verifyFormat("#if 1\n"
|
||||
"#define X \\\n"
|
||||
" { \\\n"
|
||||
" x; \\\n"
|
||||
" x; \\\n"
|
||||
" }\n"
|
||||
"#endif",
|
||||
style);
|
||||
verifyFormat("#define X \\\n"
|
||||
" { \\\n"
|
||||
" x; \\\n"
|
||||
" x; \\\n"
|
||||
" }",
|
||||
style);
|
||||
|
||||
style.IndentWidth = 4;
|
||||
style.PPIndentWidth = 1;
|
||||
style.IndentPPDirectives = FormatStyle::PPDIS_AfterHash;
|
||||
verifyFormat("#ifdef foo\n"
|
||||
"# define bar() \\\n"
|
||||
" if (A) { \\\n"
|
||||
" B(); \\\n"
|
||||
" } \\\n"
|
||||
" C();\n"
|
||||
"#endif",
|
||||
style);
|
||||
verifyFormat("#if abc\n"
|
||||
"# ifdef foo\n"
|
||||
"# define bar() \\\n"
|
||||
" if (A) { \\\n"
|
||||
" if (B) { \\\n"
|
||||
" C(); \\\n"
|
||||
" } \\\n"
|
||||
" } \\\n"
|
||||
" D();\n"
|
||||
"# endif\n"
|
||||
"#endif",
|
||||
style);
|
||||
verifyFormat("#ifndef foo\n"
|
||||
"#define foo\n"
|
||||
"if (emacs) {\n"
|
||||
"#ifdef is\n"
|
||||
"# define lit \\\n"
|
||||
" if (af) { \\\n"
|
||||
" return duh(); \\\n"
|
||||
" }\n"
|
||||
"#endif\n"
|
||||
"}\n"
|
||||
"#endif",
|
||||
style);
|
||||
verifyFormat("#define X \\\n"
|
||||
" { \\\n"
|
||||
" x; \\\n"
|
||||
" x; \\\n"
|
||||
" }",
|
||||
style);
|
||||
|
||||
style.PPIndentWidth = 2;
|
||||
style.IndentWidth = 8;
|
||||
verifyFormat("#ifdef foo\n"
|
||||
"# define bar() \\\n"
|
||||
" if (A) { \\\n"
|
||||
" B(); \\\n"
|
||||
" } \\\n"
|
||||
" C();\n"
|
||||
"#endif",
|
||||
style);
|
||||
|
||||
style.PPIndentWidth = 4;
|
||||
style.IndentWidth = 1;
|
||||
verifyFormat("#define X \\\n"
|
||||
" { \\\n"
|
||||
" x; \\\n"
|
||||
" x; \\\n"
|
||||
" }",
|
||||
style);
|
||||
|
||||
style.IndentWidth = 4;
|
||||
style.PPIndentWidth = 1;
|
||||
style.IndentPPDirectives = FormatStyle::PPDIS_BeforeHash;
|
||||
verifyFormat("if (emacs) {\n"
|
||||
"#ifdef is\n"
|
||||
" #define lit \\\n"
|
||||
" if (af) { \\\n"
|
||||
" return duh(); \\\n"
|
||||
" }\n"
|
||||
"#endif\n"
|
||||
"}",
|
||||
style);
|
||||
verifyFormat("#if abc\n"
|
||||
" #ifdef foo\n"
|
||||
" #define bar() \\\n"
|
||||
" if (A) { \\\n"
|
||||
" B(); \\\n"
|
||||
" } \\\n"
|
||||
" C();\n"
|
||||
" #endif\n"
|
||||
"#endif",
|
||||
style);
|
||||
verifyFormat("#if 1\n"
|
||||
" #define X \\\n"
|
||||
" { \\\n"
|
||||
" x; \\\n"
|
||||
" x; \\\n"
|
||||
" }\n"
|
||||
"#endif",
|
||||
style);
|
||||
|
||||
style.PPIndentWidth = 2;
|
||||
verifyFormat("#ifdef foo\n"
|
||||
" #define bar() \\\n"
|
||||
" if (A) { \\\n"
|
||||
" B(); \\\n"
|
||||
" } \\\n"
|
||||
" C();\n"
|
||||
"#endif",
|
||||
style);
|
||||
|
||||
style.PPIndentWidth = 4;
|
||||
style.IndentWidth = 1;
|
||||
verifyFormat("#if 1\n"
|
||||
" #define X \\\n"
|
||||
" { \\\n"
|
||||
" x; \\\n"
|
||||
" x; \\\n"
|
||||
" }\n"
|
||||
"#endif",
|
||||
style);
|
||||
}
|
||||
|
||||
TEST_F(FormatTest, IndentsPPDirectiveInReducedSpace) {
|
||||
|
||||
Reference in New Issue
Block a user