Skip to content

Commit f438cb7

Browse files
committed
clang-format: Fix corner case for string splitting ..
.. in conjunction with Style.AlwaysBreakBeforeMultilineStrings. Also, simplify the implementation by handling newly split strings and already split strings by the same code. llvm-svn: 189102
1 parent 377496b commit f438cb7

File tree

3 files changed

+31
-12
lines changed

3 files changed

+31
-12
lines changed

clang/lib/Format/ContinuationIndenter.cpp

Lines changed: 18 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -116,12 +116,9 @@ bool ContinuationIndenter::mustBreak(const LineState &State) {
116116
!Current.isOneOf(tok::r_paren, tok::r_brace))
117117
return true;
118118
if (Style.AlwaysBreakBeforeMultilineStrings &&
119-
State.Column > State.Stack.back().Indent &&
120-
Current.is(tok::string_literal) && Previous.isNot(tok::lessless) &&
121-
Previous.Type != TT_InlineASMColon &&
122-
((Current.getNextNonComment() &&
123-
Current.getNextNonComment()->is(tok::string_literal)) ||
124-
(Current.TokenText.find("\\\n") != StringRef::npos)))
119+
State.Column > State.Stack.back().Indent && // Breaking saves columns.
120+
Previous.isNot(tok::lessless) && Previous.Type != TT_InlineASMColon &&
121+
NextIsMultilineString(State))
125122
return true;
126123

127124
if (!Style.BreakBeforeBinaryOperators) {
@@ -547,13 +544,8 @@ unsigned ContinuationIndenter::moveStateToNextToken(LineState &State,
547544
}
548545

549546
State.Column += Current.CodePointCount;
550-
551547
State.NextToken = State.NextToken->Next;
552-
553-
unsigned Penalty = 0;
554-
if (Newline || !Style.AlwaysBreakBeforeMultilineStrings ||
555-
Current.isNot(tok::string_literal) || !Current.CanBreakBefore)
556-
Penalty += breakProtrudingToken(Current, State, DryRun);
548+
unsigned Penalty = breakProtrudingToken(Current, State, DryRun);
557549

558550
// If the previous has a special role, let it consume tokens as appropriate.
559551
// It is necessary to start at the previous token for the only implemented
@@ -688,5 +680,19 @@ unsigned ContinuationIndenter::getColumnLimit() const {
688680
return Style.ColumnLimit - (Line.InPPDirective ? 2 : 0);
689681
}
690682

683+
bool ContinuationIndenter::NextIsMultilineString(const LineState &State) {
684+
const FormatToken &Current = *State.NextToken;
685+
if (!Current.is(tok::string_literal))
686+
return false;
687+
if (Current.getNextNonComment() &&
688+
Current.getNextNonComment()->is(tok::string_literal))
689+
return true; // Implicit concatenation.
690+
if (State.Column + Current.CodePointCount + Current.UnbreakableTailLength >
691+
Style.ColumnLimit)
692+
return true; // String will be split.
693+
// String literal might have escaped newlines.
694+
return Current.TokenText.find("\\\n") != StringRef::npos;
695+
}
696+
691697
} // namespace format
692698
} // namespace clang

clang/lib/Format/ContinuationIndenter.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,13 @@ class ContinuationIndenter {
8484
unsigned breakProtrudingToken(const FormatToken &Current, LineState &State,
8585
bool DryRun);
8686

87+
/// \brief Returns \c true if the next token starts a multiline string
88+
/// literal.
89+
///
90+
/// This includes implicitly concatenated strings, strings that will be broken
91+
/// by clang-format and string literals with escaped newlines.
92+
bool NextIsMultilineString(const LineState &State);
93+
8794
FormatStyle Style;
8895
SourceManager &SourceMgr;
8996
const AnnotatedLine &Line;

clang/unittests/Format/FormatTest.cpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5265,6 +5265,12 @@ TEST_F(FormatTest, BreakStringLiterals) {
52655265
format("llvm::outs() << "
52665266
"\"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa aaaaaaaaaaaaaaaaaa"
52675267
"aaaaaaaaaaaaaaaaaaa\";"));
5268+
EXPECT_EQ("ffff(\n"
5269+
" {\"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa \"\n"
5270+
" \"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\"});",
5271+
format("ffff({\"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa "
5272+
"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\"});",
5273+
getGoogleStyle()));
52685274

52695275
FormatStyle AlignLeft = getLLVMStyleWithColumns(12);
52705276
AlignLeft.AlignEscapedNewlinesLeft = true;

0 commit comments

Comments
 (0)