llvm-project
2848 строк · 122.3 Кб
1//===--- ContinuationIndenter.cpp - Format C++ code -----------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8///
9/// \file
10/// This file implements the continuation indenter.
11///
12//===----------------------------------------------------------------------===//
13
14#include "ContinuationIndenter.h"15#include "BreakableToken.h"16#include "FormatInternal.h"17#include "FormatToken.h"18#include "WhitespaceManager.h"19#include "clang/Basic/OperatorPrecedence.h"20#include "clang/Basic/SourceManager.h"21#include "clang/Basic/TokenKinds.h"22#include "clang/Format/Format.h"23#include "llvm/ADT/StringSet.h"24#include "llvm/Support/Debug.h"25#include <optional>26
27#define DEBUG_TYPE "format-indenter"28
29namespace clang {30namespace format {31
32// Returns true if a TT_SelectorName should be indented when wrapped,
33// false otherwise.
34static bool shouldIndentWrappedSelectorName(const FormatStyle &Style,35LineType LineType) {36return Style.IndentWrappedFunctionNames || LineType == LT_ObjCMethodDecl;37}
38
39// Returns true if a binary operator following \p Tok should be unindented when
40// the style permits it.
41static bool shouldUnindentNextOperator(const FormatToken &Tok) {42const FormatToken *Previous = Tok.getPreviousNonComment();43return Previous && (Previous->getPrecedence() == prec::Assignment ||44Previous->isOneOf(tok::kw_return, TT_RequiresClause));45}
46
47// Returns the length of everything up to the first possible line break after
48// the ), ], } or > matching \c Tok.
49static unsigned getLengthToMatchingParen(const FormatToken &Tok,50ArrayRef<ParenState> Stack) {51// Normally whether or not a break before T is possible is calculated and52// stored in T.CanBreakBefore. Braces, array initializers and text proto53// messages like `key: < ... >` are an exception: a break is possible54// before a closing brace R if a break was inserted after the corresponding55// opening brace. The information about whether or not a break is needed56// before a closing brace R is stored in the ParenState field57// S.BreakBeforeClosingBrace where S is the state that R closes.58//59// In order to decide whether there can be a break before encountered right60// braces, this implementation iterates over the sequence of tokens and over61// the paren stack in lockstep, keeping track of the stack level which visited62// right braces correspond to in MatchingStackIndex.63//64// For example, consider:65// L. <- line number66// 1. {67// 2. {1},68// 3. {2},69// 4. {{3}}}70// ^ where we call this method with this token.71// The paren stack at this point contains 3 brace levels:72// 0. { at line 1, BreakBeforeClosingBrace: true73// 1. first { at line 4, BreakBeforeClosingBrace: false74// 2. second { at line 4, BreakBeforeClosingBrace: false,75// where there might be fake parens levels in-between these levels.76// The algorithm will start at the first } on line 4, which is the matching77// brace of the initial left brace and at level 2 of the stack. Then,78// examining BreakBeforeClosingBrace: false at level 2, it will continue to79// the second } on line 4, and will traverse the stack downwards until it80// finds the matching { on level 1. Then, examining BreakBeforeClosingBrace:81// false at level 1, it will continue to the third } on line 4 and will82// traverse the stack downwards until it finds the matching { on level 0.83// Then, examining BreakBeforeClosingBrace: true at level 0, the algorithm84// will stop and will use the second } on line 4 to determine the length to85// return, as in this example the range will include the tokens: {3}}86//87// The algorithm will only traverse the stack if it encounters braces, array88// initializer squares or text proto angle brackets.89if (!Tok.MatchingParen)90return 0;91FormatToken *End = Tok.MatchingParen;92// Maintains a stack level corresponding to the current End token.93int MatchingStackIndex = Stack.size() - 1;94// Traverses the stack downwards, looking for the level to which LBrace95// corresponds. Returns either a pointer to the matching level or nullptr if96// LParen is not found in the initial portion of the stack up to97// MatchingStackIndex.98auto FindParenState = [&](const FormatToken *LBrace) -> const ParenState * {99while (MatchingStackIndex >= 0 && Stack[MatchingStackIndex].Tok != LBrace)100--MatchingStackIndex;101return MatchingStackIndex >= 0 ? &Stack[MatchingStackIndex] : nullptr;102};103for (; End->Next; End = End->Next) {104if (End->Next->CanBreakBefore)105break;106if (!End->Next->closesScope())107continue;108if (End->Next->MatchingParen &&109End->Next->MatchingParen->isOneOf(110tok::l_brace, TT_ArrayInitializerLSquare, tok::less)) {111const ParenState *State = FindParenState(End->Next->MatchingParen);112if (State && State->BreakBeforeClosingBrace)113break;114}115}116return End->TotalLength - Tok.TotalLength + 1;117}
118
119static unsigned getLengthToNextOperator(const FormatToken &Tok) {120if (!Tok.NextOperator)121return 0;122return Tok.NextOperator->TotalLength - Tok.TotalLength;123}
124
125// Returns \c true if \c Tok is the "." or "->" of a call and starts the next
126// segment of a builder type call.
127static bool startsSegmentOfBuilderTypeCall(const FormatToken &Tok) {128return Tok.isMemberAccess() && Tok.Previous && Tok.Previous->closesScope();129}
130
131// Returns \c true if \c Current starts a new parameter.
132static bool startsNextParameter(const FormatToken &Current,133const FormatStyle &Style) {134const FormatToken &Previous = *Current.Previous;135if (Current.is(TT_CtorInitializerComma) &&136Style.BreakConstructorInitializers == FormatStyle::BCIS_BeforeComma) {137return true;138}139if (Style.Language == FormatStyle::LK_Proto && Current.is(TT_SelectorName))140return true;141return Previous.is(tok::comma) && !Current.isTrailingComment() &&142((Previous.isNot(TT_CtorInitializerComma) ||143Style.BreakConstructorInitializers !=144FormatStyle::BCIS_BeforeComma) &&145(Previous.isNot(TT_InheritanceComma) ||146Style.BreakInheritanceList != FormatStyle::BILS_BeforeComma));147}
148
149static bool opensProtoMessageField(const FormatToken &LessTok,150const FormatStyle &Style) {151if (LessTok.isNot(tok::less))152return false;153return Style.Language == FormatStyle::LK_TextProto ||154(Style.Language == FormatStyle::LK_Proto &&155(LessTok.NestingLevel > 0 ||156(LessTok.Previous && LessTok.Previous->is(tok::equal))));157}
158
159// Returns the delimiter of a raw string literal, or std::nullopt if TokenText
160// is not the text of a raw string literal. The delimiter could be the empty
161// string. For example, the delimiter of R"deli(cont)deli" is deli.
162static std::optional<StringRef> getRawStringDelimiter(StringRef TokenText) {163if (TokenText.size() < 5 // The smallest raw string possible is 'R"()"'.164|| !TokenText.starts_with("R\"") || !TokenText.ends_with("\"")) {165return std::nullopt;166}167
168// A raw string starts with 'R"<delimiter>(' and delimiter is ascii and has169// size at most 16 by the standard, so the first '(' must be among the first170// 19 bytes.171size_t LParenPos = TokenText.substr(0, 19).find_first_of('(');172if (LParenPos == StringRef::npos)173return std::nullopt;174StringRef Delimiter = TokenText.substr(2, LParenPos - 2);175
176// Check that the string ends in ')Delimiter"'.177size_t RParenPos = TokenText.size() - Delimiter.size() - 2;178if (TokenText[RParenPos] != ')')179return std::nullopt;180if (!TokenText.substr(RParenPos + 1).starts_with(Delimiter))181return std::nullopt;182return Delimiter;183}
184
185// Returns the canonical delimiter for \p Language, or the empty string if no
186// canonical delimiter is specified.
187static StringRef188getCanonicalRawStringDelimiter(const FormatStyle &Style,189FormatStyle::LanguageKind Language) {190for (const auto &Format : Style.RawStringFormats)191if (Format.Language == Language)192return StringRef(Format.CanonicalDelimiter);193return "";194}
195
196RawStringFormatStyleManager::RawStringFormatStyleManager(197const FormatStyle &CodeStyle) {198for (const auto &RawStringFormat : CodeStyle.RawStringFormats) {199std::optional<FormatStyle> LanguageStyle =200CodeStyle.GetLanguageStyle(RawStringFormat.Language);201if (!LanguageStyle) {202FormatStyle PredefinedStyle;203if (!getPredefinedStyle(RawStringFormat.BasedOnStyle,204RawStringFormat.Language, &PredefinedStyle)) {205PredefinedStyle = getLLVMStyle();206PredefinedStyle.Language = RawStringFormat.Language;207}208LanguageStyle = PredefinedStyle;209}210LanguageStyle->ColumnLimit = CodeStyle.ColumnLimit;211for (StringRef Delimiter : RawStringFormat.Delimiters)212DelimiterStyle.insert({Delimiter, *LanguageStyle});213for (StringRef EnclosingFunction : RawStringFormat.EnclosingFunctions)214EnclosingFunctionStyle.insert({EnclosingFunction, *LanguageStyle});215}216}
217
218std::optional<FormatStyle>219RawStringFormatStyleManager::getDelimiterStyle(StringRef Delimiter) const {220auto It = DelimiterStyle.find(Delimiter);221if (It == DelimiterStyle.end())222return std::nullopt;223return It->second;224}
225
226std::optional<FormatStyle>227RawStringFormatStyleManager::getEnclosingFunctionStyle(228StringRef EnclosingFunction) const {229auto It = EnclosingFunctionStyle.find(EnclosingFunction);230if (It == EnclosingFunctionStyle.end())231return std::nullopt;232return It->second;233}
234
235ContinuationIndenter::ContinuationIndenter(const FormatStyle &Style,236const AdditionalKeywords &Keywords,237const SourceManager &SourceMgr,238WhitespaceManager &Whitespaces,239encoding::Encoding Encoding,240bool BinPackInconclusiveFunctions)241: Style(Style), Keywords(Keywords), SourceMgr(SourceMgr),242Whitespaces(Whitespaces), Encoding(Encoding),243BinPackInconclusiveFunctions(BinPackInconclusiveFunctions),244CommentPragmasRegex(Style.CommentPragmas), RawStringFormats(Style) {}245
246LineState ContinuationIndenter::getInitialState(unsigned FirstIndent,247unsigned FirstStartColumn,248const AnnotatedLine *Line,249bool DryRun) {250LineState State;251State.FirstIndent = FirstIndent;252if (FirstStartColumn && Line->First->NewlinesBefore == 0)253State.Column = FirstStartColumn;254else255State.Column = FirstIndent;256// With preprocessor directive indentation, the line starts on column 0257// since it's indented after the hash, but FirstIndent is set to the258// preprocessor indent.259if (Style.IndentPPDirectives == FormatStyle::PPDIS_AfterHash &&260(Line->Type == LT_PreprocessorDirective ||261Line->Type == LT_ImportStatement)) {262State.Column = 0;263}264State.Line = Line;265State.NextToken = Line->First;266State.Stack.push_back(ParenState(/*Tok=*/nullptr, FirstIndent, FirstIndent,267/*AvoidBinPacking=*/false,268/*NoLineBreak=*/false));269State.NoContinuation = false;270State.StartOfStringLiteral = 0;271State.NoLineBreak = false;272State.StartOfLineLevel = 0;273State.LowestLevelOnLine = 0;274State.IgnoreStackForComparison = false;275
276if (Style.Language == FormatStyle::LK_TextProto) {277// We need this in order to deal with the bin packing of text fields at278// global scope.279auto &CurrentState = State.Stack.back();280CurrentState.AvoidBinPacking = true;281CurrentState.BreakBeforeParameter = true;282CurrentState.AlignColons = false;283}284
285// The first token has already been indented and thus consumed.286moveStateToNextToken(State, DryRun, /*Newline=*/false);287return State;288}
289
290bool ContinuationIndenter::canBreak(const LineState &State) {291const FormatToken &Current = *State.NextToken;292const FormatToken &Previous = *Current.Previous;293const auto &CurrentState = State.Stack.back();294assert(&Previous == Current.Previous);295if (!Current.CanBreakBefore && !(CurrentState.BreakBeforeClosingBrace &&296Current.closesBlockOrBlockTypeList(Style))) {297return false;298}299// The opening "{" of a braced list has to be on the same line as the first300// element if it is nested in another braced init list or function call.301if (!Current.MustBreakBefore && Previous.is(tok::l_brace) &&302Previous.isNot(TT_DictLiteral) && Previous.is(BK_BracedInit) &&303Previous.Previous &&304Previous.Previous->isOneOf(tok::l_brace, tok::l_paren, tok::comma)) {305return false;306}307// This prevents breaks like:308// ...309// SomeParameter, OtherParameter).DoSomething(310// ...311// As they hide "DoSomething" and are generally bad for readability.312if (Previous.opensScope() && Previous.isNot(tok::l_brace) &&313State.LowestLevelOnLine < State.StartOfLineLevel &&314State.LowestLevelOnLine < Current.NestingLevel) {315return false;316}317if (Current.isMemberAccess() && CurrentState.ContainsUnwrappedBuilder)318return false;319
320// Don't create a 'hanging' indent if there are multiple blocks in a single321// statement and we are aligning lambda blocks to their signatures.322if (Previous.is(tok::l_brace) && State.Stack.size() > 1 &&323State.Stack[State.Stack.size() - 2].NestedBlockInlined &&324State.Stack[State.Stack.size() - 2].HasMultipleNestedBlocks &&325Style.LambdaBodyIndentation == FormatStyle::LBI_Signature) {326return false;327}328
329// Don't break after very short return types (e.g. "void") as that is often330// unexpected.331if (Current.is(TT_FunctionDeclarationName)) {332if (Style.BreakAfterReturnType == FormatStyle::RTBS_None &&333State.Column < 6) {334return false;335}336
337if (Style.BreakAfterReturnType == FormatStyle::RTBS_ExceptShortType) {338assert(State.Column >= State.FirstIndent);339if (State.Column - State.FirstIndent < 6)340return false;341}342}343
344// If binary operators are moved to the next line (including commas for some345// styles of constructor initializers), that's always ok.346if (!Current.isOneOf(TT_BinaryOperator, tok::comma) &&347// Allow breaking opening brace of lambdas (when passed as function348// arguments) to a new line when BeforeLambdaBody brace wrapping is349// enabled.350(!Style.BraceWrapping.BeforeLambdaBody ||351Current.isNot(TT_LambdaLBrace)) &&352CurrentState.NoLineBreakInOperand) {353return false;354}355
356if (Previous.is(tok::l_square) && Previous.is(TT_ObjCMethodExpr))357return false;358
359if (Current.is(TT_ConditionalExpr) && Previous.is(tok::r_paren) &&360Previous.MatchingParen && Previous.MatchingParen->Previous &&361Previous.MatchingParen->Previous->MatchingParen &&362Previous.MatchingParen->Previous->MatchingParen->is(TT_LambdaLBrace)) {363// We have a lambda within a conditional expression, allow breaking here.364assert(Previous.MatchingParen->Previous->is(tok::r_brace));365return true;366}367
368return !State.NoLineBreak && !CurrentState.NoLineBreak;369}
370
371bool ContinuationIndenter::mustBreak(const LineState &State) {372const FormatToken &Current = *State.NextToken;373const FormatToken &Previous = *Current.Previous;374const auto &CurrentState = State.Stack.back();375if (Style.BraceWrapping.BeforeLambdaBody && Current.CanBreakBefore &&376Current.is(TT_LambdaLBrace) && Previous.isNot(TT_LineComment)) {377auto LambdaBodyLength = getLengthToMatchingParen(Current, State.Stack);378return LambdaBodyLength > getColumnLimit(State);379}380if (Current.MustBreakBefore ||381(Current.is(TT_InlineASMColon) &&382(Style.BreakBeforeInlineASMColon == FormatStyle::BBIAS_Always ||383(Style.BreakBeforeInlineASMColon == FormatStyle::BBIAS_OnlyMultiline &&384Style.ColumnLimit > 0)))) {385return true;386}387if (CurrentState.BreakBeforeClosingBrace &&388(Current.closesBlockOrBlockTypeList(Style) ||389(Current.is(tok::r_brace) &&390Current.isBlockIndentedInitRBrace(Style)))) {391return true;392}393if (CurrentState.BreakBeforeClosingParen && Current.is(tok::r_paren))394return true;395if (Style.Language == FormatStyle::LK_ObjC &&396Style.ObjCBreakBeforeNestedBlockParam &&397Current.ObjCSelectorNameParts > 1 &&398Current.startsSequence(TT_SelectorName, tok::colon, tok::caret)) {399return true;400}401// Avoid producing inconsistent states by requiring breaks where they are not402// permitted for C# generic type constraints.403if (CurrentState.IsCSharpGenericTypeConstraint &&404Previous.isNot(TT_CSharpGenericTypeConstraintComma)) {405return false;406}407if ((startsNextParameter(Current, Style) || Previous.is(tok::semi) ||408(Previous.is(TT_TemplateCloser) && Current.is(TT_StartOfName) &&409State.Line->First->isNot(TT_AttributeSquare) && Style.isCpp() &&410// FIXME: This is a temporary workaround for the case where clang-format411// sets BreakBeforeParameter to avoid bin packing and this creates a412// completely unnecessary line break after a template type that isn't413// line-wrapped.414(Previous.NestingLevel == 1 || Style.BinPackParameters)) ||415(Style.BreakBeforeTernaryOperators && Current.is(TT_ConditionalExpr) &&416Previous.isNot(tok::question)) ||417(!Style.BreakBeforeTernaryOperators &&418Previous.is(TT_ConditionalExpr))) &&419CurrentState.BreakBeforeParameter && !Current.isTrailingComment() &&420!Current.isOneOf(tok::r_paren, tok::r_brace)) {421return true;422}423if (CurrentState.IsChainedConditional &&424((Style.BreakBeforeTernaryOperators && Current.is(TT_ConditionalExpr) &&425Current.is(tok::colon)) ||426(!Style.BreakBeforeTernaryOperators && Previous.is(TT_ConditionalExpr) &&427Previous.is(tok::colon)))) {428return true;429}430if (((Previous.is(TT_DictLiteral) && Previous.is(tok::l_brace)) ||431(Previous.is(TT_ArrayInitializerLSquare) &&432Previous.ParameterCount > 1) ||433opensProtoMessageField(Previous, Style)) &&434Style.ColumnLimit > 0 &&435getLengthToMatchingParen(Previous, State.Stack) + State.Column - 1 >436getColumnLimit(State)) {437return true;438}439
440const FormatToken &BreakConstructorInitializersToken =441Style.BreakConstructorInitializers == FormatStyle::BCIS_AfterColon442? Previous443: Current;444if (BreakConstructorInitializersToken.is(TT_CtorInitializerColon) &&445(State.Column + State.Line->Last->TotalLength - Previous.TotalLength >446getColumnLimit(State) ||447CurrentState.BreakBeforeParameter) &&448(!Current.isTrailingComment() || Current.NewlinesBefore > 0) &&449(Style.AllowShortFunctionsOnASingleLine != FormatStyle::SFS_All ||450Style.BreakConstructorInitializers != FormatStyle::BCIS_BeforeColon ||451Style.ColumnLimit != 0)) {452return true;453}454
455if (Current.is(TT_ObjCMethodExpr) && Previous.isNot(TT_SelectorName) &&456State.Line->startsWith(TT_ObjCMethodSpecifier)) {457return true;458}459if (Current.is(TT_SelectorName) && Previous.isNot(tok::at) &&460CurrentState.ObjCSelectorNameFound && CurrentState.BreakBeforeParameter &&461(Style.ObjCBreakBeforeNestedBlockParam ||462!Current.startsSequence(TT_SelectorName, tok::colon, tok::caret))) {463return true;464}465
466unsigned NewLineColumn = getNewLineColumn(State);467if (Current.isMemberAccess() && Style.ColumnLimit != 0 &&468State.Column + getLengthToNextOperator(Current) > Style.ColumnLimit &&469(State.Column > NewLineColumn ||470Current.NestingLevel < State.StartOfLineLevel)) {471return true;472}473
474if (startsSegmentOfBuilderTypeCall(Current) &&475(CurrentState.CallContinuation != 0 ||476CurrentState.BreakBeforeParameter) &&477// JavaScript is treated different here as there is a frequent pattern:478// SomeFunction(function() {479// ...480// }.bind(...));481// FIXME: We should find a more generic solution to this problem.482!(State.Column <= NewLineColumn && Style.isJavaScript()) &&483!(Previous.closesScopeAfterBlock() && State.Column <= NewLineColumn)) {484return true;485}486
487// If the template declaration spans multiple lines, force wrap before the488// function/class declaration.489if (Previous.ClosesTemplateDeclaration && CurrentState.BreakBeforeParameter &&490Current.CanBreakBefore) {491return true;492}493
494if (State.Line->First->isNot(tok::kw_enum) && State.Column <= NewLineColumn)495return false;496
497if (Style.AlwaysBreakBeforeMultilineStrings &&498(NewLineColumn == State.FirstIndent + Style.ContinuationIndentWidth ||499Previous.is(tok::comma) || Current.NestingLevel < 2) &&500!Previous.isOneOf(tok::kw_return, tok::lessless, tok::at,501Keywords.kw_dollar) &&502!Previous.isOneOf(TT_InlineASMColon, TT_ConditionalExpr) &&503nextIsMultilineString(State)) {504return true;505}506
507// Using CanBreakBefore here and below takes care of the decision whether the508// current style uses wrapping before or after operators for the given509// operator.510if (Previous.is(TT_BinaryOperator) && Current.CanBreakBefore) {511const auto PreviousPrecedence = Previous.getPrecedence();512if (PreviousPrecedence != prec::Assignment &&513CurrentState.BreakBeforeParameter && !Current.isTrailingComment()) {514const bool LHSIsBinaryExpr =515Previous.Previous && Previous.Previous->EndsBinaryExpression;516if (LHSIsBinaryExpr)517return true;518// If we need to break somewhere inside the LHS of a binary expression, we519// should also break after the operator. Otherwise, the formatting would520// hide the operator precedence, e.g. in:521// if (aaaaaaaaaaaaaa ==522// bbbbbbbbbbbbbb && c) {..523// For comparisons, we only apply this rule, if the LHS is a binary524// expression itself as otherwise, the line breaks seem superfluous.525// We need special cases for ">>" which we have split into two ">" while526// lexing in order to make template parsing easier.527const bool IsComparison =528(PreviousPrecedence == prec::Relational ||529PreviousPrecedence == prec::Equality ||530PreviousPrecedence == prec::Spaceship) &&531Previous.Previous &&532Previous.Previous->isNot(TT_BinaryOperator); // For >>.533if (!IsComparison)534return true;535}536} else if (Current.is(TT_BinaryOperator) && Current.CanBreakBefore &&537CurrentState.BreakBeforeParameter) {538return true;539}540
541// Same as above, but for the first "<<" operator.542if (Current.is(tok::lessless) && Current.isNot(TT_OverloadedOperator) &&543CurrentState.BreakBeforeParameter && CurrentState.FirstLessLess == 0) {544return true;545}546
547if (Current.NestingLevel == 0 && !Current.isTrailingComment()) {548// Always break after "template <...>"(*) and leading annotations. This is549// only for cases where the entire line does not fit on a single line as a550// different LineFormatter would be used otherwise.551// *: Except when another option interferes with that, like concepts.552if (Previous.ClosesTemplateDeclaration) {553if (Current.is(tok::kw_concept)) {554switch (Style.BreakBeforeConceptDeclarations) {555case FormatStyle::BBCDS_Allowed:556break;557case FormatStyle::BBCDS_Always:558return true;559case FormatStyle::BBCDS_Never:560return false;561}562}563if (Current.is(TT_RequiresClause)) {564switch (Style.RequiresClausePosition) {565case FormatStyle::RCPS_SingleLine:566case FormatStyle::RCPS_WithPreceding:567return false;568default:569return true;570}571}572return Style.BreakTemplateDeclarations != FormatStyle::BTDS_No &&573(Style.BreakTemplateDeclarations != FormatStyle::BTDS_Leave ||574Current.NewlinesBefore > 0);575}576if (Previous.is(TT_FunctionAnnotationRParen) &&577State.Line->Type != LT_PreprocessorDirective) {578return true;579}580if (Previous.is(TT_LeadingJavaAnnotation) && Current.isNot(tok::l_paren) &&581Current.isNot(TT_LeadingJavaAnnotation)) {582return true;583}584}585
586if (Style.isJavaScript() && Previous.is(tok::r_paren) &&587Previous.is(TT_JavaAnnotation)) {588// Break after the closing parenthesis of TypeScript decorators before589// functions, getters and setters.590static const llvm::StringSet<> BreakBeforeDecoratedTokens = {"get", "set",591"function"};592if (BreakBeforeDecoratedTokens.contains(Current.TokenText))593return true;594}595
596if (Current.is(TT_FunctionDeclarationName) &&597!State.Line->ReturnTypeWrapped &&598// Don't break before a C# function when no break after return type.599(!Style.isCSharp() ||600Style.BreakAfterReturnType > FormatStyle::RTBS_ExceptShortType) &&601// Don't always break between a JavaScript `function` and the function602// name.603!Style.isJavaScript() && Previous.isNot(tok::kw_template) &&604CurrentState.BreakBeforeParameter) {605return true;606}607
608// The following could be precomputed as they do not depend on the state.609// However, as they should take effect only if the UnwrappedLine does not fit610// into the ColumnLimit, they are checked here in the ContinuationIndenter.611if (Style.ColumnLimit != 0 && Previous.is(BK_Block) &&612Previous.is(tok::l_brace) &&613!Current.isOneOf(tok::r_brace, tok::comment)) {614return true;615}616
617if (Current.is(tok::lessless) &&618((Previous.is(tok::identifier) && Previous.TokenText == "endl") ||619(Previous.Tok.isLiteral() && (Previous.TokenText.ends_with("\\n\"") ||620Previous.TokenText == "\'\\n\'")))) {621return true;622}623
624if (Previous.is(TT_BlockComment) && Previous.IsMultiline)625return true;626
627if (State.NoContinuation)628return true;629
630return false;631}
632
633unsigned ContinuationIndenter::addTokenToState(LineState &State, bool Newline,634bool DryRun,635unsigned ExtraSpaces) {636const FormatToken &Current = *State.NextToken;637assert(State.NextToken->Previous);638const FormatToken &Previous = *State.NextToken->Previous;639
640assert(!State.Stack.empty());641State.NoContinuation = false;642
643if (Current.is(TT_ImplicitStringLiteral) &&644(!Previous.Tok.getIdentifierInfo() ||645Previous.Tok.getIdentifierInfo()->getPPKeywordID() ==646tok::pp_not_keyword)) {647unsigned EndColumn =648SourceMgr.getSpellingColumnNumber(Current.WhitespaceRange.getEnd());649if (Current.LastNewlineOffset != 0) {650// If there is a newline within this token, the final column will solely651// determined by the current end column.652State.Column = EndColumn;653} else {654unsigned StartColumn =655SourceMgr.getSpellingColumnNumber(Current.WhitespaceRange.getBegin());656assert(EndColumn >= StartColumn);657State.Column += EndColumn - StartColumn;658}659moveStateToNextToken(State, DryRun, /*Newline=*/false);660return 0;661}662
663unsigned Penalty = 0;664if (Newline)665Penalty = addTokenOnNewLine(State, DryRun);666else667addTokenOnCurrentLine(State, DryRun, ExtraSpaces);668
669return moveStateToNextToken(State, DryRun, Newline) + Penalty;670}
671
672void ContinuationIndenter::addTokenOnCurrentLine(LineState &State, bool DryRun,673unsigned ExtraSpaces) {674FormatToken &Current = *State.NextToken;675assert(State.NextToken->Previous);676const FormatToken &Previous = *State.NextToken->Previous;677auto &CurrentState = State.Stack.back();678
679bool DisallowLineBreaksOnThisLine =680Style.LambdaBodyIndentation == FormatStyle::LBI_Signature &&681Style.isCpp() && [&Current] {682// Deal with lambda arguments in C++. The aim here is to ensure that we683// don't over-indent lambda function bodies when lambdas are passed as684// arguments to function calls. We do this by ensuring that either all685// arguments (including any lambdas) go on the same line as the function686// call, or we break before the first argument.687const auto *Prev = Current.Previous;688if (!Prev)689return false;690// For example, `/*Newline=*/false`.691if (Prev->is(TT_BlockComment) && Current.SpacesRequiredBefore == 0)692return false;693const auto *PrevNonComment = Current.getPreviousNonComment();694if (!PrevNonComment || PrevNonComment->isNot(tok::l_paren))695return false;696if (Current.isOneOf(tok::comment, tok::l_paren, TT_LambdaLSquare))697return false;698auto BlockParameterCount = PrevNonComment->BlockParameterCount;699if (BlockParameterCount == 0)700return false;701
702// Multiple lambdas in the same function call.703if (BlockParameterCount > 1)704return true;705
706// A lambda followed by another arg.707if (!PrevNonComment->Role)708return false;709auto Comma = PrevNonComment->Role->lastComma();710if (!Comma)711return false;712auto Next = Comma->getNextNonComment();713return Next &&714!Next->isOneOf(TT_LambdaLSquare, tok::l_brace, tok::caret);715}();716
717if (DisallowLineBreaksOnThisLine)718State.NoLineBreak = true;719
720if (Current.is(tok::equal) &&721(State.Line->First->is(tok::kw_for) || Current.NestingLevel == 0) &&722CurrentState.VariablePos == 0 &&723(!Previous.Previous ||724Previous.Previous->isNot(TT_DesignatedInitializerPeriod))) {725CurrentState.VariablePos = State.Column;726// Move over * and & if they are bound to the variable name.727const FormatToken *Tok = &Previous;728while (Tok && CurrentState.VariablePos >= Tok->ColumnWidth) {729CurrentState.VariablePos -= Tok->ColumnWidth;730if (Tok->SpacesRequiredBefore != 0)731break;732Tok = Tok->Previous;733}734if (Previous.PartOfMultiVariableDeclStmt)735CurrentState.LastSpace = CurrentState.VariablePos;736}737
738unsigned Spaces = Current.SpacesRequiredBefore + ExtraSpaces;739
740// Indent preprocessor directives after the hash if required.741int PPColumnCorrection = 0;742if (Style.IndentPPDirectives == FormatStyle::PPDIS_AfterHash &&743Previous.is(tok::hash) && State.FirstIndent > 0 &&744&Previous == State.Line->First &&745(State.Line->Type == LT_PreprocessorDirective ||746State.Line->Type == LT_ImportStatement)) {747Spaces += State.FirstIndent;748
749// For preprocessor indent with tabs, State.Column will be 1 because of the750// hash. This causes second-level indents onward to have an extra space751// after the tabs. We avoid this misalignment by subtracting 1 from the752// column value passed to replaceWhitespace().753if (Style.UseTab != FormatStyle::UT_Never)754PPColumnCorrection = -1;755}756
757if (!DryRun) {758Whitespaces.replaceWhitespace(Current, /*Newlines=*/0, Spaces,759State.Column + Spaces + PPColumnCorrection,760/*IsAligned=*/false, State.Line->InMacroBody);761}762
763// If "BreakBeforeInheritanceComma" mode, don't break within the inheritance764// declaration unless there is multiple inheritance.765if (Style.BreakInheritanceList == FormatStyle::BILS_BeforeComma &&766Current.is(TT_InheritanceColon)) {767CurrentState.NoLineBreak = true;768}769if (Style.BreakInheritanceList == FormatStyle::BILS_AfterColon &&770Previous.is(TT_InheritanceColon)) {771CurrentState.NoLineBreak = true;772}773
774if (Current.is(TT_SelectorName) && !CurrentState.ObjCSelectorNameFound) {775unsigned MinIndent = std::max(776State.FirstIndent + Style.ContinuationIndentWidth, CurrentState.Indent);777unsigned FirstColonPos = State.Column + Spaces + Current.ColumnWidth;778if (Current.LongestObjCSelectorName == 0)779CurrentState.AlignColons = false;780else if (MinIndent + Current.LongestObjCSelectorName > FirstColonPos)781CurrentState.ColonPos = MinIndent + Current.LongestObjCSelectorName;782else783CurrentState.ColonPos = FirstColonPos;784}785
786// In "AlwaysBreak" or "BlockIndent" mode, enforce wrapping directly after the787// parenthesis by disallowing any further line breaks if there is no line788// break after the opening parenthesis. Don't break if it doesn't conserve789// columns.790auto IsOpeningBracket = [&](const FormatToken &Tok) {791auto IsStartOfBracedList = [&]() {792return Tok.is(tok::l_brace) && Tok.isNot(BK_Block) &&793Style.Cpp11BracedListStyle;794};795if (!Tok.isOneOf(tok::l_paren, TT_TemplateOpener, tok::l_square) &&796!IsStartOfBracedList()) {797return false;798}799if (!Tok.Previous)800return true;801if (Tok.Previous->isIf())802return Style.AlignAfterOpenBracket == FormatStyle::BAS_AlwaysBreak;803return !Tok.Previous->isOneOf(TT_CastRParen, tok::kw_for, tok::kw_while,804tok::kw_switch);805};806if ((Style.AlignAfterOpenBracket == FormatStyle::BAS_AlwaysBreak ||807Style.AlignAfterOpenBracket == FormatStyle::BAS_BlockIndent) &&808IsOpeningBracket(Previous) && State.Column > getNewLineColumn(State) &&809// Don't do this for simple (no expressions) one-argument function calls810// as that feels like needlessly wasting whitespace, e.g.:811//812// caaaaaaaaaaaall(813// caaaaaaaaaaaall(814// caaaaaaaaaaaall(815// caaaaaaaaaaaaaaaaaaaaaaall(aaaaaaaaaaaaaa, aaaaaaaaa))));816Current.FakeLParens.size() > 0 &&817Current.FakeLParens.back() > prec::Unknown) {818CurrentState.NoLineBreak = true;819}820if (Previous.is(TT_TemplateString) && Previous.opensScope())821CurrentState.NoLineBreak = true;822
823// Align following lines within parentheses / brackets if configured.824// Note: This doesn't apply to macro expansion lines, which are MACRO( , , )825// with args as children of the '(' and ',' tokens. It does not make sense to826// align the commas with the opening paren.827if (Style.AlignAfterOpenBracket != FormatStyle::BAS_DontAlign &&828!CurrentState.IsCSharpGenericTypeConstraint && Previous.opensScope() &&829Previous.isNot(TT_ObjCMethodExpr) && Previous.isNot(TT_RequiresClause) &&830Previous.isNot(TT_TableGenDAGArgOpener) &&831Previous.isNot(TT_TableGenDAGArgOpenerToBreak) &&832!(Current.MacroParent && Previous.MacroParent) &&833(Current.isNot(TT_LineComment) ||834Previous.isOneOf(BK_BracedInit, TT_VerilogMultiLineListLParen))) {835CurrentState.Indent = State.Column + Spaces;836CurrentState.IsAligned = true;837}838if (CurrentState.AvoidBinPacking && startsNextParameter(Current, Style))839CurrentState.NoLineBreak = true;840if (startsSegmentOfBuilderTypeCall(Current) &&841State.Column > getNewLineColumn(State)) {842CurrentState.ContainsUnwrappedBuilder = true;843}844
845if (Current.is(TT_TrailingReturnArrow) &&846Style.Language == FormatStyle::LK_Java) {847CurrentState.NoLineBreak = true;848}849if (Current.isMemberAccess() && Previous.is(tok::r_paren) &&850(Previous.MatchingParen &&851(Previous.TotalLength - Previous.MatchingParen->TotalLength > 10))) {852// If there is a function call with long parameters, break before trailing853// calls. This prevents things like:854// EXPECT_CALL(SomeLongParameter).Times(855// 2);856// We don't want to do this for short parameters as they can just be857// indexes.858CurrentState.NoLineBreak = true;859}860
861// Don't allow the RHS of an operator to be split over multiple lines unless862// there is a line-break right after the operator.863// Exclude relational operators, as there, it is always more desirable to864// have the LHS 'left' of the RHS.865const FormatToken *P = Current.getPreviousNonComment();866if (Current.isNot(tok::comment) && P &&867(P->isOneOf(TT_BinaryOperator, tok::comma) ||868(P->is(TT_ConditionalExpr) && P->is(tok::colon))) &&869!P->isOneOf(TT_OverloadedOperator, TT_CtorInitializerComma) &&870P->getPrecedence() != prec::Assignment &&871P->getPrecedence() != prec::Relational &&872P->getPrecedence() != prec::Spaceship) {873bool BreakBeforeOperator =874P->MustBreakBefore || P->is(tok::lessless) ||875(P->is(TT_BinaryOperator) &&876Style.BreakBeforeBinaryOperators != FormatStyle::BOS_None) ||877(P->is(TT_ConditionalExpr) && Style.BreakBeforeTernaryOperators);878// Don't do this if there are only two operands. In these cases, there is879// always a nice vertical separation between them and the extra line break880// does not help.881bool HasTwoOperands = P->OperatorIndex == 0 && !P->NextOperator &&882P->isNot(TT_ConditionalExpr);883if ((!BreakBeforeOperator &&884!(HasTwoOperands &&885Style.AlignOperands != FormatStyle::OAS_DontAlign)) ||886(!CurrentState.LastOperatorWrapped && BreakBeforeOperator)) {887CurrentState.NoLineBreakInOperand = true;888}889}890
891State.Column += Spaces;892if (Current.isNot(tok::comment) && Previous.is(tok::l_paren) &&893Previous.Previous &&894(Previous.Previous->is(tok::kw_for) || Previous.Previous->isIf())) {895// Treat the condition inside an if as if it was a second function896// parameter, i.e. let nested calls have a continuation indent.897CurrentState.LastSpace = State.Column;898CurrentState.NestedBlockIndent = State.Column;899} else if (!Current.isOneOf(tok::comment, tok::caret) &&900((Previous.is(tok::comma) &&901Previous.isNot(TT_OverloadedOperator)) ||902(Previous.is(tok::colon) && Previous.is(TT_ObjCMethodExpr)))) {903CurrentState.LastSpace = State.Column;904} else if (Previous.is(TT_CtorInitializerColon) &&905(!Current.isTrailingComment() || Current.NewlinesBefore > 0) &&906Style.BreakConstructorInitializers ==907FormatStyle::BCIS_AfterColon) {908CurrentState.Indent = State.Column;909CurrentState.LastSpace = State.Column;910} else if (Previous.isOneOf(TT_ConditionalExpr, TT_CtorInitializerColon)) {911CurrentState.LastSpace = State.Column;912} else if (Previous.is(TT_BinaryOperator) &&913((Previous.getPrecedence() != prec::Assignment &&914(Previous.isNot(tok::lessless) || Previous.OperatorIndex != 0 ||915Previous.NextOperator)) ||916Current.StartsBinaryExpression)) {917// Indent relative to the RHS of the expression unless this is a simple918// assignment without binary expression on the RHS.919if (Style.BreakBeforeBinaryOperators == FormatStyle::BOS_None)920CurrentState.LastSpace = State.Column;921} else if (Previous.is(TT_InheritanceColon)) {922CurrentState.Indent = State.Column;923CurrentState.LastSpace = State.Column;924} else if (Current.is(TT_CSharpGenericTypeConstraintColon)) {925CurrentState.ColonPos = State.Column;926} else if (Previous.opensScope()) {927// If a function has a trailing call, indent all parameters from the928// opening parenthesis. This avoids confusing indents like:929// OuterFunction(InnerFunctionCall( // break930// ParameterToInnerFunction)) // break931// .SecondInnerFunctionCall();932if (Previous.MatchingParen) {933const FormatToken *Next = Previous.MatchingParen->getNextNonComment();934if (Next && Next->isMemberAccess() && State.Stack.size() > 1 &&935State.Stack[State.Stack.size() - 2].CallContinuation == 0) {936CurrentState.LastSpace = State.Column;937}938}939}940}
941
942unsigned ContinuationIndenter::addTokenOnNewLine(LineState &State,943bool DryRun) {944FormatToken &Current = *State.NextToken;945assert(State.NextToken->Previous);946const FormatToken &Previous = *State.NextToken->Previous;947auto &CurrentState = State.Stack.back();948
949// Extra penalty that needs to be added because of the way certain line950// breaks are chosen.951unsigned Penalty = 0;952
953const FormatToken *PreviousNonComment = Current.getPreviousNonComment();954const FormatToken *NextNonComment = Previous.getNextNonComment();955if (!NextNonComment)956NextNonComment = &Current;957// The first line break on any NestingLevel causes an extra penalty in order958// prefer similar line breaks.959if (!CurrentState.ContainsLineBreak)960Penalty += 15;961CurrentState.ContainsLineBreak = true;962
963Penalty += State.NextToken->SplitPenalty;964
965// Breaking before the first "<<" is generally not desirable if the LHS is966// short. Also always add the penalty if the LHS is split over multiple lines967// to avoid unnecessary line breaks that just work around this penalty.968if (NextNonComment->is(tok::lessless) && CurrentState.FirstLessLess == 0 &&969(State.Column <= Style.ColumnLimit / 3 ||970CurrentState.BreakBeforeParameter)) {971Penalty += Style.PenaltyBreakFirstLessLess;972}973
974State.Column = getNewLineColumn(State);975
976// Add Penalty proportional to amount of whitespace away from FirstColumn977// This tends to penalize several lines that are far-right indented,978// and prefers a line-break prior to such a block, e.g:979//980// Constructor() :981// member(value), looooooooooooooooong_member(982// looooooooooong_call(param_1, param_2, param_3))983// would then become984// Constructor() :985// member(value),986// looooooooooooooooong_member(987// looooooooooong_call(param_1, param_2, param_3))988if (State.Column > State.FirstIndent) {989Penalty +=990Style.PenaltyIndentedWhitespace * (State.Column - State.FirstIndent);991}992
993// Indent nested blocks relative to this column, unless in a very specific994// JavaScript special case where:995//996// var loooooong_name =997// function() {998// // code999// }1000//1001// is common and should be formatted like a free-standing function. The same1002// goes for wrapping before the lambda return type arrow.1003if (Current.isNot(TT_TrailingReturnArrow) &&1004(!Style.isJavaScript() || Current.NestingLevel != 0 ||1005!PreviousNonComment || PreviousNonComment->isNot(tok::equal) ||1006!Current.isOneOf(Keywords.kw_async, Keywords.kw_function))) {1007CurrentState.NestedBlockIndent = State.Column;1008}1009
1010if (NextNonComment->isMemberAccess()) {1011if (CurrentState.CallContinuation == 0)1012CurrentState.CallContinuation = State.Column;1013} else if (NextNonComment->is(TT_SelectorName)) {1014if (!CurrentState.ObjCSelectorNameFound) {1015if (NextNonComment->LongestObjCSelectorName == 0) {1016CurrentState.AlignColons = false;1017} else {1018CurrentState.ColonPos =1019(shouldIndentWrappedSelectorName(Style, State.Line->Type)1020? std::max(CurrentState.Indent,1021State.FirstIndent + Style.ContinuationIndentWidth)1022: CurrentState.Indent) +1023std::max(NextNonComment->LongestObjCSelectorName,1024NextNonComment->ColumnWidth);1025}1026} else if (CurrentState.AlignColons &&1027CurrentState.ColonPos <= NextNonComment->ColumnWidth) {1028CurrentState.ColonPos = State.Column + NextNonComment->ColumnWidth;1029}1030} else if (PreviousNonComment && PreviousNonComment->is(tok::colon) &&1031PreviousNonComment->isOneOf(TT_ObjCMethodExpr, TT_DictLiteral)) {1032// FIXME: This is hacky, find a better way. The problem is that in an ObjC1033// method expression, the block should be aligned to the line starting it,1034// e.g.:1035// [aaaaaaaaaaaaaaa aaaaaaaaa: \\ break for some reason1036// ^(int *i) {1037// // ...1038// }];1039// Thus, we set LastSpace of the next higher NestingLevel, to which we move1040// when we consume all of the "}"'s FakeRParens at the "{".1041if (State.Stack.size() > 1) {1042State.Stack[State.Stack.size() - 2].LastSpace =1043std::max(CurrentState.LastSpace, CurrentState.Indent) +1044Style.ContinuationIndentWidth;1045}1046}1047
1048if ((PreviousNonComment &&1049PreviousNonComment->isOneOf(tok::comma, tok::semi) &&1050!CurrentState.AvoidBinPacking) ||1051Previous.is(TT_BinaryOperator)) {1052CurrentState.BreakBeforeParameter = false;1053}1054if (PreviousNonComment &&1055(PreviousNonComment->isOneOf(TT_TemplateCloser, TT_JavaAnnotation) ||1056PreviousNonComment->ClosesRequiresClause) &&1057Current.NestingLevel == 0) {1058CurrentState.BreakBeforeParameter = false;1059}1060if (NextNonComment->is(tok::question) ||1061(PreviousNonComment && PreviousNonComment->is(tok::question))) {1062CurrentState.BreakBeforeParameter = true;1063}1064if (Current.is(TT_BinaryOperator) && Current.CanBreakBefore)1065CurrentState.BreakBeforeParameter = false;1066
1067if (!DryRun) {1068unsigned MaxEmptyLinesToKeep = Style.MaxEmptyLinesToKeep + 1;1069if (Current.is(tok::r_brace) && Current.MatchingParen &&1070// Only strip trailing empty lines for l_braces that have children, i.e.1071// for function expressions (lambdas, arrows, etc).1072!Current.MatchingParen->Children.empty()) {1073// lambdas and arrow functions are expressions, thus their r_brace is not1074// on its own line, and thus not covered by UnwrappedLineFormatter's logic1075// about removing empty lines on closing blocks. Special case them here.1076MaxEmptyLinesToKeep = 1;1077}1078unsigned Newlines =1079std::max(1u, std::min(Current.NewlinesBefore, MaxEmptyLinesToKeep));1080bool ContinuePPDirective =1081State.Line->InPPDirective && State.Line->Type != LT_ImportStatement;1082Whitespaces.replaceWhitespace(Current, Newlines, State.Column, State.Column,1083CurrentState.IsAligned, ContinuePPDirective);1084}1085
1086if (!Current.isTrailingComment())1087CurrentState.LastSpace = State.Column;1088if (Current.is(tok::lessless)) {1089// If we are breaking before a "<<", we always want to indent relative to1090// RHS. This is necessary only for "<<", as we special-case it and don't1091// always indent relative to the RHS.1092CurrentState.LastSpace += 3; // 3 -> width of "<< ".1093}1094
1095State.StartOfLineLevel = Current.NestingLevel;1096State.LowestLevelOnLine = Current.NestingLevel;1097
1098// Any break on this level means that the parent level has been broken1099// and we need to avoid bin packing there.1100bool NestedBlockSpecialCase =1101(!Style.isCpp() && Current.is(tok::r_brace) && State.Stack.size() > 1 &&1102State.Stack[State.Stack.size() - 2].NestedBlockInlined) ||1103(Style.Language == FormatStyle::LK_ObjC && Current.is(tok::r_brace) &&1104State.Stack.size() > 1 && !Style.ObjCBreakBeforeNestedBlockParam);1105// Do not force parameter break for statements with requires expressions.1106NestedBlockSpecialCase =1107NestedBlockSpecialCase ||1108(Current.MatchingParen &&1109Current.MatchingParen->is(TT_RequiresExpressionLBrace));1110if (!NestedBlockSpecialCase) {1111auto ParentLevelIt = std::next(State.Stack.rbegin());1112if (Style.LambdaBodyIndentation == FormatStyle::LBI_OuterScope &&1113Current.MatchingParen && Current.MatchingParen->is(TT_LambdaLBrace)) {1114// If the first character on the new line is a lambda's closing brace, the1115// stack still contains that lambda's parenthesis. As such, we need to1116// recurse further down the stack than usual to find the parenthesis level1117// containing the lambda, which is where we want to set1118// BreakBeforeParameter.1119//1120// We specifically special case "OuterScope"-formatted lambdas here1121// because, when using that setting, breaking before the parameter1122// directly following the lambda is particularly unsightly. However, when1123// "OuterScope" is not set, the logic to find the parent parenthesis level1124// still appears to be sometimes incorrect. It has not been fixed yet1125// because it would lead to significant changes in existing behaviour.1126//1127// TODO: fix the non-"OuterScope" case too.1128auto FindCurrentLevel = [&](const auto &It) {1129return std::find_if(It, State.Stack.rend(), [](const auto &PState) {1130return PState.Tok != nullptr; // Ignore fake parens.1131});1132};1133auto MaybeIncrement = [&](const auto &It) {1134return It != State.Stack.rend() ? std::next(It) : It;1135};1136auto LambdaLevelIt = FindCurrentLevel(State.Stack.rbegin());1137auto LevelContainingLambdaIt =1138FindCurrentLevel(MaybeIncrement(LambdaLevelIt));1139ParentLevelIt = MaybeIncrement(LevelContainingLambdaIt);1140}1141for (auto I = ParentLevelIt, E = State.Stack.rend(); I != E; ++I)1142I->BreakBeforeParameter = true;1143}1144
1145if (PreviousNonComment &&1146!PreviousNonComment->isOneOf(tok::comma, tok::colon, tok::semi) &&1147((PreviousNonComment->isNot(TT_TemplateCloser) &&1148!PreviousNonComment->ClosesRequiresClause) ||1149Current.NestingLevel != 0) &&1150!PreviousNonComment->isOneOf(1151TT_BinaryOperator, TT_FunctionAnnotationRParen, TT_JavaAnnotation,1152TT_LeadingJavaAnnotation) &&1153Current.isNot(TT_BinaryOperator) && !PreviousNonComment->opensScope() &&1154// We don't want to enforce line breaks for subsequent arguments just1155// because we have been forced to break before a lambda body.1156(!Style.BraceWrapping.BeforeLambdaBody ||1157Current.isNot(TT_LambdaLBrace))) {1158CurrentState.BreakBeforeParameter = true;1159}1160
1161// If we break after { or the [ of an array initializer, we should also break1162// before the corresponding } or ].1163if (PreviousNonComment &&1164(PreviousNonComment->isOneOf(tok::l_brace, TT_ArrayInitializerLSquare) ||1165opensProtoMessageField(*PreviousNonComment, Style))) {1166CurrentState.BreakBeforeClosingBrace = true;1167}1168
1169if (PreviousNonComment && PreviousNonComment->is(tok::l_paren)) {1170CurrentState.BreakBeforeClosingParen =1171Style.AlignAfterOpenBracket == FormatStyle::BAS_BlockIndent;1172}1173
1174if (CurrentState.AvoidBinPacking) {1175// If we are breaking after '(', '{', '<', or this is the break after a ':'1176// to start a member initializer list in a constructor, this should not1177// be considered bin packing unless the relevant AllowAll option is false or1178// this is a dict/object literal.1179bool PreviousIsBreakingCtorInitializerColon =1180PreviousNonComment && PreviousNonComment->is(TT_CtorInitializerColon) &&1181Style.BreakConstructorInitializers == FormatStyle::BCIS_AfterColon;1182bool AllowAllConstructorInitializersOnNextLine =1183Style.PackConstructorInitializers == FormatStyle::PCIS_NextLine ||1184Style.PackConstructorInitializers == FormatStyle::PCIS_NextLineOnly;1185if (!(Previous.isOneOf(tok::l_paren, tok::l_brace, TT_BinaryOperator) ||1186PreviousIsBreakingCtorInitializerColon) ||1187(!Style.AllowAllParametersOfDeclarationOnNextLine &&1188State.Line->MustBeDeclaration) ||1189(!Style.AllowAllArgumentsOnNextLine &&1190!State.Line->MustBeDeclaration) ||1191(!AllowAllConstructorInitializersOnNextLine &&1192PreviousIsBreakingCtorInitializerColon) ||1193Previous.is(TT_DictLiteral)) {1194CurrentState.BreakBeforeParameter = true;1195}1196
1197// If we are breaking after a ':' to start a member initializer list,1198// and we allow all arguments on the next line, we should not break1199// before the next parameter.1200if (PreviousIsBreakingCtorInitializerColon &&1201AllowAllConstructorInitializersOnNextLine) {1202CurrentState.BreakBeforeParameter = false;1203}1204}1205
1206return Penalty;1207}
1208
1209unsigned ContinuationIndenter::getNewLineColumn(const LineState &State) {1210if (!State.NextToken || !State.NextToken->Previous)1211return 0;1212
1213FormatToken &Current = *State.NextToken;1214const auto &CurrentState = State.Stack.back();1215
1216if (CurrentState.IsCSharpGenericTypeConstraint &&1217Current.isNot(TT_CSharpGenericTypeConstraint)) {1218return CurrentState.ColonPos + 2;1219}1220
1221const FormatToken &Previous = *Current.Previous;1222// If we are continuing an expression, we want to use the continuation indent.1223unsigned ContinuationIndent =1224std::max(CurrentState.LastSpace, CurrentState.Indent) +1225Style.ContinuationIndentWidth;1226const FormatToken *PreviousNonComment = Current.getPreviousNonComment();1227const FormatToken *NextNonComment = Previous.getNextNonComment();1228if (!NextNonComment)1229NextNonComment = &Current;1230
1231// Java specific bits.1232if (Style.Language == FormatStyle::LK_Java &&1233Current.isOneOf(Keywords.kw_implements, Keywords.kw_extends)) {1234return std::max(CurrentState.LastSpace,1235CurrentState.Indent + Style.ContinuationIndentWidth);1236}1237
1238// Indentation of the statement following a Verilog case label is taken care1239// of in moveStateToNextToken.1240if (Style.isVerilog() && PreviousNonComment &&1241Keywords.isVerilogEndOfLabel(*PreviousNonComment)) {1242return State.FirstIndent;1243}1244
1245if (Style.BreakBeforeBraces == FormatStyle::BS_Whitesmiths &&1246State.Line->First->is(tok::kw_enum)) {1247return (Style.IndentWidth * State.Line->First->IndentLevel) +1248Style.IndentWidth;1249}1250
1251if ((NextNonComment->is(tok::l_brace) && NextNonComment->is(BK_Block)) ||1252(Style.isVerilog() && Keywords.isVerilogBegin(*NextNonComment))) {1253if (Current.NestingLevel == 0 ||1254(Style.LambdaBodyIndentation == FormatStyle::LBI_OuterScope &&1255State.NextToken->is(TT_LambdaLBrace))) {1256return State.FirstIndent;1257}1258return CurrentState.Indent;1259}1260if (Current.is(TT_TrailingReturnArrow) &&1261Previous.isOneOf(tok::kw_noexcept, tok::kw_mutable, tok::kw_constexpr,1262tok::kw_consteval, tok::kw_static, TT_AttributeSquare)) {1263return ContinuationIndent;1264}1265if ((Current.isOneOf(tok::r_brace, tok::r_square) ||1266(Current.is(tok::greater) && (Style.isProto() || Style.isTableGen()))) &&1267State.Stack.size() > 1) {1268if (Current.closesBlockOrBlockTypeList(Style))1269return State.Stack[State.Stack.size() - 2].NestedBlockIndent;1270if (Current.MatchingParen && Current.MatchingParen->is(BK_BracedInit))1271return State.Stack[State.Stack.size() - 2].LastSpace;1272return State.FirstIndent;1273}1274// Indent a closing parenthesis at the previous level if followed by a semi,1275// const, or opening brace. This allows indentations such as:1276// foo(1277// a,1278// );1279// int Foo::getter(1280// //1281// ) const {1282// return foo;1283// }1284// function foo(1285// a,1286// ) {1287// code(); //1288// }1289if (Current.is(tok::r_paren) && State.Stack.size() > 1 &&1290(!Current.Next ||1291Current.Next->isOneOf(tok::semi, tok::kw_const, tok::l_brace))) {1292return State.Stack[State.Stack.size() - 2].LastSpace;1293}1294// When DAGArg closer exists top of line, it should be aligned in the similar1295// way as function call above.1296if (Style.isTableGen() && Current.is(TT_TableGenDAGArgCloser) &&1297State.Stack.size() > 1) {1298return State.Stack[State.Stack.size() - 2].LastSpace;1299}1300if (Style.AlignAfterOpenBracket == FormatStyle::BAS_BlockIndent &&1301(Current.is(tok::r_paren) ||1302(Current.is(tok::r_brace) && Current.MatchingParen &&1303Current.MatchingParen->is(BK_BracedInit))) &&1304State.Stack.size() > 1) {1305return State.Stack[State.Stack.size() - 2].LastSpace;1306}1307if (NextNonComment->is(TT_TemplateString) && NextNonComment->closesScope())1308return State.Stack[State.Stack.size() - 2].LastSpace;1309// Field labels in a nested type should be aligned to the brace. For example1310// in ProtoBuf:1311// optional int32 b = 2 [(foo_options) = {aaaaaaaaaaaaaaaaaaa: 123,1312// bbbbbbbbbbbbbbbbbbbbbbbb:"baz"}];1313// For Verilog, a quote following a brace is treated as an identifier. And1314// Both braces and colons get annotated as TT_DictLiteral. So we have to1315// check.1316if (Current.is(tok::identifier) && Current.Next &&1317(!Style.isVerilog() || Current.Next->is(tok::colon)) &&1318(Current.Next->is(TT_DictLiteral) ||1319(Style.isProto() && Current.Next->isOneOf(tok::less, tok::l_brace)))) {1320return CurrentState.Indent;1321}1322if (NextNonComment->is(TT_ObjCStringLiteral) &&1323State.StartOfStringLiteral != 0) {1324return State.StartOfStringLiteral - 1;1325}1326if (NextNonComment->isStringLiteral() && State.StartOfStringLiteral != 0)1327return State.StartOfStringLiteral;1328if (NextNonComment->is(tok::lessless) && CurrentState.FirstLessLess != 0)1329return CurrentState.FirstLessLess;1330if (NextNonComment->isMemberAccess()) {1331if (CurrentState.CallContinuation == 0)1332return ContinuationIndent;1333return CurrentState.CallContinuation;1334}1335if (CurrentState.QuestionColumn != 0 &&1336((NextNonComment->is(tok::colon) &&1337NextNonComment->is(TT_ConditionalExpr)) ||1338Previous.is(TT_ConditionalExpr))) {1339if (((NextNonComment->is(tok::colon) && NextNonComment->Next &&1340!NextNonComment->Next->FakeLParens.empty() &&1341NextNonComment->Next->FakeLParens.back() == prec::Conditional) ||1342(Previous.is(tok::colon) && !Current.FakeLParens.empty() &&1343Current.FakeLParens.back() == prec::Conditional)) &&1344!CurrentState.IsWrappedConditional) {1345// NOTE: we may tweak this slightly:1346// * not remove the 'lead' ContinuationIndentWidth1347// * always un-indent by the operator when1348// BreakBeforeTernaryOperators=true1349unsigned Indent = CurrentState.Indent;1350if (Style.AlignOperands != FormatStyle::OAS_DontAlign)1351Indent -= Style.ContinuationIndentWidth;1352if (Style.BreakBeforeTernaryOperators && CurrentState.UnindentOperator)1353Indent -= 2;1354return Indent;1355}1356return CurrentState.QuestionColumn;1357}1358if (Previous.is(tok::comma) && CurrentState.VariablePos != 0)1359return CurrentState.VariablePos;1360if (Current.is(TT_RequiresClause)) {1361if (Style.IndentRequiresClause)1362return CurrentState.Indent + Style.IndentWidth;1363switch (Style.RequiresClausePosition) {1364case FormatStyle::RCPS_OwnLine:1365case FormatStyle::RCPS_WithFollowing:1366return CurrentState.Indent;1367default:1368break;1369}1370}1371if (NextNonComment->isOneOf(TT_CtorInitializerColon, TT_InheritanceColon,1372TT_InheritanceComma)) {1373return State.FirstIndent + Style.ConstructorInitializerIndentWidth;1374}1375if ((PreviousNonComment &&1376(PreviousNonComment->ClosesTemplateDeclaration ||1377PreviousNonComment->ClosesRequiresClause ||1378(PreviousNonComment->is(TT_AttributeMacro) &&1379Current.isNot(tok::l_paren)) ||1380PreviousNonComment->isOneOf(1381TT_AttributeRParen, TT_AttributeSquare, TT_FunctionAnnotationRParen,1382TT_JavaAnnotation, TT_LeadingJavaAnnotation))) ||1383(!Style.IndentWrappedFunctionNames &&1384NextNonComment->isOneOf(tok::kw_operator, TT_FunctionDeclarationName))) {1385return std::max(CurrentState.LastSpace, CurrentState.Indent);1386}1387if (NextNonComment->is(TT_SelectorName)) {1388if (!CurrentState.ObjCSelectorNameFound) {1389unsigned MinIndent = CurrentState.Indent;1390if (shouldIndentWrappedSelectorName(Style, State.Line->Type)) {1391MinIndent = std::max(MinIndent,1392State.FirstIndent + Style.ContinuationIndentWidth);1393}1394// If LongestObjCSelectorName is 0, we are indenting the first1395// part of an ObjC selector (or a selector component which is1396// not colon-aligned due to block formatting).1397//1398// Otherwise, we are indenting a subsequent part of an ObjC1399// selector which should be colon-aligned to the longest1400// component of the ObjC selector.1401//1402// In either case, we want to respect Style.IndentWrappedFunctionNames.1403return MinIndent +1404std::max(NextNonComment->LongestObjCSelectorName,1405NextNonComment->ColumnWidth) -1406NextNonComment->ColumnWidth;1407}1408if (!CurrentState.AlignColons)1409return CurrentState.Indent;1410if (CurrentState.ColonPos > NextNonComment->ColumnWidth)1411return CurrentState.ColonPos - NextNonComment->ColumnWidth;1412return CurrentState.Indent;1413}1414if (NextNonComment->is(tok::colon) && NextNonComment->is(TT_ObjCMethodExpr))1415return CurrentState.ColonPos;1416if (NextNonComment->is(TT_ArraySubscriptLSquare)) {1417if (CurrentState.StartOfArraySubscripts != 0) {1418return CurrentState.StartOfArraySubscripts;1419} else if (Style.isCSharp()) { // C# allows `["key"] = value` inside object1420// initializers.1421return CurrentState.Indent;1422}1423return ContinuationIndent;1424}1425
1426// OpenMP clauses want to get additional indentation when they are pushed onto1427// the next line.1428if (State.Line->InPragmaDirective) {1429FormatToken *PragmaType = State.Line->First->Next->Next;1430if (PragmaType && PragmaType->TokenText == "omp")1431return CurrentState.Indent + Style.ContinuationIndentWidth;1432}1433
1434// This ensure that we correctly format ObjC methods calls without inputs,1435// i.e. where the last element isn't selector like: [callee method];1436if (NextNonComment->is(tok::identifier) && NextNonComment->FakeRParens == 0 &&1437NextNonComment->Next && NextNonComment->Next->is(TT_ObjCMethodExpr)) {1438return CurrentState.Indent;1439}1440
1441if (NextNonComment->isOneOf(TT_StartOfName, TT_PointerOrReference) ||1442Previous.isOneOf(tok::coloncolon, tok::equal, TT_JsTypeColon)) {1443return ContinuationIndent;1444}1445if (PreviousNonComment && PreviousNonComment->is(tok::colon) &&1446PreviousNonComment->isOneOf(TT_ObjCMethodExpr, TT_DictLiteral)) {1447return ContinuationIndent;1448}1449if (NextNonComment->is(TT_CtorInitializerComma))1450return CurrentState.Indent;1451if (PreviousNonComment && PreviousNonComment->is(TT_CtorInitializerColon) &&1452Style.BreakConstructorInitializers == FormatStyle::BCIS_AfterColon) {1453return CurrentState.Indent;1454}1455if (PreviousNonComment && PreviousNonComment->is(TT_InheritanceColon) &&1456Style.BreakInheritanceList == FormatStyle::BILS_AfterColon) {1457return CurrentState.Indent;1458}1459if (Previous.is(tok::r_paren) &&1460Previous.isNot(TT_TableGenDAGArgOperatorToBreak) &&1461!Current.isBinaryOperator() &&1462!Current.isOneOf(tok::colon, tok::comment)) {1463return ContinuationIndent;1464}1465if (Current.is(TT_ProtoExtensionLSquare))1466return CurrentState.Indent;1467if (Current.isBinaryOperator() && CurrentState.UnindentOperator) {1468return CurrentState.Indent - Current.Tok.getLength() -1469Current.SpacesRequiredBefore;1470}1471if (Current.is(tok::comment) && NextNonComment->isBinaryOperator() &&1472CurrentState.UnindentOperator) {1473return CurrentState.Indent - NextNonComment->Tok.getLength() -1474NextNonComment->SpacesRequiredBefore;1475}1476if (CurrentState.Indent == State.FirstIndent && PreviousNonComment &&1477!PreviousNonComment->isOneOf(tok::r_brace, TT_CtorInitializerComma)) {1478// Ensure that we fall back to the continuation indent width instead of1479// just flushing continuations left.1480return CurrentState.Indent + Style.ContinuationIndentWidth;1481}1482return CurrentState.Indent;1483}
1484
1485static bool hasNestedBlockInlined(const FormatToken *Previous,1486const FormatToken &Current,1487const FormatStyle &Style) {1488if (Previous->isNot(tok::l_paren))1489return true;1490if (Previous->ParameterCount > 1)1491return true;1492
1493// Also a nested block if contains a lambda inside function with 1 parameter.1494return Style.BraceWrapping.BeforeLambdaBody && Current.is(TT_LambdaLSquare);1495}
1496
1497unsigned ContinuationIndenter::moveStateToNextToken(LineState &State,1498bool DryRun, bool Newline) {1499assert(State.Stack.size());1500const FormatToken &Current = *State.NextToken;1501auto &CurrentState = State.Stack.back();1502
1503if (Current.is(TT_CSharpGenericTypeConstraint))1504CurrentState.IsCSharpGenericTypeConstraint = true;1505if (Current.isOneOf(tok::comma, TT_BinaryOperator))1506CurrentState.NoLineBreakInOperand = false;1507if (Current.isOneOf(TT_InheritanceColon, TT_CSharpGenericTypeConstraintColon))1508CurrentState.AvoidBinPacking = true;1509if (Current.is(tok::lessless) && Current.isNot(TT_OverloadedOperator)) {1510if (CurrentState.FirstLessLess == 0)1511CurrentState.FirstLessLess = State.Column;1512else1513CurrentState.LastOperatorWrapped = Newline;1514}1515if (Current.is(TT_BinaryOperator) && Current.isNot(tok::lessless))1516CurrentState.LastOperatorWrapped = Newline;1517if (Current.is(TT_ConditionalExpr) && Current.Previous &&1518Current.Previous->isNot(TT_ConditionalExpr)) {1519CurrentState.LastOperatorWrapped = Newline;1520}1521if (Current.is(TT_ArraySubscriptLSquare) &&1522CurrentState.StartOfArraySubscripts == 0) {1523CurrentState.StartOfArraySubscripts = State.Column;1524}1525
1526auto IsWrappedConditional = [](const FormatToken &Tok) {1527if (!(Tok.is(TT_ConditionalExpr) && Tok.is(tok::question)))1528return false;1529if (Tok.MustBreakBefore)1530return true;1531
1532const FormatToken *Next = Tok.getNextNonComment();1533return Next && Next->MustBreakBefore;1534};1535if (IsWrappedConditional(Current))1536CurrentState.IsWrappedConditional = true;1537if (Style.BreakBeforeTernaryOperators && Current.is(tok::question))1538CurrentState.QuestionColumn = State.Column;1539if (!Style.BreakBeforeTernaryOperators && Current.isNot(tok::colon)) {1540const FormatToken *Previous = Current.Previous;1541while (Previous && Previous->isTrailingComment())1542Previous = Previous->Previous;1543if (Previous && Previous->is(tok::question))1544CurrentState.QuestionColumn = State.Column;1545}1546if (!Current.opensScope() && !Current.closesScope() &&1547Current.isNot(TT_PointerOrReference)) {1548State.LowestLevelOnLine =1549std::min(State.LowestLevelOnLine, Current.NestingLevel);1550}1551if (Current.isMemberAccess())1552CurrentState.StartOfFunctionCall = !Current.NextOperator ? 0 : State.Column;1553if (Current.is(TT_SelectorName))1554CurrentState.ObjCSelectorNameFound = true;1555if (Current.is(TT_CtorInitializerColon) &&1556Style.BreakConstructorInitializers != FormatStyle::BCIS_AfterColon) {1557// Indent 2 from the column, so:1558// SomeClass::SomeClass()1559// : First(...), ...1560// Next(...)1561// ^ line up here.1562CurrentState.Indent = State.Column + (Style.BreakConstructorInitializers ==1563FormatStyle::BCIS_BeforeComma1564? 01565: 2);1566CurrentState.NestedBlockIndent = CurrentState.Indent;1567if (Style.PackConstructorInitializers > FormatStyle::PCIS_BinPack) {1568CurrentState.AvoidBinPacking = true;1569CurrentState.BreakBeforeParameter =1570Style.ColumnLimit > 0 &&1571Style.PackConstructorInitializers != FormatStyle::PCIS_NextLine &&1572Style.PackConstructorInitializers != FormatStyle::PCIS_NextLineOnly;1573} else {1574CurrentState.BreakBeforeParameter = false;1575}1576}1577if (Current.is(TT_CtorInitializerColon) &&1578Style.BreakConstructorInitializers == FormatStyle::BCIS_AfterColon) {1579CurrentState.Indent =1580State.FirstIndent + Style.ConstructorInitializerIndentWidth;1581CurrentState.NestedBlockIndent = CurrentState.Indent;1582if (Style.PackConstructorInitializers > FormatStyle::PCIS_BinPack)1583CurrentState.AvoidBinPacking = true;1584else1585CurrentState.BreakBeforeParameter = false;1586}1587if (Current.is(TT_InheritanceColon)) {1588CurrentState.Indent =1589State.FirstIndent + Style.ConstructorInitializerIndentWidth;1590}1591if (Current.isOneOf(TT_BinaryOperator, TT_ConditionalExpr) && Newline)1592CurrentState.NestedBlockIndent = State.Column + Current.ColumnWidth + 1;1593if (Current.isOneOf(TT_LambdaLSquare, TT_TrailingReturnArrow))1594CurrentState.LastSpace = State.Column;1595if (Current.is(TT_RequiresExpression) &&1596Style.RequiresExpressionIndentation == FormatStyle::REI_Keyword) {1597CurrentState.NestedBlockIndent = State.Column;1598}1599
1600// Insert scopes created by fake parenthesis.1601const FormatToken *Previous = Current.getPreviousNonComment();1602
1603// Add special behavior to support a format commonly used for JavaScript1604// closures:1605// SomeFunction(function() {1606// foo();1607// bar();1608// }, a, b, c);1609if (Current.isNot(tok::comment) && !Current.ClosesRequiresClause &&1610Previous && Previous->isOneOf(tok::l_brace, TT_ArrayInitializerLSquare) &&1611Previous->isNot(TT_DictLiteral) && State.Stack.size() > 1 &&1612!CurrentState.HasMultipleNestedBlocks) {1613if (State.Stack[State.Stack.size() - 2].NestedBlockInlined && Newline)1614for (ParenState &PState : llvm::drop_end(State.Stack))1615PState.NoLineBreak = true;1616State.Stack[State.Stack.size() - 2].NestedBlockInlined = false;1617}1618if (Previous && (Previous->isOneOf(TT_BinaryOperator, TT_ConditionalExpr) ||1619(Previous->isOneOf(tok::l_paren, tok::comma, tok::colon) &&1620!Previous->isOneOf(TT_DictLiteral, TT_ObjCMethodExpr)))) {1621CurrentState.NestedBlockInlined =1622!Newline && hasNestedBlockInlined(Previous, Current, Style);1623}1624
1625moveStatePastFakeLParens(State, Newline);1626moveStatePastScopeCloser(State);1627// Do not use CurrentState here, since the two functions before may change the1628// Stack.1629bool AllowBreak = !State.Stack.back().NoLineBreak &&1630!State.Stack.back().NoLineBreakInOperand;1631moveStatePastScopeOpener(State, Newline);1632moveStatePastFakeRParens(State);1633
1634if (Current.is(TT_ObjCStringLiteral) && State.StartOfStringLiteral == 0)1635State.StartOfStringLiteral = State.Column + 1;1636if (Current.is(TT_CSharpStringLiteral) && State.StartOfStringLiteral == 0) {1637State.StartOfStringLiteral = State.Column + 1;1638} else if (Current.is(TT_TableGenMultiLineString) &&1639State.StartOfStringLiteral == 0) {1640State.StartOfStringLiteral = State.Column + 1;1641} else if (Current.isStringLiteral() && State.StartOfStringLiteral == 0) {1642State.StartOfStringLiteral = State.Column;1643} else if (!Current.isOneOf(tok::comment, tok::identifier, tok::hash) &&1644!Current.isStringLiteral()) {1645State.StartOfStringLiteral = 0;1646}1647
1648State.Column += Current.ColumnWidth;1649State.NextToken = State.NextToken->Next;1650// Verilog case labels are on the same unwrapped lines as the statements that1651// follow. TokenAnnotator identifies them and sets MustBreakBefore.1652// Indentation is taken care of here. A case label can only have 1 statement1653// in Verilog, so we don't have to worry about lines that follow.1654if (Style.isVerilog() && State.NextToken &&1655State.NextToken->MustBreakBefore &&1656Keywords.isVerilogEndOfLabel(Current)) {1657State.FirstIndent += Style.IndentWidth;1658CurrentState.Indent = State.FirstIndent;1659}1660
1661unsigned Penalty =1662handleEndOfLine(Current, State, DryRun, AllowBreak, Newline);1663
1664if (Current.Role)1665Current.Role->formatFromToken(State, this, DryRun);1666// If the previous has a special role, let it consume tokens as appropriate.1667// It is necessary to start at the previous token for the only implemented1668// role (comma separated list). That way, the decision whether or not to break1669// after the "{" is already done and both options are tried and evaluated.1670// FIXME: This is ugly, find a better way.1671if (Previous && Previous->Role)1672Penalty += Previous->Role->formatAfterToken(State, this, DryRun);1673
1674return Penalty;1675}
1676
1677void ContinuationIndenter::moveStatePastFakeLParens(LineState &State,1678bool Newline) {1679const FormatToken &Current = *State.NextToken;1680if (Current.FakeLParens.empty())1681return;1682
1683const FormatToken *Previous = Current.getPreviousNonComment();1684
1685// Don't add extra indentation for the first fake parenthesis after1686// 'return', assignments, opening <({[, or requires clauses. The indentation1687// for these cases is special cased.1688bool SkipFirstExtraIndent =1689Previous &&1690(Previous->opensScope() ||1691Previous->isOneOf(tok::semi, tok::kw_return, TT_RequiresClause) ||1692(Previous->getPrecedence() == prec::Assignment &&1693Style.AlignOperands != FormatStyle::OAS_DontAlign) ||1694Previous->is(TT_ObjCMethodExpr));1695for (const auto &PrecedenceLevel : llvm::reverse(Current.FakeLParens)) {1696const auto &CurrentState = State.Stack.back();1697ParenState NewParenState = CurrentState;1698NewParenState.Tok = nullptr;1699NewParenState.ContainsLineBreak = false;1700NewParenState.LastOperatorWrapped = true;1701NewParenState.IsChainedConditional = false;1702NewParenState.IsWrappedConditional = false;1703NewParenState.UnindentOperator = false;1704NewParenState.NoLineBreak =1705NewParenState.NoLineBreak || CurrentState.NoLineBreakInOperand;1706
1707// Don't propagate AvoidBinPacking into subexpressions of arg/param lists.1708if (PrecedenceLevel > prec::Comma)1709NewParenState.AvoidBinPacking = false;1710
1711// Indent from 'LastSpace' unless these are fake parentheses encapsulating1712// a builder type call after 'return' or, if the alignment after opening1713// brackets is disabled.1714if (!Current.isTrailingComment() &&1715(Style.AlignOperands != FormatStyle::OAS_DontAlign ||1716PrecedenceLevel < prec::Assignment) &&1717(!Previous || Previous->isNot(tok::kw_return) ||1718(Style.Language != FormatStyle::LK_Java && PrecedenceLevel > 0)) &&1719(Style.AlignAfterOpenBracket != FormatStyle::BAS_DontAlign ||1720PrecedenceLevel > prec::Comma || Current.NestingLevel == 0) &&1721(!Style.isTableGen() ||1722(Previous && Previous->isOneOf(TT_TableGenDAGArgListComma,1723TT_TableGenDAGArgListCommaToBreak)))) {1724NewParenState.Indent = std::max(1725std::max(State.Column, NewParenState.Indent), CurrentState.LastSpace);1726}1727
1728// Special case for generic selection expressions, its comma-separated1729// expressions are not aligned to the opening paren like regular calls, but1730// rather continuation-indented relative to the _Generic keyword.1731if (Previous && Previous->endsSequence(tok::l_paren, tok::kw__Generic) &&1732State.Stack.size() > 1) {1733NewParenState.Indent = State.Stack[State.Stack.size() - 2].Indent +1734Style.ContinuationIndentWidth;1735}1736
1737if ((shouldUnindentNextOperator(Current) ||1738(Previous &&1739(PrecedenceLevel == prec::Conditional &&1740Previous->is(tok::question) && Previous->is(TT_ConditionalExpr)))) &&1741!Newline) {1742// If BreakBeforeBinaryOperators is set, un-indent a bit to account for1743// the operator and keep the operands aligned.1744if (Style.AlignOperands == FormatStyle::OAS_AlignAfterOperator)1745NewParenState.UnindentOperator = true;1746// Mark indentation as alignment if the expression is aligned.1747if (Style.AlignOperands != FormatStyle::OAS_DontAlign)1748NewParenState.IsAligned = true;1749}1750
1751// Do not indent relative to the fake parentheses inserted for "." or "->".1752// This is a special case to make the following to statements consistent:1753// OuterFunction(InnerFunctionCall( // break1754// ParameterToInnerFunction));1755// OuterFunction(SomeObject.InnerFunctionCall( // break1756// ParameterToInnerFunction));1757if (PrecedenceLevel > prec::Unknown)1758NewParenState.LastSpace = std::max(NewParenState.LastSpace, State.Column);1759if (PrecedenceLevel != prec::Conditional &&1760Current.isNot(TT_UnaryOperator) &&1761Style.AlignAfterOpenBracket != FormatStyle::BAS_DontAlign) {1762NewParenState.StartOfFunctionCall = State.Column;1763}1764
1765// Indent conditional expressions, unless they are chained "else-if"1766// conditionals. Never indent expression where the 'operator' is ',', ';' or1767// an assignment (i.e. *I <= prec::Assignment) as those have different1768// indentation rules. Indent other expression, unless the indentation needs1769// to be skipped.1770if (PrecedenceLevel == prec::Conditional && Previous &&1771Previous->is(tok::colon) && Previous->is(TT_ConditionalExpr) &&1772&PrecedenceLevel == &Current.FakeLParens.back() &&1773!CurrentState.IsWrappedConditional) {1774NewParenState.IsChainedConditional = true;1775NewParenState.UnindentOperator = State.Stack.back().UnindentOperator;1776} else if (PrecedenceLevel == prec::Conditional ||1777(!SkipFirstExtraIndent && PrecedenceLevel > prec::Assignment &&1778!Current.isTrailingComment())) {1779NewParenState.Indent += Style.ContinuationIndentWidth;1780}1781if ((Previous && !Previous->opensScope()) || PrecedenceLevel != prec::Comma)1782NewParenState.BreakBeforeParameter = false;1783State.Stack.push_back(NewParenState);1784SkipFirstExtraIndent = false;1785}1786}
1787
1788void ContinuationIndenter::moveStatePastFakeRParens(LineState &State) {1789for (unsigned i = 0, e = State.NextToken->FakeRParens; i != e; ++i) {1790unsigned VariablePos = State.Stack.back().VariablePos;1791if (State.Stack.size() == 1) {1792// Do not pop the last element.1793break;1794}1795State.Stack.pop_back();1796State.Stack.back().VariablePos = VariablePos;1797}1798
1799if (State.NextToken->ClosesRequiresClause && Style.IndentRequiresClause) {1800// Remove the indentation of the requires clauses (which is not in Indent,1801// but in LastSpace).1802State.Stack.back().LastSpace -= Style.IndentWidth;1803}1804}
1805
1806void ContinuationIndenter::moveStatePastScopeOpener(LineState &State,1807bool Newline) {1808const FormatToken &Current = *State.NextToken;1809if (!Current.opensScope())1810return;1811
1812const auto &CurrentState = State.Stack.back();1813
1814// Don't allow '<' or '(' in C# generic type constraints to start new scopes.1815if (Current.isOneOf(tok::less, tok::l_paren) &&1816CurrentState.IsCSharpGenericTypeConstraint) {1817return;1818}1819
1820if (Current.MatchingParen && Current.is(BK_Block)) {1821moveStateToNewBlock(State, Newline);1822return;1823}1824
1825unsigned NewIndent;1826unsigned LastSpace = CurrentState.LastSpace;1827bool AvoidBinPacking;1828bool BreakBeforeParameter = false;1829unsigned NestedBlockIndent = std::max(CurrentState.StartOfFunctionCall,1830CurrentState.NestedBlockIndent);1831if (Current.isOneOf(tok::l_brace, TT_ArrayInitializerLSquare) ||1832opensProtoMessageField(Current, Style)) {1833if (Current.opensBlockOrBlockTypeList(Style)) {1834NewIndent = Style.IndentWidth +1835std::min(State.Column, CurrentState.NestedBlockIndent);1836} else if (Current.is(tok::l_brace)) {1837NewIndent =1838CurrentState.LastSpace + Style.BracedInitializerIndentWidth.value_or(1839Style.ContinuationIndentWidth);1840} else {1841NewIndent = CurrentState.LastSpace + Style.ContinuationIndentWidth;1842}1843const FormatToken *NextNonComment = Current.getNextNonComment();1844bool EndsInComma = Current.MatchingParen &&1845Current.MatchingParen->Previous &&1846Current.MatchingParen->Previous->is(tok::comma);1847AvoidBinPacking = EndsInComma || Current.is(TT_DictLiteral) ||1848Style.isProto() || !Style.BinPackArguments ||1849(NextNonComment && NextNonComment->isOneOf(1850TT_DesignatedInitializerPeriod,1851TT_DesignatedInitializerLSquare));1852BreakBeforeParameter = EndsInComma;1853if (Current.ParameterCount > 1)1854NestedBlockIndent = std::max(NestedBlockIndent, State.Column + 1);1855} else {1856NewIndent =1857Style.ContinuationIndentWidth +1858std::max(CurrentState.LastSpace, CurrentState.StartOfFunctionCall);1859
1860if (Style.isTableGen() && Current.is(TT_TableGenDAGArgOpenerToBreak) &&1861Style.TableGenBreakInsideDAGArg == FormatStyle::DAS_BreakElements) {1862// For the case the next token is a TableGen DAGArg operator identifier1863// that is not marked to have a line break after it.1864// In this case the option DAS_BreakElements requires to align the1865// DAGArg elements to the operator.1866const FormatToken *Next = Current.Next;1867if (Next && Next->is(TT_TableGenDAGArgOperatorID))1868NewIndent = State.Column + Next->TokenText.size() + 2;1869}1870
1871// Ensure that different different brackets force relative alignment, e.g.:1872// void SomeFunction(vector< // break1873// int> v);1874// FIXME: We likely want to do this for more combinations of brackets.1875if (Current.is(tok::less) && Current.ParentBracket == tok::l_paren) {1876NewIndent = std::max(NewIndent, CurrentState.Indent);1877LastSpace = std::max(LastSpace, CurrentState.Indent);1878}1879
1880bool EndsInComma =1881Current.MatchingParen &&1882Current.MatchingParen->getPreviousNonComment() &&1883Current.MatchingParen->getPreviousNonComment()->is(tok::comma);1884
1885// If ObjCBinPackProtocolList is unspecified, fall back to BinPackParameters1886// for backwards compatibility.1887bool ObjCBinPackProtocolList =1888(Style.ObjCBinPackProtocolList == FormatStyle::BPS_Auto &&1889Style.BinPackParameters) ||1890Style.ObjCBinPackProtocolList == FormatStyle::BPS_Always;1891
1892bool BinPackDeclaration =1893(State.Line->Type != LT_ObjCDecl && Style.BinPackParameters) ||1894(State.Line->Type == LT_ObjCDecl && ObjCBinPackProtocolList);1895
1896bool GenericSelection =1897Current.getPreviousNonComment() &&1898Current.getPreviousNonComment()->is(tok::kw__Generic);1899
1900AvoidBinPacking =1901(CurrentState.IsCSharpGenericTypeConstraint) || GenericSelection ||1902(Style.isJavaScript() && EndsInComma) ||1903(State.Line->MustBeDeclaration && !BinPackDeclaration) ||1904(!State.Line->MustBeDeclaration && !Style.BinPackArguments) ||1905(Style.ExperimentalAutoDetectBinPacking &&1906(Current.is(PPK_OnePerLine) ||1907(!BinPackInconclusiveFunctions && Current.is(PPK_Inconclusive))));1908
1909if (Current.is(TT_ObjCMethodExpr) && Current.MatchingParen &&1910Style.ObjCBreakBeforeNestedBlockParam) {1911if (Style.ColumnLimit) {1912// If this '[' opens an ObjC call, determine whether all parameters fit1913// into one line and put one per line if they don't.1914if (getLengthToMatchingParen(Current, State.Stack) + State.Column >1915getColumnLimit(State)) {1916BreakBeforeParameter = true;1917}1918} else {1919// For ColumnLimit = 0, we have to figure out whether there is or has to1920// be a line break within this call.1921for (const FormatToken *Tok = &Current;1922Tok && Tok != Current.MatchingParen; Tok = Tok->Next) {1923if (Tok->MustBreakBefore ||1924(Tok->CanBreakBefore && Tok->NewlinesBefore > 0)) {1925BreakBeforeParameter = true;1926break;1927}1928}1929}1930}1931
1932if (Style.isJavaScript() && EndsInComma)1933BreakBeforeParameter = true;1934}1935// Generally inherit NoLineBreak from the current scope to nested scope.1936// However, don't do this for non-empty nested blocks, dict literals and1937// array literals as these follow different indentation rules.1938bool NoLineBreak =1939Current.Children.empty() &&1940!Current.isOneOf(TT_DictLiteral, TT_ArrayInitializerLSquare) &&1941(CurrentState.NoLineBreak || CurrentState.NoLineBreakInOperand ||1942(Current.is(TT_TemplateOpener) &&1943CurrentState.ContainsUnwrappedBuilder));1944State.Stack.push_back(1945ParenState(&Current, NewIndent, LastSpace, AvoidBinPacking, NoLineBreak));1946auto &NewState = State.Stack.back();1947NewState.NestedBlockIndent = NestedBlockIndent;1948NewState.BreakBeforeParameter = BreakBeforeParameter;1949NewState.HasMultipleNestedBlocks = (Current.BlockParameterCount > 1);1950
1951if (Style.BraceWrapping.BeforeLambdaBody && Current.Next &&1952Current.is(tok::l_paren)) {1953// Search for any parameter that is a lambda.1954FormatToken const *next = Current.Next;1955while (next) {1956if (next->is(TT_LambdaLSquare)) {1957NewState.HasMultipleNestedBlocks = true;1958break;1959}1960next = next->Next;1961}1962}1963
1964NewState.IsInsideObjCArrayLiteral = Current.is(TT_ArrayInitializerLSquare) &&1965Current.Previous &&1966Current.Previous->is(tok::at);1967}
1968
1969void ContinuationIndenter::moveStatePastScopeCloser(LineState &State) {1970const FormatToken &Current = *State.NextToken;1971if (!Current.closesScope())1972return;1973
1974// If we encounter a closing ), ], } or >, we can remove a level from our1975// stacks.1976if (State.Stack.size() > 1 &&1977(Current.isOneOf(tok::r_paren, tok::r_square, TT_TemplateString) ||1978(Current.is(tok::r_brace) && State.NextToken != State.Line->First) ||1979State.NextToken->is(TT_TemplateCloser) ||1980State.NextToken->is(TT_TableGenListCloser) ||1981(Current.is(tok::greater) && Current.is(TT_DictLiteral)))) {1982State.Stack.pop_back();1983}1984
1985auto &CurrentState = State.Stack.back();1986
1987// Reevaluate whether ObjC message arguments fit into one line.1988// If a receiver spans multiple lines, e.g.:1989// [[object block:^{1990// return 42;1991// }] a:42 b:42];1992// BreakBeforeParameter is calculated based on an incorrect assumption1993// (it is checked whether the whole expression fits into one line without1994// considering a line break inside a message receiver).1995// We check whether arguments fit after receiver scope closer (into the same1996// line).1997if (CurrentState.BreakBeforeParameter && Current.MatchingParen &&1998Current.MatchingParen->Previous) {1999const FormatToken &CurrentScopeOpener = *Current.MatchingParen->Previous;2000if (CurrentScopeOpener.is(TT_ObjCMethodExpr) &&2001CurrentScopeOpener.MatchingParen) {2002int NecessarySpaceInLine =2003getLengthToMatchingParen(CurrentScopeOpener, State.Stack) +2004CurrentScopeOpener.TotalLength - Current.TotalLength - 1;2005if (State.Column + Current.ColumnWidth + NecessarySpaceInLine <=2006Style.ColumnLimit) {2007CurrentState.BreakBeforeParameter = false;2008}2009}2010}2011
2012if (Current.is(tok::r_square)) {2013// If this ends the array subscript expr, reset the corresponding value.2014const FormatToken *NextNonComment = Current.getNextNonComment();2015if (NextNonComment && NextNonComment->isNot(tok::l_square))2016CurrentState.StartOfArraySubscripts = 0;2017}2018}
2019
2020void ContinuationIndenter::moveStateToNewBlock(LineState &State, bool NewLine) {2021if (Style.LambdaBodyIndentation == FormatStyle::LBI_OuterScope &&2022State.NextToken->is(TT_LambdaLBrace) &&2023!State.Line->MightBeFunctionDecl) {2024State.Stack.back().NestedBlockIndent = State.FirstIndent;2025}2026unsigned NestedBlockIndent = State.Stack.back().NestedBlockIndent;2027// ObjC block sometimes follow special indentation rules.2028unsigned NewIndent =2029NestedBlockIndent + (State.NextToken->is(TT_ObjCBlockLBrace)2030? Style.ObjCBlockIndentWidth2031: Style.IndentWidth);2032
2033// Even when wrapping before lambda body, the left brace can still be added to2034// the same line. This occurs when checking whether the whole lambda body can2035// go on a single line. In this case we have to make sure there are no line2036// breaks in the body, otherwise we could just end up with a regular lambda2037// body without the brace wrapped.2038bool NoLineBreak = Style.BraceWrapping.BeforeLambdaBody && !NewLine &&2039State.NextToken->is(TT_LambdaLBrace);2040
2041State.Stack.push_back(ParenState(State.NextToken, NewIndent,2042State.Stack.back().LastSpace,2043/*AvoidBinPacking=*/true, NoLineBreak));2044State.Stack.back().NestedBlockIndent = NestedBlockIndent;2045State.Stack.back().BreakBeforeParameter = true;2046}
2047
2048static unsigned getLastLineEndColumn(StringRef Text, unsigned StartColumn,2049unsigned TabWidth,2050encoding::Encoding Encoding) {2051size_t LastNewlinePos = Text.find_last_of("\n");2052if (LastNewlinePos == StringRef::npos) {2053return StartColumn +2054encoding::columnWidthWithTabs(Text, StartColumn, TabWidth, Encoding);2055} else {2056return encoding::columnWidthWithTabs(Text.substr(LastNewlinePos),2057/*StartColumn=*/0, TabWidth, Encoding);2058}2059}
2060
2061unsigned ContinuationIndenter::reformatRawStringLiteral(2062const FormatToken &Current, LineState &State,2063const FormatStyle &RawStringStyle, bool DryRun, bool Newline) {2064unsigned StartColumn = State.Column - Current.ColumnWidth;2065StringRef OldDelimiter = *getRawStringDelimiter(Current.TokenText);2066StringRef NewDelimiter =2067getCanonicalRawStringDelimiter(Style, RawStringStyle.Language);2068if (NewDelimiter.empty())2069NewDelimiter = OldDelimiter;2070// The text of a raw string is between the leading 'R"delimiter(' and the2071// trailing 'delimiter)"'.2072unsigned OldPrefixSize = 3 + OldDelimiter.size();2073unsigned OldSuffixSize = 2 + OldDelimiter.size();2074// We create a virtual text environment which expects a null-terminated2075// string, so we cannot use StringRef.2076std::string RawText = std::string(2077Current.TokenText.substr(OldPrefixSize).drop_back(OldSuffixSize));2078if (NewDelimiter != OldDelimiter) {2079// Don't update to the canonical delimiter 'deli' if ')deli"' occurs in the2080// raw string.2081std::string CanonicalDelimiterSuffix = (")" + NewDelimiter + "\"").str();2082if (StringRef(RawText).contains(CanonicalDelimiterSuffix))2083NewDelimiter = OldDelimiter;2084}2085
2086unsigned NewPrefixSize = 3 + NewDelimiter.size();2087unsigned NewSuffixSize = 2 + NewDelimiter.size();2088
2089// The first start column is the column the raw text starts after formatting.2090unsigned FirstStartColumn = StartColumn + NewPrefixSize;2091
2092// The next start column is the intended indentation a line break inside2093// the raw string at level 0. It is determined by the following rules:2094// - if the content starts on newline, it is one level more than the current2095// indent, and2096// - if the content does not start on a newline, it is the first start2097// column.2098// These rules have the advantage that the formatted content both does not2099// violate the rectangle rule and visually flows within the surrounding2100// source.2101bool ContentStartsOnNewline = Current.TokenText[OldPrefixSize] == '\n';2102// If this token is the last parameter (checked by looking if it's followed by2103// `)` and is not on a newline, the base the indent off the line's nested2104// block indent. Otherwise, base the indent off the arguments indent, so we2105// can achieve:2106//2107// fffffffffff(1, 2, 3, R"pb(2108// key1: 1 #2109// key2: 2)pb");2110//2111// fffffffffff(1, 2, 3,2112// R"pb(2113// key1: 1 #2114// key2: 22115// )pb");2116//2117// fffffffffff(1, 2, 3,2118// R"pb(2119// key1: 1 #2120// key2: 22121// )pb",2122// 5);2123unsigned CurrentIndent =2124(!Newline && Current.Next && Current.Next->is(tok::r_paren))2125? State.Stack.back().NestedBlockIndent2126: State.Stack.back().Indent;2127unsigned NextStartColumn = ContentStartsOnNewline2128? CurrentIndent + Style.IndentWidth2129: FirstStartColumn;2130
2131// The last start column is the column the raw string suffix starts if it is2132// put on a newline.2133// The last start column is the intended indentation of the raw string postfix2134// if it is put on a newline. It is determined by the following rules:2135// - if the raw string prefix starts on a newline, it is the column where2136// that raw string prefix starts, and2137// - if the raw string prefix does not start on a newline, it is the current2138// indent.2139unsigned LastStartColumn =2140Current.NewlinesBefore ? FirstStartColumn - NewPrefixSize : CurrentIndent;2141
2142std::pair<tooling::Replacements, unsigned> Fixes = internal::reformat(2143RawStringStyle, RawText, {tooling::Range(0, RawText.size())},2144FirstStartColumn, NextStartColumn, LastStartColumn, "<stdin>",2145/*Status=*/nullptr);2146
2147auto NewCode = applyAllReplacements(RawText, Fixes.first);2148tooling::Replacements NoFixes;2149if (!NewCode)2150return addMultilineToken(Current, State);2151if (!DryRun) {2152if (NewDelimiter != OldDelimiter) {2153// In 'R"delimiter(...', the delimiter starts 2 characters after the start2154// of the token.2155SourceLocation PrefixDelimiterStart =2156Current.Tok.getLocation().getLocWithOffset(2);2157auto PrefixErr = Whitespaces.addReplacement(tooling::Replacement(2158SourceMgr, PrefixDelimiterStart, OldDelimiter.size(), NewDelimiter));2159if (PrefixErr) {2160llvm::errs()2161<< "Failed to update the prefix delimiter of a raw string: "2162<< llvm::toString(std::move(PrefixErr)) << "\n";2163}2164// In 'R"delimiter(...)delimiter"', the suffix delimiter starts at2165// position length - 1 - |delimiter|.2166SourceLocation SuffixDelimiterStart =2167Current.Tok.getLocation().getLocWithOffset(Current.TokenText.size() -21681 - OldDelimiter.size());2169auto SuffixErr = Whitespaces.addReplacement(tooling::Replacement(2170SourceMgr, SuffixDelimiterStart, OldDelimiter.size(), NewDelimiter));2171if (SuffixErr) {2172llvm::errs()2173<< "Failed to update the suffix delimiter of a raw string: "2174<< llvm::toString(std::move(SuffixErr)) << "\n";2175}2176}2177SourceLocation OriginLoc =2178Current.Tok.getLocation().getLocWithOffset(OldPrefixSize);2179for (const tooling::Replacement &Fix : Fixes.first) {2180auto Err = Whitespaces.addReplacement(tooling::Replacement(2181SourceMgr, OriginLoc.getLocWithOffset(Fix.getOffset()),2182Fix.getLength(), Fix.getReplacementText()));2183if (Err) {2184llvm::errs() << "Failed to reformat raw string: "2185<< llvm::toString(std::move(Err)) << "\n";2186}2187}2188}2189unsigned RawLastLineEndColumn = getLastLineEndColumn(2190*NewCode, FirstStartColumn, Style.TabWidth, Encoding);2191State.Column = RawLastLineEndColumn + NewSuffixSize;2192// Since we're updating the column to after the raw string literal here, we2193// have to manually add the penalty for the prefix R"delim( over the column2194// limit.2195unsigned PrefixExcessCharacters =2196StartColumn + NewPrefixSize > Style.ColumnLimit2197? StartColumn + NewPrefixSize - Style.ColumnLimit2198: 0;2199bool IsMultiline =2200ContentStartsOnNewline || (NewCode->find('\n') != std::string::npos);2201if (IsMultiline) {2202// Break before further function parameters on all levels.2203for (ParenState &Paren : State.Stack)2204Paren.BreakBeforeParameter = true;2205}2206return Fixes.second + PrefixExcessCharacters * Style.PenaltyExcessCharacter;2207}
2208
2209unsigned ContinuationIndenter::addMultilineToken(const FormatToken &Current,2210LineState &State) {2211// Break before further function parameters on all levels.2212for (ParenState &Paren : State.Stack)2213Paren.BreakBeforeParameter = true;2214
2215unsigned ColumnsUsed = State.Column;2216// We can only affect layout of the first and the last line, so the penalty2217// for all other lines is constant, and we ignore it.2218State.Column = Current.LastLineColumnWidth;2219
2220if (ColumnsUsed > getColumnLimit(State))2221return Style.PenaltyExcessCharacter * (ColumnsUsed - getColumnLimit(State));2222return 0;2223}
2224
2225unsigned ContinuationIndenter::handleEndOfLine(const FormatToken &Current,2226LineState &State, bool DryRun,2227bool AllowBreak, bool Newline) {2228unsigned Penalty = 0;2229// Compute the raw string style to use in case this is a raw string literal2230// that can be reformatted.2231auto RawStringStyle = getRawStringStyle(Current, State);2232if (RawStringStyle && !Current.Finalized) {2233Penalty = reformatRawStringLiteral(Current, State, *RawStringStyle, DryRun,2234Newline);2235} else if (Current.IsMultiline && Current.isNot(TT_BlockComment)) {2236// Don't break multi-line tokens other than block comments and raw string2237// literals. Instead, just update the state.2238Penalty = addMultilineToken(Current, State);2239} else if (State.Line->Type != LT_ImportStatement) {2240// We generally don't break import statements.2241LineState OriginalState = State;2242
2243// Whether we force the reflowing algorithm to stay strictly within the2244// column limit.2245bool Strict = false;2246// Whether the first non-strict attempt at reflowing did intentionally2247// exceed the column limit.2248bool Exceeded = false;2249std::tie(Penalty, Exceeded) = breakProtrudingToken(2250Current, State, AllowBreak, /*DryRun=*/true, Strict);2251if (Exceeded) {2252// If non-strict reflowing exceeds the column limit, try whether strict2253// reflowing leads to an overall lower penalty.2254LineState StrictState = OriginalState;2255unsigned StrictPenalty =2256breakProtrudingToken(Current, StrictState, AllowBreak,2257/*DryRun=*/true, /*Strict=*/true)2258.first;2259Strict = StrictPenalty <= Penalty;2260if (Strict) {2261Penalty = StrictPenalty;2262State = StrictState;2263}2264}2265if (!DryRun) {2266// If we're not in dry-run mode, apply the changes with the decision on2267// strictness made above.2268breakProtrudingToken(Current, OriginalState, AllowBreak, /*DryRun=*/false,2269Strict);2270}2271}2272if (State.Column > getColumnLimit(State)) {2273unsigned ExcessCharacters = State.Column - getColumnLimit(State);2274Penalty += Style.PenaltyExcessCharacter * ExcessCharacters;2275}2276return Penalty;2277}
2278
2279// Returns the enclosing function name of a token, or the empty string if not
2280// found.
2281static StringRef getEnclosingFunctionName(const FormatToken &Current) {2282// Look for: 'function(' or 'function<templates>(' before Current.2283auto Tok = Current.getPreviousNonComment();2284if (!Tok || Tok->isNot(tok::l_paren))2285return "";2286Tok = Tok->getPreviousNonComment();2287if (!Tok)2288return "";2289if (Tok->is(TT_TemplateCloser)) {2290Tok = Tok->MatchingParen;2291if (Tok)2292Tok = Tok->getPreviousNonComment();2293}2294if (!Tok || Tok->isNot(tok::identifier))2295return "";2296return Tok->TokenText;2297}
2298
2299std::optional<FormatStyle>2300ContinuationIndenter::getRawStringStyle(const FormatToken &Current,2301const LineState &State) {2302if (!Current.isStringLiteral())2303return std::nullopt;2304auto Delimiter = getRawStringDelimiter(Current.TokenText);2305if (!Delimiter)2306return std::nullopt;2307auto RawStringStyle = RawStringFormats.getDelimiterStyle(*Delimiter);2308if (!RawStringStyle && Delimiter->empty()) {2309RawStringStyle = RawStringFormats.getEnclosingFunctionStyle(2310getEnclosingFunctionName(Current));2311}2312if (!RawStringStyle)2313return std::nullopt;2314RawStringStyle->ColumnLimit = getColumnLimit(State);2315return RawStringStyle;2316}
2317
2318std::unique_ptr<BreakableToken>2319ContinuationIndenter::createBreakableToken(const FormatToken &Current,2320LineState &State, bool AllowBreak) {2321unsigned StartColumn = State.Column - Current.ColumnWidth;2322if (Current.isStringLiteral()) {2323// Strings in JSON cannot be broken. Breaking strings in JavaScript is2324// disabled for now.2325if (Style.isJson() || Style.isJavaScript() || !Style.BreakStringLiterals ||2326!AllowBreak) {2327return nullptr;2328}2329
2330// Don't break string literals inside preprocessor directives (except for2331// #define directives, as their contents are stored in separate lines and2332// are not affected by this check).2333// This way we avoid breaking code with line directives and unknown2334// preprocessor directives that contain long string literals.2335if (State.Line->Type == LT_PreprocessorDirective)2336return nullptr;2337// Exempts unterminated string literals from line breaking. The user will2338// likely want to terminate the string before any line breaking is done.2339if (Current.IsUnterminatedLiteral)2340return nullptr;2341// Don't break string literals inside Objective-C array literals (doing so2342// raises the warning -Wobjc-string-concatenation).2343if (State.Stack.back().IsInsideObjCArrayLiteral)2344return nullptr;2345
2346// The "DPI"/"DPI-C" in SystemVerilog direct programming interface2347// imports/exports cannot be split, e.g.2348// `import "DPI" function foo();`2349// FIXME: make this use same infra as C++ import checks2350if (Style.isVerilog() && Current.Previous &&2351Current.Previous->isOneOf(tok::kw_export, Keywords.kw_import)) {2352return nullptr;2353}2354StringRef Text = Current.TokenText;2355
2356// We need this to address the case where there is an unbreakable tail only2357// if certain other formatting decisions have been taken. The2358// UnbreakableTailLength of Current is an overapproximation in that case and2359// we need to be correct here.2360unsigned UnbreakableTailLength = (State.NextToken && canBreak(State))2361? 02362: Current.UnbreakableTailLength;2363
2364if (Style.isVerilog() || Style.Language == FormatStyle::LK_Java ||2365Style.isJavaScript() || Style.isCSharp()) {2366BreakableStringLiteralUsingOperators::QuoteStyleType QuoteStyle;2367if (Style.isJavaScript() && Text.starts_with("'") &&2368Text.ends_with("'")) {2369QuoteStyle = BreakableStringLiteralUsingOperators::SingleQuotes;2370} else if (Style.isCSharp() && Text.starts_with("@\"") &&2371Text.ends_with("\"")) {2372QuoteStyle = BreakableStringLiteralUsingOperators::AtDoubleQuotes;2373} else if (Text.starts_with("\"") && Text.ends_with("\"")) {2374QuoteStyle = BreakableStringLiteralUsingOperators::DoubleQuotes;2375} else {2376return nullptr;2377}2378return std::make_unique<BreakableStringLiteralUsingOperators>(2379Current, QuoteStyle,2380/*UnindentPlus=*/shouldUnindentNextOperator(Current), StartColumn,2381UnbreakableTailLength, State.Line->InPPDirective, Encoding, Style);2382}2383
2384StringRef Prefix;2385StringRef Postfix;2386// FIXME: Handle whitespace between '_T', '(', '"..."', and ')'.2387// FIXME: Store Prefix and Suffix (or PrefixLength and SuffixLength to2388// reduce the overhead) for each FormatToken, which is a string, so that we2389// don't run multiple checks here on the hot path.2390if ((Text.ends_with(Postfix = "\"") &&2391(Text.starts_with(Prefix = "@\"") || Text.starts_with(Prefix = "\"") ||2392Text.starts_with(Prefix = "u\"") ||2393Text.starts_with(Prefix = "U\"") ||2394Text.starts_with(Prefix = "u8\"") ||2395Text.starts_with(Prefix = "L\""))) ||2396(Text.starts_with(Prefix = "_T(\"") &&2397Text.ends_with(Postfix = "\")"))) {2398return std::make_unique<BreakableStringLiteral>(2399Current, StartColumn, Prefix, Postfix, UnbreakableTailLength,2400State.Line->InPPDirective, Encoding, Style);2401}2402} else if (Current.is(TT_BlockComment)) {2403if (!Style.ReflowComments ||2404// If a comment token switches formatting, like2405// /* clang-format on */, we don't want to break it further,2406// but we may still want to adjust its indentation.2407switchesFormatting(Current)) {2408return nullptr;2409}2410return std::make_unique<BreakableBlockComment>(2411Current, StartColumn, Current.OriginalColumn, !Current.Previous,2412State.Line->InPPDirective, Encoding, Style, Whitespaces.useCRLF());2413} else if (Current.is(TT_LineComment) &&2414(!Current.Previous ||2415Current.Previous->isNot(TT_ImplicitStringLiteral))) {2416bool RegularComments = [&]() {2417for (const FormatToken *T = &Current; T && T->is(TT_LineComment);2418T = T->Next) {2419if (!(T->TokenText.starts_with("//") || T->TokenText.starts_with("#")))2420return false;2421}2422return true;2423}();2424if (!Style.ReflowComments ||2425CommentPragmasRegex.match(Current.TokenText.substr(2)) ||2426switchesFormatting(Current) || !RegularComments) {2427return nullptr;2428}2429return std::make_unique<BreakableLineCommentSection>(2430Current, StartColumn, /*InPPDirective=*/false, Encoding, Style);2431}2432return nullptr;2433}
2434
2435std::pair<unsigned, bool>2436ContinuationIndenter::breakProtrudingToken(const FormatToken &Current,2437LineState &State, bool AllowBreak,2438bool DryRun, bool Strict) {2439std::unique_ptr<const BreakableToken> Token =2440createBreakableToken(Current, State, AllowBreak);2441if (!Token)2442return {0, false};2443assert(Token->getLineCount() > 0);2444unsigned ColumnLimit = getColumnLimit(State);2445if (Current.is(TT_LineComment)) {2446// We don't insert backslashes when breaking line comments.2447ColumnLimit = Style.ColumnLimit;2448}2449if (ColumnLimit == 0) {2450// To make the rest of the function easier set the column limit to the2451// maximum, if there should be no limit.2452ColumnLimit = std::numeric_limits<decltype(ColumnLimit)>::max();2453}2454if (Current.UnbreakableTailLength >= ColumnLimit)2455return {0, false};2456// ColumnWidth was already accounted into State.Column before calling2457// breakProtrudingToken.2458unsigned StartColumn = State.Column - Current.ColumnWidth;2459unsigned NewBreakPenalty = Current.isStringLiteral()2460? Style.PenaltyBreakString2461: Style.PenaltyBreakComment;2462// Stores whether we intentionally decide to let a line exceed the column2463// limit.2464bool Exceeded = false;2465// Stores whether we introduce a break anywhere in the token.2466bool BreakInserted = Token->introducesBreakBeforeToken();2467// Store whether we inserted a new line break at the end of the previous2468// logical line.2469bool NewBreakBefore = false;2470// We use a conservative reflowing strategy. Reflow starts after a line is2471// broken or the corresponding whitespace compressed. Reflow ends as soon as a2472// line that doesn't get reflown with the previous line is reached.2473bool Reflow = false;2474// Keep track of where we are in the token:2475// Where we are in the content of the current logical line.2476unsigned TailOffset = 0;2477// The column number we're currently at.2478unsigned ContentStartColumn =2479Token->getContentStartColumn(0, /*Break=*/false);2480// The number of columns left in the current logical line after TailOffset.2481unsigned RemainingTokenColumns =2482Token->getRemainingLength(0, TailOffset, ContentStartColumn);2483// Adapt the start of the token, for example indent.2484if (!DryRun)2485Token->adaptStartOfLine(0, Whitespaces);2486
2487unsigned ContentIndent = 0;2488unsigned Penalty = 0;2489LLVM_DEBUG(llvm::dbgs() << "Breaking protruding token at column "2490<< StartColumn << ".\n");2491for (unsigned LineIndex = 0, EndIndex = Token->getLineCount();2492LineIndex != EndIndex; ++LineIndex) {2493LLVM_DEBUG(llvm::dbgs()2494<< " Line: " << LineIndex << " (Reflow: " << Reflow << ")\n");2495NewBreakBefore = false;2496// If we did reflow the previous line, we'll try reflowing again. Otherwise2497// we'll start reflowing if the current line is broken or whitespace is2498// compressed.2499bool TryReflow = Reflow;2500// Break the current token until we can fit the rest of the line.2501while (ContentStartColumn + RemainingTokenColumns > ColumnLimit) {2502LLVM_DEBUG(llvm::dbgs() << " Over limit, need: "2503<< (ContentStartColumn + RemainingTokenColumns)2504<< ", space: " << ColumnLimit2505<< ", reflown prefix: " << ContentStartColumn2506<< ", offset in line: " << TailOffset << "\n");2507// If the current token doesn't fit, find the latest possible split in the2508// current line so that breaking at it will be under the column limit.2509// FIXME: Use the earliest possible split while reflowing to correctly2510// compress whitespace within a line.2511BreakableToken::Split Split =2512Token->getSplit(LineIndex, TailOffset, ColumnLimit,2513ContentStartColumn, CommentPragmasRegex);2514if (Split.first == StringRef::npos) {2515// No break opportunity - update the penalty and continue with the next2516// logical line.2517if (LineIndex < EndIndex - 1) {2518// The last line's penalty is handled in addNextStateToQueue() or when2519// calling replaceWhitespaceAfterLastLine below.2520Penalty += Style.PenaltyExcessCharacter *2521(ContentStartColumn + RemainingTokenColumns - ColumnLimit);2522}2523LLVM_DEBUG(llvm::dbgs() << " No break opportunity.\n");2524break;2525}2526assert(Split.first != 0);2527
2528if (Token->supportsReflow()) {2529// Check whether the next natural split point after the current one can2530// still fit the line, either because we can compress away whitespace,2531// or because the penalty the excess characters introduce is lower than2532// the break penalty.2533// We only do this for tokens that support reflowing, and thus allow us2534// to change the whitespace arbitrarily (e.g. comments).2535// Other tokens, like string literals, can be broken on arbitrary2536// positions.2537
2538// First, compute the columns from TailOffset to the next possible split2539// position.2540// For example:2541// ColumnLimit: |2542// // Some text that breaks2543// ^ tail offset2544// ^-- split2545// ^-------- to split columns2546// ^--- next split2547// ^--------------- to next split columns2548unsigned ToSplitColumns = Token->getRangeLength(2549LineIndex, TailOffset, Split.first, ContentStartColumn);2550LLVM_DEBUG(llvm::dbgs() << " ToSplit: " << ToSplitColumns << "\n");2551
2552BreakableToken::Split NextSplit = Token->getSplit(2553LineIndex, TailOffset + Split.first + Split.second, ColumnLimit,2554ContentStartColumn + ToSplitColumns + 1, CommentPragmasRegex);2555// Compute the columns necessary to fit the next non-breakable sequence2556// into the current line.2557unsigned ToNextSplitColumns = 0;2558if (NextSplit.first == StringRef::npos) {2559ToNextSplitColumns = Token->getRemainingLength(LineIndex, TailOffset,2560ContentStartColumn);2561} else {2562ToNextSplitColumns = Token->getRangeLength(2563LineIndex, TailOffset,2564Split.first + Split.second + NextSplit.first, ContentStartColumn);2565}2566// Compress the whitespace between the break and the start of the next2567// unbreakable sequence.2568ToNextSplitColumns =2569Token->getLengthAfterCompression(ToNextSplitColumns, Split);2570LLVM_DEBUG(llvm::dbgs()2571<< " ContentStartColumn: " << ContentStartColumn << "\n");2572LLVM_DEBUG(llvm::dbgs()2573<< " ToNextSplit: " << ToNextSplitColumns << "\n");2574// If the whitespace compression makes us fit, continue on the current2575// line.2576bool ContinueOnLine =2577ContentStartColumn + ToNextSplitColumns <= ColumnLimit;2578unsigned ExcessCharactersPenalty = 0;2579if (!ContinueOnLine && !Strict) {2580// Similarly, if the excess characters' penalty is lower than the2581// penalty of introducing a new break, continue on the current line.2582ExcessCharactersPenalty =2583(ContentStartColumn + ToNextSplitColumns - ColumnLimit) *2584Style.PenaltyExcessCharacter;2585LLVM_DEBUG(llvm::dbgs()2586<< " Penalty excess: " << ExcessCharactersPenalty2587<< "\n break : " << NewBreakPenalty << "\n");2588if (ExcessCharactersPenalty < NewBreakPenalty) {2589Exceeded = true;2590ContinueOnLine = true;2591}2592}2593if (ContinueOnLine) {2594LLVM_DEBUG(llvm::dbgs() << " Continuing on line...\n");2595// The current line fits after compressing the whitespace - reflow2596// the next line into it if possible.2597TryReflow = true;2598if (!DryRun) {2599Token->compressWhitespace(LineIndex, TailOffset, Split,2600Whitespaces);2601}2602// When we continue on the same line, leave one space between content.2603ContentStartColumn += ToSplitColumns + 1;2604Penalty += ExcessCharactersPenalty;2605TailOffset += Split.first + Split.second;2606RemainingTokenColumns = Token->getRemainingLength(2607LineIndex, TailOffset, ContentStartColumn);2608continue;2609}2610}2611LLVM_DEBUG(llvm::dbgs() << " Breaking...\n");2612// Update the ContentIndent only if the current line was not reflown with2613// the previous line, since in that case the previous line should still2614// determine the ContentIndent. Also never intent the last line.2615if (!Reflow)2616ContentIndent = Token->getContentIndent(LineIndex);2617LLVM_DEBUG(llvm::dbgs()2618<< " ContentIndent: " << ContentIndent << "\n");2619ContentStartColumn = ContentIndent + Token->getContentStartColumn(2620LineIndex, /*Break=*/true);2621
2622unsigned NewRemainingTokenColumns = Token->getRemainingLength(2623LineIndex, TailOffset + Split.first + Split.second,2624ContentStartColumn);2625if (NewRemainingTokenColumns == 0) {2626// No content to indent.2627ContentIndent = 0;2628ContentStartColumn =2629Token->getContentStartColumn(LineIndex, /*Break=*/true);2630NewRemainingTokenColumns = Token->getRemainingLength(2631LineIndex, TailOffset + Split.first + Split.second,2632ContentStartColumn);2633}2634
2635// When breaking before a tab character, it may be moved by a few columns,2636// but will still be expanded to the next tab stop, so we don't save any2637// columns.2638if (NewRemainingTokenColumns >= RemainingTokenColumns) {2639// FIXME: Do we need to adjust the penalty?2640break;2641}2642
2643LLVM_DEBUG(llvm::dbgs() << " Breaking at: " << TailOffset + Split.first2644<< ", " << Split.second << "\n");2645if (!DryRun) {2646Token->insertBreak(LineIndex, TailOffset, Split, ContentIndent,2647Whitespaces);2648}2649
2650Penalty += NewBreakPenalty;2651TailOffset += Split.first + Split.second;2652RemainingTokenColumns = NewRemainingTokenColumns;2653BreakInserted = true;2654NewBreakBefore = true;2655}2656// In case there's another line, prepare the state for the start of the next2657// line.2658if (LineIndex + 1 != EndIndex) {2659unsigned NextLineIndex = LineIndex + 1;2660if (NewBreakBefore) {2661// After breaking a line, try to reflow the next line into the current2662// one once RemainingTokenColumns fits.2663TryReflow = true;2664}2665if (TryReflow) {2666// We decided that we want to try reflowing the next line into the2667// current one.2668// We will now adjust the state as if the reflow is successful (in2669// preparation for the next line), and see whether that works. If we2670// decide that we cannot reflow, we will later reset the state to the2671// start of the next line.2672Reflow = false;2673// As we did not continue breaking the line, RemainingTokenColumns is2674// known to fit after ContentStartColumn. Adapt ContentStartColumn to2675// the position at which we want to format the next line if we do2676// actually reflow.2677// When we reflow, we need to add a space between the end of the current2678// line and the next line's start column.2679ContentStartColumn += RemainingTokenColumns + 1;2680// Get the split that we need to reflow next logical line into the end2681// of the current one; the split will include any leading whitespace of2682// the next logical line.2683BreakableToken::Split SplitBeforeNext =2684Token->getReflowSplit(NextLineIndex, CommentPragmasRegex);2685LLVM_DEBUG(llvm::dbgs()2686<< " Size of reflown text: " << ContentStartColumn2687<< "\n Potential reflow split: ");2688if (SplitBeforeNext.first != StringRef::npos) {2689LLVM_DEBUG(llvm::dbgs() << SplitBeforeNext.first << ", "2690<< SplitBeforeNext.second << "\n");2691TailOffset = SplitBeforeNext.first + SplitBeforeNext.second;2692// If the rest of the next line fits into the current line below the2693// column limit, we can safely reflow.2694RemainingTokenColumns = Token->getRemainingLength(2695NextLineIndex, TailOffset, ContentStartColumn);2696Reflow = true;2697if (ContentStartColumn + RemainingTokenColumns > ColumnLimit) {2698LLVM_DEBUG(llvm::dbgs()2699<< " Over limit after reflow, need: "2700<< (ContentStartColumn + RemainingTokenColumns)2701<< ", space: " << ColumnLimit2702<< ", reflown prefix: " << ContentStartColumn2703<< ", offset in line: " << TailOffset << "\n");2704// If the whole next line does not fit, try to find a point in2705// the next line at which we can break so that attaching the part2706// of the next line to that break point onto the current line is2707// below the column limit.2708BreakableToken::Split Split =2709Token->getSplit(NextLineIndex, TailOffset, ColumnLimit,2710ContentStartColumn, CommentPragmasRegex);2711if (Split.first == StringRef::npos) {2712LLVM_DEBUG(llvm::dbgs() << " Did not find later break\n");2713Reflow = false;2714} else {2715// Check whether the first split point gets us below the column2716// limit. Note that we will execute this split below as part of2717// the normal token breaking and reflow logic within the line.2718unsigned ToSplitColumns = Token->getRangeLength(2719NextLineIndex, TailOffset, Split.first, ContentStartColumn);2720if (ContentStartColumn + ToSplitColumns > ColumnLimit) {2721LLVM_DEBUG(llvm::dbgs() << " Next split protrudes, need: "2722<< (ContentStartColumn + ToSplitColumns)2723<< ", space: " << ColumnLimit);2724unsigned ExcessCharactersPenalty =2725(ContentStartColumn + ToSplitColumns - ColumnLimit) *2726Style.PenaltyExcessCharacter;2727if (NewBreakPenalty < ExcessCharactersPenalty)2728Reflow = false;2729}2730}2731}2732} else {2733LLVM_DEBUG(llvm::dbgs() << "not found.\n");2734}2735}2736if (!Reflow) {2737// If we didn't reflow into the next line, the only space to consider is2738// the next logical line. Reset our state to match the start of the next2739// line.2740TailOffset = 0;2741ContentStartColumn =2742Token->getContentStartColumn(NextLineIndex, /*Break=*/false);2743RemainingTokenColumns = Token->getRemainingLength(2744NextLineIndex, TailOffset, ContentStartColumn);2745// Adapt the start of the token, for example indent.2746if (!DryRun)2747Token->adaptStartOfLine(NextLineIndex, Whitespaces);2748} else {2749// If we found a reflow split and have added a new break before the next2750// line, we are going to remove the line break at the start of the next2751// logical line. For example, here we'll add a new line break after2752// 'text', and subsequently delete the line break between 'that' and2753// 'reflows'.2754// // some text that2755// // reflows2756// ->2757// // some text2758// // that reflows2759// When adding the line break, we also added the penalty for it, so we2760// need to subtract that penalty again when we remove the line break due2761// to reflowing.2762if (NewBreakBefore) {2763assert(Penalty >= NewBreakPenalty);2764Penalty -= NewBreakPenalty;2765}2766if (!DryRun)2767Token->reflow(NextLineIndex, Whitespaces);2768}2769}2770}2771
2772BreakableToken::Split SplitAfterLastLine =2773Token->getSplitAfterLastLine(TailOffset);2774if (SplitAfterLastLine.first != StringRef::npos) {2775LLVM_DEBUG(llvm::dbgs() << "Replacing whitespace after last line.\n");2776
2777// We add the last line's penalty here, since that line is going to be split2778// now.2779Penalty += Style.PenaltyExcessCharacter *2780(ContentStartColumn + RemainingTokenColumns - ColumnLimit);2781
2782if (!DryRun) {2783Token->replaceWhitespaceAfterLastLine(TailOffset, SplitAfterLastLine,2784Whitespaces);2785}2786ContentStartColumn =2787Token->getContentStartColumn(Token->getLineCount() - 1, /*Break=*/true);2788RemainingTokenColumns = Token->getRemainingLength(2789Token->getLineCount() - 1,2790TailOffset + SplitAfterLastLine.first + SplitAfterLastLine.second,2791ContentStartColumn);2792}2793
2794State.Column = ContentStartColumn + RemainingTokenColumns -2795Current.UnbreakableTailLength;2796
2797if (BreakInserted) {2798if (!DryRun)2799Token->updateAfterBroken(Whitespaces);2800
2801// If we break the token inside a parameter list, we need to break before2802// the next parameter on all levels, so that the next parameter is clearly2803// visible. Line comments already introduce a break.2804if (Current.isNot(TT_LineComment))2805for (ParenState &Paren : State.Stack)2806Paren.BreakBeforeParameter = true;2807
2808if (Current.is(TT_BlockComment))2809State.NoContinuation = true;2810
2811State.Stack.back().LastSpace = StartColumn;2812}2813
2814Token->updateNextToken(State);2815
2816return {Penalty, Exceeded};2817}
2818
2819unsigned ContinuationIndenter::getColumnLimit(const LineState &State) const {2820// In preprocessor directives reserve two chars for trailing " \".2821return Style.ColumnLimit - (State.Line->InPPDirective ? 2 : 0);2822}
2823
2824bool ContinuationIndenter::nextIsMultilineString(const LineState &State) {2825const FormatToken &Current = *State.NextToken;2826if (!Current.isStringLiteral() || Current.is(TT_ImplicitStringLiteral))2827return false;2828// We never consider raw string literals "multiline" for the purpose of2829// AlwaysBreakBeforeMultilineStrings implementation as they are special-cased2830// (see TokenAnnotator::mustBreakBefore().2831if (Current.TokenText.starts_with("R\""))2832return false;2833if (Current.IsMultiline)2834return true;2835if (Current.getNextNonComment() &&2836Current.getNextNonComment()->isStringLiteral()) {2837return true; // Implicit concatenation.2838}2839if (Style.ColumnLimit != 0 && Style.BreakStringLiterals &&2840State.Column + Current.ColumnWidth + Current.UnbreakableTailLength >2841Style.ColumnLimit) {2842return true; // String will be split.2843}2844return false;2845}
2846
2847} // namespace format2848} // namespace clang2849