19#include "llvm/ADT/SmallPtrSet.h"
20#include "llvm/Support/Debug.h"
22#define DEBUG_TYPE "format-token-annotator"
43static bool startsWithInitStatement(
const AnnotatedLine &
Line) {
44 return Line.startsWith(tok::kw_for) ||
Line.startsWith(tok::kw_if) ||
45 Line.startsWith(tok::kw_switch);
59static bool canBeObjCSelectorComponent(
const FormatToken &Tok) {
60 return Tok.Tok.getIdentifierInfo();
66static bool isLambdaParameterList(
const FormatToken *Left) {
68 if (
Left->Previous &&
Left->Previous->is(tok::greater) &&
69 Left->Previous->MatchingParen &&
70 Left->Previous->MatchingParen->is(TT_TemplateOpener)) {
71 Left =
Left->Previous->MatchingParen;
75 return Left->Previous &&
Left->Previous->is(tok::r_square) &&
76 Left->Previous->MatchingParen &&
77 Left->Previous->MatchingParen->is(TT_LambdaLSquare);
82static bool isKeywordWithCondition(
const FormatToken &Tok) {
83 return Tok.isOneOf(tok::kw_if, tok::kw_for, tok::kw_while, tok::kw_switch,
84 tok::kw_constexpr, tok::kw_catch);
88static bool isCppAttribute(
bool IsCpp,
const FormatToken &Tok) {
89 if (!IsCpp || !Tok.startsSequence(tok::l_square, tok::l_square))
92 if (Tok.Previous && Tok.Previous->is(tok::at))
94 const FormatToken *AttrTok = Tok.Next->Next;
99 if (AttrTok->startsSequence(tok::kw_using, tok::identifier, tok::colon))
101 if (AttrTok->isNot(tok::identifier))
103 while (AttrTok && !AttrTok->startsSequence(tok::r_square, tok::r_square)) {
107 if (AttrTok->is(tok::colon) ||
108 AttrTok->startsSequence(tok::identifier, tok::identifier) ||
109 AttrTok->startsSequence(tok::r_paren, tok::identifier)) {
112 if (AttrTok->is(tok::ellipsis))
114 AttrTok = AttrTok->Next;
116 return AttrTok && AttrTok->startsSequence(tok::r_square, tok::r_square);
124class AnnotatingParser {
126 AnnotatingParser(
const FormatStyle &Style, AnnotatedLine &Line,
127 const AdditionalKeywords &Keywords,
128 SmallVector<ScopeType> &Scopes)
129 : Style(Style), Line(Line), CurrentToken(Line.
First), AutoFound(
false),
131 Keywords(Keywords), Scopes(Scopes), TemplateDeclarationDepth(0) {
132 assert(IsCpp == LangOpts.CXXOperatorNames);
133 Contexts.push_back(Context(tok::unknown, 1,
false));
134 resetTokenMetadata();
138 ScopeType getScopeType(
const FormatToken &Token)
const {
139 switch (Token.getType()) {
140 case TT_FunctionLBrace:
141 case TT_LambdaLBrace:
144 case TT_StructLBrace:
153 if (!CurrentToken || !CurrentToken->Previous)
155 if (NonTemplateLess.count(CurrentToken->Previous) > 0)
158 const FormatToken &
Previous = *CurrentToken->Previous;
160 if (
Previous.Previous->Tok.isLiteral())
162 if (
Previous.Previous->is(tok::r_brace))
164 if (
Previous.Previous->is(tok::r_paren) && Contexts.size() > 1 &&
165 (!
Previous.Previous->MatchingParen ||
166 Previous.Previous->MatchingParen->isNot(
167 TT_OverloadedOperatorLParen))) {
170 if (
Previous.Previous->is(tok::kw_operator) &&
171 CurrentToken->is(tok::l_paren)) {
176 FormatToken *
Left = CurrentToken->Previous;
177 Left->ParentBracket = Contexts.back().ContextKind;
178 ScopedContextCreator ContextCreator(*
this, tok::less, 12);
180 Contexts.back().IsExpression =
false;
183 if (
Left->Previous &&
Left->Previous->isNot(tok::kw_template))
184 Contexts.back().ContextType = Context::TemplateArgument;
187 CurrentToken->is(tok::question)) {
191 while (CurrentToken) {
192 if (CurrentToken->is(tok::greater)) {
199 if (CurrentToken->Next && CurrentToken->Next->is(tok::greater) &&
200 Left->ParentBracket != tok::less &&
201 CurrentToken->getStartOfNonWhitespace() ==
202 CurrentToken->Next->getStartOfNonWhitespace().getLocWithOffset(
206 Left->MatchingParen = CurrentToken;
207 CurrentToken->MatchingParen =
Left;
215 Left->Previous->isOneOf(TT_SelectorName, TT_DictLiteral))) {
216 CurrentToken->setType(TT_DictLiteral);
218 CurrentToken->setType(TT_TemplateCloser);
219 CurrentToken->Tok.setLength(1);
221 if (CurrentToken->Next && CurrentToken->Next->Tok.isLiteral())
226 if (CurrentToken->is(tok::question) &&
231 if (CurrentToken->isOneOf(tok::r_paren, tok::r_square, tok::r_brace))
239 if (CurrentToken->Previous->isOneOf(tok::pipepipe, tok::ampamp) &&
240 CurrentToken->Previous->is(TT_BinaryOperator) &&
241 Contexts[Contexts.size() - 2].IsExpression &&
242 !Line.startsWith(tok::kw_template)) {
245 updateParameterCount(Left, CurrentToken);
247 if (FormatToken *
Previous = CurrentToken->getPreviousNonComment()) {
248 if (CurrentToken->is(tok::colon) ||
249 (CurrentToken->isOneOf(tok::l_brace, tok::less) &&
255 if (Style.isTableGen()) {
256 if (CurrentToken->isOneOf(tok::comma, tok::equal)) {
263 if (!parseTableGenValue())
273 bool parseUntouchableParens() {
274 while (CurrentToken) {
275 CurrentToken->Finalized =
true;
276 switch (CurrentToken->Tok.getKind()) {
279 if (!parseUntouchableParens())
294 bool parseParens(
bool LookForDecls =
false) {
297 assert(CurrentToken->Previous &&
"Unknown previous token");
298 FormatToken &OpeningParen = *CurrentToken->Previous;
299 assert(OpeningParen.is(tok::l_paren));
300 FormatToken *PrevNonComment = OpeningParen.getPreviousNonComment();
301 OpeningParen.ParentBracket = Contexts.back().ContextKind;
302 ScopedContextCreator ContextCreator(*
this, tok::l_paren, 1);
305 Contexts.back().ColonIsForRangeExpr =
306 Contexts.size() == 2 && Contexts[0].ColonIsForRangeExpr;
308 if (OpeningParen.Previous &&
309 OpeningParen.Previous->is(TT_UntouchableMacroFunc)) {
310 OpeningParen.Finalized =
true;
311 return parseUntouchableParens();
314 bool StartsObjCMethodExpr =
false;
315 if (!Style.isVerilog()) {
316 if (FormatToken *MaybeSel = OpeningParen.Previous) {
318 if (MaybeSel->isObjCAtKeyword(tok::objc_selector) &&
319 MaybeSel->Previous && MaybeSel->Previous->is(tok::at)) {
320 StartsObjCMethodExpr =
true;
325 if (OpeningParen.is(TT_OverloadedOperatorLParen)) {
327 FormatToken *Prev = &OpeningParen;
328 while (Prev->isNot(tok::kw_operator)) {
329 Prev = Prev->Previous;
330 assert(Prev &&
"Expect a kw_operator prior to the OperatorLParen!");
336 bool OperatorCalledAsMemberFunction =
337 Prev->Previous && Prev->Previous->isOneOf(tok::period, tok::arrow);
338 Contexts.back().IsExpression = OperatorCalledAsMemberFunction;
339 }
else if (OpeningParen.is(TT_VerilogInstancePortLParen)) {
340 Contexts.back().IsExpression =
true;
341 Contexts.back().ContextType = Context::VerilogInstancePortList;
342 }
else if (Style.isJavaScript() &&
343 (Line.startsWith(Keywords.kw_type, tok::identifier) ||
344 Line.startsWith(tok::kw_export, Keywords.kw_type,
348 Contexts.back().IsExpression =
false;
349 }
else if (OpeningParen.Previous &&
350 (OpeningParen.Previous->isOneOf(
351 tok::kw_static_assert, tok::kw_noexcept, tok::kw_explicit,
352 tok::kw_while, tok::l_paren, tok::comma,
353 TT_BinaryOperator) ||
354 OpeningParen.Previous->isIf())) {
356 Contexts.back().IsExpression =
true;
357 }
else if (Style.isJavaScript() && OpeningParen.Previous &&
358 (OpeningParen.Previous->is(Keywords.kw_function) ||
359 (OpeningParen.Previous->endsSequence(tok::identifier,
360 Keywords.kw_function)))) {
362 Contexts.back().IsExpression =
false;
363 }
else if (Style.isJavaScript() && OpeningParen.Previous &&
364 OpeningParen.Previous->is(TT_JsTypeColon)) {
366 Contexts.back().IsExpression =
false;
367 }
else if (isLambdaParameterList(&OpeningParen)) {
369 OpeningParen.setType(TT_LambdaDefinitionLParen);
370 Contexts.back().IsExpression =
false;
371 }
else if (OpeningParen.is(TT_RequiresExpressionLParen)) {
372 Contexts.back().IsExpression =
false;
373 }
else if (OpeningParen.Previous &&
374 OpeningParen.Previous->is(tok::kw__Generic)) {
375 Contexts.back().ContextType = Context::C11GenericSelection;
376 Contexts.back().IsExpression =
true;
377 }
else if (Line.InPPDirective &&
378 (!OpeningParen.Previous ||
379 OpeningParen.Previous->isNot(tok::identifier))) {
380 Contexts.back().IsExpression =
true;
381 }
else if (Contexts[Contexts.size() - 2].CaretFound) {
383 Contexts.back().IsExpression =
false;
384 }
else if (OpeningParen.Previous &&
385 OpeningParen.Previous->is(TT_ForEachMacro)) {
387 Contexts.back().ContextType = Context::ForEachMacro;
388 Contexts.back().IsExpression =
false;
389 }
else if (OpeningParen.Previous && OpeningParen.Previous->MatchingParen &&
390 OpeningParen.Previous->MatchingParen->isOneOf(
391 TT_ObjCBlockLParen, TT_FunctionTypeLParen)) {
392 Contexts.back().IsExpression =
false;
393 }
else if (!Line.MustBeDeclaration && !Line.InPPDirective) {
395 OpeningParen.Previous &&
396 OpeningParen.Previous->isOneOf(tok::kw_for, tok::kw_catch);
397 Contexts.back().IsExpression = !IsForOrCatch;
400 if (Style.isTableGen()) {
401 if (FormatToken *Prev = OpeningParen.Previous) {
402 if (Prev->is(TT_TableGenCondOperator)) {
403 Contexts.back().IsTableGenCondOpe =
true;
404 Contexts.back().IsExpression =
true;
405 }
else if (Contexts.size() > 1 &&
406 Contexts[Contexts.size() - 2].IsTableGenBangOpe) {
411 Contexts.back().IsTableGenBangOpe =
true;
412 Contexts.back().IsExpression =
true;
415 if (!parseTableGenDAGArg())
417 return parseTableGenDAGArgAndList(&OpeningParen);
424 if (PrevNonComment && OpeningParen.is(TT_Unknown)) {
425 if (PrevNonComment->isAttribute()) {
426 OpeningParen.setType(TT_AttributeLParen);
427 }
else if (PrevNonComment->isOneOf(TT_TypenameMacro, tok::kw_decltype,
430#include
"clang/Basic/TransformTypeTraits.def"
432 OpeningParen.setType(TT_TypeDeclarationParen);
434 if (PrevNonComment->isOneOf(tok::kw_decltype, tok::kw_typeof))
435 Contexts.back().IsExpression =
true;
439 if (StartsObjCMethodExpr) {
440 Contexts.back().ColonIsObjCMethodExpr =
true;
441 OpeningParen.setType(TT_ObjCMethodExpr);
452 bool MightBeFunctionType = !Contexts[Contexts.size() - 2].IsExpression;
453 bool ProbablyFunctionType =
454 CurrentToken->isPointerOrReference() || CurrentToken->is(tok::caret);
455 bool HasMultipleLines =
false;
456 bool HasMultipleParametersOnALine =
false;
457 bool MightBeObjCForRangeLoop =
458 OpeningParen.Previous && OpeningParen.Previous->is(tok::kw_for);
459 FormatToken *PossibleObjCForInToken =
nullptr;
460 while (CurrentToken) {
465 if (LookForDecls && CurrentToken->Next) {
466 FormatToken *Prev = CurrentToken->getPreviousNonComment();
468 FormatToken *PrevPrev = Prev->getPreviousNonComment();
469 FormatToken *Next = CurrentToken->Next;
470 if (PrevPrev && PrevPrev->is(tok::identifier) &&
471 PrevPrev->isNot(TT_TypeName) && Prev->isPointerOrReference() &&
472 CurrentToken->is(tok::identifier) && Next->isNot(tok::equal)) {
473 Prev->setType(TT_BinaryOperator);
474 LookForDecls =
false;
479 if (CurrentToken->Previous->is(TT_PointerOrReference) &&
480 CurrentToken->Previous->Previous->isOneOf(tok::l_paren,
482 ProbablyFunctionType =
true;
484 if (CurrentToken->is(tok::comma))
485 MightBeFunctionType =
false;
486 if (CurrentToken->Previous->is(TT_BinaryOperator))
487 Contexts.back().IsExpression =
true;
488 if (CurrentToken->is(tok::r_paren)) {
489 if (OpeningParen.isNot(TT_CppCastLParen) && MightBeFunctionType &&
490 ProbablyFunctionType && CurrentToken->Next &&
491 (CurrentToken->Next->is(tok::l_paren) ||
492 (CurrentToken->Next->is(tok::l_square) &&
493 Line.MustBeDeclaration))) {
494 OpeningParen.setType(OpeningParen.Next->is(tok::caret)
496 : TT_FunctionTypeLParen);
498 OpeningParen.MatchingParen = CurrentToken;
499 CurrentToken->MatchingParen = &OpeningParen;
501 if (CurrentToken->Next && CurrentToken->Next->is(tok::l_brace) &&
502 OpeningParen.Previous && OpeningParen.Previous->is(tok::l_paren)) {
506 for (FormatToken *Tok = &OpeningParen; Tok != CurrentToken;
508 if (Tok->is(TT_BinaryOperator) && Tok->isPointerOrReference())
509 Tok->setType(TT_PointerOrReference);
513 if (StartsObjCMethodExpr) {
514 CurrentToken->setType(TT_ObjCMethodExpr);
515 if (Contexts.back().FirstObjCSelectorName) {
516 Contexts.back().FirstObjCSelectorName->LongestObjCSelectorName =
517 Contexts.back().LongestObjCSelectorName;
521 if (OpeningParen.is(TT_AttributeLParen))
522 CurrentToken->setType(TT_AttributeRParen);
523 if (OpeningParen.is(TT_TypeDeclarationParen))
524 CurrentToken->setType(TT_TypeDeclarationParen);
525 if (OpeningParen.Previous &&
526 OpeningParen.Previous->is(TT_JavaAnnotation)) {
527 CurrentToken->setType(TT_JavaAnnotation);
529 if (OpeningParen.Previous &&
530 OpeningParen.Previous->is(TT_LeadingJavaAnnotation)) {
531 CurrentToken->setType(TT_LeadingJavaAnnotation);
533 if (OpeningParen.Previous &&
534 OpeningParen.Previous->is(TT_AttributeSquare)) {
535 CurrentToken->setType(TT_AttributeSquare);
538 if (!HasMultipleLines)
540 else if (HasMultipleParametersOnALine)
548 if (CurrentToken->isOneOf(tok::r_square, tok::r_brace))
551 if (CurrentToken->is(tok::l_brace) && OpeningParen.is(TT_ObjCBlockLParen))
552 OpeningParen.setType(TT_Unknown);
553 if (CurrentToken->is(tok::comma) && CurrentToken->Next &&
554 !CurrentToken->Next->HasUnescapedNewline &&
555 !CurrentToken->Next->isTrailingComment()) {
556 HasMultipleParametersOnALine =
true;
558 bool ProbablyFunctionTypeLParen =
559 (CurrentToken->is(tok::l_paren) && CurrentToken->Next &&
560 CurrentToken->Next->isOneOf(tok::star, tok::amp, tok::caret));
561 if ((CurrentToken->Previous->isOneOf(tok::kw_const, tok::kw_auto) ||
562 CurrentToken->Previous->isTypeName(LangOpts)) &&
563 !(CurrentToken->is(tok::l_brace) ||
564 (CurrentToken->is(tok::l_paren) && !ProbablyFunctionTypeLParen))) {
565 Contexts.back().IsExpression =
false;
567 if (CurrentToken->isOneOf(tok::semi, tok::colon)) {
568 MightBeObjCForRangeLoop =
false;
569 if (PossibleObjCForInToken) {
570 PossibleObjCForInToken->setType(TT_Unknown);
571 PossibleObjCForInToken =
nullptr;
574 if (MightBeObjCForRangeLoop && CurrentToken->is(Keywords.kw_in)) {
575 PossibleObjCForInToken = CurrentToken;
576 PossibleObjCForInToken->setType(TT_ObjCForIn);
580 if (CurrentToken->is(tok::comma))
581 Contexts.back().CanBeExpression =
true;
583 if (Style.isTableGen()) {
584 if (CurrentToken->is(tok::comma)) {
585 if (Contexts.back().IsTableGenCondOpe)
586 CurrentToken->setType(TT_TableGenCondOperatorComma);
588 }
else if (CurrentToken->is(tok::colon)) {
589 if (Contexts.back().IsTableGenCondOpe)
590 CurrentToken->setType(TT_TableGenCondOperatorColon);
594 if (!parseTableGenValue())
599 FormatToken *Tok = CurrentToken;
602 updateParameterCount(&OpeningParen, Tok);
603 if (CurrentToken && CurrentToken->HasUnescapedNewline)
604 HasMultipleLines =
true;
609 bool isCSharpAttributeSpecifier(
const FormatToken &Tok) {
610 if (!Style.isCSharp())
614 if (Tok.Previous && Tok.Previous->is(tok::identifier))
618 if (Tok.Previous && Tok.Previous->is(tok::r_square)) {
619 auto *MatchingParen = Tok.Previous->MatchingParen;
620 if (!MatchingParen || MatchingParen->is(TT_ArraySubscriptLSquare))
624 const FormatToken *AttrTok = Tok.Next;
629 if (AttrTok->is(tok::r_square))
633 while (AttrTok && AttrTok->isNot(tok::r_square))
634 AttrTok = AttrTok->Next;
640 AttrTok = AttrTok->Next;
645 if (AttrTok->isAccessSpecifierKeyword() ||
646 AttrTok->isOneOf(tok::comment, tok::kw_class, tok::kw_static,
647 tok::l_square, Keywords.kw_internal)) {
653 AttrTok->Next->startsSequence(tok::identifier, tok::l_paren)) {
668 FormatToken *
Left = CurrentToken->Previous;
669 Left->ParentBracket = Contexts.back().ContextKind;
670 FormatToken *
Parent =
Left->getPreviousNonComment();
675 bool CppArrayTemplates =
677 (Contexts.back().CanBeExpression || Contexts.back().IsExpression ||
678 Contexts.back().ContextType == Context::TemplateArgument);
680 const bool IsInnerSquare = Contexts.back().InCpp11AttributeSpecifier;
681 const bool IsCpp11AttributeSpecifier =
682 isCppAttribute(IsCpp, *Left) || IsInnerSquare;
685 bool IsCSharpAttributeSpecifier =
686 isCSharpAttributeSpecifier(*Left) ||
687 Contexts.back().InCSharpAttributeSpecifier;
689 bool InsideInlineASM = Line.startsWith(tok::kw_asm);
690 bool IsCppStructuredBinding =
Left->isCppStructuredBinding(IsCpp);
691 bool StartsObjCMethodExpr =
692 !IsCppStructuredBinding && !InsideInlineASM && !CppArrayTemplates &&
693 IsCpp && !IsCpp11AttributeSpecifier && !IsCSharpAttributeSpecifier &&
694 Contexts.back().CanBeExpression &&
Left->isNot(TT_LambdaLSquare) &&
695 !CurrentToken->isOneOf(tok::l_brace, tok::r_square) &&
697 Parent->isOneOf(tok::colon, tok::l_square, tok::l_paren,
698 tok::kw_return, tok::kw_throw) ||
699 Parent->isUnaryOperator() ||
701 Parent->isOneOf(TT_ObjCForIn, TT_CastRParen) ||
704 bool ColonFound =
false;
706 unsigned BindingIncrease = 1;
707 if (IsCppStructuredBinding) {
708 Left->setType(TT_StructuredBindingLSquare);
709 }
else if (
Left->is(TT_Unknown)) {
710 if (StartsObjCMethodExpr) {
711 Left->setType(TT_ObjCMethodExpr);
712 }
else if (InsideInlineASM) {
713 Left->setType(TT_InlineASMSymbolicNameLSquare);
714 }
else if (IsCpp11AttributeSpecifier) {
715 Left->setType(TT_AttributeSquare);
716 if (!IsInnerSquare &&
Left->Previous)
717 Left->Previous->EndsCppAttributeGroup =
false;
718 }
else if (Style.isJavaScript() &&
Parent &&
719 Contexts.back().ContextKind == tok::l_brace &&
720 Parent->isOneOf(tok::l_brace, tok::comma)) {
721 Left->setType(TT_JsComputedPropertyName);
722 }
else if (IsCpp && Contexts.back().ContextKind == tok::l_brace &&
724 Left->setType(TT_DesignatedInitializerLSquare);
725 }
else if (IsCSharpAttributeSpecifier) {
726 Left->setType(TT_AttributeSquare);
727 }
else if (CurrentToken->is(tok::r_square) &&
Parent &&
728 Parent->is(TT_TemplateCloser)) {
729 Left->setType(TT_ArraySubscriptLSquare);
730 }
else if (Style.isProto()) {
757 Left->setType(TT_ArrayInitializerLSquare);
758 if (!
Left->endsSequence(tok::l_square, tok::numeric_constant,
760 !
Left->endsSequence(tok::l_square, tok::numeric_constant,
762 !
Left->endsSequence(tok::l_square, tok::colon, TT_SelectorName)) {
763 Left->setType(TT_ProtoExtensionLSquare);
764 BindingIncrease = 10;
766 }
else if (!CppArrayTemplates &&
Parent &&
767 Parent->isOneOf(TT_BinaryOperator, TT_TemplateCloser, tok::at,
768 tok::comma, tok::l_paren, tok::l_square,
769 tok::question, tok::colon, tok::kw_return,
772 Left->setType(TT_ArrayInitializerLSquare);
774 BindingIncrease = 10;
775 Left->setType(TT_ArraySubscriptLSquare);
779 ScopedContextCreator ContextCreator(*
this, tok::l_square, BindingIncrease);
780 Contexts.back().IsExpression =
true;
781 if (Style.isJavaScript() &&
Parent &&
Parent->is(TT_JsTypeColon))
782 Contexts.back().IsExpression =
false;
784 Contexts.back().ColonIsObjCMethodExpr = StartsObjCMethodExpr;
785 Contexts.back().InCpp11AttributeSpecifier = IsCpp11AttributeSpecifier;
786 Contexts.back().InCSharpAttributeSpecifier = IsCSharpAttributeSpecifier;
788 while (CurrentToken) {
789 if (CurrentToken->is(tok::r_square)) {
790 if (IsCpp11AttributeSpecifier) {
791 CurrentToken->setType(TT_AttributeSquare);
793 CurrentToken->EndsCppAttributeGroup =
true;
795 if (IsCSharpAttributeSpecifier) {
796 CurrentToken->setType(TT_AttributeSquare);
797 }
else if (((CurrentToken->Next &&
798 CurrentToken->Next->is(tok::l_paren)) ||
799 (CurrentToken->Previous &&
800 CurrentToken->Previous->Previous == Left)) &&
801 Left->is(TT_ObjCMethodExpr)) {
806 StartsObjCMethodExpr =
false;
807 Left->setType(TT_Unknown);
809 if (StartsObjCMethodExpr && CurrentToken->Previous != Left) {
810 CurrentToken->setType(TT_ObjCMethodExpr);
813 if (!ColonFound && CurrentToken->Previous &&
814 CurrentToken->Previous->is(TT_Unknown) &&
815 canBeObjCSelectorComponent(*CurrentToken->Previous)) {
816 CurrentToken->Previous->setType(TT_SelectorName);
822 Parent->overwriteFixedType(TT_BinaryOperator);
825 if (CurrentToken->is(TT_ObjCMethodExpr) && CurrentToken->Next &&
826 CurrentToken->Next->is(TT_TrailingReturnArrow)) {
827 CurrentToken->Next->overwriteFixedType(TT_Unknown);
829 Left->MatchingParen = CurrentToken;
830 CurrentToken->MatchingParen =
Left;
835 if (!Contexts.back().FirstObjCSelectorName) {
836 FormatToken *
Previous = CurrentToken->getPreviousNonComment();
838 Previous->ObjCSelectorNameParts = 1;
839 Contexts.back().FirstObjCSelectorName =
Previous;
842 Left->ParameterCount =
843 Contexts.back().FirstObjCSelectorName->ObjCSelectorNameParts;
845 if (Contexts.back().FirstObjCSelectorName) {
846 Contexts.back().FirstObjCSelectorName->LongestObjCSelectorName =
847 Contexts.back().LongestObjCSelectorName;
848 if (
Left->BlockParameterCount > 1)
849 Contexts.back().FirstObjCSelectorName->LongestObjCSelectorName = 0;
851 if (Style.isTableGen() &&
Left->is(TT_TableGenListOpener))
852 CurrentToken->setType(TT_TableGenListCloser);
856 if (CurrentToken->isOneOf(tok::r_paren, tok::r_brace))
858 if (CurrentToken->is(tok::colon)) {
859 if (IsCpp11AttributeSpecifier &&
860 CurrentToken->endsSequence(tok::colon, tok::identifier,
864 CurrentToken->setType(TT_AttributeColon);
865 }
else if (!Style.isVerilog() && !Line.InPragmaDirective &&
866 Left->isOneOf(TT_ArraySubscriptLSquare,
867 TT_DesignatedInitializerLSquare)) {
868 Left->setType(TT_ObjCMethodExpr);
869 StartsObjCMethodExpr =
true;
870 Contexts.back().ColonIsObjCMethodExpr =
true;
873 Parent->setType(TT_CastRParen);
878 if (CurrentToken->is(tok::comma) &&
Left->is(TT_ObjCMethodExpr) &&
880 Left->setType(TT_ArrayInitializerLSquare);
882 FormatToken *Tok = CurrentToken;
883 if (Style.isTableGen()) {
884 if (CurrentToken->isOneOf(tok::comma, tok::minus, tok::ellipsis)) {
890 if (!parseTableGenValue())
893 updateParameterCount(Left, Tok);
898 updateParameterCount(Left, Tok);
903 void skipToNextNonComment() {
905 while (CurrentToken && CurrentToken->is(tok::comment))
914 bool parseTableGenValue(
bool ParseNameMode =
false) {
917 while (CurrentToken->is(tok::comment))
919 if (!parseTableGenSimpleValue())
924 if (CurrentToken->is(tok::hash)) {
925 if (CurrentToken->Next &&
926 CurrentToken->Next->isOneOf(tok::colon, tok::semi, tok::l_brace)) {
929 CurrentToken->setType(TT_TableGenTrailingPasteOperator);
933 FormatToken *HashTok = CurrentToken;
934 skipToNextNonComment();
935 HashTok->setType(TT_Unknown);
936 if (!parseTableGenValue(ParseNameMode))
941 if (ParseNameMode && CurrentToken->is(tok::l_brace))
944 if (CurrentToken->isOneOf(tok::l_brace, tok::l_square, tok::period)) {
945 CurrentToken->setType(TT_TableGenValueSuffix);
946 FormatToken *Suffix = CurrentToken;
947 skipToNextNonComment();
948 if (Suffix->is(tok::l_square))
949 return parseSquare();
950 if (Suffix->is(tok::l_brace)) {
951 Scopes.push_back(getScopeType(*Suffix));
961 bool tryToParseTableGenTokVar() {
964 if (CurrentToken->is(tok::identifier) &&
965 CurrentToken->TokenText.front() ==
'$') {
966 skipToNextNonComment();
974 bool parseTableGenDAGArg(
bool AlignColon =
false) {
975 if (tryToParseTableGenTokVar())
977 if (parseTableGenValue()) {
978 if (CurrentToken && CurrentToken->is(tok::colon)) {
980 CurrentToken->setType(TT_TableGenDAGArgListColonToAlign);
982 CurrentToken->setType(TT_TableGenDAGArgListColon);
983 skipToNextNonComment();
984 return tryToParseTableGenTokVar();
994 bool isTableGenDAGArgBreakingOperator(
const FormatToken &Tok) {
995 auto &Opes = Style.TableGenBreakingDAGArgOperators;
1000 if (Tok.isNot(tok::identifier) ||
1001 Tok.isOneOf(TT_TableGenBangOperator, TT_TableGenCondOperator)) {
1005 if (!Tok.Next || Tok.Next->is(tok::colon))
1007 return std::find(Opes.begin(), Opes.end(), Tok.TokenText.str()) !=
1013 bool parseTableGenDAGArgAndList(FormatToken *Opener) {
1014 FormatToken *FirstTok = CurrentToken;
1015 if (!parseTableGenDAGArg())
1017 bool BreakInside =
false;
1021 if (isTableGenDAGArgBreakingOperator(*FirstTok)) {
1024 Opener->setType(TT_TableGenDAGArgOpenerToBreak);
1025 if (FirstTok->isOneOf(TT_TableGenBangOperator,
1026 TT_TableGenCondOperator)) {
1029 CurrentToken->Previous->setType(TT_TableGenDAGArgOperatorToBreak);
1030 }
else if (FirstTok->is(tok::identifier)) {
1032 FirstTok->setType(TT_TableGenDAGArgOperatorToBreak);
1034 FirstTok->setType(TT_TableGenDAGArgOperatorID);
1039 bool FirstDAGArgListElm =
true;
1040 while (CurrentToken) {
1041 if (!FirstDAGArgListElm && CurrentToken->is(tok::comma)) {
1042 CurrentToken->setType(BreakInside ? TT_TableGenDAGArgListCommaToBreak
1043 : TT_TableGenDAGArgListComma);
1044 skipToNextNonComment();
1046 if (CurrentToken && CurrentToken->is(tok::r_paren)) {
1047 CurrentToken->setType(TT_TableGenDAGArgCloser);
1048 Opener->MatchingParen = CurrentToken;
1049 CurrentToken->MatchingParen = Opener;
1050 skipToNextNonComment();
1053 if (!parseTableGenDAGArg(
1055 Style.AlignConsecutiveTableGenBreakingDAGArgColons.Enabled)) {
1058 FirstDAGArgListElm =
false;
1063 bool parseTableGenSimpleValue() {
1064 assert(Style.isTableGen());
1067 FormatToken *Tok = CurrentToken;
1068 skipToNextNonComment();
1070 if (Tok->isOneOf(tok::numeric_constant, tok::string_literal,
1071 TT_TableGenMultiLineString, tok::kw_true, tok::kw_false,
1072 tok::question, tok::kw_int)) {
1076 if (Tok->is(tok::l_brace)) {
1077 Scopes.push_back(getScopeType(*Tok));
1078 return parseBrace();
1081 if (Tok->is(tok::l_square)) {
1082 Tok->setType(TT_TableGenListOpener);
1085 if (Tok->is(tok::less)) {
1086 CurrentToken->setType(TT_TemplateOpener);
1087 return parseAngle();
1093 if (Tok->is(tok::l_paren)) {
1094 Tok->setType(TT_TableGenDAGArgOpener);
1095 return parseTableGenDAGArgAndList(Tok);
1098 if (Tok->is(TT_TableGenBangOperator)) {
1099 if (CurrentToken && CurrentToken->is(tok::less)) {
1100 CurrentToken->setType(TT_TemplateOpener);
1101 skipToNextNonComment();
1105 if (!CurrentToken || CurrentToken->isNot(tok::l_paren))
1107 skipToNextNonComment();
1109 Contexts.back().IsTableGenBangOpe =
true;
1110 bool Result = parseParens();
1111 Contexts.back().IsTableGenBangOpe =
false;
1115 if (Tok->is(TT_TableGenCondOperator)) {
1117 skipToNextNonComment();
1118 if (!Tok || Tok->isNot(tok::l_paren))
1120 bool Result = parseParens();
1126 if (Tok->is(tok::identifier)) {
1128 if (CurrentToken && CurrentToken->is(tok::less)) {
1129 CurrentToken->setType(TT_TemplateOpener);
1130 skipToNextNonComment();
1131 return parseAngle();
1139 bool couldBeInStructArrayInitializer()
const {
1140 if (Contexts.size() < 2)
1144 const auto End = std::next(Contexts.rbegin(), 2);
1145 auto Last = Contexts.rbegin();
1148 if (
Last->ContextKind == tok::l_brace)
1150 return Depth == 2 &&
Last->ContextKind != tok::l_brace;
1157 assert(CurrentToken->Previous);
1158 FormatToken &OpeningBrace = *CurrentToken->Previous;
1159 assert(OpeningBrace.is(tok::l_brace));
1160 OpeningBrace.ParentBracket = Contexts.back().ContextKind;
1162 if (Contexts.back().CaretFound)
1163 OpeningBrace.overwriteFixedType(TT_ObjCBlockLBrace);
1164 Contexts.back().CaretFound =
false;
1166 ScopedContextCreator ContextCreator(*
this, tok::l_brace, 1);
1167 Contexts.back().ColonIsDictLiteral =
true;
1169 Contexts.back().IsExpression =
true;
1170 if (Style.isJavaScript() && OpeningBrace.Previous &&
1171 OpeningBrace.Previous->is(TT_JsTypeColon)) {
1172 Contexts.back().IsExpression =
false;
1174 if (Style.isVerilog() &&
1175 (!OpeningBrace.getPreviousNonComment() ||
1176 OpeningBrace.getPreviousNonComment()->isNot(Keywords.kw_apostrophe))) {
1177 Contexts.back().VerilogMayBeConcatenation =
true;
1179 if (Style.isTableGen())
1180 Contexts.back().ColonIsDictLiteral =
false;
1182 unsigned CommaCount = 0;
1183 while (CurrentToken) {
1184 if (CurrentToken->is(tok::r_brace)) {
1185 assert(!Scopes.empty());
1186 assert(Scopes.back() == getScopeType(OpeningBrace));
1188 assert(OpeningBrace.Optional == CurrentToken->Optional);
1189 OpeningBrace.MatchingParen = CurrentToken;
1190 CurrentToken->MatchingParen = &OpeningBrace;
1192 if (OpeningBrace.ParentBracket == tok::l_brace &&
1193 couldBeInStructArrayInitializer() && CommaCount > 0) {
1194 Contexts.back().ContextType = Context::StructArrayInitializer;
1200 if (CurrentToken->isOneOf(tok::r_paren, tok::r_square))
1202 updateParameterCount(&OpeningBrace, CurrentToken);
1203 if (CurrentToken->isOneOf(tok::colon, tok::l_brace, tok::less)) {
1204 FormatToken *
Previous = CurrentToken->getPreviousNonComment();
1205 if (
Previous->is(TT_JsTypeOptionalQuestion))
1207 if ((CurrentToken->is(tok::colon) && !Style.isTableGen() &&
1208 (!Contexts.back().ColonIsDictLiteral || !IsCpp)) ||
1210 OpeningBrace.setType(TT_DictLiteral);
1211 if (
Previous->Tok.getIdentifierInfo() ||
1212 Previous->is(tok::string_literal)) {
1213 Previous->setType(TT_SelectorName);
1216 if (CurrentToken->is(tok::colon) && OpeningBrace.is(TT_Unknown) &&
1217 !Style.isTableGen()) {
1218 OpeningBrace.setType(TT_DictLiteral);
1219 }
else if (Style.isJavaScript()) {
1220 OpeningBrace.overwriteFixedType(TT_DictLiteral);
1223 if (CurrentToken->is(tok::comma)) {
1224 if (Style.isJavaScript())
1225 OpeningBrace.overwriteFixedType(TT_DictLiteral);
1228 if (!consumeToken())
1234 void updateParameterCount(FormatToken *Left, FormatToken *Current) {
1238 if (Current->is(tok::l_brace) && Current->is(
BK_Block))
1239 ++
Left->BlockParameterCount;
1240 if (Current->is(tok::comma)) {
1241 ++
Left->ParameterCount;
1243 Left->Role.reset(
new CommaSeparatedList(Style));
1244 Left->Role->CommaFound(Current);
1245 }
else if (
Left->ParameterCount == 0 && Current->isNot(tok::comment)) {
1246 Left->ParameterCount = 1;
1250 bool parseConditional() {
1251 while (CurrentToken) {
1252 if (CurrentToken->is(tok::colon)) {
1253 CurrentToken->setType(TT_ConditionalExpr);
1257 if (!consumeToken())
1263 bool parseTemplateDeclaration() {
1264 if (!CurrentToken || CurrentToken->isNot(tok::less))
1267 CurrentToken->setType(TT_TemplateOpener);
1270 TemplateDeclarationDepth++;
1271 const bool WellFormed = parseAngle();
1272 TemplateDeclarationDepth--;
1276 if (CurrentToken && TemplateDeclarationDepth == 0)
1277 CurrentToken->Previous->ClosesTemplateDeclaration =
true;
1282 bool consumeToken() {
1284 const auto *Prev = CurrentToken->getPreviousNonComment();
1285 if (Prev && Prev->is(tok::r_square) && Prev->is(TT_AttributeSquare) &&
1286 CurrentToken->isOneOf(tok::kw_if, tok::kw_switch, tok::kw_case,
1287 tok::kw_default, tok::kw_for, tok::kw_while) &&
1289 CurrentToken->MustBreakBefore =
true;
1292 FormatToken *Tok = CurrentToken;
1296 if (Tok->is(TT_VerilogTableItem))
1299 if (Tok->is(TT_TableGenMultiLineString))
1301 switch (Tok->Tok.getKind()) {
1304 if (!Tok->Previous && Line.MustBeDeclaration)
1305 Tok->setType(TT_ObjCMethodSpecifier);
1312 if (Tok->isTypeFinalized())
1315 if (Style.isJavaScript()) {
1316 if (Contexts.back().ColonIsForRangeExpr ||
1317 (Contexts.size() == 1 &&
1318 !Line.First->isOneOf(tok::kw_enum, tok::kw_case)) ||
1319 Contexts.back().ContextKind == tok::l_paren ||
1320 Contexts.back().ContextKind == tok::l_square ||
1321 (!Contexts.back().IsExpression &&
1322 Contexts.back().ContextKind == tok::l_brace) ||
1323 (Contexts.size() == 1 &&
1324 Line.MustBeDeclaration)) {
1325 Contexts.back().IsExpression =
false;
1326 Tok->setType(TT_JsTypeColon);
1329 }
else if (Style.isCSharp()) {
1330 if (Contexts.back().InCSharpAttributeSpecifier) {
1331 Tok->setType(TT_AttributeColon);
1334 if (Contexts.back().ContextKind == tok::l_paren) {
1335 Tok->setType(TT_CSharpNamedArgumentColon);
1338 }
else if (Style.isVerilog() && Tok->isNot(TT_BinaryOperator)) {
1341 if (Keywords.isVerilogEnd(*Tok->Previous) ||
1342 Keywords.isVerilogBegin(*Tok->Previous)) {
1343 Tok->setType(TT_VerilogBlockLabelColon);
1344 }
else if (Contexts.back().ContextKind == tok::l_square) {
1345 Tok->setType(TT_BitFieldColon);
1346 }
else if (Contexts.back().ColonIsDictLiteral) {
1347 Tok->setType(TT_DictLiteral);
1348 }
else if (Contexts.size() == 1) {
1352 Tok->setType(TT_CaseLabelColon);
1353 if (Line.Level > 1 || (!Line.InPPDirective && Line.Level > 0))
1358 if (Line.First->isOneOf(Keywords.kw_module, Keywords.kw_import) ||
1359 Line.First->startsSequence(tok::kw_export, Keywords.kw_module) ||
1360 Line.First->startsSequence(tok::kw_export, Keywords.kw_import)) {
1361 Tok->setType(TT_ModulePartitionColon);
1362 }
else if (Line.First->is(tok::kw_asm)) {
1363 Tok->setType(TT_InlineASMColon);
1364 }
else if (Contexts.back().ColonIsDictLiteral || Style.isProto()) {
1365 Tok->setType(TT_DictLiteral);
1367 if (FormatToken *
Previous = Tok->getPreviousNonComment())
1368 Previous->setType(TT_SelectorName);
1370 }
else if (Contexts.back().ColonIsObjCMethodExpr ||
1371 Line.startsWith(TT_ObjCMethodSpecifier)) {
1372 Tok->setType(TT_ObjCMethodExpr);
1373 const FormatToken *BeforePrevious = Tok->Previous->Previous;
1376 bool UnknownIdentifierInMethodDeclaration =
1377 Line.startsWith(TT_ObjCMethodSpecifier) &&
1378 Tok->Previous->is(tok::identifier) && Tok->Previous->is(TT_Unknown);
1379 if (!BeforePrevious ||
1381 !(BeforePrevious->is(TT_CastRParen) ||
1382 (BeforePrevious->is(TT_ObjCMethodExpr) &&
1383 BeforePrevious->is(tok::colon))) ||
1384 BeforePrevious->is(tok::r_square) ||
1385 Contexts.back().LongestObjCSelectorName == 0 ||
1386 UnknownIdentifierInMethodDeclaration) {
1387 Tok->Previous->setType(TT_SelectorName);
1388 if (!Contexts.back().FirstObjCSelectorName) {
1389 Contexts.back().FirstObjCSelectorName = Tok->Previous;
1390 }
else if (Tok->Previous->ColumnWidth >
1391 Contexts.back().LongestObjCSelectorName) {
1392 Contexts.back().LongestObjCSelectorName =
1393 Tok->Previous->ColumnWidth;
1395 Tok->Previous->ParameterIndex =
1396 Contexts.back().FirstObjCSelectorName->ObjCSelectorNameParts;
1397 ++Contexts.back().FirstObjCSelectorName->ObjCSelectorNameParts;
1399 }
else if (Contexts.back().ColonIsForRangeExpr) {
1400 Tok->setType(TT_RangeBasedForLoopColon);
1401 }
else if (Contexts.back().ContextType == Context::C11GenericSelection) {
1402 Tok->setType(TT_GenericSelectionColon);
1403 }
else if (CurrentToken && CurrentToken->is(tok::numeric_constant)) {
1404 Tok->setType(TT_BitFieldColon);
1405 }
else if (Contexts.size() == 1 &&
1406 !Line.First->isOneOf(tok::kw_enum, tok::kw_case,
1408 FormatToken *Prev = Tok->getPreviousNonComment();
1411 if (Prev->isOneOf(tok::r_paren, tok::kw_noexcept) ||
1412 Prev->ClosesRequiresClause) {
1413 Tok->setType(TT_CtorInitializerColon);
1414 }
else if (Prev->is(tok::kw_try)) {
1416 FormatToken *PrevPrev = Prev->getPreviousNonComment();
1419 if (PrevPrev && PrevPrev->isOneOf(tok::r_paren, tok::kw_noexcept))
1420 Tok->setType(TT_CtorInitializerColon);
1422 Tok->setType(TT_InheritanceColon);
1423 if (Prev->isAccessSpecifierKeyword())
1426 }
else if (canBeObjCSelectorComponent(*Tok->Previous) && Tok->Next &&
1427 (Tok->Next->isOneOf(tok::r_paren, tok::comma) ||
1428 (canBeObjCSelectorComponent(*Tok->Next) && Tok->Next->Next &&
1429 Tok->Next->Next->is(tok::colon)))) {
1432 Tok->setType(TT_ObjCMethodExpr);
1439 if (Style.isJavaScript() && !Contexts.back().IsExpression)
1440 Tok->setType(TT_JsTypeOperator);
1443 if (Style.isTableGen()) {
1445 if (!parseTableGenValue())
1447 if (CurrentToken && CurrentToken->is(Keywords.kw_then))
1452 CurrentToken->isOneOf(tok::kw_constexpr, tok::identifier)) {
1457 if (CurrentToken && CurrentToken->is(tok::l_paren)) {
1459 if (!parseParens(
true))
1464 if (Style.isJavaScript()) {
1466 if ((Tok->Previous && Tok->Previous->is(tok::period)) ||
1467 (Tok->Next && Tok->Next->is(tok::colon))) {
1471 if (CurrentToken && CurrentToken->is(Keywords.kw_await))
1474 if (IsCpp && CurrentToken && CurrentToken->is(tok::kw_co_await))
1476 Contexts.back().ColonIsForRangeExpr =
true;
1477 if (!CurrentToken || CurrentToken->isNot(tok::l_paren))
1488 if (Tok->Previous && Tok->Previous->is(tok::r_paren) &&
1489 Tok->Previous->MatchingParen &&
1490 Tok->Previous->MatchingParen->is(TT_OverloadedOperatorLParen)) {
1491 Tok->Previous->setType(TT_OverloadedOperator);
1492 Tok->Previous->MatchingParen->setType(TT_OverloadedOperator);
1493 Tok->setType(TT_OverloadedOperatorLParen);
1496 if (Style.isVerilog()) {
1502 auto IsInstancePort = [&]() {
1503 const FormatToken *Prev = Tok->getPreviousNonComment();
1504 const FormatToken *PrevPrev;
1512 if (!Prev || !(PrevPrev = Prev->getPreviousNonComment()))
1515 if (Keywords.isVerilogIdentifier(*Prev) &&
1516 Keywords.isVerilogIdentifier(*PrevPrev)) {
1520 if (Prev->is(Keywords.kw_verilogHash) &&
1521 Keywords.isVerilogIdentifier(*PrevPrev)) {
1525 if (Keywords.isVerilogIdentifier(*Prev) && PrevPrev->is(tok::r_paren))
1528 if (Keywords.isVerilogIdentifier(*Prev) && PrevPrev->is(tok::comma)) {
1529 const FormatToken *PrevParen = PrevPrev->getPreviousNonComment();
1530 if (PrevParen->is(tok::r_paren) && PrevParen->MatchingParen &&
1531 PrevParen->MatchingParen->is(TT_VerilogInstancePortLParen)) {
1538 if (IsInstancePort())
1539 Tok->setFinalizedType(TT_VerilogInstancePortLParen);
1544 if (Line.MustBeDeclaration && Contexts.size() == 1 &&
1545 !Contexts.back().IsExpression && !Line.startsWith(TT_ObjCProperty) &&
1546 !Line.startsWith(tok::l_paren) &&
1547 !Tok->isOneOf(TT_TypeDeclarationParen, TT_RequiresExpressionLParen)) {
1548 if (
const auto *
Previous = Tok->Previous;
1551 !
Previous->isOneOf(TT_RequiresClause, TT_LeadingJavaAnnotation))) {
1552 Line.MightBeFunctionDecl =
true;
1553 Tok->MightBeFunctionDeclParen =
true;
1558 if (Style.isTableGen())
1559 Tok->setType(TT_TableGenListOpener);
1565 FormatToken *
Previous = Tok->getPreviousNonComment();
1567 Previous->setType(TT_SelectorName);
1569 Scopes.push_back(getScopeType(*Tok));
1575 Tok->setType(TT_TemplateOpener);
1583 Tok->Previous->isOneOf(TT_SelectorName, TT_DictLiteral))) {
1584 Tok->setType(TT_DictLiteral);
1585 FormatToken *
Previous = Tok->getPreviousNonComment();
1587 Previous->setType(TT_SelectorName);
1589 if (Style.isTableGen())
1590 Tok->setType(TT_TemplateOpener);
1592 Tok->setType(TT_BinaryOperator);
1593 NonTemplateLess.insert(Tok);
1603 if (!Scopes.empty())
1611 Tok->setType(TT_BinaryOperator);
1612 if (Tok->Previous && Tok->Previous->is(TT_TemplateCloser))
1613 Tok->SpacesRequiredBefore = 1;
1615 case tok::kw_operator:
1616 if (Style.isProto())
1618 while (CurrentToken &&
1619 !CurrentToken->isOneOf(tok::l_paren, tok::semi, tok::r_paren)) {
1620 if (CurrentToken->isOneOf(tok::star, tok::amp))
1621 CurrentToken->setType(TT_PointerOrReference);
1622 auto Next = CurrentToken->getNextNonComment();
1625 if (Next->is(tok::less))
1631 auto Previous = CurrentToken->getPreviousNonComment();
1633 if (CurrentToken->is(tok::comma) &&
Previous->isNot(tok::kw_operator))
1635 if (
Previous->isOneOf(TT_BinaryOperator, TT_UnaryOperator, tok::comma,
1636 tok::star, tok::arrow, tok::amp, tok::ampamp) ||
1638 Previous->TokenText.starts_with(
"\"\"")) {
1639 Previous->setType(TT_OverloadedOperator);
1640 if (CurrentToken->isOneOf(tok::less, tok::greater))
1644 if (CurrentToken && CurrentToken->is(tok::l_paren))
1645 CurrentToken->setType(TT_OverloadedOperatorLParen);
1646 if (CurrentToken && CurrentToken->Previous->is(TT_BinaryOperator))
1647 CurrentToken->Previous->setType(TT_OverloadedOperator);
1650 if (Style.isJavaScript() && Tok->Next &&
1651 Tok->Next->isOneOf(tok::semi, tok::comma, tok::colon, tok::r_paren,
1652 tok::r_brace, tok::r_square)) {
1657 Tok->setType(TT_JsTypeOptionalQuestion);
1662 if (Line.MustBeDeclaration && !Contexts.back().IsExpression &&
1663 Style.isJavaScript()) {
1666 if (Style.isCSharp()) {
1672 (Tok->Next->startsSequence(tok::question, tok::r_paren) ||
1673 Tok->Next->startsSequence(tok::question, tok::greater) ||
1674 Tok->Next->startsSequence(tok::question, tok::identifier,
1676 Tok->setType(TT_CSharpNullable);
1681 if (Tok->Next && Tok->Next->is(tok::identifier) && Tok->Next->Next &&
1682 Tok->Next->Next->is(tok::equal)) {
1683 Tok->setType(TT_CSharpNullable);
1692 if (!Contexts.back().IsExpression && Line.MustBeDeclaration &&
1694 !Tok->Next->isOneOf(tok::identifier, tok::string_literal) ||
1696 !Tok->Next->Next->isOneOf(tok::colon, tok::question))) {
1697 Tok->setType(TT_CSharpNullable);
1703 case tok::kw_template:
1704 parseTemplateDeclaration();
1707 switch (Contexts.back().ContextType) {
1708 case Context::CtorInitializer:
1709 Tok->setType(TT_CtorInitializerComma);
1711 case Context::InheritanceList:
1712 Tok->setType(TT_InheritanceComma);
1714 case Context::VerilogInstancePortList:
1715 Tok->setFinalizedType(TT_VerilogInstancePortComma);
1718 if (Style.isVerilog() && Contexts.size() == 1 &&
1719 Line.startsWith(Keywords.kw_assign)) {
1720 Tok->setFinalizedType(TT_VerilogAssignComma);
1721 }
else if (Contexts.back().FirstStartOfName &&
1722 (Contexts.size() == 1 || startsWithInitStatement(Line))) {
1723 Contexts.back().FirstStartOfName->PartOfMultiVariableDeclStmt =
true;
1724 Line.IsMultiVariableDeclStmt =
true;
1728 if (Contexts.back().ContextType == Context::ForEachMacro)
1729 Contexts.back().IsExpression =
true;
1731 case tok::kw_default:
1733 if (Style.isVerilog() && Keywords.isVerilogEndOfLabel(*Tok) &&
1734 (Line.Level > 1 || (!Line.InPPDirective && Line.Level > 0))) {
1738 case tok::identifier:
1739 if (Tok->isOneOf(Keywords.kw___has_include,
1740 Keywords.kw___has_include_next)) {
1743 if (Style.isCSharp() && Tok->is(Keywords.kw_where) && Tok->Next &&
1744 Tok->Next->isNot(tok::l_paren)) {
1745 Tok->setType(TT_CSharpGenericTypeConstraint);
1746 parseCSharpGenericTypeConstraint();
1747 if (!Tok->getPreviousNonComment())
1748 Line.IsContinuation =
true;
1750 if (Style.isTableGen()) {
1751 if (Tok->is(Keywords.kw_assert)) {
1752 if (!parseTableGenValue())
1754 }
else if (Tok->isOneOf(Keywords.kw_def, Keywords.kw_defm) &&
1756 !Tok->Next->isOneOf(tok::colon, tok::l_brace))) {
1758 if (!parseTableGenValue(
true))
1764 if (Tok->Previous && Tok->Previous->is(tok::kw_noexcept))
1765 Tok->setType(TT_TrailingReturnArrow);
1769 if (Style.isTableGen() && !parseTableGenValue())
1778 void parseCSharpGenericTypeConstraint() {
1779 int OpenAngleBracketsCount = 0;
1780 while (CurrentToken) {
1781 if (CurrentToken->is(tok::less)) {
1783 CurrentToken->setType(TT_TemplateOpener);
1784 ++OpenAngleBracketsCount;
1786 }
else if (CurrentToken->is(tok::greater)) {
1787 CurrentToken->setType(TT_TemplateCloser);
1788 --OpenAngleBracketsCount;
1790 }
else if (CurrentToken->is(tok::comma) && OpenAngleBracketsCount == 0) {
1793 CurrentToken->setType(TT_CSharpGenericTypeConstraintComma);
1795 }
else if (CurrentToken->is(Keywords.kw_where)) {
1796 CurrentToken->setType(TT_CSharpGenericTypeConstraint);
1798 }
else if (CurrentToken->is(tok::colon)) {
1799 CurrentToken->setType(TT_CSharpGenericTypeConstraintColon);
1807 void parseIncludeDirective() {
1808 if (CurrentToken && CurrentToken->is(tok::less)) {
1810 while (CurrentToken) {
1813 if (CurrentToken->isNot(tok::comment) &&
1814 !CurrentToken->TokenText.starts_with(
"//")) {
1815 CurrentToken->setType(TT_ImplicitStringLiteral);
1822 void parseWarningOrError() {
1827 while (CurrentToken) {
1828 CurrentToken->setType(TT_ImplicitStringLiteral);
1833 void parsePragma() {
1836 CurrentToken->isOneOf(Keywords.kw_mark, Keywords.kw_option,
1837 Keywords.kw_region)) {
1838 bool IsMarkOrRegion =
1839 CurrentToken->isOneOf(Keywords.kw_mark, Keywords.kw_region);
1842 while (CurrentToken) {
1843 if (IsMarkOrRegion || CurrentToken->Previous->is(TT_BinaryOperator))
1844 CurrentToken->setType(TT_ImplicitStringLiteral);
1850 void parseHasInclude() {
1851 if (!CurrentToken || CurrentToken->isNot(tok::l_paren))
1854 parseIncludeDirective();
1858 LineType parsePreprocessorDirective() {
1859 bool IsFirstToken = CurrentToken->IsFirst;
1865 if (Style.isJavaScript() && IsFirstToken) {
1869 while (CurrentToken) {
1871 CurrentToken->setType(TT_ImplicitStringLiteral);
1877 if (CurrentToken->is(tok::numeric_constant)) {
1878 CurrentToken->SpacesRequiredBefore = 1;
1883 if (!CurrentToken->Tok.getIdentifierInfo())
1887 if (Style.isVerilog() && !Keywords.isVerilogPPDirective(*CurrentToken))
1889 switch (CurrentToken->Tok.getIdentifierInfo()->getPPKeywordID()) {
1890 case tok::pp_include:
1891 case tok::pp_include_next:
1892 case tok::pp_import:
1894 parseIncludeDirective();
1898 case tok::pp_warning:
1899 parseWarningOrError();
1901 case tok::pp_pragma:
1906 Contexts.back().IsExpression =
true;
1909 CurrentToken->SpacesRequiredBefore =
true;
1915 while (CurrentToken) {
1916 FormatToken *Tok = CurrentToken;
1918 if (Tok->is(tok::l_paren)) {
1920 }
else if (Tok->isOneOf(Keywords.kw___has_include,
1921 Keywords.kw___has_include_next)) {
1932 NonTemplateLess.clear();
1933 if (!Line.InMacroBody && CurrentToken->is(tok::hash)) {
1937 auto Type = parsePreprocessorDirective();
1945 IdentifierInfo *Info = CurrentToken->Tok.getIdentifierInfo();
1947 CurrentToken->is(Keywords.kw_package)) ||
1948 (!Style.isVerilog() && Info &&
1949 Info->getPPKeywordID() == tok::pp_import && CurrentToken->Next &&
1950 CurrentToken->Next->isOneOf(tok::string_literal, tok::identifier,
1953 parseIncludeDirective();
1959 if (CurrentToken->is(tok::less) && Line.Last->is(tok::greater)) {
1960 parseIncludeDirective();
1967 CurrentToken->isOneOf(Keywords.kw_option, Keywords.kw_package)) {
1969 if (CurrentToken && CurrentToken->is(tok::identifier)) {
1970 while (CurrentToken)
1976 bool KeywordVirtualFound =
false;
1977 bool ImportStatement =
false;
1980 if (Style.isJavaScript() && CurrentToken->is(Keywords.kw_import))
1981 ImportStatement =
true;
1983 while (CurrentToken) {
1984 if (CurrentToken->is(tok::kw_virtual))
1985 KeywordVirtualFound =
true;
1986 if (Style.isJavaScript()) {
1993 if (Line.First->is(tok::kw_export) &&
1994 CurrentToken->is(Keywords.kw_from) && CurrentToken->Next &&
1995 CurrentToken->Next->isStringLiteral()) {
1996 ImportStatement =
true;
1998 if (isClosureImportStatement(*CurrentToken))
1999 ImportStatement =
true;
2001 if (!consumeToken())
2006 if (KeywordVirtualFound)
2008 if (ImportStatement)
2011 if (Line.startsWith(TT_ObjCMethodSpecifier)) {
2012 if (Contexts.back().FirstObjCSelectorName) {
2013 Contexts.back().FirstObjCSelectorName->LongestObjCSelectorName =
2014 Contexts.back().LongestObjCSelectorName;
2019 for (
const auto &ctx : Contexts)
2020 if (ctx.ContextType == Context::StructArrayInitializer)
2027 bool isClosureImportStatement(
const FormatToken &Tok) {
2030 return Tok.TokenText ==
"goog" && Tok.Next && Tok.Next->is(tok::period) &&
2032 (Tok.Next->Next->TokenText ==
"module" ||
2033 Tok.Next->Next->TokenText ==
"provide" ||
2034 Tok.Next->Next->TokenText ==
"require" ||
2035 Tok.Next->Next->TokenText ==
"requireType" ||
2036 Tok.Next->Next->TokenText ==
"forwardDeclare") &&
2037 Tok.Next->Next->Next && Tok.Next->Next->Next->is(tok::l_paren);
2040 void resetTokenMetadata() {
2046 if (!CurrentToken->isTypeFinalized() &&
2047 !CurrentToken->isOneOf(
2048 TT_LambdaLSquare, TT_LambdaLBrace, TT_AttributeMacro, TT_IfMacro,
2049 TT_ForEachMacro, TT_TypenameMacro, TT_FunctionLBrace,
2050 TT_ImplicitStringLiteral, TT_InlineASMBrace, TT_FatArrow,
2051 TT_NamespaceMacro, TT_OverloadedOperator, TT_RegexLiteral,
2052 TT_TemplateString, TT_ObjCStringLiteral, TT_UntouchableMacroFunc,
2053 TT_StatementAttributeLikeMacro, TT_FunctionLikeOrFreestandingMacro,
2054 TT_ClassLBrace, TT_EnumLBrace, TT_RecordLBrace, TT_StructLBrace,
2055 TT_UnionLBrace, TT_RequiresClause,
2056 TT_RequiresClauseInARequiresExpression, TT_RequiresExpression,
2057 TT_RequiresExpressionLParen, TT_RequiresExpressionLBrace,
2058 TT_BracedListLBrace)) {
2059 CurrentToken->setType(TT_Unknown);
2061 CurrentToken->Role.reset();
2062 CurrentToken->MatchingParen =
nullptr;
2063 CurrentToken->FakeLParens.clear();
2064 CurrentToken->FakeRParens = 0;
2071 CurrentToken->NestingLevel = Contexts.size() - 1;
2072 CurrentToken->BindingStrength = Contexts.back().BindingStrength;
2073 modifyContext(*CurrentToken);
2074 determineTokenType(*CurrentToken);
2075 CurrentToken = CurrentToken->Next;
2077 resetTokenMetadata();
2120 StructArrayInitializer,
2124 C11GenericSelection,
2126 VerilogInstancePortList,
2132 struct ScopedContextCreator {
2133 AnnotatingParser &
P;
2139 P.Contexts.back().BindingStrength + Increase,
2140 P.Contexts.back().IsExpression));
2143 ~ScopedContextCreator() {
2145 if (
P.Contexts.back().ContextType == Context::StructArrayInitializer) {
2146 P.Contexts.pop_back();
2147 P.Contexts.back().ContextType = Context::StructArrayInitializer;
2151 P.Contexts.pop_back();
2155 void modifyContext(
const FormatToken &Current) {
2156 auto AssignmentStartsExpression = [&]() {
2160 if (Line.First->isOneOf(tok::kw_using, tok::kw_return))
2162 if (Line.First->is(tok::kw_template)) {
2163 assert(Current.Previous);
2164 if (Current.Previous->is(tok::kw_operator)) {
2170 const FormatToken *Tok = Line.First->getNextNonComment();
2172 if (Tok->isNot(TT_TemplateOpener)) {
2179 if (Contexts.back().ContextKind == tok::less) {
2180 assert(Current.Previous->Previous);
2181 return !Current.Previous->Previous->isOneOf(tok::kw_typename,
2185 Tok = Tok->MatchingParen;
2188 Tok = Tok->getNextNonComment();
2192 if (Tok->isOneOf(tok::kw_class, tok::kw_enum, tok::kw_struct,
2202 if (Style.isJavaScript() &&
2203 (Line.startsWith(Keywords.kw_type, tok::identifier) ||
2204 Line.startsWith(tok::kw_export, Keywords.kw_type,
2205 tok::identifier))) {
2209 return !Current.Previous || Current.Previous->isNot(tok::kw_operator);
2212 if (AssignmentStartsExpression()) {
2213 Contexts.back().IsExpression =
true;
2214 if (!Line.startsWith(TT_UnaryOperator)) {
2215 for (FormatToken *
Previous = Current.Previous;
2217 !
Previous->Previous->isOneOf(tok::comma, tok::semi);
2219 if (
Previous->isOneOf(tok::r_square, tok::r_paren, tok::greater)) {
2226 if (
Previous->isOneOf(TT_BinaryOperator, TT_UnaryOperator) &&
2228 Previous->Previous->isNot(tok::equal)) {
2229 Previous->setType(TT_PointerOrReference);
2233 }
else if (Current.is(tok::lessless) &&
2234 (!Current.Previous ||
2235 Current.Previous->isNot(tok::kw_operator))) {
2236 Contexts.back().IsExpression =
true;
2237 }
else if (Current.isOneOf(tok::kw_return, tok::kw_throw)) {
2238 Contexts.back().IsExpression =
true;
2239 }
else if (Current.is(TT_TrailingReturnArrow)) {
2240 Contexts.back().IsExpression =
false;
2241 }
else if (Current.is(Keywords.kw_assert)) {
2243 }
else if (Current.Previous &&
2244 Current.Previous->is(TT_CtorInitializerColon)) {
2245 Contexts.back().IsExpression =
true;
2246 Contexts.back().ContextType = Context::CtorInitializer;
2247 }
else if (Current.Previous && Current.Previous->is(TT_InheritanceColon)) {
2248 Contexts.back().ContextType = Context::InheritanceList;
2249 }
else if (Current.isOneOf(tok::r_paren, tok::greater, tok::comma)) {
2250 for (FormatToken *
Previous = Current.Previous;
2253 Previous->setType(TT_PointerOrReference);
2255 if (Line.MustBeDeclaration &&
2256 Contexts.front().ContextType != Context::CtorInitializer) {
2257 Contexts.back().IsExpression =
false;
2259 }
else if (Current.is(tok::kw_new)) {
2260 Contexts.back().CanBeExpression =
false;
2261 }
else if (Current.is(tok::semi) ||
2262 (Current.is(tok::exclaim) && Current.Previous &&
2263 Current.Previous->isNot(tok::kw_operator))) {
2267 Contexts.back().IsExpression =
true;
2271 static FormatToken *untilMatchingParen(FormatToken *Current) {
2275 if (Current->is(tok::l_paren))
2277 if (Current->is(tok::r_paren))
2281 Current = Current->Next;
2286 static bool isDeductionGuide(FormatToken &Current) {
2288 if (Current.Previous && Current.Previous->is(tok::r_paren) &&
2289 Current.startsSequence(tok::arrow, tok::identifier, tok::less)) {
2291 FormatToken *TemplateCloser = Current.Next->Next;
2292 int NestingLevel = 0;
2293 while (TemplateCloser) {
2295 if (TemplateCloser->is(tok::l_paren)) {
2297 TemplateCloser = untilMatchingParen(TemplateCloser);
2298 if (!TemplateCloser)
2301 if (TemplateCloser->is(tok::less))
2303 if (TemplateCloser->is(tok::greater))
2305 if (NestingLevel < 1)
2307 TemplateCloser = TemplateCloser->Next;
2311 if (TemplateCloser && TemplateCloser->Next &&
2312 TemplateCloser->Next->is(tok::semi) &&
2313 Current.Previous->MatchingParen) {
2316 FormatToken *LeadingIdentifier =
2317 Current.Previous->MatchingParen->Previous;
2319 return LeadingIdentifier &&
2320 LeadingIdentifier->TokenText == Current.Next->TokenText;
2326 void determineTokenType(FormatToken &Current) {
2327 if (Current.isNot(TT_Unknown)) {
2332 if ((Style.isJavaScript() || Style.isCSharp()) &&
2333 Current.is(tok::exclaim)) {
2334 if (Current.Previous) {
2336 Style.isJavaScript()
2337 ? Keywords.isJavaScriptIdentifier(
2338 *Current.Previous,
true)
2339 : Current.Previous->is(tok::identifier);
2341 Current.Previous->isOneOf(
2342 tok::kw_default, tok::kw_namespace, tok::r_paren, tok::r_square,
2343 tok::r_brace, tok::kw_false, tok::kw_true, Keywords.kw_type,
2344 Keywords.kw_get, Keywords.kw_init, Keywords.kw_set) ||
2345 Current.Previous->Tok.isLiteral()) {
2346 Current.setType(TT_NonNullAssertion);
2351 Current.Next->isOneOf(TT_BinaryOperator, Keywords.kw_as)) {
2352 Current.setType(TT_NonNullAssertion);
2361 Current.is(Keywords.kw_instanceof)) {
2362 Current.setType(TT_BinaryOperator);
2363 }
else if (isStartOfName(Current) &&
2364 (!Line.MightBeFunctionDecl || Current.NestingLevel != 0)) {
2365 Contexts.back().FirstStartOfName = &Current;
2366 Current.setType(TT_StartOfName);
2367 }
else if (Current.is(tok::semi)) {
2371 Contexts.back().FirstStartOfName =
nullptr;
2372 }
else if (Current.isOneOf(tok::kw_auto, tok::kw___auto_type)) {
2374 }
else if (Current.is(tok::arrow) &&
2376 Current.setType(TT_TrailingReturnArrow);
2377 }
else if (Current.is(tok::arrow) && Style.isVerilog()) {
2379 Current.setType(TT_BinaryOperator);
2380 }
else if (Current.is(tok::arrow) && AutoFound &&
2381 Line.MightBeFunctionDecl && Current.NestingLevel == 0 &&
2382 !Current.Previous->isOneOf(tok::kw_operator, tok::identifier)) {
2384 Current.setType(TT_TrailingReturnArrow);
2385 }
else if (Current.is(tok::arrow) && Current.Previous &&
2386 Current.Previous->is(tok::r_brace)) {
2389 Current.setType(TT_TrailingReturnArrow);
2390 }
else if (isDeductionGuide(Current)) {
2392 Current.setType(TT_TrailingReturnArrow);
2393 }
else if (Current.isPointerOrReference()) {
2394 Current.setType(determineStarAmpUsage(
2396 Contexts.back().CanBeExpression && Contexts.back().IsExpression,
2397 Contexts.back().ContextType == Context::TemplateArgument));
2398 }
else if (Current.isOneOf(tok::minus, tok::plus, tok::caret) ||
2399 (Style.isVerilog() && Current.is(tok::pipe))) {
2400 Current.setType(determinePlusMinusCaretUsage(Current));
2401 if (Current.is(TT_UnaryOperator) && Current.is(tok::caret))
2402 Contexts.back().CaretFound =
true;
2403 }
else if (Current.isOneOf(tok::minusminus, tok::plusplus)) {
2404 Current.setType(determineIncrementUsage(Current));
2405 }
else if (Current.isOneOf(tok::exclaim, tok::tilde)) {
2406 Current.setType(TT_UnaryOperator);
2407 }
else if (Current.is(tok::question)) {
2408 if (Style.isJavaScript() && Line.MustBeDeclaration &&
2409 !Contexts.back().IsExpression) {
2412 Current.setType(TT_JsTypeOptionalQuestion);
2413 }
else if (Style.isTableGen()) {
2415 Current.setType(TT_Unknown);
2417 Current.setType(TT_ConditionalExpr);
2419 }
else if (Current.isBinaryOperator() &&
2420 (!Current.Previous || Current.Previous->isNot(tok::l_square)) &&
2421 (Current.isNot(tok::greater) &&
2423 if (Style.isVerilog()) {
2424 if (Current.is(tok::lessequal) && Contexts.size() == 1 &&
2425 !Contexts.back().VerilogAssignmentFound) {
2429 Current.setFinalizedType(TT_BinaryOperator);
2432 Contexts.back().VerilogAssignmentFound =
true;
2434 Current.setType(TT_BinaryOperator);
2435 }
else if (Current.is(tok::comment)) {
2436 if (Current.TokenText.starts_with(
"/*")) {
2437 if (Current.TokenText.ends_with(
"*/")) {
2438 Current.setType(TT_BlockComment);
2442 Current.Tok.setKind(tok::unknown);
2445 Current.setType(TT_LineComment);
2447 }
else if (Current.is(tok::string_literal)) {
2448 if (Style.isVerilog() && Contexts.back().VerilogMayBeConcatenation &&
2449 Current.getPreviousNonComment() &&
2450 Current.getPreviousNonComment()->isOneOf(tok::comma, tok::l_brace) &&
2451 Current.getNextNonComment() &&
2452 Current.getNextNonComment()->isOneOf(tok::comma, tok::r_brace)) {
2453 Current.setType(TT_StringInConcatenation);
2455 }
else if (Current.is(tok::l_paren)) {
2456 if (lParenStartsCppCast(Current))
2457 Current.setType(TT_CppCastLParen);
2458 }
else if (Current.is(tok::r_paren)) {
2459 if (rParenEndsCast(Current))
2460 Current.setType(TT_CastRParen);
2461 if (Current.MatchingParen && Current.Next &&
2462 !Current.Next->isBinaryOperator() &&
2463 !Current.Next->isOneOf(
2464 tok::semi, tok::colon, tok::l_brace, tok::l_paren, tok::comma,
2465 tok::period, tok::arrow, tok::coloncolon, tok::kw_noexcept)) {
2466 if (FormatToken *AfterParen = Current.MatchingParen->Next;
2467 AfterParen && AfterParen->isNot(tok::caret)) {
2469 if (FormatToken *BeforeParen = Current.MatchingParen->Previous;
2470 BeforeParen && BeforeParen->is(tok::identifier) &&
2471 BeforeParen->isNot(TT_TypenameMacro) &&
2472 BeforeParen->TokenText == BeforeParen->TokenText.upper() &&
2473 (!BeforeParen->Previous ||
2474 BeforeParen->Previous->ClosesTemplateDeclaration ||
2475 BeforeParen->Previous->ClosesRequiresClause)) {
2476 Current.setType(TT_FunctionAnnotationRParen);
2480 }
else if (Current.is(tok::at) && Current.Next && !Style.isJavaScript() &&
2484 switch (Current.Next->Tok.getObjCKeywordID()) {
2485 case tok::objc_interface:
2486 case tok::objc_implementation:
2487 case tok::objc_protocol:
2488 Current.setType(TT_ObjCDecl);
2490 case tok::objc_property:
2491 Current.setType(TT_ObjCProperty);
2496 }
else if (Current.is(tok::period)) {
2497 FormatToken *PreviousNoComment = Current.getPreviousNonComment();
2498 if (PreviousNoComment &&
2499 PreviousNoComment->isOneOf(tok::comma, tok::l_brace)) {
2500 Current.setType(TT_DesignatedInitializerPeriod);
2502 Current.Previous->isOneOf(TT_JavaAnnotation,
2503 TT_LeadingJavaAnnotation)) {
2504 Current.setType(Current.Previous->getType());
2506 }
else if (canBeObjCSelectorComponent(Current) &&
2509 Current.Previous && Current.Previous->is(TT_CastRParen) &&
2510 Current.Previous->MatchingParen &&
2511 Current.Previous->MatchingParen->Previous &&
2512 Current.Previous->MatchingParen->Previous->is(
2513 TT_ObjCMethodSpecifier)) {
2517 Current.setType(TT_SelectorName);
2518 }
else if (Current.isOneOf(tok::identifier, tok::kw_const, tok::kw_noexcept,
2519 tok::kw_requires) &&
2521 !Current.Previous->isOneOf(tok::equal, tok::at,
2522 TT_CtorInitializerComma,
2523 TT_CtorInitializerColon) &&
2524 Line.MightBeFunctionDecl && Contexts.size() == 1) {
2527 Current.setType(TT_TrailingAnnotation);
2529 Style.isJavaScript()) &&
2531 if (Current.Previous->is(tok::at) &&
2532 Current.isNot(Keywords.kw_interface)) {
2533 const FormatToken &AtToken = *Current.Previous;
2534 const FormatToken *
Previous = AtToken.getPreviousNonComment();
2536 Current.setType(TT_LeadingJavaAnnotation);
2538 Current.setType(TT_JavaAnnotation);
2539 }
else if (Current.Previous->is(tok::period) &&
2540 Current.Previous->isOneOf(TT_JavaAnnotation,
2541 TT_LeadingJavaAnnotation)) {
2542 Current.setType(Current.Previous->getType());
2552 bool isStartOfName(
const FormatToken &Tok) {
2554 if (Style.isVerilog())
2557 if (Tok.isNot(tok::identifier) || !Tok.Previous)
2560 if (
const auto *NextNonComment = Tok.getNextNonComment();
2561 (!NextNonComment && !Line.InMacroBody) ||
2563 (NextNonComment->isPointerOrReference() ||
2564 NextNonComment->is(tok::string_literal) ||
2565 (Line.InPragmaDirective && NextNonComment->is(tok::identifier))))) {
2569 if (Tok.Previous->isOneOf(TT_LeadingJavaAnnotation, Keywords.kw_instanceof,
2573 if (Style.isJavaScript() && Tok.Previous->is(Keywords.kw_in))
2577 FormatToken *PreviousNotConst = Tok.getPreviousNonComment();
2580 if (!Style.isJavaScript())
2581 while (PreviousNotConst && PreviousNotConst->is(tok::kw_const))
2582 PreviousNotConst = PreviousNotConst->getPreviousNonComment();
2584 if (!PreviousNotConst)
2587 if (PreviousNotConst->ClosesRequiresClause)
2590 if (Style.isTableGen()) {
2592 if (Keywords.isTableGenDefinition(*PreviousNotConst))
2595 if (Contexts.back().ContextKind != tok::l_brace)
2599 bool IsPPKeyword = PreviousNotConst->is(tok::identifier) &&
2600 PreviousNotConst->Previous &&
2601 PreviousNotConst->Previous->is(tok::hash);
2603 if (PreviousNotConst->is(TT_TemplateCloser)) {
2604 return PreviousNotConst && PreviousNotConst->MatchingParen &&
2605 PreviousNotConst->MatchingParen->Previous &&
2606 PreviousNotConst->MatchingParen->Previous->isNot(tok::period) &&
2607 PreviousNotConst->MatchingParen->Previous->isNot(tok::kw_template);
2610 if ((PreviousNotConst->is(tok::r_paren) &&
2611 PreviousNotConst->is(TT_TypeDeclarationParen)) ||
2612 PreviousNotConst->is(TT_AttributeRParen)) {
2621 if (PreviousNotConst->isOneOf(tok::identifier, tok::kw_auto) &&
2622 PreviousNotConst->isNot(TT_StatementAttributeLikeMacro)) {
2627 if (PreviousNotConst->is(TT_PointerOrReference))
2631 if (PreviousNotConst->isTypeName(LangOpts))
2636 PreviousNotConst->is(tok::r_square)) {
2641 return Style.isJavaScript() && PreviousNotConst->is(tok::kw_const);
2645 bool lParenStartsCppCast(
const FormatToken &Tok) {
2650 FormatToken *LeftOfParens = Tok.getPreviousNonComment();
2651 if (LeftOfParens && LeftOfParens->is(TT_TemplateCloser) &&
2652 LeftOfParens->MatchingParen) {
2653 auto *Prev = LeftOfParens->MatchingParen->getPreviousNonComment();
2655 Prev->isOneOf(tok::kw_const_cast, tok::kw_dynamic_cast,
2656 tok::kw_reinterpret_cast, tok::kw_static_cast)) {
2666 bool rParenEndsCast(
const FormatToken &Tok) {
2667 assert(Tok.is(tok::r_paren));
2669 if (!Tok.MatchingParen || !Tok.Previous)
2676 const auto *LParen = Tok.MatchingParen;
2677 const auto *BeforeRParen = Tok.Previous;
2678 const auto *AfterRParen = Tok.Next;
2681 if (BeforeRParen == LParen || !AfterRParen)
2684 if (LParen->is(TT_OverloadedOperatorLParen))
2687 auto *LeftOfParens = LParen->getPreviousNonComment();
2691 if (LeftOfParens->is(tok::r_paren) &&
2692 LeftOfParens->isNot(TT_CastRParen)) {
2693 if (!LeftOfParens->MatchingParen ||
2694 !LeftOfParens->MatchingParen->Previous) {
2697 LeftOfParens = LeftOfParens->MatchingParen->Previous;
2700 if (LeftOfParens->is(tok::r_square)) {
2702 auto MayBeArrayDelete = [](FormatToken *Tok) -> FormatToken * {
2703 if (Tok->isNot(tok::r_square))
2706 Tok = Tok->getPreviousNonComment();
2707 if (!Tok || Tok->isNot(tok::l_square))
2710 Tok = Tok->getPreviousNonComment();
2711 if (!Tok || Tok->isNot(tok::kw_delete))
2715 if (FormatToken *MaybeDelete = MayBeArrayDelete(LeftOfParens))
2716 LeftOfParens = MaybeDelete;
2722 if (LeftOfParens->Tok.getIdentifierInfo() && LeftOfParens->Previous &&
2723 LeftOfParens->Previous->is(tok::kw_operator)) {
2729 if (LeftOfParens->Tok.getIdentifierInfo() &&
2730 !LeftOfParens->isOneOf(Keywords.kw_in, tok::kw_return, tok::kw_case,
2731 tok::kw_delete, tok::kw_throw)) {
2737 if (LeftOfParens->isOneOf(tok::at, tok::r_square, TT_OverloadedOperator,
2738 TT_TemplateCloser, tok::ellipsis)) {
2743 if (AfterRParen->is(tok::question) ||
2744 (AfterRParen->is(tok::ampamp) && !BeforeRParen->isTypeName(LangOpts))) {
2749 if (AfterRParen->is(Keywords.kw_in) && Style.isCSharp())
2754 if (AfterRParen->isOneOf(tok::kw_noexcept, tok::kw_volatile, tok::kw_const,
2755 tok::kw_requires, tok::kw_throw, tok::arrow,
2756 Keywords.kw_override, Keywords.kw_final) ||
2757 isCppAttribute(IsCpp, *AfterRParen)) {
2767 if (AfterRParen->isOneOf(tok::kw_sizeof, tok::kw_alignof) ||
2768 (AfterRParen->Tok.isLiteral() &&
2769 AfterRParen->isNot(tok::string_literal))) {
2774 auto IsQualifiedPointerOrReference = [](
const FormatToken *
T,
2775 const LangOptions &LangOpts) {
2777 assert(!
T->isTypeName(LangOpts) &&
"Should have already been checked");
2781 if (
T->is(TT_AttributeRParen)) {
2783 assert(
T->is(tok::r_paren));
2784 assert(
T->MatchingParen);
2785 assert(
T->MatchingParen->is(tok::l_paren));
2786 assert(
T->MatchingParen->is(TT_AttributeLParen));
2787 if (
const auto *Tok =
T->MatchingParen->Previous;
2788 Tok && Tok->isAttribute()) {
2792 }
else if (
T->is(TT_AttributeSquare)) {
2794 if (
T->MatchingParen &&
T->MatchingParen->Previous) {
2795 T =
T->MatchingParen->Previous;
2798 }
else if (
T->canBePointerOrReferenceQualifier()) {
2804 return T &&
T->is(TT_PointerOrReference);
2806 bool ParensAreType =
2807 BeforeRParen->isOneOf(TT_TemplateCloser, TT_TypeDeclarationParen) ||
2808 BeforeRParen->isTypeName(LangOpts) ||
2809 IsQualifiedPointerOrReference(BeforeRParen, LangOpts);
2810 bool ParensCouldEndDecl =
2811 AfterRParen->isOneOf(tok::equal, tok::semi, tok::l_brace, tok::greater);
2812 if (ParensAreType && !ParensCouldEndDecl)
2823 for (
const auto *Token = LParen->Next; Token != &Tok; Token = Token->Next)
2824 if (Token->is(TT_BinaryOperator))
2829 if (AfterRParen->isOneOf(tok::identifier, tok::kw_this))
2833 if (AfterRParen->is(tok::l_paren) && BeforeRParen->Previous) {
2834 if (BeforeRParen->is(tok::identifier) &&
2835 BeforeRParen->Previous->is(tok::l_paren)) {
2840 if (!AfterRParen->Next)
2843 if (AfterRParen->is(tok::l_brace) &&
2851 const bool NextIsAmpOrStar = AfterRParen->isOneOf(tok::amp, tok::star);
2852 if (!(AfterRParen->isUnaryOperator() || NextIsAmpOrStar) ||
2853 AfterRParen->is(tok::plus) ||
2854 !AfterRParen->Next->isOneOf(tok::identifier, tok::numeric_constant)) {
2858 if (NextIsAmpOrStar &&
2859 (AfterRParen->Next->is(tok::numeric_constant) || Line.InPPDirective)) {
2863 if (Line.InPPDirective && AfterRParen->is(tok::minus))
2867 for (
auto *Prev = BeforeRParen; Prev != LParen; Prev = Prev->Previous)
2868 if (!Prev->isOneOf(tok::kw_const, tok::identifier, tok::coloncolon))
2875 bool determineUnaryOperatorByUsage(
const FormatToken &Tok) {
2876 const FormatToken *PrevToken = Tok.getPreviousNonComment();
2886 if (PrevToken->isOneOf(
2887 TT_ConditionalExpr, tok::l_paren, tok::comma, tok::colon, tok::semi,
2888 tok::equal, tok::question, tok::l_square, tok::l_brace,
2889 tok::kw_case, tok::kw_co_await, tok::kw_co_return, tok::kw_co_yield,
2890 tok::kw_delete, tok::kw_return, tok::kw_throw)) {
2897 if (PrevToken->is(tok::kw_sizeof))
2901 if (PrevToken->isOneOf(TT_CastRParen, TT_UnaryOperator))
2905 if (PrevToken->is(TT_BinaryOperator))
2913 bool InTemplateArgument) {
2914 if (Style.isJavaScript())
2915 return TT_BinaryOperator;
2918 if (Style.isCSharp() && Tok.is(tok::ampamp))
2919 return TT_BinaryOperator;
2921 if (Style.isVerilog()) {
2926 if (Tok.is(tok::star))
2927 return TT_BinaryOperator;
2928 return determineUnaryOperatorByUsage(Tok) ? TT_UnaryOperator
2929 : TT_BinaryOperator;
2932 const FormatToken *PrevToken = Tok.getPreviousNonComment();
2934 return TT_UnaryOperator;
2935 if (PrevToken->is(TT_TypeName))
2936 return TT_PointerOrReference;
2937 if (PrevToken->isOneOf(tok::kw_new, tok::kw_delete) && Tok.is(tok::ampamp))
2938 return TT_BinaryOperator;
2940 const FormatToken *NextToken = Tok.getNextNonComment();
2942 if (InTemplateArgument && NextToken && NextToken->is(tok::kw_noexcept))
2943 return TT_BinaryOperator;
2946 NextToken->isOneOf(tok::arrow, tok::equal, tok::comma, tok::r_paren,
2947 TT_RequiresClause) ||
2949 NextToken->canBePointerOrReferenceQualifier() ||
2950 (NextToken->is(tok::l_brace) && !NextToken->getNextNonComment())) {
2951 return TT_PointerOrReference;
2954 if (PrevToken->is(tok::coloncolon))
2955 return TT_PointerOrReference;
2957 if (PrevToken->is(tok::r_paren) && PrevToken->is(TT_TypeDeclarationParen))
2958 return TT_PointerOrReference;
2960 if (determineUnaryOperatorByUsage(Tok))
2961 return TT_UnaryOperator;
2963 if (NextToken->is(tok::l_square) && NextToken->isNot(TT_LambdaLSquare))
2964 return TT_PointerOrReference;
2966 return TT_PointerOrReference;
2967 if (NextToken->isOneOf(tok::comma, tok::semi))
2968 return TT_PointerOrReference;
2980 if (PrevToken->is(tok::r_brace) && Tok.is(tok::star) &&
2981 !PrevToken->MatchingParen) {
2982 return TT_PointerOrReference;
2985 if (PrevToken->endsSequence(tok::r_square, tok::l_square, tok::kw_delete))
2986 return TT_UnaryOperator;
2988 if (PrevToken->Tok.isLiteral() ||
2989 PrevToken->isOneOf(tok::r_paren, tok::r_square, tok::kw_true,
2990 tok::kw_false, tok::r_brace)) {
2991 return TT_BinaryOperator;
2994 const FormatToken *NextNonParen = NextToken;
2995 while (NextNonParen && NextNonParen->is(tok::l_paren))
2996 NextNonParen = NextNonParen->getNextNonComment();
2997 if (NextNonParen && (NextNonParen->Tok.isLiteral() ||
2998 NextNonParen->isOneOf(tok::kw_true, tok::kw_false) ||
2999 NextNonParen->isUnaryOperator())) {
3000 return TT_BinaryOperator;
3006 if (InTemplateArgument && NextToken->Tok.isAnyIdentifier())
3007 return TT_BinaryOperator;
3011 if (Tok.is(tok::ampamp) &&
3012 NextToken->isOneOf(tok::l_paren, tok::star, tok::amp)) {
3013 return TT_BinaryOperator;
3018 if (NextToken->Tok.isAnyIdentifier()) {
3019 const FormatToken *NextNextToken = NextToken->getNextNonComment();
3020 if (NextNextToken && NextNextToken->is(tok::arrow))
3021 return TT_BinaryOperator;
3027 return TT_BinaryOperator;
3030 if (!Scopes.empty() && Scopes.back() ==
ST_Class)
3031 return TT_PointerOrReference;
3034 auto IsChainedOperatorAmpOrMember = [](
const FormatToken *token) {
3035 return !token || token->isOneOf(tok::amp, tok::period, tok::arrow,
3036 tok::arrowstar, tok::periodstar);
3041 if (Tok.is(tok::amp) && PrevToken && PrevToken->Tok.isAnyIdentifier() &&
3042 IsChainedOperatorAmpOrMember(PrevToken->getPreviousNonComment()) &&
3043 NextToken && NextToken->Tok.isAnyIdentifier()) {
3044 if (
auto NextNext = NextToken->getNextNonComment();
3046 (IsChainedOperatorAmpOrMember(NextNext) || NextNext->is(tok::semi))) {
3047 return TT_BinaryOperator;
3051 return TT_PointerOrReference;
3054 TokenType determinePlusMinusCaretUsage(
const FormatToken &Tok) {
3055 if (determineUnaryOperatorByUsage(Tok))
3056 return TT_UnaryOperator;
3058 const FormatToken *PrevToken = Tok.getPreviousNonComment();
3060 return TT_UnaryOperator;
3062 if (PrevToken->is(tok::at))
3063 return TT_UnaryOperator;
3066 return TT_BinaryOperator;
3070 TokenType determineIncrementUsage(
const FormatToken &Tok) {
3071 const FormatToken *PrevToken = Tok.getPreviousNonComment();
3072 if (!PrevToken || PrevToken->is(TT_CastRParen))
3073 return TT_UnaryOperator;
3074 if (PrevToken->isOneOf(tok::r_paren, tok::r_square, tok::identifier))
3075 return TT_TrailingUnaryOperator;
3077 return TT_UnaryOperator;
3080 SmallVector<Context, 8> Contexts;
3082 const FormatStyle &Style;
3083 AnnotatedLine &Line;
3084 FormatToken *CurrentToken;
3087 LangOptions LangOpts;
3088 const AdditionalKeywords &Keywords;
3090 SmallVector<ScopeType> &Scopes;
3098 int TemplateDeclarationDepth;
3106class ExpressionParser {
3108 ExpressionParser(
const FormatStyle &Style,
const AdditionalKeywords &Keywords,
3109 AnnotatedLine &Line)
3110 : Style(Style), Keywords(Keywords), Line(Line), Current(Line.
First) {}
3113 void parse(
int Precedence = 0) {
3116 while (Current && (Current->is(tok::kw_return) ||
3117 (Current->is(tok::colon) &&
3118 Current->isOneOf(TT_ObjCMethodExpr, TT_DictLiteral)))) {
3122 if (!Current || Precedence > PrecedenceArrowAndPeriod)
3127 parseConditionalExpr();
3133 if (Precedence == PrecedenceUnaryOperator) {
3134 parseUnaryOperator();
3138 FormatToken *Start = Current;
3139 FormatToken *LatestOperator =
nullptr;
3140 unsigned OperatorIndex = 0;
3142 FormatToken *VerilogFirstOfType =
nullptr;
3151 if (Style.isVerilog() && Precedence ==
prec::Comma) {
3152 VerilogFirstOfType =
3153 verilogGroupDecl(VerilogFirstOfType, LatestOperator);
3157 parse(Precedence + 1);
3159 int CurrentPrecedence = getCurrentPrecedence();
3161 if (Precedence == CurrentPrecedence && Current &&
3162 Current->is(TT_SelectorName)) {
3164 addFakeParenthesis(Start,
prec::Level(Precedence));
3168 if ((Style.isCSharp() || Style.isJavaScript() ||
3173 FormatToken *Prev = Current->getPreviousNonComment();
3174 if (Prev && Prev->is(tok::string_literal) &&
3175 (Prev == Start || Prev->endsSequence(tok::string_literal, tok::plus,
3176 TT_StringInConcatenation))) {
3177 Prev->setType(TT_StringInConcatenation);
3184 (Current->closesScope() &&
3185 (Current->MatchingParen || Current->is(TT_TemplateString))) ||
3186 (CurrentPrecedence != -1 && CurrentPrecedence < Precedence) ||
3195 if (Current->opensScope() ||
3196 Current->isOneOf(TT_RequiresClause,
3197 TT_RequiresClauseInARequiresExpression)) {
3200 while (Current && (!Current->closesScope() || Current->opensScope())) {
3207 if (CurrentPrecedence == Precedence) {
3209 LatestOperator->NextOperator = Current;
3210 LatestOperator = Current;
3211 Current->OperatorIndex = OperatorIndex;
3214 next(Precedence > 0);
3219 if (Style.isVerilog() && Precedence ==
prec::Comma && VerilogFirstOfType)
3220 addFakeParenthesis(VerilogFirstOfType,
prec::Comma);
3222 if (LatestOperator && (Current || Precedence > 0)) {
3228 Start->Previous->isOneOf(TT_RequiresClause,
3229 TT_RequiresClauseInARequiresExpression))
3231 auto Ret = Current ? Current : Line.Last;
3232 while (!
Ret->ClosesRequiresClause &&
Ret->Previous)
3238 if (Precedence == PrecedenceArrowAndPeriod) {
3242 addFakeParenthesis(Start,
prec::Level(Precedence), End);
3250 int getCurrentPrecedence() {
3252 const FormatToken *NextNonComment = Current->getNextNonComment();
3253 if (Current->is(TT_ConditionalExpr))
3255 if (NextNonComment && Current->is(TT_SelectorName) &&
3256 (NextNonComment->isOneOf(TT_DictLiteral, TT_JsTypeColon) ||
3257 (Style.isProto() && NextNonComment->is(tok::less)))) {
3260 if (Current->is(TT_JsComputedPropertyName))
3262 if (Current->is(TT_TrailingReturnArrow))
3264 if (Current->is(TT_FatArrow))
3266 if (Current->isOneOf(tok::semi, TT_InlineASMColon, TT_SelectorName) ||
3267 (Current->is(tok::comment) && NextNonComment &&
3268 NextNonComment->is(TT_SelectorName))) {
3271 if (Current->is(TT_RangeBasedForLoopColon))
3274 Current->is(Keywords.kw_instanceof)) {
3277 if (Style.isJavaScript() &&
3278 Current->isOneOf(Keywords.kw_in, Keywords.kw_as)) {
3281 if (Current->is(TT_BinaryOperator) || Current->is(tok::comma))
3282 return Current->getPrecedence();
3283 if (Current->isOneOf(tok::period, tok::arrow) &&
3284 Current->isNot(TT_TrailingReturnArrow)) {
3285 return PrecedenceArrowAndPeriod;
3288 Current->isOneOf(Keywords.kw_extends, Keywords.kw_implements,
3289 Keywords.kw_throws)) {
3294 if (Style.isVerilog() && Current->is(tok::colon))
3300 void addFakeParenthesis(FormatToken *Start,
prec::Level Precedence,
3301 FormatToken *End =
nullptr) {
3306 if (Start->MacroParent)
3309 Start->FakeLParens.push_back(Precedence);
3311 Start->StartsBinaryExpression =
true;
3312 if (!End && Current)
3313 End = Current->getPreviousNonComment();
3317 End->EndsBinaryExpression =
true;
3323 void parseUnaryOperator() {
3325 while (Current && Current->is(TT_UnaryOperator)) {
3326 Tokens.push_back(Current);
3329 parse(PrecedenceArrowAndPeriod);
3330 for (FormatToken *Token : llvm::reverse(Tokens)) {
3336 void parseConditionalExpr() {
3337 while (Current && Current->isTrailingComment())
3339 FormatToken *Start = Current;
3341 if (!Current || Current->isNot(tok::question))
3345 if (!Current || Current->isNot(TT_ConditionalExpr))
3352 void next(
bool SkipPastLeadingComments =
true) {
3354 Current = Current->Next;
3356 (Current->NewlinesBefore == 0 || SkipPastLeadingComments) &&
3357 Current->isTrailingComment()) {
3358 Current = Current->Next;
3364 FormatToken *verilogGroupDecl(FormatToken *FirstOfType,
3365 FormatToken *PreviousComma) {
3369 FormatToken *Start = Current;
3372 while (Start->startsSequence(tok::l_paren, tok::star)) {
3373 if (!(Start = Start->MatchingParen) ||
3374 !(Start = Start->getNextNonComment())) {
3379 FormatToken *Tok = Start;
3381 if (Tok->is(Keywords.kw_assign))
3382 Tok = Tok->getNextNonComment();
3390 FormatToken *
First =
nullptr;
3392 FormatToken *Next = Tok->getNextNonComment();
3394 if (Tok->is(tok::hash)) {
3399 Tok = Tok->getNextNonComment();
3400 }
else if (Tok->is(tok::hashhash)) {
3404 Tok = Tok->getNextNonComment();
3405 }
else if (Keywords.isVerilogQualifier(*Tok) ||
3406 Keywords.isVerilogIdentifier(*Tok)) {
3410 while (Tok && Tok->isOneOf(tok::period, tok::coloncolon) &&
3411 (Tok = Tok->getNextNonComment())) {
3412 if (Keywords.isVerilogIdentifier(*Tok))
3413 Tok = Tok->getNextNonComment();
3417 }
else if (Tok->is(tok::l_paren)) {
3422 Keywords.kw_highz0, Keywords.kw_highz1, Keywords.kw_large,
3423 Keywords.kw_medium, Keywords.kw_pull0, Keywords.kw_pull1,
3424 Keywords.kw_small, Keywords.kw_strong0, Keywords.kw_strong1,
3425 Keywords.kw_supply0, Keywords.kw_supply1, Keywords.kw_weak0,
3426 Keywords.kw_weak1)) {
3427 Tok->setType(TT_VerilogStrength);
3428 Tok = Tok->MatchingParen;
3430 Tok->setType(TT_VerilogStrength);
3431 Tok = Tok->getNextNonComment();
3436 }
else if (Tok->is(Keywords.kw_verilogHash)) {
3438 if (Next->is(tok::l_paren))
3439 Next = Next->MatchingParen;
3441 Tok = Next->getNextNonComment();
3448 FormatToken *Second =
nullptr;
3450 while (Tok && Tok->is(tok::l_square) && (Tok = Tok->MatchingParen))
3451 Tok = Tok->getNextNonComment();
3452 if (Tok && (Tok->is(tok::hash) || Keywords.isVerilogIdentifier(*Tok)))
3457 FormatToken *TypedName =
nullptr;
3461 First->setType(TT_VerilogDimensionedTypeName);
3462 }
else if (
First != Start) {
3470 if (TypedName->is(TT_Unknown))
3471 TypedName->setType(TT_StartOfName);
3473 if (FirstOfType && PreviousComma) {
3474 PreviousComma->setType(TT_VerilogTypeComma);
3475 addFakeParenthesis(FirstOfType,
prec::Comma, PreviousComma->Previous);
3478 FirstOfType = TypedName;
3485 while (Current && Current != FirstOfType) {
3486 if (Current->opensScope()) {
3497 const FormatStyle &Style;
3498 const AdditionalKeywords &Keywords;
3499 const AnnotatedLine &Line;
3500 FormatToken *Current;
3509 assert(
Line->First);
3516 Line->First->OriginalColumn) {
3517 const bool PPDirectiveOrImportStmt =
3520 if (PPDirectiveOrImportStmt)
3526 PPDirectiveOrImportStmt
3528 : NextNonCommentLine->
Level;
3530 NextNonCommentLine =
Line->First->isNot(tok::r_brace) ?
Line :
nullptr;
3539 for (
const auto *Tok =
Line.First; Tok; Tok = Tok->Next)
3548 for (
FormatToken *Tok =
Line.getFirstNonComment(), *Name =
nullptr; Tok;
3549 Tok = Tok->getNextNonComment()) {
3551 if (Tok->is(tok::l_square) && Tok->is(TT_AttributeSquare)) {
3560 if (Tok->is(tok::l_paren) && Tok->isNot(TT_FunctionTypeLParen) &&
3561 Tok->MatchingParen) {
3569 if (Tok->isOneOf(tok::kw_friend, tok::kw_inline, tok::kw_virtual,
3570 tok::kw_constexpr, tok::kw_consteval, tok::kw_explicit)) {
3575 if (Tok->is(tok::coloncolon)) {
3582 while (Tok->startsSequence(tok::identifier, tok::coloncolon)) {
3584 Tok = Tok->Next->Next;
3590 if (Tok->is(tok::tilde)) {
3597 if (Tok->isNot(tok::identifier) || Tok->isNot(TT_Unknown))
3608 assert(Tok && Tok->
is(tok::identifier));
3611 if (Prev && Prev->is(tok::tilde))
3614 if (!Prev || !Prev->endsSequence(tok::coloncolon, tok::identifier))
3617 assert(Prev->Previous);
3618 return Prev->Previous->TokenText == Tok->
TokenText;
3622 AnnotatingParser
Parser(Style,
Line, Keywords, Scopes);
3625 for (
auto &Child :
Line.Children)
3638 ExpressionParser ExprParser(Style, Keywords,
Line);
3644 if (Tok && ((!Scopes.empty() && Scopes.back() ==
ST_Class) ||
3646 Tok->setFinalizedType(TT_CtorDtorDeclName);
3647 assert(OpeningParen);
3652 if (
Line.startsWith(TT_ObjCMethodSpecifier))
3654 else if (
Line.startsWith(TT_ObjCDecl))
3656 else if (
Line.startsWith(TT_ObjCProperty))
3660 First->SpacesRequiredBefore = 1;
3661 First->CanBreakBefore =
First->MustBreakBefore;
3663 if (
First->is(tok::eof) &&
First->NewlinesBefore == 0 &&
3664 Style.InsertNewlineAtEOF) {
3665 First->NewlinesBefore = 1;
3677 if (Current.
is(TT_FunctionDeclarationName))
3685 if (
const auto *PrevPrev =
Previous.Previous;
3686 PrevPrev && PrevPrev->is(TT_ObjCDecl)) {
3690 auto skipOperatorName =
3692 for (; Next; Next = Next->Next) {
3693 if (Next->is(TT_OverloadedOperatorLParen))
3695 if (Next->is(TT_OverloadedOperator))
3697 if (Next->isOneOf(tok::kw_new, tok::kw_delete)) {
3700 Next->Next->startsSequence(tok::l_square, tok::r_square)) {
3701 Next = Next->Next->Next;
3705 if (Next->startsSequence(tok::l_square, tok::r_square)) {
3710 if ((Next->isTypeName(LangOpts) || Next->is(tok::identifier)) &&
3711 Next->Next && Next->Next->isPointerOrReference()) {
3716 if (Next->is(TT_TemplateOpener) && Next->MatchingParen) {
3717 Next = Next->MatchingParen;
3726 const auto *Next = Current.
Next;
3727 const bool IsCpp = LangOpts.CXXOperatorNames;
3730 if (Current.
is(tok::kw_operator)) {
3731 if (
Previous.Tok.getIdentifierInfo() &&
3732 !
Previous.isOneOf(tok::kw_return, tok::kw_co_return)) {
3737 assert(
Previous.MatchingParen->is(tok::l_paren));
3738 assert(
Previous.MatchingParen->is(TT_TypeDeclarationParen));
3743 Next = skipOperatorName(Next);
3747 for (; Next; Next = Next->Next) {
3748 if (Next->is(TT_TemplateOpener) && Next->MatchingParen) {
3749 Next = Next->MatchingParen;
3750 }
else if (Next->is(tok::coloncolon)) {
3754 if (Next->is(tok::kw_operator)) {
3755 Next = skipOperatorName(Next->Next);
3758 if (Next->isNot(tok::identifier))
3760 }
else if (isCppAttribute(IsCpp, *Next)) {
3761 Next = Next->MatchingParen;
3764 }
else if (Next->is(tok::l_paren)) {
3773 if (!Next || Next->isNot(tok::l_paren) || !Next->MatchingParen)
3775 ClosingParen = Next->MatchingParen;
3776 assert(ClosingParen->
is(tok::r_paren));
3778 if (
Line.Last->is(tok::l_brace))
3780 if (Next->Next == ClosingParen)
3783 if (ClosingParen->
Next && ClosingParen->
Next->
is(TT_PointerOrReference))
3796 if (IsCpp && Next->Next && Next->Next->is(tok::identifier) &&
3797 !
Line.endsWith(tok::semi)) {
3801 for (
const FormatToken *Tok = Next->Next; Tok && Tok != ClosingParen;
3803 if (Tok->is(TT_TypeDeclarationParen))
3805 if (Tok->isOneOf(tok::l_paren, TT_TemplateOpener) && Tok->MatchingParen) {
3806 Tok = Tok->MatchingParen;
3809 if (Tok->is(tok::kw_const) || Tok->isTypeName(LangOpts) ||
3810 Tok->isOneOf(TT_PointerOrReference, TT_StartOfName, tok::ellipsis)) {
3813 if (Tok->isOneOf(tok::l_brace, TT_ObjCMethodExpr) || Tok->Tok.isLiteral())
3819bool TokenAnnotator::mustBreakForReturnType(
const AnnotatedLine &
Line)
const {
3820 assert(
Line.MightBeFunctionDecl);
3828 switch (Style.BreakAfterReturnType) {
3838 return Line.mightBeFunctionDefinition();
3851 :
Line.FirstStartColumn +
First->ColumnWidth;
3853 bool InFunctionDecl =
Line.MightBeFunctionDecl;
3854 bool AlignArrayOfStructures =
3857 if (AlignArrayOfStructures)
3858 calculateArrayInitializerColumnList(
Line);
3860 bool SeenName =
false;
3861 bool LineIsFunctionDeclaration =
false;
3865 for (
auto *Tok = Current; Tok; Tok = Tok->Next) {
3866 if (Tok->is(TT_StartOfName))
3868 if (Tok->Previous->EndsCppAttributeGroup)
3869 AfterLastAttribute = Tok;
3870 if (
const bool IsCtorOrDtor = Tok->is(TT_CtorDtorDeclName);
3875 LineIsFunctionDeclaration =
true;
3879 assert(OpeningParen);
3880 if (OpeningParen->is(TT_Unknown))
3881 OpeningParen->setType(TT_FunctionDeclarationLParen);
3887 if (IsCpp && (LineIsFunctionDeclaration ||
First->is(TT_CtorDtorDeclName)) &&
3888 Line.endsWith(tok::semi, tok::r_brace)) {
3889 auto *Tok =
Line.Last->Previous;
3890 while (Tok->isNot(tok::r_brace))
3891 Tok = Tok->Previous;
3892 if (
auto *LBrace = Tok->MatchingParen; LBrace) {
3893 assert(LBrace->is(tok::l_brace));
3896 LBrace->setFinalizedType(TT_FunctionLBrace);
3900 if (IsCpp && SeenName && AfterLastAttribute &&
3903 if (LineIsFunctionDeclaration)
3904 Line.ReturnTypeWrapped =
true;
3908 if (!LineIsFunctionDeclaration) {
3910 for (
const auto *Tok =
First; Tok; Tok = Tok->Next) {
3911 if (Tok->isNot(tok::kw_operator))
3915 }
while (Tok && Tok->isNot(TT_OverloadedOperatorLParen));
3916 if (!Tok || !Tok->MatchingParen)
3918 const auto *LeftParen = Tok;
3919 for (Tok = Tok->Next; Tok && Tok != LeftParen->MatchingParen;
3921 if (Tok->isNot(tok::identifier))
3923 auto *Next = Tok->Next;
3924 const bool NextIsBinaryOperator =
3925 Next && Next->isPointerOrReference() && Next->Next &&
3926 Next->Next->is(tok::identifier);
3927 if (!NextIsBinaryOperator)
3929 Next->setType(TT_BinaryOperator);
3933 }
else if (ClosingParen) {
3934 for (
auto *Tok = ClosingParen->
Next; Tok; Tok = Tok->
Next) {
3935 if (Tok->is(TT_CtorInitializerColon))
3937 if (Tok->is(tok::arrow)) {
3938 Tok->setType(TT_TrailingReturnArrow);
3941 if (Tok->isNot(TT_TrailingAnnotation))
3943 const auto *Next = Tok->Next;
3944 if (!Next || Next->isNot(tok::l_paren))
3946 Tok = Next->MatchingParen;
3955 if (Current->is(TT_LineComment)) {
3957 Current->SpacesRequiredBefore =
3958 (Style.Cpp11BracedListStyle && !Style.SpacesInParensOptions.Other)
3961 }
else if (Prev->
is(TT_VerilogMultiLineListLParen)) {
3962 Current->SpacesRequiredBefore = 0;
3964 Current->SpacesRequiredBefore = Style.SpacesBeforeTrailingComments;
3974 if (!Current->HasUnescapedNewline) {
3977 if (
Parameter->isOneOf(tok::comment, tok::r_brace))
3980 if (
Parameter->Previous->isNot(TT_CtorInitializerComma) &&
3988 }
else if (!Current->Finalized && Current->SpacesRequiredBefore == 0 &&
3989 spaceRequiredBefore(
Line, *Current)) {
3990 Current->SpacesRequiredBefore = 1;
3993 const auto &Children = Prev->
Children;
3994 if (!Children.empty() && Children.back()->Last->is(TT_LineComment)) {
3995 Current->MustBreakBefore =
true;
3997 Current->MustBreakBefore =
3998 Current->MustBreakBefore || mustBreakBefore(
Line, *Current);
3999 if (!Current->MustBreakBefore && InFunctionDecl &&
4000 Current->is(TT_FunctionDeclarationName)) {
4001 Current->MustBreakBefore = mustBreakForReturnType(
Line);
4005 Current->CanBreakBefore =
4006 Current->MustBreakBefore || canBreakBefore(
Line, *Current);
4007 unsigned ChildSize = 0;
4013 if (Current->MustBreakBefore || Prev->
Children.size() > 1 ||
4015 Prev->
Children[0]->First->MustBreakBefore) ||
4016 Current->IsMultiline) {
4017 Current->TotalLength = Prev->
TotalLength + Style.ColumnLimit;
4019 Current->TotalLength = Prev->
TotalLength + Current->ColumnWidth +
4020 ChildSize + Current->SpacesRequiredBefore;
4023 if (Current->is(TT_CtorInitializerColon))
4024 InFunctionDecl =
false;
4035 Current->SplitPenalty = splitPenalty(
Line, *Current, InFunctionDecl);
4037 Current->is(TT_SelectorName) && Current->ParameterIndex > 0) {
4038 if (Current->ParameterIndex == 1)
4039 Current->SplitPenalty += 5 * Current->BindingStrength;
4041 Current->SplitPenalty += 20 * Current->BindingStrength;
4044 Current = Current->Next;
4047 calculateUnbreakableTailLengths(
Line);
4048 unsigned IndentLevel =
Line.Level;
4049 for (Current =
First; Current; Current = Current->Next) {
4051 Current->Role->precomputeFormattingInfos(Current);
4052 if (Current->MatchingParen &&
4053 Current->MatchingParen->opensBlockOrBlockTypeList(Style) &&
4057 Current->IndentLevel = IndentLevel;
4058 if (Current->opensBlockOrBlockTypeList(Style))
4062 LLVM_DEBUG({ printDebugInfo(
Line); });
4065void TokenAnnotator::calculateUnbreakableTailLengths(
4067 unsigned UnbreakableTailLength = 0;
4070 Current->UnbreakableTailLength = UnbreakableTailLength;
4071 if (Current->CanBreakBefore ||
4072 Current->isOneOf(tok::comment, tok::string_literal)) {
4073 UnbreakableTailLength = 0;
4075 UnbreakableTailLength +=
4076 Current->ColumnWidth + Current->SpacesRequiredBefore;
4078 Current = Current->Previous;
4082void TokenAnnotator::calculateArrayInitializerColumnList(
4083 AnnotatedLine &
Line)
const {
4086 auto *CurrentToken =
Line.First;
4087 CurrentToken->ArrayInitializerLineStart =
true;
4089 while (CurrentToken && CurrentToken !=
Line.Last) {
4090 if (CurrentToken->is(tok::l_brace)) {
4091 CurrentToken->IsArrayInitializer =
true;
4092 if (CurrentToken->Next)
4093 CurrentToken->Next->MustBreakBefore =
true;
4095 calculateInitializerColumnList(
Line, CurrentToken->Next, Depth + 1);
4097 CurrentToken = CurrentToken->Next;
4102FormatToken *TokenAnnotator::calculateInitializerColumnList(
4103 AnnotatedLine &
Line, FormatToken *CurrentToken,
unsigned Depth)
const {
4104 while (CurrentToken && CurrentToken !=
Line.Last) {
4105 if (CurrentToken->is(tok::l_brace))
4107 else if (CurrentToken->is(tok::r_brace))
4109 if (Depth == 2 && CurrentToken->isOneOf(tok::l_brace, tok::comma)) {
4110 CurrentToken = CurrentToken->Next;
4113 CurrentToken->StartsColumn =
true;
4114 CurrentToken = CurrentToken->Previous;
4116 CurrentToken = CurrentToken->Next;
4118 return CurrentToken;
4121unsigned TokenAnnotator::splitPenalty(
const AnnotatedLine &
Line,
4122 const FormatToken &Tok,
4123 bool InFunctionDecl)
const {
4124 const FormatToken &
Left = *Tok.Previous;
4125 const FormatToken &
Right = Tok;
4127 if (
Left.is(tok::semi))
4132 if (
Right.isOneOf(Keywords.kw_extends, Keywords.kw_throws))
4134 if (
Right.is(Keywords.kw_implements))
4136 if (
Left.is(tok::comma) &&
Left.NestingLevel == 0)
4138 }
else if (Style.isJavaScript()) {
4139 if (
Right.is(Keywords.kw_function) &&
Left.isNot(tok::comma))
4141 if (
Left.is(TT_JsTypeColon))
4143 if ((
Left.is(TT_TemplateString) &&
Left.TokenText.ends_with(
"${")) ||
4144 (
Right.is(TT_TemplateString) &&
Right.TokenText.starts_with(
"}"))) {
4148 if (
Left.opensScope() &&
Right.closesScope())
4151 if (
Right.is(tok::l_square))
4153 if (
Right.is(tok::period))
4157 if (
Right.is(tok::identifier) &&
Right.Next &&
Right.Next->is(TT_DictLiteral))
4159 if (
Right.is(tok::l_square)) {
4160 if (
Left.is(tok::r_square))
4163 if (
Right.is(TT_LambdaLSquare) &&
Left.is(tok::equal))
4165 if (!
Right.isOneOf(TT_ObjCMethodExpr, TT_LambdaLSquare,
4166 TT_ArrayInitializerLSquare,
4167 TT_DesignatedInitializerLSquare, TT_AttributeSquare)) {
4172 if (
Left.is(tok::coloncolon))
4173 return Style.PenaltyBreakScopeResolution;
4174 if (
Right.isOneOf(TT_StartOfName, TT_FunctionDeclarationName) ||
4175 Right.is(tok::kw_operator)) {
4176 if (
Line.startsWith(tok::kw_for) &&
Right.PartOfMultiVariableDeclStmt)
4178 if (
Left.is(TT_StartOfName))
4180 if (InFunctionDecl &&
Right.NestingLevel == 0)
4181 return Style.PenaltyReturnTypeOnItsOwnLine;
4184 if (
Right.is(TT_PointerOrReference))
4186 if (
Right.is(TT_TrailingReturnArrow))
4188 if (
Left.is(tok::equal) &&
Right.is(tok::l_brace))
4190 if (
Left.is(TT_CastRParen))
4192 if (
Left.isOneOf(tok::kw_class, tok::kw_struct, tok::kw_union))
4194 if (
Left.is(tok::comment))
4197 if (
Left.isOneOf(TT_RangeBasedForLoopColon, TT_InheritanceColon,
4198 TT_CtorInitializerColon)) {
4202 if (
Right.isMemberAccess()) {
4222 return !
Right.NextOperator || !
Right.NextOperator->Previous->closesScope()
4227 if (
Right.is(TT_TrailingAnnotation) &&
4228 (!
Right.Next ||
Right.Next->isNot(tok::l_paren))) {
4231 if (
Line.startsWith(TT_ObjCMethodSpecifier))
4238 bool is_short_annotation =
Right.TokenText.size() < 10;
4239 return (
Left.is(tok::r_paren) ? 100 : 120) + (is_short_annotation ? 50 : 0);
4243 if (
Line.startsWith(tok::kw_for) &&
Left.is(tok::equal))
4248 if (
Right.is(TT_SelectorName))
4250 if (
Left.is(tok::colon) &&
Left.is(TT_ObjCMethodExpr))
4251 return Line.MightBeFunctionDecl ? 50 : 500;
4257 Left.Previous->isOneOf(tok::identifier, tok::greater)) {
4261 if (
Left.is(tok::l_paren) && Style.PenaltyBreakOpenParenthesis != 0)
4262 return Style.PenaltyBreakOpenParenthesis;
4263 if (
Left.is(tok::l_paren) && InFunctionDecl &&
4267 if (
Left.is(tok::l_paren) &&
Left.Previous &&
4268 (
Left.Previous->isOneOf(tok::kw_for, tok::kw__Generic) ||
4269 Left.Previous->isIf())) {
4272 if (
Left.is(tok::equal) && InFunctionDecl)
4274 if (
Right.is(tok::r_brace))
4276 if (
Left.is(TT_TemplateOpener))
4278 if (
Left.opensScope()) {
4283 (
Left.ParameterCount <= 1 || Style.AllowAllArgumentsOnNextLine)) {
4286 if (
Left.is(tok::l_brace) && !Style.Cpp11BracedListStyle)
4288 return Left.ParameterCount > 1 ? Style.PenaltyBreakBeforeFirstCallParameter
4291 if (
Left.is(TT_JavaAnnotation))
4294 if (
Left.is(TT_UnaryOperator))
4296 if (
Left.isOneOf(tok::plus, tok::comma) &&
Left.Previous &&
4297 Left.Previous->isLabelString() &&
4298 (
Left.NextOperator ||
Left.OperatorIndex != 0)) {
4301 if (
Right.is(tok::plus) &&
Left.isLabelString() &&
4302 (
Right.NextOperator ||
Right.OperatorIndex != 0)) {
4305 if (
Left.is(tok::comma))
4307 if (
Right.is(tok::lessless) &&
Left.isLabelString() &&
4308 (
Right.NextOperator ||
Right.OperatorIndex != 1)) {
4311 if (
Right.is(tok::lessless)) {
4313 if (
Left.isNot(tok::r_paren) ||
Right.OperatorIndex > 0) {
4319 if (
Left.ClosesTemplateDeclaration)
4320 return Style.PenaltyBreakTemplateDeclaration;
4321 if (
Left.ClosesRequiresClause)
4323 if (
Left.is(TT_ConditionalExpr))
4329 return Style.PenaltyBreakAssignment;
4336bool TokenAnnotator::spaceRequiredBeforeParens(
const FormatToken &Right)
const {
4339 if (
Right.is(TT_OverloadedOperatorLParen) &&
4340 Style.SpaceBeforeParensOptions.AfterOverloadedOperator) {
4343 if (Style.SpaceBeforeParensOptions.BeforeNonEmptyParentheses &&
4344 Right.ParameterCount > 0) {
4350bool TokenAnnotator::spaceRequiredBetween(
const AnnotatedLine &
Line,
4351 const FormatToken &Left,
4352 const FormatToken &Right)
const {
4353 if (
Left.is(tok::kw_return) &&
4354 !
Right.isOneOf(tok::semi, tok::r_paren, tok::hashhash)) {
4357 if (
Left.is(tok::kw_throw) &&
Right.is(tok::l_paren) &&
Right.MatchingParen &&
4358 Right.MatchingParen->is(TT_CastRParen)) {
4364 Left.Tok.getObjCKeywordID() == tok::objc_property) {
4367 if (
Right.is(tok::hashhash))
4368 return Left.is(tok::hash);
4369 if (
Left.isOneOf(tok::hashhash, tok::hash))
4370 return Right.is(tok::hash);
4372 Right.MatchingParen == &Left &&
Line.Children.empty()) {
4373 return Style.SpaceInEmptyBlock;
4375 if ((
Left.is(tok::l_paren) &&
Right.is(tok::r_paren)) ||
4378 return Style.SpacesInParensOptions.InEmptyParentheses;
4381 Style.SpacesInParensOptions.ExceptDoubleParentheses &&
4382 Left.is(tok::r_paren) &&
Right.is(tok::r_paren)) {
4383 auto *InnerLParen =
Left.MatchingParen;
4384 if (InnerLParen && InnerLParen->Previous ==
Right.MatchingParen) {
4385 InnerLParen->SpacesRequiredBefore = 0;
4389 if (Style.SpacesInParensOptions.InConditionalStatements) {
4390 const FormatToken *LeftParen =
nullptr;
4391 if (
Left.is(tok::l_paren))
4393 else if (
Right.is(tok::r_paren) &&
Right.MatchingParen)
4394 LeftParen =
Right.MatchingParen;
4396 if (LeftParen->is(TT_ConditionLParen))
4398 if (LeftParen->Previous && isKeywordWithCondition(*LeftParen->Previous))
4404 if (
Left.is(tok::kw_auto) &&
Right.isOneOf(TT_LambdaLBrace, TT_FunctionLBrace,
4406 TT_FunctionTypeLParen)) {
4411 if (
Left.is(tok::kw_auto) &&
Right.isOneOf(tok::l_paren, tok::l_brace))
4414 const auto *BeforeLeft =
Left.Previous;
4417 if (
Right.is(tok::l_paren) &&
Left.is(tok::kw_co_await) && BeforeLeft &&
4418 BeforeLeft->is(tok::kw_operator)) {
4422 if (
Left.isOneOf(tok::kw_co_await, tok::kw_co_yield, tok::kw_co_return) &&
4423 !
Right.isOneOf(tok::semi, tok::r_paren)) {
4427 if (
Left.is(tok::l_paren) ||
Right.is(tok::r_paren)) {
4428 return (
Right.is(TT_CastRParen) ||
4429 (
Left.MatchingParen &&
Left.MatchingParen->is(TT_CastRParen)))
4430 ? Style.SpacesInParensOptions.InCStyleCasts
4431 : Style.SpacesInParensOptions.Other;
4433 if (
Right.isOneOf(tok::semi, tok::comma))
4436 bool IsLightweightGeneric =
Right.MatchingParen &&
4437 Right.MatchingParen->Next &&
4438 Right.MatchingParen->Next->is(tok::colon);
4439 return !IsLightweightGeneric && Style.ObjCSpaceBeforeProtocolList;
4441 if (
Right.is(tok::less) &&
Left.is(tok::kw_template))
4442 return Style.SpaceAfterTemplateKeyword;
4443 if (
Left.isOneOf(tok::exclaim, tok::tilde))
4445 if (
Left.is(tok::at) &&
4446 Right.isOneOf(tok::identifier, tok::string_literal, tok::char_constant,
4447 tok::numeric_constant, tok::l_paren, tok::l_brace,
4448 tok::kw_true, tok::kw_false)) {
4451 if (
Left.is(tok::colon))
4452 return Left.isNot(TT_ObjCMethodExpr);
4453 if (
Left.is(tok::coloncolon)) {
4454 return Right.is(tok::star) &&
Right.is(TT_PointerOrReference) &&
4457 if (
Left.is(tok::less) ||
Right.isOneOf(tok::greater, tok::less)) {
4460 (
Left.is(TT_DictLiteral) ||
Right.is(TT_DictLiteral)))) {
4462 if (
Left.is(tok::less) &&
Right.is(tok::greater))
4464 return !Style.Cpp11BracedListStyle;
4467 if (
Right.isNot(TT_OverloadedOperatorLParen))
4470 if (
Right.is(tok::ellipsis)) {
4471 return Left.Tok.isLiteral() || (
Left.is(tok::identifier) && BeforeLeft &&
4472 BeforeLeft->is(tok::kw_case));
4474 if (
Left.is(tok::l_square) &&
Right.is(tok::amp))
4475 return Style.SpacesInSquareBrackets;
4476 if (
Right.is(TT_PointerOrReference)) {
4477 if (
Left.is(tok::r_paren) &&
Line.MightBeFunctionDecl) {
4478 if (!
Left.MatchingParen)
4480 FormatToken *TokenBeforeMatchingParen =
4481 Left.MatchingParen->getPreviousNonComment();
4482 if (!TokenBeforeMatchingParen ||
Left.isNot(TT_TypeDeclarationParen))
4490 (
Left.is(TT_AttributeRParen) ||
4491 Left.canBePointerOrReferenceQualifier())) {
4494 if (
Left.Tok.isLiteral())
4497 if (
Left.isTypeOrIdentifier(LangOpts) &&
Right.Next &&
Right.Next->Next &&
4498 Right.Next->Next->is(TT_RangeBasedForLoopColon)) {
4499 return getTokenPointerOrReferenceAlignment(Right) !=
4502 return !
Left.isOneOf(TT_PointerOrReference, tok::l_paren) &&
4503 (getTokenPointerOrReferenceAlignment(Right) !=
4505 (
Line.IsMultiVariableDeclStmt &&
4506 (
Left.NestingLevel == 0 ||
4507 (
Left.NestingLevel == 1 && startsWithInitStatement(
Line)))));
4509 if (
Right.is(TT_FunctionTypeLParen) &&
Left.isNot(tok::l_paren) &&
4510 (
Left.isNot(TT_PointerOrReference) ||
4512 !
Line.IsMultiVariableDeclStmt))) {
4515 if (
Left.is(TT_PointerOrReference)) {
4520 Right.canBePointerOrReferenceQualifier()) {
4524 if (
Right.Tok.isLiteral())
4527 if (
Right.is(TT_BlockComment))
4531 if (
Right.isOneOf(Keywords.kw_override, Keywords.kw_final, tok::kw_noexcept,
4532 TT_RequiresClause) &&
4533 Right.isNot(TT_StartOfName)) {
4540 if (BeforeLeft && BeforeLeft->isTypeOrIdentifier(LangOpts) &&
Right.Next &&
4541 Right.Next->is(TT_RangeBasedForLoopColon)) {
4542 return getTokenPointerOrReferenceAlignment(Left) !=
4545 if (
Right.isOneOf(TT_PointerOrReference, TT_ArraySubscriptLSquare,
4557 if (
Line.IsMultiVariableDeclStmt &&
4558 (
Left.NestingLevel ==
Line.First->NestingLevel ||
4559 ((
Left.NestingLevel ==
Line.First->NestingLevel + 1) &&
4560 startsWithInitStatement(
Line)))) {
4565 if (BeforeLeft->is(tok::coloncolon)) {
4566 return Left.is(tok::star) &&
4569 return !BeforeLeft->isOneOf(tok::l_paren, tok::l_square);
4572 if (
Left.is(tok::ellipsis) && BeforeLeft &&
4573 BeforeLeft->isPointerOrReference()) {
4577 if (
Right.is(tok::star) &&
Left.is(tok::l_paren))
4579 if (
Left.is(tok::star) &&
Right.isPointerOrReference())
4581 if (
Right.isPointerOrReference()) {
4592 if (
Previous->is(tok::coloncolon)) {
4611 if (
Previous->endsSequence(tok::kw_operator))
4615 (Style.SpaceAroundPointerQualifiers ==
4621 if (Style.isCSharp() &&
Left.is(Keywords.kw_is) &&
Right.is(tok::l_square))
4623 const auto SpaceRequiredForArrayInitializerLSquare =
4624 [](
const FormatToken &LSquareTok,
const FormatStyle &Style) {
4625 return Style.SpacesInContainerLiterals ||
4626 (Style.isProto() && !Style.Cpp11BracedListStyle &&
4627 LSquareTok.endsSequence(tok::l_square, tok::colon,
4630 if (
Left.is(tok::l_square)) {
4631 return (
Left.is(TT_ArrayInitializerLSquare) &&
Right.isNot(tok::r_square) &&
4632 SpaceRequiredForArrayInitializerLSquare(Left, Style)) ||
4633 (
Left.isOneOf(TT_ArraySubscriptLSquare, TT_StructuredBindingLSquare,
4634 TT_LambdaLSquare) &&
4635 Style.SpacesInSquareBrackets &&
Right.isNot(tok::r_square));
4637 if (
Right.is(tok::r_square)) {
4638 return Right.MatchingParen &&
4639 ((
Right.MatchingParen->is(TT_ArrayInitializerLSquare) &&
4640 SpaceRequiredForArrayInitializerLSquare(*
Right.MatchingParen,
4642 (Style.SpacesInSquareBrackets &&
4643 Right.MatchingParen->isOneOf(TT_ArraySubscriptLSquare,
4644 TT_StructuredBindingLSquare,
4645 TT_LambdaLSquare)));
4647 if (
Right.is(tok::l_square) &&
4648 !
Right.isOneOf(TT_ObjCMethodExpr, TT_LambdaLSquare,
4649 TT_DesignatedInitializerLSquare,
4650 TT_StructuredBindingLSquare, TT_AttributeSquare) &&
4651 !
Left.isOneOf(tok::numeric_constant, TT_DictLiteral) &&
4652 !(
Left.isNot(tok::r_square) && Style.SpaceBeforeSquareBrackets &&
4653 Right.is(TT_ArraySubscriptLSquare))) {
4656 if (
Left.is(tok::l_brace) &&
Right.is(tok::r_brace))
4657 return !
Left.Children.empty();
4659 (
Right.is(tok::r_brace) &&
Right.MatchingParen &&
4661 return !Style.Cpp11BracedListStyle || Style.SpacesInParensOptions.Other;
4663 if (
Left.is(TT_BlockComment)) {
4665 return Style.isJavaScript() || !
Left.TokenText.ends_with(
"=*/");
4670 if (
Left.is(TT_TemplateCloser) &&
Right.is(TT_AttributeSquare))
4673 if (
Right.is(tok::l_paren)) {
4674 if (
Left.is(TT_TemplateCloser) &&
Right.isNot(TT_FunctionTypeLParen))
4675 return spaceRequiredBeforeParens(Right);
4676 if (
Left.isOneOf(TT_RequiresClause,
4677 TT_RequiresClauseInARequiresExpression)) {
4678 return Style.SpaceBeforeParensOptions.AfterRequiresInClause ||
4679 spaceRequiredBeforeParens(Right);
4681 if (
Left.is(TT_RequiresExpression)) {
4682 return Style.SpaceBeforeParensOptions.AfterRequiresInExpression ||
4683 spaceRequiredBeforeParens(Right);
4685 if (
Left.is(TT_AttributeRParen) ||
4686 (
Left.is(tok::r_square) &&
Left.is(TT_AttributeSquare))) {
4689 if (
Left.is(TT_ForEachMacro)) {
4690 return Style.SpaceBeforeParensOptions.AfterForeachMacros ||
4691 spaceRequiredBeforeParens(Right);
4693 if (
Left.is(TT_IfMacro)) {
4694 return Style.SpaceBeforeParensOptions.AfterIfMacros ||
4695 spaceRequiredBeforeParens(Right);
4698 Left.isOneOf(tok::kw_new, tok::kw_delete) &&
4699 Right.isNot(TT_OverloadedOperatorLParen) &&
4700 !(
Line.MightBeFunctionDecl &&
Left.is(TT_FunctionDeclarationName))) {
4701 return Style.SpaceBeforeParensOptions.AfterPlacementOperator;
4705 if (
Left.is(tok::semi))
4707 if (
Left.isOneOf(tok::pp_elif, tok::kw_for, tok::kw_while, tok::kw_switch,
4708 tok::kw_case, TT_ForEachMacro, TT_ObjCForIn) ||
4710 Right.is(TT_ConditionLParen)) {
4711 return Style.SpaceBeforeParensOptions.AfterControlStatements ||
4712 spaceRequiredBeforeParens(Right);
4717 if (
Right.is(TT_OverloadedOperatorLParen))
4718 return spaceRequiredBeforeParens(Right);
4720 if (
Line.MightBeFunctionDecl &&
Right.is(TT_FunctionDeclarationLParen)) {
4721 if (spaceRequiredBeforeParens(Right))
4723 const auto &Options = Style.SpaceBeforeParensOptions;
4724 return Line.mightBeFunctionDefinition()
4725 ? Options.AfterFunctionDefinitionName
4726 : Options.AfterFunctionDeclarationName;
4730 Left.MatchingParen &&
Left.MatchingParen->is(TT_LambdaLSquare)) {
4731 return Style.SpaceBeforeParensOptions.AfterFunctionDefinitionName ||
4732 spaceRequiredBeforeParens(Right);
4734 if (!BeforeLeft || !BeforeLeft->isOneOf(tok::period, tok::arrow)) {
4735 if (
Left.isOneOf(tok::kw_try, Keywords.kw___except, tok::kw_catch)) {
4736 return Style.SpaceBeforeParensOptions.AfterControlStatements ||
4737 spaceRequiredBeforeParens(Right);
4739 if (
Left.isOneOf(tok::kw_new, tok::kw_delete)) {
4740 return ((!
Line.MightBeFunctionDecl || !BeforeLeft) &&
4742 spaceRequiredBeforeParens(Right);
4745 if (
Left.is(tok::r_square) &&
Left.MatchingParen &&
4746 Left.MatchingParen->Previous &&
4747 Left.MatchingParen->Previous->is(tok::kw_delete)) {
4749 spaceRequiredBeforeParens(Right);
4754 (
Left.Tok.getIdentifierInfo() ||
Left.is(tok::r_paren))) {
4755 return spaceRequiredBeforeParens(Right);
4759 if (
Left.is(tok::at) &&
Right.Tok.getObjCKeywordID() != tok::objc_not_keyword)
4761 if (
Right.is(TT_UnaryOperator)) {
4762 return !
Left.isOneOf(tok::l_paren, tok::l_square, tok::at) &&
4763 (
Left.isNot(tok::colon) ||
Left.isNot(TT_ObjCMethodExpr));
4769 if (!Style.isVerilog() &&
4770 (
Left.isOneOf(tok::identifier, tok::greater, tok::r_square,
4772 Left.isTypeName(LangOpts)) &&
4773 Right.is(tok::l_brace) &&
Right.getNextNonComment() &&
4777 if (
Left.is(tok::period) ||
Right.is(tok::period))
4781 if (
Right.is(tok::hash) &&
Left.is(tok::identifier) &&
4782 (
Left.TokenText ==
"L" ||
Left.TokenText ==
"u" ||
4783 Left.TokenText ==
"U" ||
Left.TokenText ==
"u8" ||
4784 Left.TokenText ==
"LR" ||
Left.TokenText ==
"uR" ||
4785 Left.TokenText ==
"UR" ||
Left.TokenText ==
"u8R")) {
4788 if (
Left.is(TT_TemplateCloser) &&
Left.MatchingParen &&
4789 Left.MatchingParen->Previous &&
4790 (
Left.MatchingParen->Previous->is(tok::period) ||
4791 Left.MatchingParen->Previous->is(tok::coloncolon))) {
4797 if (
Left.is(TT_TemplateCloser) &&
Right.is(tok::l_square))
4799 if (
Left.is(tok::l_brace) &&
Left.endsSequence(TT_DictLiteral, tok::at)) {
4803 if (
Right.is(tok::r_brace) &&
Right.MatchingParen &&
4804 Right.MatchingParen->endsSequence(TT_DictLiteral, tok::at)) {
4808 if (
Right.is(TT_TrailingAnnotation) &&
Right.isOneOf(tok::amp, tok::ampamp) &&
4809 Left.isOneOf(tok::kw_const, tok::kw_volatile) &&
4810 (!
Right.Next ||
Right.Next->is(tok::semi))) {
4820bool TokenAnnotator::spaceRequiredBefore(
const AnnotatedLine &
Line,
4821 const FormatToken &Right)
const {
4822 const FormatToken &
Left = *
Right.Previous;
4827 return Right.hasWhitespaceBefore();
4829 const bool IsVerilog = Style.isVerilog();
4830 assert(!IsVerilog || !IsCpp);
4833 if (Keywords.isWordLike(Right, IsVerilog) &&
4834 Keywords.isWordLike(Left, IsVerilog)) {
4840 if (
Left.is(tok::star) &&
Right.is(tok::comment))
4844 if (
Left.is(TT_OverloadedOperator) &&
4845 Right.isOneOf(TT_TemplateOpener, TT_TemplateCloser)) {
4849 if (
Right.is(tok::period) &&
Left.is(tok::numeric_constant))
4853 if (
Left.is(Keywords.kw_import) &&
Right.isOneOf(tok::less, tok::ellipsis))
4856 if (
Left.isOneOf(Keywords.kw_module, Keywords.kw_import) &&
4857 Right.is(TT_ModulePartitionColon)) {
4861 if (
Left.is(tok::identifier) &&
Right.is(TT_ModulePartitionColon))
4864 if (
Left.is(TT_ModulePartitionColon) &&
4865 Right.isOneOf(tok::identifier, tok::kw_private)) {
4868 if (
Left.is(tok::ellipsis) &&
Right.is(tok::identifier) &&
4869 Line.First->is(Keywords.kw_import)) {
4873 if (
Left.isOneOf(TT_AttributeRParen, TT_AttributeMacro) &&
4874 Right.is(tok::coloncolon)) {
4878 if (
Left.is(tok::kw_operator))
4879 return Right.is(tok::coloncolon);
4881 !
Left.opensScope() && Style.SpaceBeforeCpp11BracedList) {
4884 if (
Left.is(tok::less) &&
Left.is(TT_OverloadedOperator) &&
4885 Right.is(TT_TemplateOpener)) {
4889 if (
Left.is(tok::identifier) &&
Right.is(tok::numeric_constant))
4890 return Right.TokenText[0] !=
'.';
4892 if (
Left.Tok.getIdentifierInfo() &&
Right.Tok.isLiteral())
4894 }
else if (Style.isProto()) {
4895 if (
Right.is(tok::period) &&
4896 Left.isOneOf(Keywords.kw_optional, Keywords.kw_required,
4897 Keywords.kw_repeated, Keywords.kw_extend)) {
4900 if (
Right.is(tok::l_paren) &&
4901 Left.isOneOf(Keywords.kw_returns, Keywords.kw_option)) {
4904 if (
Right.isOneOf(tok::l_brace, tok::less) &&
Left.is(TT_SelectorName))
4907 if (
Left.is(tok::slash) ||
Right.is(tok::slash))
4909 if (
Left.MatchingParen &&
4910 Left.MatchingParen->is(TT_ProtoExtensionLSquare) &&
4911 Right.isOneOf(tok::l_brace, tok::less)) {
4912 return !Style.Cpp11BracedListStyle;
4915 if (
Left.is(tok::percent))
4919 if (
Left.is(tok::numeric_constant) &&
Right.is(tok::percent))
4920 return Right.hasWhitespaceBefore();
4921 }
else if (Style.isJson()) {
4922 if (
Right.is(tok::colon) &&
Left.is(tok::string_literal))
4923 return Style.SpaceBeforeJsonColon;
4924 }
else if (Style.isCSharp()) {
4930 if (
Left.is(tok::kw_this) &&
Right.is(tok::l_square))
4934 if (
Left.is(tok::kw_new) &&
Right.is(tok::l_paren))
4938 if (
Right.is(tok::l_brace))
4942 if (
Left.is(tok::l_brace) &&
Right.isNot(tok::r_brace))
4945 if (
Left.isNot(tok::l_brace) &&
Right.is(tok::r_brace))
4949 if (
Left.is(TT_FatArrow) ||
Right.is(TT_FatArrow))
4953 if (
Left.is(TT_AttributeColon) ||
Right.is(TT_AttributeColon))
4957 if (
Left.is(TT_TemplateCloser) &&
Right.is(TT_StartOfName))
4961 if (
Left.is(tok::l_square) ||
Right.is(tok::r_square))
4962 return Style.SpacesInSquareBrackets;
4965 if (
Right.is(TT_CSharpNullable))
4969 if (
Right.is(TT_NonNullAssertion))
4973 if (
Left.is(tok::comma) &&
Right.is(tok::comma))
4977 if (
Left.is(Keywords.kw_var) &&
Right.is(tok::l_paren))
4981 if (
Right.is(tok::l_paren)) {
4982 if (
Left.isOneOf(tok::kw_using, Keywords.kw_async, Keywords.kw_when,
4983 Keywords.kw_lock)) {
4984 return Style.SpaceBeforeParensOptions.AfterControlStatements ||
4985 spaceRequiredBeforeParens(Right);
4991 if ((
Left.isAccessSpecifierKeyword() ||
4992 Left.isOneOf(tok::kw_virtual, tok::kw_extern, tok::kw_static,
4993 Keywords.kw_internal, Keywords.kw_abstract,
4994 Keywords.kw_sealed, Keywords.kw_override,
4995 Keywords.kw_async, Keywords.kw_unsafe)) &&
4996 Right.is(tok::l_paren)) {
4999 }
else if (Style.isJavaScript()) {
5000 if (
Left.is(TT_FatArrow))
5003 if (
Right.is(tok::l_paren) &&
Left.is(Keywords.kw_await) &&
Left.Previous &&
5004 Left.Previous->is(tok::kw_for)) {
5007 if (
Left.is(Keywords.kw_async) &&
Right.is(tok::l_paren) &&
5008 Right.MatchingParen) {
5009 const FormatToken *Next =
Right.MatchingParen->getNextNonComment();
5012 if (Next && Next->is(TT_FatArrow))
5015 if ((
Left.is(TT_TemplateString) &&
Left.TokenText.ends_with(
"${")) ||
5016 (
Right.is(TT_TemplateString) &&
Right.TokenText.starts_with(
"}"))) {
5021 if (Keywords.isJavaScriptIdentifier(Left,
5023 Right.is(TT_TemplateString)) {
5026 if (
Right.is(tok::star) &&
5027 Left.isOneOf(Keywords.kw_function, Keywords.kw_yield)) {
5030 if (
Right.isOneOf(tok::l_brace, tok::l_square) &&
5031 Left.isOneOf(Keywords.kw_function, Keywords.kw_yield,
5032 Keywords.kw_extends, Keywords.kw_implements)) {
5035 if (
Right.is(tok::l_paren)) {
5037 if (
Line.MustBeDeclaration &&
Left.Tok.getIdentifierInfo())
5041 if (
Left.Previous &&
Left.Previous->is(tok::period) &&
5042 Left.Tok.getIdentifierInfo()) {
5046 if (
Left.isOneOf(tok::kw_throw, Keywords.kw_await, Keywords.kw_typeof,
5052 if (
Left.endsSequence(tok::kw_const, Keywords.kw_as))
5054 if ((
Left.isOneOf(Keywords.kw_let, Keywords.kw_var, Keywords.kw_in,
5059 (
Left.is(Keywords.kw_of) &&
Left.Previous &&
5060 (
Left.Previous->is(tok::identifier) ||
5061 Left.Previous->isOneOf(tok::r_square, tok::r_brace)))) &&
5062 (!
Left.Previous ||
Left.Previous->isNot(tok::period))) {
5065 if (
Left.isOneOf(tok::kw_for, Keywords.kw_as) &&
Left.Previous &&
5066 Left.Previous->is(tok::period) &&
Right.is(tok::l_paren)) {
5069 if (
Left.is(Keywords.kw_as) &&
5070 Right.isOneOf(tok::l_square, tok::l_brace, tok::l_paren)) {
5073 if (
Left.is(tok::kw_default) &&
Left.Previous &&
5074 Left.Previous->is(tok::kw_export)) {
5077 if (
Left.is(Keywords.kw_is) &&
Right.is(tok::l_brace))
5079 if (
Right.isOneOf(TT_JsTypeColon, TT_JsTypeOptionalQuestion))
5081 if (
Left.is(TT_JsTypeOperator) ||
Right.is(TT_JsTypeOperator))
5083 if ((
Left.is(tok::l_brace) ||
Right.is(tok::r_brace)) &&
5084 Line.First->isOneOf(Keywords.kw_import, tok::kw_export)) {
5087 if (
Left.is(tok::ellipsis))
5089 if (
Left.is(TT_TemplateCloser) &&
5090 !
Right.isOneOf(tok::equal, tok::l_brace, tok::comma, tok::l_square,
5091 Keywords.kw_implements, Keywords.kw_extends)) {
5097 if (
Right.is(TT_NonNullAssertion))
5099 if (
Left.is(TT_NonNullAssertion) &&
5100 Right.isOneOf(Keywords.kw_as, Keywords.kw_in)) {
5104 if (
Left.is(TT_CaseLabelArrow) ||
Right.is(TT_CaseLabelArrow))
5106 if (
Left.is(tok::r_square) &&
Right.is(tok::l_brace))
5109 if (
Left.is(tok::l_square) ||
Right.is(tok::r_square))
5110 return Style.SpacesInSquareBrackets;
5112 if (
Left.is(Keywords.kw_synchronized) &&
Right.is(tok::l_paren)) {
5113 return Style.SpaceBeforeParensOptions.AfterControlStatements ||
5114 spaceRequiredBeforeParens(Right);
5116 if ((
Left.isAccessSpecifierKeyword() ||
5117 Left.isOneOf(tok::kw_static, Keywords.kw_final, Keywords.kw_abstract,
5118 Keywords.kw_native)) &&
5119 Right.is(TT_TemplateOpener)) {
5122 }
else if (IsVerilog) {
5124 if (
Left.is(tok::identifier) &&
Left.TokenText[0] ==
'\\')
5128 if ((
Left.is(TT_VerilogTableItem) &&
5129 !
Right.isOneOf(tok::r_paren, tok::semi)) ||
5130 (
Right.is(TT_VerilogTableItem) &&
Left.isNot(tok::l_paren))) {
5131 const FormatToken *Next =
Right.getNextNonComment();
5132 return !(Next && Next->is(tok::r_paren));
5135 if (
Left.isNot(TT_BinaryOperator) &&
5136 Left.isOneOf(Keywords.kw_verilogHash, Keywords.kw_verilogHashHash)) {
5140 if (
Right.isNot(tok::semi) &&
5141 (
Left.endsSequence(tok::numeric_constant, Keywords.kw_verilogHash) ||
5142 Left.endsSequence(tok::numeric_constant,
5143 Keywords.kw_verilogHashHash) ||
5144 (
Left.is(tok::r_paren) &&
Left.MatchingParen &&
5145 Left.MatchingParen->endsSequence(tok::l_paren, tok::at)))) {
5150 if (
Left.is(Keywords.kw_apostrophe) ||
5151 (
Left.is(TT_VerilogNumberBase) &&
Right.is(tok::numeric_constant))) {
5155 if (
Left.is(tok::arrow) ||
Right.is(tok::arrow))
5160 if (
Left.is(tok::at) &&
Right.isOneOf(tok::l_paren, tok::star, tok::at))
5163 if (
Right.is(tok::l_square) &&
5164 Left.isOneOf(TT_VerilogDimensionedTypeName, Keywords.kw_function)) {
5168 if (
Right.isOneOf(tok::period, Keywords.kw_apostrophe) &&
5169 Keywords.isVerilogIdentifier(Left) &&
Left.getPreviousNonComment() &&
5170 Left.getPreviousNonComment()->is(Keywords.kw_tagged)) {
5176 if ((
Right.is(Keywords.kw_apostrophe) ||
5178 !(
Left.isOneOf(Keywords.kw_assign, Keywords.kw_unique) ||
5179 Keywords.isVerilogWordOperator(Left)) &&
5180 (
Left.isOneOf(tok::r_square, tok::r_paren, tok::r_brace,
5181 tok::numeric_constant) ||
5182 Keywords.isWordLike(Left))) {
5186 if ((
Right.is(tok::star) &&
Left.is(tok::coloncolon)) ||
5187 (
Left.is(tok::star) &&
Right.is(tok::semi))) {
5191 if (
Left.endsSequence(tok::star, tok::l_paren) &&
Right.is(tok::identifier))
5194 if (
Right.is(tok::l_paren) &&
Right.is(TT_VerilogStrength))
5197 if ((
Left.is(tok::l_brace) &&
5198 Right.isOneOf(tok::lessless, tok::greatergreater)) ||
5199 (
Left.endsSequence(tok::lessless, tok::l_brace) ||
5200 Left.endsSequence(tok::greatergreater, tok::l_brace))) {
5203 }
else if (Style.isTableGen()) {
5205 if (
Left.is(tok::l_square) &&
Right.is(tok::l_brace))
5207 if (
Left.is(tok::r_brace) &&
Right.is(tok::r_square))
5210 if (
Right.isOneOf(TT_TableGenDAGArgListColon,
5211 TT_TableGenDAGArgListColonToAlign) ||
5212 Left.isOneOf(TT_TableGenDAGArgListColon,
5213 TT_TableGenDAGArgListColonToAlign)) {
5216 if (
Right.is(TT_TableGenCondOperatorColon))
5218 if (
Left.isOneOf(TT_TableGenDAGArgOperatorID,
5219 TT_TableGenDAGArgOperatorToBreak) &&
5220 Right.isNot(TT_TableGenDAGArgCloser)) {
5224 if (
Right.isOneOf(tok::l_paren, tok::less) &&
5225 Left.isOneOf(TT_TableGenBangOperator, TT_TableGenCondOperator)) {
5230 if (
Left.is(TT_TableGenTrailingPasteOperator) &&
5231 Right.isOneOf(tok::l_brace, tok::colon)) {
5235 if (
Left.is(tok::hash) ||
Right.is(tok::hash))
5238 if (Keywords.isTableGenDefinition(Left))
5242 if (
Left.is(TT_ImplicitStringLiteral))
5243 return Right.hasWhitespaceBefore();
5245 if (
Left.is(TT_ObjCMethodSpecifier))
5247 if (
Left.is(tok::r_paren) &&
Left.isNot(TT_AttributeRParen) &&
5248 canBeObjCSelectorComponent(Right)) {
5256 (
Right.is(tok::equal) ||
Left.is(tok::equal))) {
5260 if (
Right.is(TT_TrailingReturnArrow) ||
Left.is(TT_TrailingReturnArrow))
5263 if (
Left.is(tok::comma) &&
Right.isNot(TT_OverloadedOperatorLParen) &&
5266 (
Left.Children.empty() || !
Left.MacroParent)) {
5269 if (
Right.is(tok::comma))
5271 if (
Right.is(TT_ObjCBlockLParen))
5273 if (
Right.is(TT_CtorInitializerColon))
5274 return Style.SpaceBeforeCtorInitializerColon;
5275 if (
Right.is(TT_InheritanceColon) && !Style.SpaceBeforeInheritanceColon)
5277 if (
Right.is(TT_RangeBasedForLoopColon) &&
5278 !Style.SpaceBeforeRangeBasedForLoopColon) {
5281 if (
Left.is(TT_BitFieldColon)) {
5285 if (
Right.is(tok::colon)) {
5286 if (
Right.is(TT_CaseLabelColon))
5287 return Style.SpaceBeforeCaseColon;
5288 if (
Right.is(TT_GotoLabelColon))
5291 if (!
Right.getNextNonComment())
5293 if (
Right.is(TT_ObjCMethodExpr))
5295 if (
Left.is(tok::question))
5297 if (
Right.is(TT_InlineASMColon) &&
Left.is(tok::coloncolon))
5299 if (
Right.is(TT_DictLiteral))
5300 return Style.SpacesInContainerLiterals;
5301 if (
Right.is(TT_AttributeColon))
5303 if (
Right.is(TT_CSharpNamedArgumentColon))
5305 if (
Right.is(TT_GenericSelectionColon))
5307 if (
Right.is(TT_BitFieldColon)) {
5314 if ((
Left.isOneOf(tok::minus, tok::minusminus) &&
5315 Right.isOneOf(tok::minus, tok::minusminus)) ||
5316 (
Left.isOneOf(tok::plus, tok::plusplus) &&
5317 Right.isOneOf(tok::plus, tok::plusplus))) {
5320 if (
Left.is(TT_UnaryOperator)) {
5323 if (
Left.is(tok::amp) &&
Right.is(tok::r_square))
5324 return Style.SpacesInSquareBrackets;
5325 return Style.SpaceAfterLogicalNot &&
Left.is(tok::exclaim);
5330 if (
Left.is(TT_CastRParen)) {
5331 return Style.SpaceAfterCStyleCast ||
5332 Right.isOneOf(TT_BinaryOperator, TT_SelectorName);
5335 auto ShouldAddSpacesInAngles = [
this, &
Right]() {
5339 return Right.hasWhitespaceBefore();
5343 if (
Left.is(tok::greater) &&
Right.is(tok::greater)) {
5346 return !Style.Cpp11BracedListStyle;
5348 return Right.is(TT_TemplateCloser) &&
Left.is(TT_TemplateCloser) &&
5350 ShouldAddSpacesInAngles());
5352 if (
Right.isOneOf(tok::arrow, tok::arrowstar, tok::periodstar) ||
5353 Left.isOneOf(tok::arrow, tok::period, tok::arrowstar, tok::periodstar) ||
5354 (
Right.is(tok::period) &&
Right.isNot(TT_DesignatedInitializerPeriod))) {
5357 if (!Style.SpaceBeforeAssignmentOperators &&
Left.isNot(TT_TemplateCloser) &&
5362 (
Left.is(tok::identifier) ||
Left.is(tok::kw_this))) {
5365 if (
Right.is(tok::coloncolon) &&
Left.is(tok::identifier)) {
5369 return Right.hasWhitespaceBefore();
5371 if (
Right.is(tok::coloncolon) &&
5372 !
Left.isOneOf(tok::l_brace, tok::comment, tok::l_paren)) {
5374 return (
Left.is(TT_TemplateOpener) &&
5376 ShouldAddSpacesInAngles())) ||
5377 !(
Left.isOneOf(tok::l_paren, tok::r_paren, tok::l_square,
5378 tok::kw___super, TT_TemplateOpener,
5379 TT_TemplateCloser)) ||
5380 (
Left.is(tok::l_paren) && Style.SpacesInParensOptions.Other);
5382 if ((
Left.is(TT_TemplateOpener)) != (
Right.is(TT_TemplateCloser)))
5383 return ShouldAddSpacesInAngles();
5385 if (
Right.is(TT_StructuredBindingLSquare)) {
5386 return !
Left.isOneOf(tok::amp, tok::ampamp) ||
5390 if (
Right.Next &&
Right.Next->is(TT_StructuredBindingLSquare) &&
5391 Right.isOneOf(tok::amp, tok::ampamp)) {
5394 if ((
Right.is(TT_BinaryOperator) &&
Left.isNot(tok::l_paren)) ||
5395 (
Left.isOneOf(TT_BinaryOperator, TT_ConditionalExpr) &&
5396 Right.isNot(tok::r_paren))) {
5399 if (
Right.is(TT_TemplateOpener) &&
Left.is(tok::r_paren) &&
5400 Left.MatchingParen &&
5401 Left.MatchingParen->is(TT_OverloadedOperatorLParen)) {
5404 if (
Right.is(tok::less) &&
Left.isNot(tok::l_paren) &&
5408 if (
Right.is(TT_TrailingUnaryOperator))
5410 if (
Left.is(TT_RegexLiteral))
5412 return spaceRequiredBetween(
Line, Left, Right);
5418 !Tok.
isOneOf(TT_ObjCBlockLBrace, TT_LambdaLBrace, TT_DictLiteral);
5435 !Tok.
isOneOf(TT_ObjCBlockLBrace, TT_DictLiteral);
5438bool TokenAnnotator::mustBreakBefore(
const AnnotatedLine &
Line,
5439 const FormatToken &Right)
const {
5440 const FormatToken &Left = *Right.Previous;
5441 if (Right.NewlinesBefore > 1 && Style.MaxEmptyLinesToKeep > 0)
5444 if (Style.BreakFunctionDefinitionParameters &&
Line.MightBeFunctionDecl &&
5445 Line.mightBeFunctionDefinition() && Left.MightBeFunctionDeclParen &&
5446 Left.ParameterCount > 0) {
5450 const auto *BeforeLeft = Left.Previous;
5451 const auto *AfterRight = Right.Next;
5453 if (Style.isCSharp()) {
5454 if (Left.is(TT_FatArrow) && Right.is(tok::l_brace) &&
5455 Style.BraceWrapping.AfterFunction) {
5458 if (
Right.is(TT_CSharpNamedArgumentColon) ||
5459 Left.is(TT_CSharpNamedArgumentColon)) {
5462 if (
Right.is(TT_CSharpGenericTypeConstraint))
5464 if (AfterRight && AfterRight->is(TT_FatArrow) &&
5465 (
Right.is(tok::numeric_constant) ||
5466 (
Right.is(tok::identifier) &&
Right.TokenText ==
"_"))) {
5471 if (
Left.is(TT_AttributeSquare) &&
Left.is(tok::r_square) &&
5472 (
Right.isAccessSpecifier(
false) ||
5473 Right.is(Keywords.kw_internal))) {
5477 if (
Left.is(TT_AttributeSquare) &&
Right.is(TT_AttributeSquare) &&
5478 Left.is(tok::r_square) &&
Right.is(tok::l_square)) {
5481 }
else if (Style.isJavaScript()) {
5483 if (
Right.is(tok::string_literal) &&
Left.is(tok::plus) && BeforeLeft &&
5484 BeforeLeft->is(tok::string_literal)) {
5487 if (
Left.is(TT_DictLiteral) &&
Left.is(tok::l_brace) &&
Line.Level == 0 &&
5488 BeforeLeft && BeforeLeft->is(tok::equal) &&
5489 Line.First->isOneOf(tok::identifier, Keywords.kw_import, tok::kw_export,
5493 !
Line.First->isOneOf(Keywords.kw_var, Keywords.kw_let)) {
5498 if (
Left.is(tok::l_brace) &&
Line.Level == 0 &&
5499 (
Line.startsWith(tok::kw_enum) ||
5500 Line.startsWith(tok::kw_const, tok::kw_enum) ||
5501 Line.startsWith(tok::kw_export, tok::kw_enum) ||
5502 Line.startsWith(tok::kw_export, tok::kw_const, tok::kw_enum))) {
5507 if (
Right.is(tok::r_brace) &&
Left.is(tok::l_brace) && BeforeLeft &&
5508 BeforeLeft->is(TT_FatArrow)) {
5510 switch (Style.AllowShortLambdasOnASingleLine) {
5516 return !
Left.Children.empty();
5520 return (
Left.NestingLevel == 0 &&
Line.Level == 0) &&
5521 !
Left.Children.empty();
5523 llvm_unreachable(
"Unknown FormatStyle::ShortLambdaStyle enum");
5526 if (
Right.is(tok::r_brace) &&
Left.is(tok::l_brace) &&
5527 !
Left.Children.empty()) {
5531 (
Left.NestingLevel == 0 &&
Line.Level == 0 &&
5532 Style.AllowShortFunctionsOnASingleLine &
5536 if (
Right.is(tok::plus) &&
Left.is(tok::string_literal) && AfterRight &&
5537 AfterRight->is(tok::string_literal)) {
5540 }
else if (Style.isVerilog()) {
5542 if (
Left.is(TT_VerilogAssignComma))
5545 if (
Left.is(TT_VerilogTypeComma))
5549 if (Style.VerilogBreakBetweenInstancePorts &&
5550 (
Left.is(TT_VerilogInstancePortComma) ||
5551 (
Left.is(tok::r_paren) && Keywords.isVerilogIdentifier(Right) &&
5552 Left.MatchingParen &&
5553 Left.MatchingParen->is(TT_VerilogInstancePortLParen)))) {
5558 if (!Keywords.isVerilogBegin(Right) && Keywords.isVerilogEndOfLabel(Left))
5560 }
else if (Style.BreakAdjacentStringLiterals &&
5561 (IsCpp || Style.isProto() ||
5563 if (
Left.isStringLiteral() &&
Right.isStringLiteral())
5568 if (Style.isJson()) {
5572 if (
Left.is(TT_DictLiteral) &&
Left.is(tok::l_brace))
5575 if ((
Left.is(TT_ArrayInitializerLSquare) &&
Left.is(tok::l_square) &&
5576 Right.isNot(tok::r_square)) ||
5577 Left.is(tok::comma)) {
5578 if (
Right.is(tok::l_brace))
5582 for (
const auto *Tok = &Right; Tok; Tok = Tok->Next) {
5583 if (Tok->isOneOf(tok::l_brace, tok::l_square))
5585 if (Tok->isOneOf(tok::r_brace, tok::r_square))
5588 return Style.BreakArrays;
5590 }
else if (Style.isTableGen()) {
5594 if (
Left.is(TT_TableGenCondOperatorComma))
5596 if (
Left.is(TT_TableGenDAGArgOperatorToBreak) &&
5597 Right.isNot(TT_TableGenDAGArgCloser)) {
5600 if (
Left.is(TT_TableGenDAGArgListCommaToBreak))
5602 if (
Right.is(TT_TableGenDAGArgCloser) &&
Right.MatchingParen &&
5603 Right.MatchingParen->is(TT_TableGenDAGArgOpenerToBreak) &&
5610 if (
Line.startsWith(tok::kw_asm) &&
Right.is(TT_InlineASMColon) &&
5620 const FormatToken *BeforeClosingBrace =
nullptr;
5621 if ((
Left.isOneOf(tok::l_brace, TT_ArrayInitializerLSquare) ||
5622 (Style.isJavaScript() &&
Left.is(tok::l_paren))) &&
5624 BeforeClosingBrace =
Left.MatchingParen->Previous;
5625 }
else if (
Right.MatchingParen &&
5626 (
Right.MatchingParen->isOneOf(tok::l_brace,
5627 TT_ArrayInitializerLSquare) ||
5628 (Style.isJavaScript() &&
5629 Right.MatchingParen->is(tok::l_paren)))) {
5630 BeforeClosingBrace = &
Left;
5632 if (BeforeClosingBrace && (BeforeClosingBrace->is(tok::comma) ||
5633 BeforeClosingBrace->isTrailingComment())) {
5638 if (
Right.is(tok::comment)) {
5640 (
Right.NewlinesBefore > 0 &&
Right.HasUnescapedNewline);
5642 if (
Left.isTrailingComment())
5644 if (
Left.IsUnterminatedLiteral)
5647 if (BeforeLeft && BeforeLeft->is(tok::lessless) &&
5648 Left.is(tok::string_literal) &&
Right.is(tok::lessless) && AfterRight &&
5649 AfterRight->is(tok::string_literal)) {
5650 return Right.NewlinesBefore > 0;
5653 if (
Right.is(TT_RequiresClause)) {
5654 switch (Style.RequiresClausePosition) {
5663 if (
Left.ClosesTemplateDeclaration &&
Left.MatchingParen &&
5664 Left.MatchingParen->NestingLevel == 0) {
5668 if (
Right.is(tok::kw_concept))
5672 Right.NewlinesBefore > 0);
5674 if (
Left.ClosesRequiresClause &&
Right.isNot(tok::semi)) {
5675 switch (Style.RequiresClausePosition) {
5685 (
Left.is(TT_CtorInitializerComma) ||
5686 Right.is(TT_CtorInitializerColon))) {
5691 Left.isOneOf(TT_CtorInitializerColon, TT_CtorInitializerComma)) {
5697 Right.isOneOf(TT_CtorInitializerComma, TT_CtorInitializerColon)) {
5703 Right.is(TT_CtorInitializerColon)) {
5708 Left.is(TT_CtorInitializerColon)) {
5714 Right.is(TT_InheritanceComma)) {
5718 Left.is(TT_InheritanceComma)) {
5721 if (
Right.is(tok::string_literal) &&
Right.TokenText.starts_with(
"R\"")) {
5725 return Right.IsMultiline &&
Right.NewlinesBefore > 0;
5727 if ((
Left.is(tok::l_brace) ||
5728 (
Left.is(tok::less) && BeforeLeft && BeforeLeft->is(tok::equal))) &&
5734 if (
Right.is(TT_InlineASMBrace))
5735 return Right.HasUnescapedNewline;
5738 auto *FirstNonComment =
Line.getFirstNonComment();
5740 FirstNonComment && (FirstNonComment->is(Keywords.kw_internal) ||
5741 FirstNonComment->isAccessSpecifierKeyword());
5743 if (Style.BraceWrapping.AfterEnum) {
5744 if (
Line.startsWith(tok::kw_enum) ||
5745 Line.startsWith(tok::kw_typedef, tok::kw_enum)) {
5750 FirstNonComment->Next->is(tok::kw_enum)) {
5756 if (Style.BraceWrapping.AfterClass &&
5758 FirstNonComment->Next->is(Keywords.kw_interface)) ||
5759 Line.startsWith(Keywords.kw_interface))) {
5764 if (
Right.isNot(TT_FunctionLBrace)) {
5765 return (
Line.startsWith(tok::kw_class) &&
5766 Style.BraceWrapping.AfterClass) ||
5767 (
Line.startsWith(tok::kw_struct) &&
5768 Style.BraceWrapping.AfterStruct);
5772 if (
Left.is(TT_ObjCBlockLBrace) &&
5778 if (
Left.isOneOf(TT_AttributeRParen, TT_AttributeMacro) &&
5779 Right.is(TT_ObjCDecl)) {
5783 if (
Left.is(TT_LambdaLBrace)) {
5791 (!
Left.Children.empty() &&
5797 if (Style.BraceWrapping.BeforeLambdaBody &&
Right.is(TT_LambdaLBrace) &&
5798 (
Left.isPointerOrReference() ||
Left.is(TT_TemplateCloser))) {
5804 Left.is(TT_LeadingJavaAnnotation) &&
5805 Right.isNot(TT_LeadingJavaAnnotation) &&
Right.isNot(tok::l_paren) &&
5806 (
Line.Last->is(tok::l_brace) || Style.BreakAfterJavaFieldAnnotations)) {
5810 if (
Right.is(TT_ProtoExtensionLSquare))
5840 if (Style.isProto() &&
Right.is(TT_SelectorName) &&
5841 Right.isNot(tok::r_square) && AfterRight) {
5844 if (
Left.is(tok::at))
5850 const auto *LBrace = AfterRight;
5851 if (LBrace && LBrace->is(tok::colon)) {
5852 LBrace = LBrace->Next;
5853 if (LBrace && LBrace->is(tok::at)) {
5854 LBrace = LBrace->Next;
5856 LBrace = LBrace->Next;
5868 ((LBrace->is(tok::l_brace) &&
5869 (LBrace->is(TT_DictLiteral) ||
5870 (LBrace->Next && LBrace->Next->is(tok::r_brace)))) ||
5871 LBrace->is(TT_ArrayInitializerLSquare) || LBrace->is(tok::less))) {
5878 if (
Left.ParameterCount == 0)
5893 if (
Left.isOneOf(tok::r_brace, tok::greater, tok::r_square))
5900bool TokenAnnotator::canBreakBefore(
const AnnotatedLine &
Line,
5901 const FormatToken &Right)
const {
5902 const FormatToken &
Left = *
Right.Previous;
5904 if (Style.isCSharp()) {
5905 if (
Left.isOneOf(TT_CSharpNamedArgumentColon, TT_AttributeColon) ||
5906 Right.isOneOf(TT_CSharpNamedArgumentColon, TT_AttributeColon)) {
5910 if (
Line.First->is(TT_CSharpGenericTypeConstraint))
5911 return Left.is(TT_CSharpGenericTypeConstraintComma);
5913 if (
Right.is(TT_CSharpNullable))
5916 if (
Left.isOneOf(Keywords.kw_throws, Keywords.kw_extends,
5917 Keywords.kw_implements)) {
5920 if (
Right.isOneOf(Keywords.kw_throws, Keywords.kw_extends,
5921 Keywords.kw_implements)) {
5924 }
else if (Style.isJavaScript()) {
5925 const FormatToken *NonComment =
Right.getPreviousNonComment();
5927 (NonComment->isAccessSpecifierKeyword() ||
5928 NonComment->isOneOf(
5929 tok::kw_return, Keywords.kw_yield, tok::kw_continue, tok::kw_break,
5930 tok::kw_throw, Keywords.kw_interface, Keywords.kw_type,
5931 tok::kw_static, Keywords.kw_readonly, Keywords.kw_override,
5932 Keywords.kw_abstract, Keywords.kw_get, Keywords.kw_set,
5933 Keywords.kw_async, Keywords.kw_await))) {
5936 if (
Right.NestingLevel == 0 &&
5937 (
Left.Tok.getIdentifierInfo() ||
5938 Left.isOneOf(tok::r_square, tok::r_paren)) &&
5939 Right.isOneOf(tok::l_square, tok::l_paren)) {
5942 if (NonComment && NonComment->is(tok::identifier) &&
5943 NonComment->TokenText ==
"asserts") {
5946 if (
Left.is(TT_FatArrow) &&
Right.is(tok::l_brace))
5948 if (
Left.is(TT_JsTypeColon))
5951 if (
Left.is(tok::exclaim) &&
Right.is(tok::colon))
5956 if (
Right.is(Keywords.kw_is)) {
5957 const FormatToken *Next =
Right.getNextNonComment();
5965 if (!Next || Next->isNot(tok::colon))
5968 if (
Left.is(Keywords.kw_in))
5970 if (
Right.is(Keywords.kw_in))
5972 if (
Right.is(Keywords.kw_as))
5974 if (
Right.isOneOf(Keywords.kw_extends, Keywords.kw_infer)) {
5980 if (
Left.is(Keywords.kw_as))
5982 if (
Left.is(TT_NonNullAssertion))
5984 if (
Left.is(Keywords.kw_declare) &&
5985 Right.isOneOf(Keywords.kw_module, tok::kw_namespace,
5986 Keywords.kw_function, tok::kw_class, tok::kw_enum,
5987 Keywords.kw_interface, Keywords.kw_type, Keywords.kw_var,
5988 Keywords.kw_let, tok::kw_const)) {
5993 if (
Left.isOneOf(Keywords.kw_module, tok::kw_namespace) &&
5994 Right.isOneOf(tok::identifier, tok::string_literal)) {
5997 if (
Right.is(TT_TemplateString) &&
Right.closesScope())
6001 if (
Left.is(tok::identifier) &&
Right.is(TT_TemplateString))
6003 if (
Left.is(TT_TemplateString) &&
Left.opensScope())
6005 }
else if (Style.isTableGen()) {
6007 if (Keywords.isTableGenDefinition(Left))
6010 if (
Right.is(tok::l_paren)) {
6011 return !
Left.isOneOf(TT_TableGenBangOperator, TT_TableGenCondOperator,
6015 if (
Left.is(TT_TableGenValueSuffix))
6018 if (
Left.is(tok::hash) ||
Right.is(tok::hash))
6020 if (
Left.isOneOf(TT_TableGenBangOperator, TT_TableGenCondOperator))
6024 if (
Left.is(tok::at))
6026 if (
Left.Tok.getObjCKeywordID() == tok::objc_interface)
6028 if (
Left.isOneOf(TT_JavaAnnotation, TT_LeadingJavaAnnotation))
6029 return Right.isNot(tok::l_paren);
6030 if (
Right.is(TT_PointerOrReference)) {
6031 return Line.IsMultiVariableDeclStmt ||
6032 (getTokenPointerOrReferenceAlignment(Right) ==
6034 (!
Right.Next ||
Right.Next->isNot(TT_FunctionDeclarationName)));
6036 if (
Right.isOneOf(TT_StartOfName, TT_FunctionDeclarationName) ||
6037 Right.is(tok::kw_operator)) {
6040 if (
Left.is(TT_PointerOrReference))
6042 if (
Right.isTrailingComment()) {
6049 (
Left.is(TT_CtorInitializerColon) &&
Right.NewlinesBefore > 0 &&
6052 if (
Left.is(tok::question) &&
Right.is(tok::colon))
6054 if (
Right.is(TT_ConditionalExpr) ||
Right.is(tok::question))
6055 return Style.BreakBeforeTernaryOperators;
6056 if (
Left.is(TT_ConditionalExpr) ||
Left.is(tok::question))
6057 return !Style.BreakBeforeTernaryOperators;
6058 if (
Left.is(TT_InheritanceColon))
6060 if (
Right.is(TT_InheritanceColon))
6062 if (
Right.is(TT_ObjCMethodExpr) &&
Right.isNot(tok::r_square) &&
6063 Left.isNot(TT_SelectorName)) {
6067 if (
Right.is(tok::colon) &&
6068 !
Right.isOneOf(TT_CtorInitializerColon, TT_InlineASMColon)) {
6071 if (
Left.is(tok::colon) &&
Left.isOneOf(TT_DictLiteral, TT_ObjCMethodExpr)) {
6072 if (Style.isProto()) {
6073 if (!Style.AlwaysBreakBeforeMultilineStrings &&
Right.isStringLiteral())
6099 if (((
Right.is(tok::l_brace) ||
Right.is(tok::less)) &&
6100 Right.is(TT_DictLiteral)) ||
6101 Right.is(TT_ArrayInitializerLSquare)) {
6107 if (
Right.is(tok::r_square) &&
Right.MatchingParen &&
6108 Right.MatchingParen->is(TT_ProtoExtensionLSquare)) {
6111 if (
Right.is(TT_SelectorName) || (
Right.is(tok::identifier) &&
Right.Next &&
6112 Right.Next->is(TT_ObjCMethodExpr))) {
6113 return Left.isNot(tok::period);
6117 if (
Right.is(tok::kw_concept))
6119 if (
Right.is(TT_RequiresClause))
6121 if (
Left.ClosesTemplateDeclaration) {
6123 Right.NewlinesBefore > 0;
6125 if (
Left.is(TT_FunctionAnnotationRParen))
6127 if (
Left.ClosesRequiresClause)
6129 if (
Right.isOneOf(TT_RangeBasedForLoopColon, TT_OverloadedOperatorLParen,
6130 TT_OverloadedOperator)) {
6133 if (
Left.is(TT_RangeBasedForLoopColon))
6135 if (
Right.is(TT_RangeBasedForLoopColon))
6137 if (
Left.is(TT_TemplateCloser) &&
Right.is(TT_TemplateOpener))
6139 if ((
Left.is(tok::greater) &&
Right.is(tok::greater)) ||
6140 (
Left.is(tok::less) &&
Right.is(tok::less))) {
6143 if (
Right.is(TT_BinaryOperator) &&
6149 if (
Left.isOneOf(TT_TemplateCloser, TT_UnaryOperator) ||
6150 Left.is(tok::kw_operator)) {
6153 if (
Left.is(tok::equal) && !
Right.isOneOf(tok::kw_default, tok::kw_delete) &&
6157 if (
Left.is(tok::equal) &&
Right.is(tok::l_brace) &&
6158 !Style.Cpp11BracedListStyle) {
6161 if (
Left.is(TT_AttributeLParen) ||
6162 (
Left.is(tok::l_paren) &&
Left.is(TT_TypeDeclarationParen))) {
6165 if (
Left.is(tok::l_paren) &&
Left.Previous &&
6166 (
Left.Previous->isOneOf(TT_BinaryOperator, TT_CastRParen))) {
6169 if (
Right.is(TT_ImplicitStringLiteral))
6172 if (
Right.is(TT_TemplateCloser))
6174 if (
Right.is(tok::r_square) &&
Right.MatchingParen &&
6175 Right.MatchingParen->is(TT_LambdaLSquare)) {
6181 if (
Right.is(tok::r_brace)) {
6183 (
Right.isBlockIndentedInitRBrace(Style)));
6187 if (
Right.is(tok::r_paren)) {
6189 !
Right.MatchingParen) {
6192 auto Next =
Right.Next;
6193 if (Next && Next->is(tok::r_paren))
6195 if (Next && Next->is(tok::l_paren))
6197 const FormatToken *
Previous =
Right.MatchingParen->Previous;
6201 if (
Left.isOneOf(tok::r_paren, TT_TrailingAnnotation) &&
6202 Right.is(TT_TrailingAnnotation) &&
6209 if (
Left.is(TT_TrailingAnnotation)) {
6210 return !
Right.isOneOf(tok::l_brace, tok::semi, tok::equal, tok::l_paren,
6211 tok::less, tok::coloncolon);
6214 if (
Right.isAttribute())
6217 if (
Right.is(tok::l_square) &&
Right.is(TT_AttributeSquare))
6218 return Left.isNot(TT_AttributeSquare);
6220 if (
Left.is(tok::identifier) &&
Right.is(tok::string_literal))
6223 if (
Right.is(tok::identifier) &&
Right.Next &&
Right.Next->is(TT_DictLiteral))
6226 if (
Left.is(TT_CtorInitializerColon)) {
6228 (!
Right.isTrailingComment() ||
Right.NewlinesBefore > 0);
6230 if (
Right.is(TT_CtorInitializerColon))
6232 if (
Left.is(TT_CtorInitializerComma) &&
6236 if (
Right.is(TT_CtorInitializerComma) &&
6240 if (
Left.is(TT_InheritanceComma) &&
6244 if (
Right.is(TT_InheritanceComma) &&
6248 if (
Left.is(TT_ArrayInitializerLSquare))
6250 if (
Right.is(tok::kw_typename) &&
Left.isNot(tok::kw_const))
6252 if ((
Left.isBinaryOperator() ||
Left.is(TT_BinaryOperator)) &&
6253 !
Left.isOneOf(tok::arrowstar, tok::lessless) &&
6259 if ((
Left.is(TT_AttributeSquare) &&
Right.is(tok::l_square)) ||
6260 (
Left.is(tok::r_square) &&
Right.is(TT_AttributeSquare))) {
6264 auto ShortLambdaOption = Style.AllowShortLambdasOnASingleLine;
6265 if (Style.BraceWrapping.BeforeLambdaBody &&
Right.is(TT_LambdaLBrace)) {
6272 if (
Right.is(tok::kw_noexcept) &&
Right.is(TT_TrailingAnnotation)) {
6273 switch (Style.AllowBreakBeforeNoexceptSpecifier) {
6279 return Right.Next &&
Right.Next->is(tok::l_paren);
6283 return Left.isOneOf(tok::comma, tok::coloncolon, tok::semi, tok::l_brace,
6284 tok::kw_class, tok::kw_struct, tok::comment) ||
6285 Right.isMemberAccess() ||
6286 Right.isOneOf(TT_TrailingReturnArrow, tok::lessless, tok::colon,
6287 tok::l_square, tok::at) ||
6288 (
Left.is(tok::r_paren) &&
6289 Right.isOneOf(tok::identifier, tok::kw_const)) ||
6290 (
Left.is(tok::l_paren) &&
Right.isNot(tok::r_paren)) ||
6291 (
Left.is(TT_TemplateOpener) &&
Right.isNot(TT_TemplateCloser));
6294void TokenAnnotator::printDebugInfo(
const AnnotatedLine &
Line)
const {
6295 llvm::errs() <<
"AnnotatedTokens(L=" <<
Line.Level <<
", P=" <<
Line.PPLevel
6296 <<
", T=" <<
Line.Type <<
", C=" <<
Line.IsContinuation
6298 const FormatToken *Tok =
Line.First;
6300 llvm::errs() <<
" M=" << Tok->MustBreakBefore
6301 <<
" C=" << Tok->CanBreakBefore
6303 <<
" S=" << Tok->SpacesRequiredBefore
6304 <<
" F=" << Tok->Finalized <<
" B=" << Tok->BlockParameterCount
6305 <<
" BK=" << Tok->getBlockKind() <<
" P=" << Tok->SplitPenalty
6306 <<
" Name=" << Tok->Tok.getName() <<
" L=" << Tok->TotalLength
6307 <<
" PPK=" << Tok->getPackingKind() <<
" FakeLParens=";
6309 llvm::errs() << LParen <<
"/";
6310 llvm::errs() <<
" FakeRParens=" << Tok->FakeRParens;
6311 llvm::errs() <<
" II=" << Tok->Tok.getIdentifierInfo();
6312 llvm::errs() <<
" Text='" << Tok->TokenText <<
"'\n";
6314 assert(Tok ==
Line.Last);
6317 llvm::errs() <<
"----\n";
6321TokenAnnotator::getTokenReferenceAlignment(
const FormatToken &
Reference)
const {
6322 assert(
Reference.isOneOf(tok::amp, tok::ampamp));
6323 switch (Style.ReferenceAlignment) {
6325 return Style.PointerAlignment;
6334 return Style.PointerAlignment;
6338TokenAnnotator::getTokenPointerOrReferenceAlignment(
6339 const FormatToken &PointerOrReference)
const {
6340 if (PointerOrReference.isOneOf(tok::amp, tok::ampamp)) {
6341 switch (Style.ReferenceAlignment) {
6343 return Style.PointerAlignment;
6352 assert(PointerOrReference.is(tok::star));
6353 return Style.PointerAlignment;
Defines the SourceManager interface.
bool ColonIsObjCMethodExpr
FormatToken * FirstStartOfName
bool InCpp11AttributeSpecifier
enum clang::format::@1296::AnnotatingParser::Context::@352 ContextType
unsigned LongestObjCSelectorName
bool VerilogAssignmentFound
bool InCSharpAttributeSpecifier
tok::TokenKind ContextKind
FormatToken * FirstObjCSelectorName
bool VerilogMayBeConcatenation
This file implements a token annotator, i.e.
Defines the clang::TokenKind enum and support functions.
#define TRANSFORM_TYPE_TRAIT_DEF(Enum, _)
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
Parser - This implements a parser for the C family of languages.
IdentifierInfo * getIdentifierInfo() const
bool Ret(InterpState &S, CodePtr &PC, APValue &Result)
TokenKind
Provides a simple uniform namespace for tokens from all C languages.
The JSON file list parser is used to communicate input to InstallAPI.
if(T->getSizeExpr()) TRY_TO(TraverseStmt(const_cast< Expr * >(T -> getSizeExpr())))
@ Parameter
The parameter type of a method or function.
@ Result
The result type of a method or function.
prec::Level getBinOpPrecedence(tok::TokenKind Kind, bool GreaterThanIsOperator, bool CPlusPlus11)
Return the precedence of the specified binary operator token.
const FunctionProtoType * T
AccessSpecifier
A C++ access specifier (public, private, protected), plus the special value "none" which means differ...