TokenAnnotator.cpp revision 84a1a63b034744b68a27ec171dca5b1b7cf303f0
18dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor//===--- TokenAnnotator.cpp - Format C++ code -----------------------------===//
28dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor//
38dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor//                     The LLVM Compiler Infrastructure
48dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor//
58dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor// This file is distributed under the University of Illinois Open Source
68dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor// License. See LICENSE.TXT for details.
78dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor//
88dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor//===----------------------------------------------------------------------===//
98dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor///
108dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor/// \file
118dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor/// \brief This file implements a token annotator, i.e. creates
122d88708cbe4e4ec5e04e4acb6bd7f5be68557379John McCall/// \c AnnotatedTokens out of \c FormatTokens with required extra information.
13e737f5041a36d0befb39ffeed8d50ba15916d3daDouglas Gregor///
14f312b1ea179f1c44371f9ee0cd0bc006f612de11John McCall//===----------------------------------------------------------------------===//
157cd088e519d7e6caa4c4c12db52e0e4ae35d25c2John McCall
16aba43bb13b3aa3e81990989375fba3a902bfe1c2Douglas Gregor#include "TokenAnnotator.h"
178dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor#include "clang/Basic/SourceManager.h"
188dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor#include "clang/Lex/Lexer.h"
198dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor
200c01d18094100db92d38daa923c95661512db203John McCallnamespace clang {
218dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregornamespace format {
22a88cfbfac9bbcbb9858f048d6d73a48711d8e93dDouglas Gregor
2321ef0fa27b0783ec0bc6aa5b524feb2ec840f952John McCallstatic bool isUnaryOperator(const AnnotatedToken &Tok) {
2483ddad3ab513f5d73698cf9fbeb4ed3f011bc3b9Douglas Gregor  switch (Tok.FormatTok.Tok.getKind()) {
258dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  case tok::plus:
268dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  case tok::plusplus:
278dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  case tok::minus:
28b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall  case tok::minusminus:
29b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall  case tok::exclaim:
30c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  case tok::tilde:
31c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  case tok::kw_sizeof:
32a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi  case tok::kw_alignof:
33c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor    return true;
34a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi  default:
35c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor    return false;
36a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi  }
37c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor}
38b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall
39a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumistatic bool isBinaryOperator(const AnnotatedToken &Tok) {
40c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  // Comma is a binary operator, but does not behave as such wrt. formatting.
41b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall  return getPrecedence(Tok) > prec::Comma;
42b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall}
43b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall
44b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall// Returns the previous token ignoring comments.
45b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCallstatic AnnotatedToken *getPreviousToken(AnnotatedToken &Tok) {
46c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  AnnotatedToken *PrevToken = Tok.Parent;
47c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  while (PrevToken != NULL && PrevToken->is(tok::comment))
48a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi    PrevToken = PrevToken->Parent;
49c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  return PrevToken;
50a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi}
51c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregorstatic const AnnotatedToken *getPreviousToken(const AnnotatedToken &Tok) {
52a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi  return getPreviousToken(const_cast<AnnotatedToken &>(Tok));
53c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor}
54b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall
55a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumistatic bool isTrailingComment(AnnotatedToken *Tok) {
56c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  return Tok != NULL && Tok->is(tok::comment) &&
57b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall         (Tok->Children.empty() ||
58b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall          Tok->Children[0].FormatTok.NewlinesBefore > 0);
59b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall}
607b9ff0c09025dcbe48ec7db71330e2066d1e1863DeLesley Hutchins
617b9ff0c09025dcbe48ec7db71330e2066d1e1863DeLesley Hutchins// Returns the next token ignoring comments.
627b9ff0c09025dcbe48ec7db71330e2066d1e1863DeLesley Hutchinsstatic const AnnotatedToken *getNextToken(const AnnotatedToken &Tok) {
631d8d1ccd36888f1120b3a1df9e76f35dc2edb81dJohn McCall  if (Tok.Children.empty())
6423323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins    return NULL;
6523323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins  const AnnotatedToken *NextToken = &Tok.Children[0];
6623323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins  while (NextToken->is(tok::comment)) {
67cf807c4dfdb23e8fa3f400e0b24ef5b79db7a530Sean Hunt    if (NextToken->Children.empty())
68cf807c4dfdb23e8fa3f400e0b24ef5b79db7a530Sean Hunt      return NULL;
69cf807c4dfdb23e8fa3f400e0b24ef5b79db7a530Sean Hunt    NextToken = &NextToken->Children[0];
7023323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins  }
714ced79f0971592e6e7122037de69ee9ae534ce72Chandler Carruth  return NextToken;
724ced79f0971592e6e7122037de69ee9ae534ce72Chandler Carruth}
73cf807c4dfdb23e8fa3f400e0b24ef5b79db7a530Sean Hunt
74cf807c4dfdb23e8fa3f400e0b24ef5b79db7a530Sean Hunt/// \brief A parser that gathers additional information about tokens.
75f6702a3927147655206ae729a84339c4fda4c651Richard Smith///
76f6702a3927147655206ae729a84339c4fda4c651Richard Smith/// The \c TokenAnnotator tries to matches parenthesis and square brakets and
77f6702a3927147655206ae729a84339c4fda4c651Richard Smith/// store a parenthesis levels. It also tries to resolve matching "<" and ">"
78f6702a3927147655206ae729a84339c4fda4c651Richard Smith/// into template parameter lists.
7960d7b3a319d84d688752be3870615ac0f111fb16John McCallclass AnnotatingParser {
807663f396651716c82280f8fdcf97ad8e27c1ce5aNick Lewyckypublic:
81cf807c4dfdb23e8fa3f400e0b24ef5b79db7a530Sean Hunt  AnnotatingParser(SourceManager &SourceMgr, Lexer &Lex, AnnotatedLine &Line,
82fc685ace387734599c475426b1a8efdb491054b8Aaron Ballman                   IdentifierInfo &Ident_in)
83fc685ace387734599c475426b1a8efdb491054b8Aaron Ballman      : SourceMgr(SourceMgr), Lex(Lex), Line(Line), CurrentToken(&Line.First),
84f6702a3927147655206ae729a84339c4fda4c651Richard Smith        KeywordVirtualFound(false), Ident_in(Ident_in) {
85cf807c4dfdb23e8fa3f400e0b24ef5b79db7a530Sean Hunt    Contexts.push_back(Context(1, /*IsExpression=*/ false));
867663f396651716c82280f8fdcf97ad8e27c1ce5aNick Lewycky  }
87a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi
887663f396651716c82280f8fdcf97ad8e27c1ce5aNick Lewyckyprivate:
89cf807c4dfdb23e8fa3f400e0b24ef5b79db7a530Sean Hunt  bool parseAngle() {
90fc685ace387734599c475426b1a8efdb491054b8Aaron Ballman    if (CurrentToken == NULL)
91fc685ace387734599c475426b1a8efdb491054b8Aaron Ballman      return false;
92cf807c4dfdb23e8fa3f400e0b24ef5b79db7a530Sean Hunt    ScopedContextCreator ContextCreator(*this, 10);
934ced79f0971592e6e7122037de69ee9ae534ce72Chandler Carruth    AnnotatedToken *Left = CurrentToken->Parent;
944ced79f0971592e6e7122037de69ee9ae534ce72Chandler Carruth    Contexts.back().IsExpression = false;
954ced79f0971592e6e7122037de69ee9ae534ce72Chandler Carruth    while (CurrentToken != NULL) {
964ced79f0971592e6e7122037de69ee9ae534ce72Chandler Carruth      if (CurrentToken->is(tok::greater)) {
9723323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins        Left->MatchingParen = CurrentToken;
9823323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins        CurrentToken->MatchingParen = Left;
9923323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins        CurrentToken->Type = TT_TemplateCloser;
10023323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins        next();
10123323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins        return true;
10223323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins      }
10323323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins      if (CurrentToken->is(tok::r_paren) || CurrentToken->is(tok::r_square) ||
10423323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins          CurrentToken->is(tok::r_brace))
1055bbc385ad2d8e487edfbc2756eaf4fb0b920cfe4Benjamin Kramer        return false;
1065bbc385ad2d8e487edfbc2756eaf4fb0b920cfe4Benjamin Kramer      if (CurrentToken->is(tok::pipepipe) || CurrentToken->is(tok::ampamp) ||
10731c195ac0f3869e742d42f9d02b6cd33442fb630Rafael Espindola          CurrentToken->is(tok::question) || CurrentToken->is(tok::colon))
10831c195ac0f3869e742d42f9d02b6cd33442fb630Rafael Espindola        return false;
10923323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins      updateParameterCount(Left, CurrentToken);
110d8fe2d56fb5463c9d109e8c6dab2e98b06bee186Anders Carlsson      if (!consumeToken())
111d8fe2d56fb5463c9d109e8c6dab2e98b06bee186Anders Carlsson        return false;
112d8fe2d56fb5463c9d109e8c6dab2e98b06bee186Anders Carlsson    }
1134f722be4587a7a0dece399fb5405dda158971ae1Douglas Gregor    return false;
1144f722be4587a7a0dece399fb5405dda158971ae1Douglas Gregor  }
115b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie
1164f722be4587a7a0dece399fb5405dda158971ae1Douglas Gregor  bool parseParens(bool LookForDecls = false) {
1174f722be4587a7a0dece399fb5405dda158971ae1Douglas Gregor    if (CurrentToken == NULL)
1184f722be4587a7a0dece399fb5405dda158971ae1Douglas Gregor      return false;
11957ad37823e198f977cac605dbfbaefb4daf325e9Chris Lattner    ScopedContextCreator ContextCreator(*this, 1);
12057ad37823e198f977cac605dbfbaefb4daf325e9Chris Lattner
12157ad37823e198f977cac605dbfbaefb4daf325e9Chris Lattner    // FIXME: This is a bit of a hack. Do better.
12257ad37823e198f977cac605dbfbaefb4daf325e9Chris Lattner    Contexts.back().ColonIsForRangeExpr =
12357ad37823e198f977cac605dbfbaefb4daf325e9Chris Lattner        Contexts.size() == 2 && Contexts[0].ColonIsForRangeExpr;
12457ad37823e198f977cac605dbfbaefb4daf325e9Chris Lattner
12557ad37823e198f977cac605dbfbaefb4daf325e9Chris Lattner    bool StartsObjCMethodExpr = false;
12657ad37823e198f977cac605dbfbaefb4daf325e9Chris Lattner    AnnotatedToken *Left = CurrentToken->Parent;
1274f722be4587a7a0dece399fb5405dda158971ae1Douglas Gregor    if (CurrentToken->is(tok::caret)) {
128b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie      // ^( starts a block.
1294f722be4587a7a0dece399fb5405dda158971ae1Douglas Gregor      Left->Type = TT_ObjCBlockLParen;
1304f722be4587a7a0dece399fb5405dda158971ae1Douglas Gregor    } else if (AnnotatedToken *MaybeSel = Left->Parent) {
1313dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall      // @selector( starts a selector.
1323dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall      if (MaybeSel->isObjCAtKeyword(tok::objc_selector) && MaybeSel->Parent &&
1333dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall          MaybeSel->Parent->is(tok::at)) {
1343dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall        StartsObjCMethodExpr = true;
1353dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall      }
1363dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall    }
1370cfaf6a270ecd0f5c7e541a8047c87948317548bDouglas Gregor
1380cfaf6a270ecd0f5c7e541a8047c87948317548bDouglas Gregor    if (StartsObjCMethodExpr) {
1393dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall      Contexts.back().ColonIsObjCMethodExpr = true;
1403dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall      Left->Type = TT_ObjCMethodExpr;
1413dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall    }
1423dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall
1433dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall    while (CurrentToken != NULL) {
1443dbd3d5c04cd5abd7dfd83b15f51d7c610a3c512John McCall      // LookForDecls is set when "if (" has been seen. Check for
1453e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      // 'identifier' '*' 'identifier' followed by not '=' -- this
1463e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      // '*' has to be a binary operator but determineStarAmpUsage() will
1478dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      // categorize it as an unary operator, so set the right type here.
148a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall      if (LookForDecls && !CurrentToken->Children.empty()) {
149561f81243f665cf2001caadc45df505f826b72d6Douglas Gregor        AnnotatedToken &Prev = *CurrentToken->Parent;
150836adf6771d5170d936599dfcce21687e37e9bbfDouglas Gregor        AnnotatedToken &Next = CurrentToken->Children[0];
151ba6a9bd384df475780be636ca45bcef5c5bbd19fJohn McCall        if (Prev.Parent->is(tok::identifier) &&
152ba6a9bd384df475780be636ca45bcef5c5bbd19fJohn McCall            (Prev.is(tok::star) || Prev.is(tok::amp)) &&
153ba6a9bd384df475780be636ca45bcef5c5bbd19fJohn McCall            CurrentToken->is(tok::identifier) && Next.isNot(tok::equal)) {
1548dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor          Prev.Type = TT_BinaryOperator;
155a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall          LookForDecls = false;
1568dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        }
157b4eeaff1595b7d0a8fbc2b3c8bec7dc63f48b7fdDouglas Gregor      }
158b4eeaff1595b7d0a8fbc2b3c8bec7dc63f48b7fdDouglas Gregor
1598dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      if (CurrentToken->is(tok::r_paren)) {
1601eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump        Left->MatchingParen = CurrentToken;
161b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith        CurrentToken->MatchingParen = Left;
162b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith
163b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith        if (StartsObjCMethodExpr) {
164b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith          CurrentToken->Type = TT_ObjCMethodExpr;
165b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith          if (Contexts.back().FirstObjCSelectorName != NULL) {
166b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith            Contexts.back().FirstObjCSelectorName->LongestObjCSelectorName =
167b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith                Contexts.back().LongestObjCSelectorName;
168b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith          }
169b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith        }
170b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith
171b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith        next();
172b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith        return true;
173b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith      }
174b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith      if (CurrentToken->is(tok::r_square) || CurrentToken->is(tok::r_brace))
175b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith        return false;
176b5b37d194dddb960f43f763b3f9c3e17e7be3c2dRichard Smith      updateParameterCount(Left, CurrentToken);
1778dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      if (!consumeToken())
178162e1c1b487352434552147967c3dd296ebee2f7Richard Smith        return false;
179162e1c1b487352434552147967c3dd296ebee2f7Richard Smith    }
180162e1c1b487352434552147967c3dd296ebee2f7Richard Smith    return false;
181162e1c1b487352434552147967c3dd296ebee2f7Richard Smith  }
182162e1c1b487352434552147967c3dd296ebee2f7Richard Smith
183162e1c1b487352434552147967c3dd296ebee2f7Richard Smith  bool parseSquare() {
184162e1c1b487352434552147967c3dd296ebee2f7Richard Smith    if (!CurrentToken)
1858dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      return false;
1868dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    ScopedContextCreator ContextCreator(*this, 10);
1878dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor
188cde5a400dbc9655eddf0f383585d3cf67c11c539John McCall    // A '[' could be an index subscript (after an indentifier or after
189cde5a400dbc9655eddf0f383585d3cf67c11c539John McCall    // ')' or ']'), it could be the start of an Objective-C method
190cde5a400dbc9655eddf0f383585d3cf67c11c539John McCall    // expression, or it could the the start of an Objective-C array literal.
191cde5a400dbc9655eddf0f383585d3cf67c11c539John McCall    AnnotatedToken *Left = CurrentToken->Parent;
192162e1c1b487352434552147967c3dd296ebee2f7Richard Smith    AnnotatedToken *Parent = getPreviousToken(*Left);
193cde5a400dbc9655eddf0f383585d3cf67c11c539John McCall    bool StartsObjCMethodExpr =
194162e1c1b487352434552147967c3dd296ebee2f7Richard Smith        !Parent || Parent->is(tok::colon) || Parent->is(tok::l_square) ||
195162e1c1b487352434552147967c3dd296ebee2f7Richard Smith        Parent->is(tok::l_paren) || Parent->is(tok::kw_return) ||
196cde5a400dbc9655eddf0f383585d3cf67c11c539John McCall        Parent->is(tok::kw_throw) || isUnaryOperator(*Parent) ||
197d57a38ee02c285d69d05fed6df0d7406b2517888Douglas Gregor        Parent->Type == TT_ObjCForIn || Parent->Type == TT_CastRParen ||
198a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi        getBinOpPrecedence(Parent->FormatTok.Tok.getKind(), true, true) >
199ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor        prec::Unknown;
2007c1e98f1cb37b40e619a0c8aee8b337f037b432bDouglas Gregor    bool StartsObjCArrayLiteral = Parent && Parent->is(tok::at);
2017c1e98f1cb37b40e619a0c8aee8b337f037b432bDouglas Gregor
202b710722d2348cd0945d2b4f02062c7f685146eb0Douglas Gregor    if (StartsObjCMethodExpr) {
203b710722d2348cd0945d2b4f02062c7f685146eb0Douglas Gregor      Contexts.back().ColonIsObjCMethodExpr = true;
204a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi      Left->Type = TT_ObjCMethodExpr;
2055df37bd0242e838e465f0bd51a70af424d152053Rafael Espindola    } else if (StartsObjCArrayLiteral) {
2065df37bd0242e838e465f0bd51a70af424d152053Rafael Espindola      Left->Type = TT_ObjCArrayLiteral;
2075df37bd0242e838e465f0bd51a70af424d152053Rafael Espindola    }
2085df37bd0242e838e465f0bd51a70af424d152053Rafael Espindola
2095df37bd0242e838e465f0bd51a70af424d152053Rafael Espindola    while (CurrentToken != NULL) {
2105df37bd0242e838e465f0bd51a70af424d152053Rafael Espindola      if (CurrentToken->is(tok::r_square)) {
2115126fd0dd92c4ec211c837ee78d5ce59c68dcbd5John McCall        if (!CurrentToken->Children.empty() &&
2125126fd0dd92c4ec211c837ee78d5ce59c68dcbd5John McCall            CurrentToken->Children[0].is(tok::l_paren)) {
2131d8d1ccd36888f1120b3a1df9e76f35dc2edb81dJohn McCall          // An ObjC method call is rarely followed by an open parenthesis.
214d57a38ee02c285d69d05fed6df0d7406b2517888Douglas Gregor          // FIXME: Do we incorrectly label ":" with this?
21546460a68f6508775e98c19b4bb8454bb471aac24John McCall          StartsObjCMethodExpr = false;
2161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump          Left->Type = TT_Unknown;
2178dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        }
2188dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        if (StartsObjCMethodExpr) {
2198dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor          CurrentToken->Type = TT_ObjCMethodExpr;
220162e1c1b487352434552147967c3dd296ebee2f7Richard Smith          // determineStarAmpUsage() thinks that '*' '[' is allocating an
2213e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith          // array of pointers, but if '[' starts a selector then '*' is a
2223e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith          // binary operator.
2233e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith          if (Parent != NULL &&
224162e1c1b487352434552147967c3dd296ebee2f7Richard Smith              (Parent->is(tok::star) || Parent->is(tok::amp)) &&
225162e1c1b487352434552147967c3dd296ebee2f7Richard Smith              Parent->Type == TT_PointerOrReference)
226162e1c1b487352434552147967c3dd296ebee2f7Richard Smith            Parent->Type = TT_BinaryOperator;
2273e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        } else if (StartsObjCArrayLiteral) {
2283e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith          CurrentToken->Type = TT_ObjCArrayLiteral;
2293e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        }
2303e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        Left->MatchingParen = CurrentToken;
2313e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        CurrentToken->MatchingParen = Left;
2323e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        if (Contexts.back().FirstObjCSelectorName != NULL)
2333e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith          Contexts.back().FirstObjCSelectorName->LongestObjCSelectorName =
2343e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith              Contexts.back().LongestObjCSelectorName;
2353e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        next();
2363e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        return true;
2373e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      }
2383e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      if (CurrentToken->is(tok::r_paren) || CurrentToken->is(tok::r_brace))
2393e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        return false;
2403e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      updateParameterCount(Left, CurrentToken);
2413e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      if (!consumeToken())
2423e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        return false;
2433e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    }
2443e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    return false;
2453e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  }
246ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor
2473e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  bool parseBrace() {
2483e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    // Lines are fine to end with '{'.
2493e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    if (CurrentToken == NULL)
2503e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      return true;
2513e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    ScopedContextCreator ContextCreator(*this, 1);
2523e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    AnnotatedToken *Left = CurrentToken->Parent;
2533e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    while (CurrentToken != NULL) {
2543e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      if (CurrentToken->is(tok::r_brace)) {
2553e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        Left->MatchingParen = CurrentToken;
2563e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        CurrentToken->MatchingParen = Left;
2573e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        next();
2583e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        return true;
2593e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      }
2603e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      if (CurrentToken->is(tok::r_paren) || CurrentToken->is(tok::r_square))
2613e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        return false;
2623e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      updateParameterCount(Left, CurrentToken);
2633e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      if (!consumeToken())
2643e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith        return false;
2653e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    }
2663e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    return true;
2673e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  }
268a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi
2693e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  void updateParameterCount(AnnotatedToken *Left, AnnotatedToken *Current) {
2703e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    if (Current->is(tok::comma))
2713e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith      ++Left->ParameterCount;
272162e1c1b487352434552147967c3dd296ebee2f7Richard Smith    else if (Left->ParameterCount == 0 && Current->isNot(tok::comment))
273162e1c1b487352434552147967c3dd296ebee2f7Richard Smith      Left->ParameterCount = 1;
2743d7a12a50558c31d4351e923c15ab57688f4fdf2Douglas Gregor  }
2759901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor
2769901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor  bool parseConditional() {
2779901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor    while (CurrentToken != NULL) {
2789901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor      if (CurrentToken->is(tok::colon)) {
2799901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor        CurrentToken->Type = TT_ConditionalExpr;
2809901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor        next();
2819901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor        return true;
282ce3ff2bd3a3386dbc209d3cba4b8769173b274c1John McCall      }
283a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall      if (!consumeToken())
2840a5fa06a688e1086ea553a24b42b9915996ed1f7John McCall        return false;
2850a5fa06a688e1086ea553a24b42b9915996ed1f7John McCall    }
2860a5fa06a688e1086ea553a24b42b9915996ed1f7John McCall    return false;
2870a5fa06a688e1086ea553a24b42b9915996ed1f7John McCall  }
2883d7a12a50558c31d4351e923c15ab57688f4fdf2Douglas Gregor
2893d7a12a50558c31d4351e923c15ab57688f4fdf2Douglas Gregor  bool parseTemplateDeclaration() {
290c6dbc3fa467e2355b678a6b717534928048efcb2Douglas Gregor    if (CurrentToken != NULL && CurrentToken->is(tok::less)) {
291c6dbc3fa467e2355b678a6b717534928048efcb2Douglas Gregor      CurrentToken->Type = TT_TemplateOpener;
292c6dbc3fa467e2355b678a6b717534928048efcb2Douglas Gregor      next();
293c6dbc3fa467e2355b678a6b717534928048efcb2Douglas Gregor      if (!parseAngle())
294c6dbc3fa467e2355b678a6b717534928048efcb2Douglas Gregor        return false;
295a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi      if (CurrentToken != NULL)
296b9f1b8d877541e76390cd3807c2dcff2f950360aDouglas Gregor        CurrentToken->Parent->ClosesTemplateDeclaration = true;
2973d7a12a50558c31d4351e923c15ab57688f4fdf2Douglas Gregor      return true;
298ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara    }
2993d7a12a50558c31d4351e923c15ab57688f4fdf2Douglas Gregor    return false;
3000a5fa06a688e1086ea553a24b42b9915996ed1f7John McCall  }
30116573fa9705b546b7597c273b25b85d6321e2b33Douglas Gregor
30216573fa9705b546b7597c273b25b85d6321e2b33Douglas Gregor  bool consumeToken() {
3033d7a12a50558c31d4351e923c15ab57688f4fdf2Douglas Gregor    AnnotatedToken *Tok = CurrentToken;
3045b9cc5df25c2198f270dd1d5c438fdce70d4051dSebastian Redl    next();
305ad762fcdc16b9e4705b12b09d92b8c026212b906Richard Smith    switch (Tok->FormatTok.Tok.getKind()) {
306796c1a1e3e63e459e371383ac878aa5f40b02a8cRichard Smith    case tok::plus:
3071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    case tok::minus:
308b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall      // At the start of the line, +/- specific ObjectiveC method
309b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall      // declarations.
310b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall      if (Tok->Parent == NULL)
311b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall        Tok->Type = TT_ObjCMethodSpecifier;
3121eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      break;
3137caa6825f42a0f7e97d6fc06233133c42b218e46Douglas Gregor    case tok::colon:
3147caa6825f42a0f7e97d6fc06233133c42b218e46Douglas Gregor      // Colons from ?: are handled in parseConditional().
3157caa6825f42a0f7e97d6fc06233133c42b218e46Douglas Gregor      if (Tok->Parent->is(tok::r_paren)) {
3167caa6825f42a0f7e97d6fc06233133c42b218e46Douglas Gregor        Tok->Type = TT_CtorInitializerColon;
3171eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      } else if (Contexts.back().ColonIsObjCMethodExpr ||
31846460a68f6508775e98c19b4bb8454bb471aac24John McCall                 Line.First.Type == TT_ObjCMethodSpecifier) {
319a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi        Tok->Type = TT_ObjCMethodExpr;
3206b6b42aed07726178f61954ac6e51f47da00275cArgyrios Kyrtzidis        Tok->Parent->Type = TT_ObjCSelectorName;
321c070cc602d6eefea881f71a60de09e05b54c3fddDouglas Gregor        if (Tok->Parent->FormatTok.TokenLength >
3226b6b42aed07726178f61954ac6e51f47da00275cArgyrios Kyrtzidis            Contexts.back().LongestObjCSelectorName)
3236b6b42aed07726178f61954ac6e51f47da00275cArgyrios Kyrtzidis          Contexts.back().LongestObjCSelectorName =
324a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi              Tok->Parent->FormatTok.TokenLength;
325390b4cc8b45a05612349269ef08faab3e4688f06Mike Stump        if (Contexts.back().FirstObjCSelectorName == NULL)
326390b4cc8b45a05612349269ef08faab3e4688f06Mike Stump          Contexts.back().FirstObjCSelectorName = Tok->Parent;
3276826314938f8510cd1a6b03b5d032592456ae27bJohn McCall      } else if (Contexts.back().ColonIsForRangeExpr) {
3286826314938f8510cd1a6b03b5d032592456ae27bJohn McCall        Tok->Type = TT_RangeBasedForLoopColon;
329449d0a829007ea654912098e6a73134a2c529d61Douglas Gregor      } else if (Contexts.size() == 1) {
33060c93c9981c467738369702e7aa23fd58c2b6aacDouglas Gregor        Tok->Type = TT_InheritanceColon;
33160c93c9981c467738369702e7aa23fd58c2b6aacDouglas Gregor      }
3329aab9c4116bb3ea876d92d4af10bff7f4c451f24Douglas Gregor      break;
3339aab9c4116bb3ea876d92d4af10bff7f4c451f24Douglas Gregor    case tok::kw_if:
3344e4d08403ca5cfd4d558fa2936215d3a4e5a528dDavid Blaikie    case tok::kw_while:
3359aab9c4116bb3ea876d92d4af10bff7f4c451f24Douglas Gregor      if (CurrentToken != NULL && CurrentToken->is(tok::l_paren)) {
3369aab9c4116bb3ea876d92d4af10bff7f4c451f24Douglas Gregor        next();
3379aab9c4116bb3ea876d92d4af10bff7f4c451f24Douglas Gregor        if (!parseParens(/*LookForDecls=*/ true))
3382c712f50cd56eaf3662989b556e9c6b1e8fcd11aKaelyn Uhrain          return false;
3391eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      }
3407caa6825f42a0f7e97d6fc06233133c42b218e46Douglas Gregor      break;
3413e9ea0b8cd7c4691d62e385245556be5fded58a7Richard Smith    case tok::kw_for:
3427caa6825f42a0f7e97d6fc06233133c42b218e46Douglas Gregor      Contexts.back().ColonIsForRangeExpr = true;
3437caa6825f42a0f7e97d6fc06233133c42b218e46Douglas Gregor      next();
3447caa6825f42a0f7e97d6fc06233133c42b218e46Douglas Gregor      if (!parseParens())
345f7d72f5a4a3f0e610d77c6779ca3c21920a14bc7Douglas Gregor        return false;
346f7d72f5a4a3f0e610d77c6779ca3c21920a14bc7Douglas Gregor      break;
3477caa6825f42a0f7e97d6fc06233133c42b218e46Douglas Gregor    case tok::l_paren:
348dd5756c04c98e354b85c4f7eb660ae60c6d341ecDeLesley Hutchins      if (!parseParens())
349a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi        return false;
350251b4ff2578e26959a4c036140ccd61c5e9292f2Douglas Gregor      if (Line.MustBeDeclaration)
351251b4ff2578e26959a4c036140ccd61c5e9292f2Douglas Gregor        Line.MightBeFunctionDecl = true;
352251b4ff2578e26959a4c036140ccd61c5e9292f2Douglas Gregor      break;
353a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi    case tok::l_square:
354cf3293eaeb3853d12cff47e648bbe835004e929fDouglas Gregor      if (!parseSquare())
355a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi        return false;
35660c93c9981c467738369702e7aa23fd58c2b6aacDouglas Gregor      break;
35760c93c9981c467738369702e7aa23fd58c2b6aacDouglas Gregor    case tok::l_brace:
35860c93c9981c467738369702e7aa23fd58c2b6aacDouglas Gregor      if (!parseBrace())
3591f5f3a4d58a1c7c50c331b33329fc14563533c04Douglas Gregor        return false;
360adb1d4c18ee83249d4cffc99ef902f98e846092aRichard Smith      break;
3611f5f3a4d58a1c7c50c331b33329fc14563533c04Douglas Gregor    case tok::less:
362adb1d4c18ee83249d4cffc99ef902f98e846092aRichard Smith      if (parseAngle())
3631f5f3a4d58a1c7c50c331b33329fc14563533c04Douglas Gregor        Tok->Type = TT_TemplateOpener;
3646b98b2e5f33ce2dcdb7fa385f7e21672d49f1a69Douglas Gregor      else {
3655b9cc5df25c2198f270dd1d5c438fdce70d4051dSebastian Redl        Tok->Type = TT_BinaryOperator;
3665b9cc5df25c2198f270dd1d5c438fdce70d4051dSebastian Redl        CurrentToken = Tok;
3675b9cc5df25c2198f270dd1d5c438fdce70d4051dSebastian Redl        next();
36834b41d939a1328f484511c6002ba2456db879a29Richard Smith      }
3695b9cc5df25c2198f270dd1d5c438fdce70d4051dSebastian Redl      break;
3705b9cc5df25c2198f270dd1d5c438fdce70d4051dSebastian Redl    case tok::r_paren:
3715b9cc5df25c2198f270dd1d5c438fdce70d4051dSebastian Redl    case tok::r_square:
3725b9cc5df25c2198f270dd1d5c438fdce70d4051dSebastian Redl      return false;
3735b9cc5df25c2198f270dd1d5c438fdce70d4051dSebastian Redl    case tok::r_brace:
3746aeaa60217e1ed11a621409acf1b53df0d14b591Eli Friedman      // Lines can start with '}'.
3756eef519fc8a97bb7ca6066f23d35e10f06b2c1b5Douglas Gregor      if (Tok->Parent != NULL)
3766b98b2e5f33ce2dcdb7fa385f7e21672d49f1a69Douglas Gregor        return false;
3776b98b2e5f33ce2dcdb7fa385f7e21672d49f1a69Douglas Gregor      break;
3786b98b2e5f33ce2dcdb7fa385f7e21672d49f1a69Douglas Gregor    case tok::greater:
3796eef519fc8a97bb7ca6066f23d35e10f06b2c1b5Douglas Gregor      Tok->Type = TT_BinaryOperator;
380a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi      break;
3811f5f3a4d58a1c7c50c331b33329fc14563533c04Douglas Gregor    case tok::kw_operator:
382ad762fcdc16b9e4705b12b09d92b8c026212b906Richard Smith      while (CurrentToken && CurrentToken->isNot(tok::l_paren)) {
383ad762fcdc16b9e4705b12b09d92b8c026212b906Richard Smith        if (CurrentToken->is(tok::star) || CurrentToken->is(tok::amp))
384d226f65006733ed7f709c3174f22ce33391cb58fJohn McCall          CurrentToken->Type = TT_PointerOrReference;
3853d7a12a50558c31d4351e923c15ab57688f4fdf2Douglas Gregor        consumeToken();
386e3499cae8e5323ac553ad56977bf1cd42b9a5a35Richard Smith      }
387e3499cae8e5323ac553ad56977bf1cd42b9a5a35Richard Smith      if (CurrentToken)
388e3499cae8e5323ac553ad56977bf1cd42b9a5a35Richard Smith        CurrentToken->Type = TT_OverloadedOperatorLParen;
389e3499cae8e5323ac553ad56977bf1cd42b9a5a35Richard Smith      break;
3905764f613e61cb3183f3d7ceeafd23396de96ed16Douglas Gregor    case tok::question:
391bbc6454bb98d6a6ecbaafa715222c5db834307f2Argyrios Kyrtzidis      parseConditional();
3923d7a12a50558c31d4351e923c15ab57688f4fdf2Douglas Gregor      break;
3933d7a12a50558c31d4351e923c15ab57688f4fdf2Douglas Gregor    case tok::kw_template:
3943d7a12a50558c31d4351e923c15ab57688f4fdf2Douglas Gregor      parseTemplateDeclaration();
3956206d53f67613958ae1b023aba337ebb46f11a8bAbramo Bagnara      break;
3966206d53f67613958ae1b023aba337ebb46f11a8bAbramo Bagnara    case tok::identifier:
3976206d53f67613958ae1b023aba337ebb46f11a8bAbramo Bagnara      if (Line.First.is(tok::kw_for) &&
3986206d53f67613958ae1b023aba337ebb46f11a8bAbramo Bagnara          Tok->FormatTok.Tok.getIdentifierInfo() == &Ident_in)
3996206d53f67613958ae1b023aba337ebb46f11a8bAbramo Bagnara        Tok->Type = TT_ObjCForIn;
4006206d53f67613958ae1b023aba337ebb46f11a8bAbramo Bagnara      break;
4016206d53f67613958ae1b023aba337ebb46f11a8bAbramo Bagnara    default:
4026206d53f67613958ae1b023aba337ebb46f11a8bAbramo Bagnara      break;
4038dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    }
4048dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    return true;
405a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall  }
406561f81243f665cf2001caadc45df505f826b72d6Douglas Gregor
407836adf6771d5170d936599dfcce21687e37e9bbfDouglas Gregor  void parseIncludeDirective() {
40807fb6bef6242c0f2ab47f059583edbdef924823eJohn McCall    next();
40907fb6bef6242c0f2ab47f059583edbdef924823eJohn McCall    if (CurrentToken != NULL && CurrentToken->is(tok::less)) {
41007fb6bef6242c0f2ab47f059583edbdef924823eJohn McCall      next();
411a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall      while (CurrentToken != NULL) {
41207fb6bef6242c0f2ab47f059583edbdef924823eJohn McCall        if (CurrentToken->isNot(tok::comment) ||
41307fb6bef6242c0f2ab47f059583edbdef924823eJohn McCall            !CurrentToken->Children.empty())
4148dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor          CurrentToken->Type = TT_ImplicitStringLiteral;
4158dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        next();
4168dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      }
4178dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    } else {
4188dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      while (CurrentToken != NULL) {
4198dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        if (CurrentToken->is(tok::string_literal))
4208dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor          // Mark these string literals as "implicit" literals, too, so that
42107fb6bef6242c0f2ab47f059583edbdef924823eJohn McCall          // they are not split or line-wrapped.
4228dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor          CurrentToken->Type = TT_ImplicitStringLiteral;
4238dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        next();
424b4eeaff1595b7d0a8fbc2b3c8bec7dc63f48b7fdDouglas Gregor      }
425b4eeaff1595b7d0a8fbc2b3c8bec7dc63f48b7fdDouglas Gregor    }
4268dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  }
4278dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor
4288dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  void parseWarningOrError() {
4298dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    next();
4308dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    // We still want to format the whitespace left of the first token of the
4318dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    // warning or error.
432f6702a3927147655206ae729a84339c4fda4c651Richard Smith    next();
433f6702a3927147655206ae729a84339c4fda4c651Richard Smith    while (CurrentToken != NULL) {
434f6702a3927147655206ae729a84339c4fda4c651Richard Smith      CurrentToken->Type = TT_ImplicitStringLiteral;
4351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      next();
43660d7b3a319d84d688752be3870615ac0f111fb16John McCall    }
437ce3ff2bd3a3386dbc209d3cba4b8769173b274c1John McCall  }
4388dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor
4398dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  void parsePreprocessorDirective() {
4408dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    next();
4418dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    if (CurrentToken == NULL)
442e9146f2e9f1c4e281544e8c080934c72d41012caAnders Carlsson      return;
4438dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    // Hashes in the middle of a line can lead to any strange token
4448dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    // sequence.
44507fb6bef6242c0f2ab47f059583edbdef924823eJohn McCall    if (CurrentToken->FormatTok.Tok.getIdentifierInfo() == NULL)
44607fb6bef6242c0f2ab47f059583edbdef924823eJohn McCall      return;
4471eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    switch (CurrentToken->FormatTok.Tok.getIdentifierInfo()->getPPKeywordID()) {
4488dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    case tok::pp_include:
4498dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    case tok::pp_import:
4508dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      parseIncludeDirective();
451ca5233044ef679840d1ad1c46a36b16e2ee8a6e1Richard Smith      break;
452703b6015176550eefc91f3e2f19cd19beacbc592Richard Smith    case tok::pp_error:
4538dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    case tok::pp_warning:
4548dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      parseWarningOrError();
455663b5a0be7261c29bc4c526a71cffcfa02d4153eDouglas Gregor      break;
456663b5a0be7261c29bc4c526a71cffcfa02d4153eDouglas Gregor    default:
457f4b5f5c6a1487317aab9aa30d97bccfd57c82c98Anders Carlsson      break;
458663b5a0be7261c29bc4c526a71cffcfa02d4153eDouglas Gregor    }
4591eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    while (CurrentToken != NULL)
46023323e0253716ff03c95a00fb6903019daafe3aaDeLesley Hutchins      next();
461a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi  }
462f4b5f5c6a1487317aab9aa30d97bccfd57c82c98Anders Carlsson
463f4b5f5c6a1487317aab9aa30d97bccfd57c82c98Anders Carlssonpublic:
4641eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  LineType parseLine() {
465f4b5f5c6a1487317aab9aa30d97bccfd57c82c98Anders Carlsson    int PeriodsAndArrows = 0;
466f4b5f5c6a1487317aab9aa30d97bccfd57c82c98Anders Carlsson    bool CanBeBuilderTypeStmt = true;
467f4b5f5c6a1487317aab9aa30d97bccfd57c82c98Anders Carlsson    if (CurrentToken->is(tok::hash)) {
468a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi      parsePreprocessorDirective();
4699901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor      return LT_PreprocessorDirective;
4709901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor    }
4717a126a474fdde06382b315b4e3d8ef0a21d4dc31Sebastian Redl    while (CurrentToken != NULL) {
4729901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor      if (CurrentToken->is(tok::kw_virtual))
4738dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        KeywordVirtualFound = true;
4741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      if (CurrentToken->is(tok::period) || CurrentToken->is(tok::arrow))
475f4b5f5c6a1487317aab9aa30d97bccfd57c82c98Anders Carlsson        ++PeriodsAndArrows;
47646460a68f6508775e98c19b4bb8454bb471aac24John McCall      AnnotatedToken *TheToken = CurrentToken;
477f4b5f5c6a1487317aab9aa30d97bccfd57c82c98Anders Carlsson      if (!consumeToken())
4788dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        return LT_Invalid;
4798dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      if (getPrecedence(*TheToken) > prec::Assignment &&
4808dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor          TheToken->Type == TT_BinaryOperator)
4818dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        CanBeBuilderTypeStmt = false;
48287c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet    }
48387c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet    if (KeywordVirtualFound)
48487c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet      return LT_VirtualFunctionDecl;
48587c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet
48687c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet    // Assume a builder-type call if there are 2 or more "." and "->".
48787c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet    if (PeriodsAndArrows >= 2 && CanBeBuilderTypeStmt)
48887c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet      return LT_BuilderTypeCall;
489b710722d2348cd0945d2b4f02062c7f685146eb0Douglas Gregor
490a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi    if (Line.First.Type == TT_ObjCMethodSpecifier) {
491b710722d2348cd0945d2b4f02062c7f685146eb0Douglas Gregor      if (Contexts.back().FirstObjCSelectorName != NULL)
492b710722d2348cd0945d2b4f02062c7f685146eb0Douglas Gregor        Contexts.back().FirstObjCSelectorName->LongestObjCSelectorName =
493b710722d2348cd0945d2b4f02062c7f685146eb0Douglas Gregor            Contexts.back().LongestObjCSelectorName;
494a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi      return LT_ObjCMethodDecl;
495b710722d2348cd0945d2b4f02062c7f685146eb0Douglas Gregor    }
496b710722d2348cd0945d2b4f02062c7f685146eb0Douglas Gregor
49787c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet    return LT_Other;
49840e17752086c2c497951d64f5ac6ab5039466113Francois Pichet  }
49987c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet
50087c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichetprivate:
50140e17752086c2c497951d64f5ac6ab5039466113Francois Pichet  void next() {
50287c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet    if (CurrentToken != NULL) {
50387c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet      determineTokenType(*CurrentToken);
50487c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet      CurrentToken->BindingStrength = Contexts.back().BindingStrength;
50587c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet    }
50687c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet
50787c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet    if (CurrentToken != NULL && !CurrentToken->Children.empty())
50887c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet      CurrentToken = &CurrentToken->Children[0];
50987c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet    else
51087c2e121cf0522fc266efe2922b58091cd2e0182Francois Pichet      CurrentToken = NULL;
51102cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall
51202cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall    // Reset token type in case we have already looked at it and then recovered
51306245bfb3ae40bb24a8bfb17eafeb266a4daf5caDouglas Gregor    // from an error (e.g. failure to find the matching >).
51432f2fb53d9d7c28c94d8569fd0fcf06cccee0c3dJohn McCall    if (CurrentToken != NULL)
5154fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth      CurrentToken->Type = TT_Unknown;
5164fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth  }
5174fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth
5184fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth  /// \brief A struct to hold information valid in a specific context, e.g.
5194fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth  /// a pair of parenthesis.
5204fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth  struct Context {
5214fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth    Context(unsigned BindingStrength, bool IsExpression)
5224fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth        : BindingStrength(BindingStrength), LongestObjCSelectorName(0),
5234fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth          ColonIsForRangeExpr(false), ColonIsObjCMethodExpr(false),
5244fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth          FirstObjCSelectorName(NULL), IsExpression(IsExpression) {}
5254fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth
5264fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth    unsigned BindingStrength;
52706245bfb3ae40bb24a8bfb17eafeb266a4daf5caDouglas Gregor    unsigned LongestObjCSelectorName;
528fd810b1386ed29b250e7d522ea826a65c815e49dJohn McCall    bool ColonIsForRangeExpr;
529d6f80daa84164ceeb8900da07f43b6a150edf713Richard Smith    bool ColonIsObjCMethodExpr;
5300216df8fd3ce58f5a68ef2ab141ea34c96c11164Abramo Bagnara    AnnotatedToken *FirstObjCSelectorName;
53106245bfb3ae40bb24a8bfb17eafeb266a4daf5caDouglas Gregor    bool IsExpression;
53206245bfb3ae40bb24a8bfb17eafeb266a4daf5caDouglas Gregor  };
533a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi
53406245bfb3ae40bb24a8bfb17eafeb266a4daf5caDouglas Gregor  /// \brief Puts a new \c Context onto the stack \c Contexts for the lifetime
5359a34edb710917798aa30263374f624f13b594605John McCall  /// of each instance.
53606245bfb3ae40bb24a8bfb17eafeb266a4daf5caDouglas Gregor  struct ScopedContextCreator {
53706245bfb3ae40bb24a8bfb17eafeb266a4daf5caDouglas Gregor    AnnotatingParser &P;
538a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi
539a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi    ScopedContextCreator(AnnotatingParser &P, unsigned Increase) : P(P) {
54006245bfb3ae40bb24a8bfb17eafeb266a4daf5caDouglas Gregor      P.Contexts.push_back(Context(P.Contexts.back().BindingStrength + Increase,
54106245bfb3ae40bb24a8bfb17eafeb266a4daf5caDouglas Gregor                                   P.Contexts.back().IsExpression));
54232f2fb53d9d7c28c94d8569fd0fcf06cccee0c3dJohn McCall    }
543af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
544af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    ~ScopedContextCreator() { P.Contexts.pop_back(); }
545af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  };
546af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
547af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  void determineTokenType(AnnotatedToken &Current) {
54806245bfb3ae40bb24a8bfb17eafeb266a4daf5caDouglas Gregor    if (getPrecedence(Current) == prec::Assignment) {
5491eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      Contexts.back().IsExpression = true;
55002cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall      for (AnnotatedToken *Previous = Current.Parent;
551a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi           Previous && Previous->isNot(tok::comma);
55206245bfb3ae40bb24a8bfb17eafeb266a4daf5caDouglas Gregor           Previous = Previous->Parent) {
5535fee110ac106370f75592df024001de73edced2aJohn McCall        if (Previous->Type == TT_BinaryOperator &&
5549a34edb710917798aa30263374f624f13b594605John McCall            (Previous->is(tok::star) || Previous->is(tok::amp))) {
55502cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall          Previous->Type = TT_PointerOrReference;
55602cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall        }
557fd810b1386ed29b250e7d522ea826a65c815e49dJohn McCall      }
558fd810b1386ed29b250e7d522ea826a65c815e49dJohn McCall    } else if (Current.is(tok::kw_return) || Current.is(tok::kw_throw) ||
5598dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor               (Current.is(tok::l_paren) && !Line.MustBeDeclaration &&
5608dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor                (!Current.Parent || Current.Parent->isNot(tok::kw_for)))) {
5611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      Contexts.back().IsExpression = true;
562f6702a3927147655206ae729a84339c4fda4c651Richard Smith    } else if (Current.is(tok::r_paren) || Current.is(tok::greater) ||
563f6702a3927147655206ae729a84339c4fda4c651Richard Smith               Current.is(tok::comma)) {
564f6702a3927147655206ae729a84339c4fda4c651Richard Smith      for (AnnotatedToken *Previous = Current.Parent;
5651eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump           Previous && (Previous->is(tok::star) || Previous->is(tok::amp));
56660d7b3a319d84d688752be3870615ac0f111fb16John McCall           Previous = Previous->Parent)
567ce3ff2bd3a3386dbc209d3cba4b8769173b274c1John McCall        Previous->Type = TT_PointerOrReference;
5688dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    } else if (Current.Parent &&
5698dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor               Current.Parent->Type == TT_CtorInitializerColon) {
5708dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      Contexts.back().IsExpression = true;
571e3f470a718ec00eb8b546e405fa59bc2df2d7c46Richard Smith    }
5729ae2f076ca5ab1feb3ba95629099ec2319833701John McCall
573e3f470a718ec00eb8b546e405fa59bc2df2d7c46Richard Smith    if (Current.Type == TT_Unknown) {
574e3f470a718ec00eb8b546e405fa59bc2df2d7c46Richard Smith      if (Current.Parent && Current.is(tok::identifier) &&
575e3f470a718ec00eb8b546e405fa59bc2df2d7c46Richard Smith          ((Current.Parent->is(tok::identifier) &&
5768dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor            Current.Parent->FormatTok.Tok.getIdentifierInfo()
5778dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor                ->getPPKeywordID() == tok::pp_not_keyword) ||
5788dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor           Current.Parent->Type == TT_PointerOrReference ||
57938f0df352fadc546c5666079fb22de5ec1819d92Richard Smith           Current.Parent->Type == TT_TemplateCloser)) {
58038f0df352fadc546c5666079fb22de5ec1819d92Richard Smith        Current.Type = TT_StartOfName;
58138f0df352fadc546c5666079fb22de5ec1819d92Richard Smith      } else if (Current.is(tok::star) || Current.is(tok::amp)) {
58238f0df352fadc546c5666079fb22de5ec1819d92Richard Smith        Current.Type =
58338f0df352fadc546c5666079fb22de5ec1819d92Richard Smith            determineStarAmpUsage(Current, Contexts.back().IsExpression);
58438f0df352fadc546c5666079fb22de5ec1819d92Richard Smith      } else if (Current.is(tok::minus) || Current.is(tok::plus) ||
58538f0df352fadc546c5666079fb22de5ec1819d92Richard Smith                 Current.is(tok::caret)) {
58638f0df352fadc546c5666079fb22de5ec1819d92Richard Smith        Current.Type = determinePlusMinusCaretUsage(Current);
58738f0df352fadc546c5666079fb22de5ec1819d92Richard Smith      } else if (Current.is(tok::minusminus) || Current.is(tok::plusplus)) {
588ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara        Current.Type = determineIncrementUsage(Current);
5898dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      } else if (Current.is(tok::exclaim)) {
59038f0df352fadc546c5666079fb22de5ec1819d92Richard Smith        Current.Type = TT_UnaryOperator;
591a88cefd266c428be33cc06f7e8b00ff8fc97c1ffAbramo Bagnara      } else if (isBinaryOperator(Current)) {
5921274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor        Current.Type = TT_BinaryOperator;
593f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith      } else if (Current.is(tok::comment)) {
5941274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor        std::string Data(Lexer::getSpelling(Current.FormatTok.Tok, SourceMgr,
5951274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor                                            Lex.getLangOpts()));
5961274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor        if (StringRef(Data).startswith("//"))
5971274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor          Current.Type = TT_LineComment;
598f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith        else
599f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith          Current.Type = TT_BlockComment;
600f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith      } else if (Current.is(tok::r_paren)) {
6011274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor        bool ParensNotExpr = !Current.Parent ||
602f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith                             Current.Parent->Type == TT_PointerOrReference ||
603f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith                             Current.Parent->Type == TT_TemplateCloser;
604f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith        bool ParensCouldEndDecl =
6051274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor            !Current.Children.empty() && (Current.Children[0].is(tok::equal) ||
6061274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor                                          Current.Children[0].is(tok::semi) ||
6071274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor                                          Current.Children[0].is(tok::l_brace));
6081274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor        if (ParensNotExpr && !ParensCouldEndDecl &&
6091274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor            Contexts.back().IsExpression)
6101274ccd90aec0b205fc838c3d504821ccfb55482Douglas Gregor          // FIXME: We need to get smarter and understand more cases of casts.
6115b629aa86c987f276d00453b6c9ab8424f7903feJohn McCall          Current.Type = TT_CastRParen;
6125b629aa86c987f276d00453b6c9ab8424f7903feJohn McCall      } else if (Current.is(tok::at) && Current.Children.size()) {
613f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith        switch (Current.Children[0].FormatTok.Tok.getObjCKeywordID()) {
61406c0fecd197fef21e265a41bca8dc5022de1f864Douglas Gregor        case tok::objc_interface:
615b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall        case tok::objc_implementation:
61617945a0f64fe03ff6ec0c2146005a87636e3ac12Argyrios Kyrtzidis        case tok::objc_protocol:
617f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith          Current.Type = TT_ObjCDecl;
6184ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith          break;
6194ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith        case tok::objc_property:
6204ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith          Current.Type = TT_ObjCProperty;
6214ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith          break;
6224ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith        default:
6234ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith          break;
6244ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith        }
6254ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith      }
6264ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith    }
6274ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith  }
6284ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith
6294ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith  /// \brief Return the type of the given token assuming it is * or &.
6304ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith  TokenType
6314ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith  determineStarAmpUsage(const AnnotatedToken &Tok, bool IsExpression) {
6328dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    const AnnotatedToken *PrevToken = getPreviousToken(Tok);
63396084f171f4824397dc48453146f0a9719cb9247Douglas Gregor    if (PrevToken == NULL)
63496084f171f4824397dc48453146f0a9719cb9247Douglas Gregor      return TT_UnaryOperator;
635a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi
636f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith    const AnnotatedToken *NextToken = getNextToken(Tok);
637f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith    if (NextToken == NULL)
638f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith      return TT_Unknown;
639f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith
64038f0df352fadc546c5666079fb22de5ec1819d92Richard Smith    if (PrevToken->is(tok::l_paren) || PrevToken->is(tok::l_square) ||
64138f0df352fadc546c5666079fb22de5ec1819d92Richard Smith        PrevToken->is(tok::l_brace) || PrevToken->is(tok::comma) ||
64238f0df352fadc546c5666079fb22de5ec1819d92Richard Smith        PrevToken->is(tok::kw_return) || PrevToken->is(tok::colon) ||
64338f0df352fadc546c5666079fb22de5ec1819d92Richard Smith        PrevToken->is(tok::equal) || PrevToken->Type == TT_BinaryOperator ||
64438f0df352fadc546c5666079fb22de5ec1819d92Richard Smith        PrevToken->Type == TT_UnaryOperator || PrevToken->Type == TT_CastRParen)
6454ca93d9978aac02b01814b4f749d6903a1f87ee5Richard Smith      return TT_UnaryOperator;
646f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith
647f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith    if (NextToken->is(tok::l_square))
648f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith      return TT_PointerOrReference;
649f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith
650f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith    if (PrevToken->FormatTok.Tok.isLiteral() || PrevToken->is(tok::r_paren) ||
651f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith        PrevToken->is(tok::r_square) || NextToken->FormatTok.Tok.isLiteral() ||
652f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith        isUnaryOperator(*NextToken) || NextToken->is(tok::l_paren) ||
653f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith        NextToken->is(tok::l_square))
6541af83c444e5a2f6f50a6e1c15e6ebc618ae18a5fRichard Smith      return TT_BinaryOperator;
6551af83c444e5a2f6f50a6e1c15e6ebc618ae18a5fRichard Smith
6561af83c444e5a2f6f50a6e1c15e6ebc618ae18a5fRichard Smith    // It is very unlikely that we are going to find a pointer or reference type
6575f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner    // definition on the RHS of an assignment.
6588dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    if (IsExpression)
6598dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      return TT_BinaryOperator;
660f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith
661f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith    return TT_PointerOrReference;
6628dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  }
6638dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor
66460d7b3a319d84d688752be3870615ac0f111fb16John McCall  TokenType determinePlusMinusCaretUsage(const AnnotatedToken &Tok) {
665ac7610dad6653bad02dd42de198ca358b6fb1f1dDouglas Gregor    const AnnotatedToken *PrevToken = getPreviousToken(Tok);
666f6702a3927147655206ae729a84339c4fda4c651Richard Smith    if (PrevToken == NULL)
6671eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      return TT_UnaryOperator;
668f6702a3927147655206ae729a84339c4fda4c651Richard Smith
6691eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    // Use heuristics to recognize unary operators.
670ce3ff2bd3a3386dbc209d3cba4b8769173b274c1John McCall    if (PrevToken->is(tok::equal) || PrevToken->is(tok::l_paren) ||
671ac7610dad6653bad02dd42de198ca358b6fb1f1dDouglas Gregor        PrevToken->is(tok::comma) || PrevToken->is(tok::l_square) ||
6728dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        PrevToken->is(tok::question) || PrevToken->is(tok::colon) ||
6738dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        PrevToken->is(tok::kw_return) || PrevToken->is(tok::kw_case) ||
6748dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        PrevToken->is(tok::at) || PrevToken->is(tok::l_brace))
6758dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      return TT_UnaryOperator;
6768dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor
6778dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    // There can't be two consecutive binary operators.
6788dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    if (PrevToken->Type == TT_BinaryOperator)
6798dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      return TT_UnaryOperator;
6801eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
6818dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    // Fall back to marking the token as binary operator.
6828dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    return TT_BinaryOperator;
6839ae2f076ca5ab1feb3ba95629099ec2319833701John McCall  }
6848dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor
6858dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  /// \brief Determine whether ++/-- are pre- or post-increments/-decrements.
6868dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  TokenType determineIncrementUsage(const AnnotatedToken &Tok) {
6878dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    const AnnotatedToken *PrevToken = getPreviousToken(Tok);
6888dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    if (PrevToken == NULL)
6898dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor      return TT_UnaryOperator;
6908dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor    if (PrevToken->is(tok::r_paren) || PrevToken->is(tok::r_square) ||
6918dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor        PrevToken->is(tok::identifier))
692581deb3da481053c4993c7600f97acf7768caac5David Blaikie      return TT_TrailingUnaryOperator;
6935b629aa86c987f276d00453b6c9ab8424f7903feJohn McCall
6943b85ecf2049c8670eba30d0c06f28f64168af9b8John McCall    return TT_UnaryOperator;
69517945a0f64fe03ff6ec0c2146005a87636e3ac12Argyrios Kyrtzidis  }
696d226f65006733ed7f709c3174f22ce33391cb58fJohn McCall
6978dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  SmallVector<Context, 8> Contexts;
698a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi
699f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith  SourceManager &SourceMgr;
700f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith  Lexer &Lex;
70196084f171f4824397dc48453146f0a9719cb9247Douglas Gregor  AnnotatedLine &Line;
70296084f171f4824397dc48453146f0a9719cb9247Douglas Gregor  AnnotatedToken *CurrentToken;
703581deb3da481053c4993c7600f97acf7768caac5David Blaikie  bool KeywordVirtualFound;
70496084f171f4824397dc48453146f0a9719cb9247Douglas Gregor  IdentifierInfo &Ident_in;
7058dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor};
7068dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor
7071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// \brief Parses binary expressions by inserting fake parenthesis based on
708f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith/// operator precedence.
709f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smithclass ExpressionParser {
710f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smithpublic:
711de7a0fcdf9f30cb5a97aab614f3975d93cd9926fEli Friedman  ExpressionParser(AnnotatedLine &Line) : Current(&Line.First) {}
712fee13819693c8492f0c364bc704645e844ef737aEdward O'Callaghan
7138dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  /// \brief Parse expressions with the given operatore precedence.
7148dbc2694424b4e842b1d5ea39744a137b58600c3Douglas Gregor  void parse(int Precedence = 0) {
7156477b69cc93e0a0ff15036d60d604f3544da0f29Douglas Gregor    if (Precedence > prec::PointerToMember || Current == NULL)
716b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie      return;
7176477b69cc93e0a0ff15036d60d604f3544da0f29Douglas Gregor
7186477b69cc93e0a0ff15036d60d604f3544da0f29Douglas Gregor    // Skip over "return" until we can properly parse it.
719e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall    if (Current->is(tok::kw_return))
72093ba8579c341d5329175f1413cdc3b35a36592d2John McCall      next();
72193ba8579c341d5329175f1413cdc3b35a36592d2John McCall
722550d9b28fd586db541eb6dd36f3c10d114e483d8Douglas Gregor    // Eagerly consume trailing comments.
723550d9b28fd586db541eb6dd36f3c10d114e483d8Douglas Gregor    while (isTrailingComment(Current)) {
7242a7fb27913999d132cf9e10e03dc5271faa2e9d3John McCall      next();
725e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall    }
726ce3ff2bd3a3386dbc209d3cba4b8769173b274c1John McCall
7271eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    AnnotatedToken *Start = Current;
728d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor    bool OperatorFound = false;
729e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall
730e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall    while (Current) {
73193ba8579c341d5329175f1413cdc3b35a36592d2John McCall      // Consume operators with higher precedence.
73293ba8579c341d5329175f1413cdc3b35a36592d2John McCall      parse(prec::Level(Precedence + 1));
73393ba8579c341d5329175f1413cdc3b35a36592d2John McCall
73493ba8579c341d5329175f1413cdc3b35a36592d2John McCall      int CurrentPrecedence = 0;
735c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor      if (Current) {
736c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor        if (Current->Type == TT_ConditionalExpr)
737c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor          CurrentPrecedence = 1 + (int) prec::Conditional;
738c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor        else if (Current->is(tok::semi))
739c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor          CurrentPrecedence = 1;
740c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor        else if (Current->Type == TT_BinaryOperator || Current->is(tok::comma))
74193ba8579c341d5329175f1413cdc3b35a36592d2John McCall          CurrentPrecedence = 1 + (int) getPrecedence(*Current);
74293ba8579c341d5329175f1413cdc3b35a36592d2John McCall      }
74393ba8579c341d5329175f1413cdc3b35a36592d2John McCall
74493ba8579c341d5329175f1413cdc3b35a36592d2John McCall      // At the end of the line or when an operator with higher precedence is
74593ba8579c341d5329175f1413cdc3b35a36592d2John McCall      // found, insert fake parenthesis and return.
746ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor      if (Current == NULL || closesScope(*Current) ||
74737574f55cd637340f651330f5cfda69742880d36Nick Lewycky          (CurrentPrecedence != 0 && CurrentPrecedence < Precedence)) {
74837574f55cd637340f651330f5cfda69742880d36Nick Lewycky        if (OperatorFound) {
74937574f55cd637340f651330f5cfda69742880d36Nick Lewycky          ++Start->FakeLParens;
75037574f55cd637340f651330f5cfda69742880d36Nick Lewycky          if (Current)
75137574f55cd637340f651330f5cfda69742880d36Nick Lewycky            ++Current->Parent->FakeRParens;
75237574f55cd637340f651330f5cfda69742880d36Nick Lewycky        }
75337574f55cd637340f651330f5cfda69742880d36Nick Lewycky        return;
75437574f55cd637340f651330f5cfda69742880d36Nick Lewycky      }
75593ba8579c341d5329175f1413cdc3b35a36592d2John McCall
75693ba8579c341d5329175f1413cdc3b35a36592d2John McCall      // Consume scopes: (), [], <> and {}
75793ba8579c341d5329175f1413cdc3b35a36592d2John McCall      if (opensScope(*Current)) {
75893ba8579c341d5329175f1413cdc3b35a36592d2John McCall        AnnotatedToken *Left = Current;
75993ba8579c341d5329175f1413cdc3b35a36592d2John McCall        while (Current && !closesScope(*Current)) {
76093ba8579c341d5329175f1413cdc3b35a36592d2John McCall          next();
761c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor          parse();
76293ba8579c341d5329175f1413cdc3b35a36592d2John McCall        }
763c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor        // Remove fake parens that just duplicate the real parens.
76493ba8579c341d5329175f1413cdc3b35a36592d2John McCall        if (Current && Left->Children[0].FakeLParens > 0 &&
76593ba8579c341d5329175f1413cdc3b35a36592d2John McCall            Current->Parent->FakeRParens > 0) {
76693ba8579c341d5329175f1413cdc3b35a36592d2John McCall          --Left->Children[0].FakeLParens;
76793ba8579c341d5329175f1413cdc3b35a36592d2John McCall          --Current->Parent->FakeRParens;
76893ba8579c341d5329175f1413cdc3b35a36592d2John McCall        }
76993ba8579c341d5329175f1413cdc3b35a36592d2John McCall        next();
77093ba8579c341d5329175f1413cdc3b35a36592d2John McCall      } else {
77193ba8579c341d5329175f1413cdc3b35a36592d2John McCall        // Operator found.
77293ba8579c341d5329175f1413cdc3b35a36592d2John McCall        if (CurrentPrecedence == Precedence)
77393ba8579c341d5329175f1413cdc3b35a36592d2John McCall          OperatorFound = true;
77493ba8579c341d5329175f1413cdc3b35a36592d2John McCall
77593ba8579c341d5329175f1413cdc3b35a36592d2John McCall        next();
77693ba8579c341d5329175f1413cdc3b35a36592d2John McCall      }
77793ba8579c341d5329175f1413cdc3b35a36592d2John McCall    }
77893ba8579c341d5329175f1413cdc3b35a36592d2John McCall  }
77993ba8579c341d5329175f1413cdc3b35a36592d2John McCall
78093ba8579c341d5329175f1413cdc3b35a36592d2John McCallprivate:
78193ba8579c341d5329175f1413cdc3b35a36592d2John McCall  void next() {
78293ba8579c341d5329175f1413cdc3b35a36592d2John McCall    if (Current != NULL)
78393ba8579c341d5329175f1413cdc3b35a36592d2John McCall      Current = Current->Children.empty() ? NULL : &Current->Children[0];
784c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  }
78593ba8579c341d5329175f1413cdc3b35a36592d2John McCall
7861eabb7d0c30f6a876b0fd03ad4656c096c26b8d0Douglas Gregor  bool closesScope(const AnnotatedToken &Tok) {
787c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor    return Current->is(tok::r_paren) || Current->Type == TT_TemplateCloser ||
78893ba8579c341d5329175f1413cdc3b35a36592d2John McCall           Current->is(tok::r_brace) || Current->is(tok::r_square);
78993ba8579c341d5329175f1413cdc3b35a36592d2John McCall  }
79093ba8579c341d5329175f1413cdc3b35a36592d2John McCall
791c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  bool opensScope(const AnnotatedToken &Tok) {
79293ba8579c341d5329175f1413cdc3b35a36592d2John McCall    return Current->is(tok::l_paren) || Current->Type == TT_TemplateOpener ||
793c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor           Current->is(tok::l_brace) || Current->is(tok::l_square);
794c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  }
795c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor
796c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  AnnotatedToken *Current;
797c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor};
798c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor
799c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregorvoid TokenAnnotator::annotate(AnnotatedLine &Line) {
800c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  AnnotatingParser Parser(SourceMgr, Lex, Line, Ident_in);
801a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi  Line.Type = Parser.parseLine();
802c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  if (Line.Type == LT_Invalid)
803c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor    return;
804c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor
805c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  ExpressionParser ExprParser(Line);
806c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  ExprParser.parse();
807c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor
808c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  if (Line.First.Type == TT_ObjCMethodSpecifier)
809c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor    Line.Type = LT_ObjCMethodDecl;
810c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  else if (Line.First.Type == TT_ObjCDecl)
811c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor    Line.Type = LT_ObjCDecl;
812c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  else if (Line.First.Type == TT_ObjCProperty)
813c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor    Line.Type = LT_ObjCProperty;
814c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor
815c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  Line.First.SpacesRequiredBefore = 1;
816c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  Line.First.MustBreakBefore = Line.First.FormatTok.MustBreakBefore;
817c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  Line.First.CanBreakBefore = Line.First.MustBreakBefore;
818c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor
81993ba8579c341d5329175f1413cdc3b35a36592d2John McCall  Line.First.TotalLength = Line.First.FormatTok.TokenLength;
82093ba8579c341d5329175f1413cdc3b35a36592d2John McCall}
82193ba8579c341d5329175f1413cdc3b35a36592d2John McCall
82293ba8579c341d5329175f1413cdc3b35a36592d2John McCallvoid TokenAnnotator::calculateFormattingInformation(AnnotatedLine &Line) {
82393ba8579c341d5329175f1413cdc3b35a36592d2John McCall  if (Line.First.Children.empty())
824a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi    return;
825c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  AnnotatedToken *Current = &Line.First.Children[0];
826c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor  while (Current != NULL) {
827c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor    if (Current->Type == TT_LineComment)
828c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor      Current->SpacesRequiredBefore = Style.SpacesBeforeTrailingComments;
829c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor    else
830c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor      Current->SpacesRequiredBefore =
831c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor          spaceRequiredBefore(Line, *Current) ? 1 : 0;
83293ba8579c341d5329175f1413cdc3b35a36592d2John McCall
83393ba8579c341d5329175f1413cdc3b35a36592d2John McCall    if (Current->FormatTok.MustBreakBefore) {
83493ba8579c341d5329175f1413cdc3b35a36592d2John McCall      Current->MustBreakBefore = true;
835c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor    } else if (Current->Type == TT_LineComment) {
836c53d0d762010217d02da5aa14be171817d63e3feDouglas Gregor      Current->MustBreakBefore = Current->FormatTok.NewlinesBefore > 0;
83793ba8579c341d5329175f1413cdc3b35a36592d2John McCall    } else if (isTrailingComment(Current->Parent) ||
83893ba8579c341d5329175f1413cdc3b35a36592d2John McCall               (Current->is(tok::string_literal) &&
83993ba8579c341d5329175f1413cdc3b35a36592d2John McCall                Current->Parent->is(tok::string_literal))) {
84093ba8579c341d5329175f1413cdc3b35a36592d2John McCall      Current->MustBreakBefore = true;
84193ba8579c341d5329175f1413cdc3b35a36592d2John McCall    } else if (Current->is(tok::lessless) && !Current->Children.empty() &&
842e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall               Current->Parent->is(tok::string_literal) &&
84393ba8579c341d5329175f1413cdc3b35a36592d2John McCall               Current->Children[0].is(tok::string_literal)) {
844ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara      Current->MustBreakBefore = true;
845ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara    } else {
846f0510d49a6985e9284d30cfc36a0df2a6292a638Douglas Gregor      Current->MustBreakBefore = false;
847e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall    }
848c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor    Current->CanBreakBefore =
849c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor        Current->MustBreakBefore || canBreakBefore(Line, *Current);
850b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall    if (Current->MustBreakBefore)
851e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall      Current->TotalLength = Current->Parent->TotalLength + Style.ColumnLimit;
85293ba8579c341d5329175f1413cdc3b35a36592d2John McCall    else
85393ba8579c341d5329175f1413cdc3b35a36592d2John McCall      Current->TotalLength =
85493ba8579c341d5329175f1413cdc3b35a36592d2John McCall          Current->Parent->TotalLength + Current->FormatTok.TokenLength +
855e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall          Current->SpacesRequiredBefore;
856ea7390c7b384ce607bfc8fc13c01f37cfc3776f0John McCall    // FIXME: Only calculate this if CanBreakBefore is true once static
85793ba8579c341d5329175f1413cdc3b35a36592d2John McCall    // initializers etc. are sorted out.
858ea7390c7b384ce607bfc8fc13c01f37cfc3776f0John McCall    // FIXME: Move magic numbers to a better place.
859ea7390c7b384ce607bfc8fc13c01f37cfc3776f0John McCall    Current->SplitPenalty =
860ea7390c7b384ce607bfc8fc13c01f37cfc3776f0John McCall        20 * Current->BindingStrength + splitPenalty(Line, *Current);
861ea7390c7b384ce607bfc8fc13c01f37cfc3776f0John McCall
862ea7390c7b384ce607bfc8fc13c01f37cfc3776f0John McCall    Current = Current->Children.empty() ? NULL : &Current->Children[0];
86393ba8579c341d5329175f1413cdc3b35a36592d2John McCall  }
86493ba8579c341d5329175f1413cdc3b35a36592d2John McCall}
86593ba8579c341d5329175f1413cdc3b35a36592d2John McCall
86693ba8579c341d5329175f1413cdc3b35a36592d2John McCallunsigned TokenAnnotator::splitPenalty(const AnnotatedLine &Line,
867e8c01bdb56549adcecd71ce39160eea54b2c51c8Douglas Gregor                                      const AnnotatedToken &Tok) {
86837574f55cd637340f651330f5cfda69742880d36Nick Lewycky  const AnnotatedToken &Left = *Tok.Parent;
86937574f55cd637340f651330f5cfda69742880d36Nick Lewycky  const AnnotatedToken &Right = Tok;
87093ba8579c341d5329175f1413cdc3b35a36592d2John McCall
871a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi  if (Right.Type == TT_StartOfName) {
872f0510d49a6985e9284d30cfc36a0df2a6292a638Douglas Gregor    if (Line.First.is(tok::kw_for))
8733cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall      return 3;
87424bae92f08ae098cc50a602d8cf1273b423e14daDouglas Gregor    else if (Line.MightBeFunctionDecl && Right.BindingStrength == 1)
875ea7390c7b384ce607bfc8fc13c01f37cfc3776f0John McCall      // FIXME: Clean up hack of using BindingStrength to find top-level names.
876259571e27e513cfaf691cc7447e09b31a47d5438Douglas Gregor      return Style.PenaltyReturnTypeOnItsOwnLine;
87793ba8579c341d5329175f1413cdc3b35a36592d2John McCall    else
8781b7f9cbed1b96b58a6e5f7808ebc9345a76a0936Richard Smith      return 100;
8794c51548271d2f8385127e1d943764ae8939d7794Abramo Bagnara  }
8804c51548271d2f8385127e1d943764ae8939d7794Abramo Bagnara  if (Left.is(tok::l_brace) && Right.isNot(tok::l_brace))
881e8c01bdb56549adcecd71ce39160eea54b2c51c8Douglas Gregor    return 50;
882259571e27e513cfaf691cc7447e09b31a47d5438Douglas Gregor  if (Left.is(tok::equal) && Right.is(tok::l_brace))
883a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi    return 150;
8844c51548271d2f8385127e1d943764ae8939d7794Abramo Bagnara  if (Left.is(tok::coloncolon))
8854c51548271d2f8385127e1d943764ae8939d7794Abramo Bagnara    return 500;
8864c51548271d2f8385127e1d943764ae8939d7794Abramo Bagnara
8874c51548271d2f8385127e1d943764ae8939d7794Abramo Bagnara  if (Left.Type == TT_RangeBasedForLoopColon ||
8884c51548271d2f8385127e1d943764ae8939d7794Abramo Bagnara      Left.Type == TT_InheritanceColon)
889e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall    return 2;
890d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor
891d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor  if (Right.is(tok::arrow) || Right.is(tok::period)) {
892d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor    if (Line.Type == LT_BuilderTypeCall)
893d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor      return 5; // Should be smaller than breaking at a nested comma.
894d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor    if ((Left.is(tok::r_paren) || Left.is(tok::r_square)) &&
8955f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner        Left.MatchingParen && Left.MatchingParen->ParameterCount > 0)
896d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor      return 10;
897d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor    return 150;
898d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor  }
899d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor
900d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor  // In for-loops, prefer breaking at ',' and ';'.
901d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor  if (Line.First.is(tok::kw_for) && Left.is(tok::equal))
902e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall    return 4;
903e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall
904e29ba20148e9b7835ad463b39cd4ee9223eafbbfJohn McCall  if (Left.is(tok::semi))
905d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor    return 0;
9067974c3b7062f85bb7c0ada34526cdefe1d30f89bDouglas Gregor  if (Left.is(tok::comma))
9077974c3b7062f85bb7c0ada34526cdefe1d30f89bDouglas Gregor    return 1;
908ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor
909a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi  // In Objective-C method expressions, prefer breaking before "param:" over
910ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  // breaking after it.
911ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  if (Right.Type == TT_ObjCSelectorName)
912ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    return 0;
913ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  if (Left.is(tok::colon) && Left.Type == TT_ObjCMethodExpr)
914ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    return 20;
915ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor
916a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi  if (Left.is(tok::l_paren) || Left.is(tok::l_square) ||
917ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor      Left.Type == TT_TemplateOpener)
918ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    return 20;
919ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor
920ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  if (Right.is(tok::lessless)) {
921a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi    if (Left.is(tok::string_literal)) {
922d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor      char LastChar =
923d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor          StringRef(Left.FormatTok.Tok.getLiteralData(),
924d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor                    Left.FormatTok.TokenLength).drop_back(1).rtrim().back();
925d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor      if (LastChar == ':' || LastChar == '=')
926d65587f7a6d38965fa37158d3f57990a7faf3836Douglas Gregor        return 100;
9277974c3b7062f85bb7c0ada34526cdefe1d30f89bDouglas Gregor    }
9287974c3b7062f85bb7c0ada34526cdefe1d30f89bDouglas Gregor    return prec::Shift;
9297974c3b7062f85bb7c0ada34526cdefe1d30f89bDouglas Gregor  }
930d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor  if (Left.Type == TT_ConditionalExpr)
931550d9b28fd586db541eb6dd36f3c10d114e483d8Douglas Gregor    return prec::Assignment;
932550d9b28fd586db541eb6dd36f3c10d114e483d8Douglas Gregor  prec::Level Level = getPrecedence(Left);
933a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi
934550d9b28fd586db541eb6dd36f3c10d114e483d8Douglas Gregor  if (Level != prec::Unknown)
9352a7fb27913999d132cf9e10e03dc5271faa2e9d3John McCall    return Level;
936895162da2d52f4243f61081d7436de66af4503fcDouglas Gregor
937d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor  return 3;
938d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor}
9391eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
940d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregorbool TokenAnnotator::spaceRequiredBetween(const AnnotatedLine &Line,
941a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi                                          const AnnotatedToken &Left,
942a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor                                          const AnnotatedToken &Right) {
943a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor  if (Right.is(tok::hashhash))
944a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi    return Left.is(tok::hash);
945a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor  if (Left.is(tok::hashhash) || Left.is(tok::hash))
946a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor    return Right.is(tok::hash);
947a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor  if (Right.is(tok::r_paren) || Right.is(tok::semi) || Right.is(tok::comma))
948a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi    return false;
949a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor  if (Right.is(tok::less) &&
950a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi      (Left.is(tok::kw_template) ||
951a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor       (Line.Type == LT_ObjCDecl && Style.ObjCSpaceBeforeProtocolList)))
952d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor    return true;
953d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor  if (Left.is(tok::arrow) || Right.is(tok::arrow))
9541eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    return false;
955d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor  if (Left.is(tok::exclaim) || Left.is(tok::tilde))
956a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi    return false;
957a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor  if (Left.is(tok::at) &&
95837d68185088947322a97eabdc1c0714b0debd929Douglas Gregor      (Right.is(tok::identifier) || Right.is(tok::string_literal) ||
959a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi       Right.is(tok::char_constant) || Right.is(tok::numeric_constant) ||
960a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor       Right.is(tok::l_paren) || Right.is(tok::l_brace) ||
961e976ffe18ee60b81641423f42ff6feec2f5e3cb7John McCall       Right.is(tok::kw_true) || Right.is(tok::kw_false)))
962b1a56e767cfb645fcb25027ab728dd5824d92615John McCall    return false;
963b1a56e767cfb645fcb25027ab728dd5824d92615John McCall  if (Left.is(tok::coloncolon))
964e976ffe18ee60b81641423f42ff6feec2f5e3cb7John McCall    return false;
965e976ffe18ee60b81641423f42ff6feec2f5e3cb7John McCall  if (Right.is(tok::coloncolon))
966e976ffe18ee60b81641423f42ff6feec2f5e3cb7John McCall    return Left.isNot(tok::identifier) && Left.isNot(tok::greater) &&
967b1a56e767cfb645fcb25027ab728dd5824d92615John McCall           Left.isNot(tok::l_paren);
968a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor  if (Left.is(tok::less) || Right.is(tok::greater) || Right.is(tok::less))
969a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi    return false;
970b1a56e767cfb645fcb25027ab728dd5824d92615John McCall  if (Right.is(tok::amp) || Right.is(tok::star))
9711f2e1a96bec2ba6418ae7f2d2b525a3575203b6aJohn McCall    return Left.FormatTok.Tok.isLiteral() ||
972a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor           (Left.isNot(tok::star) && Left.isNot(tok::amp) &&
9731f2e1a96bec2ba6418ae7f2d2b525a3575203b6aJohn McCall            Left.isNot(tok::l_paren) && !Style.PointerBindsToType);
9741f2e1a96bec2ba6418ae7f2d2b525a3575203b6aJohn McCall  if (Left.is(tok::amp) || Left.is(tok::star))
9751f2e1a96bec2ba6418ae7f2d2b525a3575203b6aJohn McCall    return Right.FormatTok.Tok.isLiteral() ||
9761f2e1a96bec2ba6418ae7f2d2b525a3575203b6aJohn McCall           (Right.isNot(tok::star) && Right.isNot(tok::amp) &&
977b1a56e767cfb645fcb25027ab728dd5824d92615John McCall            Style.PointerBindsToType);
978d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor  if (Right.is(tok::star) && Left.is(tok::l_paren))
979d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor    return false;
980d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor  if (Left.is(tok::l_square))
981d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor    return Left.Type == TT_ObjCArrayLiteral && Right.isNot(tok::r_square);
982d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor  if (Right.is(tok::r_square))
983d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor    return Right.Type == TT_ObjCArrayLiteral;
984d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor  if (Right.is(tok::l_square) && Right.Type != TT_ObjCMethodExpr)
985ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor    return false;
9867c1e98f1cb37b40e619a0c8aee8b337f037b432bDouglas Gregor  if (Left.is(tok::period) || Right.is(tok::period))
987ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor    return false;
9886c1c1b8c6ca743a5b6b4c81f9ac56392c12c7457John McCall  if (Left.is(tok::colon))
9896c1c1b8c6ca743a5b6b4c81f9ac56392c12c7457John McCall    return Left.Type != TT_ObjCMethodExpr;
9906c1c1b8c6ca743a5b6b4c81f9ac56392c12c7457John McCall  if (Right.is(tok::colon))
9916c1c1b8c6ca743a5b6b4c81f9ac56392c12c7457John McCall    return Right.Type != TT_ObjCMethodExpr;
992d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor  if (Left.is(tok::l_paren))
993d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor    return false;
9941eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  if (Right.is(tok::l_paren)) {
995ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara    return Line.Type == LT_ObjCDecl || Left.is(tok::kw_if) ||
996ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara           Left.is(tok::kw_for) || Left.is(tok::kw_while) ||
997b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall           Left.is(tok::kw_switch) || Left.is(tok::kw_return) ||
998b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall           Left.is(tok::kw_catch) || Left.is(tok::kw_new) ||
999b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall           Left.is(tok::kw_delete);
1000b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall  }
1001b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall  if (Left.is(tok::at) &&
1002d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor      Right.FormatTok.Tok.getObjCKeywordID() != tok::objc_not_keyword)
1003eaba1af8529c381d7bfd4dd0a8b48d2c01647972Eli Friedman    return false;
1004eaba1af8529c381d7bfd4dd0a8b48d2c01647972Eli Friedman  if (Left.is(tok::l_brace) && Right.is(tok::r_brace))
1005eaba1af8529c381d7bfd4dd0a8b48d2c01647972Eli Friedman    return false;
1006eaba1af8529c381d7bfd4dd0a8b48d2c01647972Eli Friedman  return true;
1007eaba1af8529c381d7bfd4dd0a8b48d2c01647972Eli Friedman}
1008d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor
1009f6b1185f0a8a209c06dfc1efdb6a59cc851e970cDouglas Gregorbool TokenAnnotator::spaceRequiredBefore(const AnnotatedLine &Line,
1010d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor                                         const AnnotatedToken &Tok) {
101102cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall  if (Tok.FormatTok.Tok.getIdentifierInfo() &&
101202cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall      Tok.Parent->FormatTok.Tok.getIdentifierInfo())
101302cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall    return true; // Never ever merge two identifiers.
101402cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall  if (Line.Type == LT_ObjCMethodDecl) {
101502cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall    if (Tok.Parent->Type == TT_ObjCMethodSpecifier)
10169901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor      return true;
10179901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor    if (Tok.Parent->is(tok::r_paren) && Tok.is(tok::identifier))
10189901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor      // Don't space between ')' and <id>
10197a126a474fdde06382b315b4e3d8ef0a21d4dc31Sebastian Redl      return false;
10209901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor  }
10219901c57806f7e36736ed1616e6ab3eebcc99b78cDouglas Gregor  if (Line.Type == LT_ObjCProperty &&
1022d8b285fee4471f393da8ee30f552ceacdc362afaAnders Carlsson      (Tok.is(tok::equal) || Tok.Parent->is(tok::equal)))
102317945a0f64fe03ff6ec0c2146005a87636e3ac12Argyrios Kyrtzidis    return false;
1024d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor
1025d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor  if (Tok.Parent->is(tok::comma))
1026d475b8d9e6f5ff0e6ab8d15667ce8a64c7cb9a4dDouglas Gregor    return true;
102771074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor  if (Tok.Type == TT_CtorInitializerColon || Tok.Type == TT_ObjCBlockLParen)
102871074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor    return true;
102971074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor  if (Tok.Parent->FormatTok.Tok.is(tok::kw_operator))
103071074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor    return false;
103171074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor  if (Tok.Type == TT_OverloadedOperatorLParen)
103271074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor    return false;
103371074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor  if (Tok.is(tok::colon))
103471074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor    return Line.First.isNot(tok::kw_case) && !Tok.Children.empty() &&
103571074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor           Tok.Type != TT_ObjCMethodExpr;
1036bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor  if (Tok.Parent->Type == TT_UnaryOperator || Tok.Parent->Type == TT_CastRParen)
1037bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor    return false;
1038bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor  if (Tok.Type == TT_UnaryOperator)
1039bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor    return Tok.Parent->isNot(tok::l_paren) &&
1040bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor           Tok.Parent->isNot(tok::l_square) && Tok.Parent->isNot(tok::at) &&
1041bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor           (Tok.Parent->isNot(tok::colon) ||
1042bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor            Tok.Parent->Type != TT_ObjCMethodExpr);
1043bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor  if (Tok.Parent->is(tok::greater) && Tok.is(tok::greater)) {
1044bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor    return Tok.Type == TT_TemplateCloser &&
1045bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor           Tok.Parent->Type == TT_TemplateCloser &&
1046bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor           Style.Standard != FormatStyle::LS_Cpp11;
1047bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor  }
1048bed51fef5773f043db2ad13aa2b6d2f8a8bdbdbaDouglas Gregor  if (Tok.Type == TT_BinaryOperator || Tok.Parent->Type == TT_BinaryOperator)
104971074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor    return true;
105071074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor  if (Tok.Parent->Type == TT_TemplateCloser && Tok.is(tok::l_paren))
105102cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall    return false;
105202cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall  if (Tok.is(tok::less) && Line.First.is(tok::hash))
105302cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall    return true;
105402cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall  if (Tok.Type == TT_TrailingUnaryOperator)
105502cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall    return false;
10567557a1348d2821dce126a778aa7acd7a00b814fdDouglas Gregor  return spaceRequiredBetween(Line, *Tok.Parent, Tok);
1057a735b206fdb5c15767a45289e1ffb3b568f70f2bDouglas Gregor}
1058127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor
1059127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorbool TokenAnnotator::canBreakBefore(const AnnotatedLine &Line,
1060127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor                                    const AnnotatedToken &Right) {
1061b0cb022daec8671406ab25f4b5d5a6d48d823bc4John McCall  const AnnotatedToken &Left = *Right.Parent;
1062a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi  if (Right.Type == TT_StartOfName)
106324bae92f08ae098cc50a602d8cf1273b423e14daDouglas Gregor    return true;
10641eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  if (Right.is(tok::colon) && Right.Type == TT_ObjCMethodExpr)
10651e1e9722cb4ea6027e2c4885c7a8f26d3726ca7dDouglas Gregor    return false;
10662c853e401ca406d417eb916e867226050e7be06bArgyrios Kyrtzidis  if (Left.is(tok::colon) && Left.Type == TT_ObjCMethodExpr)
10672c853e401ca406d417eb916e867226050e7be06bArgyrios Kyrtzidis    return true;
10682c853e401ca406d417eb916e867226050e7be06bArgyrios Kyrtzidis  if (Right.Type == TT_ObjCSelectorName)
10691eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    return true;
1070127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  if (Left.ClosesTemplateDeclaration)
10712c853e401ca406d417eb916e867226050e7be06bArgyrios Kyrtzidis    return true;
10722c853e401ca406d417eb916e867226050e7be06bArgyrios Kyrtzidis  if (Right.Type == TT_ConditionalExpr || Right.is(tok::question))
1073127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    return true;
10741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  if (Right.Type == TT_RangeBasedForLoopColon ||
1075b0cb022daec8671406ab25f4b5d5a6d48d823bc4John McCall      Right.Type == TT_InheritanceColon)
1076b0cb022daec8671406ab25f4b5d5a6d48d823bc4John McCall    return false;
1077b0cb022daec8671406ab25f4b5d5a6d48d823bc4John McCall  if (Left.Type == TT_RangeBasedForLoopColon ||
1078b0cb022daec8671406ab25f4b5d5a6d48d823bc4John McCall      Left.Type == TT_InheritanceColon)
1079b0cb022daec8671406ab25f4b5d5a6d48d823bc4John McCall    return true;
1080b0cb022daec8671406ab25f4b5d5a6d48d823bc4John McCall  if (Right.Type == TT_RangeBasedForLoopColon)
108179c2278a66d8fc0943774d1b7c71a32f7764e1e2Douglas Gregor    return false;
1082b212d9a8e10308cde5b7a1ce07bd59d8df14fa06Douglas Gregor  if (Left.Type == TT_PointerOrReference || Left.Type == TT_TemplateCloser ||
1083a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi      Left.Type == TT_UnaryOperator || Left.Type == TT_ConditionalExpr ||
108479c2278a66d8fc0943774d1b7c71a32f7764e1e2Douglas Gregor      Left.is(tok::question) || Left.is(tok::kw_operator))
10852a7fb27913999d132cf9e10e03dc5271faa2e9d3John McCall    return false;
10861eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  if (Left.is(tok::equal) && Line.Type == LT_VirtualFunctionDecl)
10875f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner    return false;
108864b4b43a23aa8b8009470e3cc451333f623d7d58David Blaikie
108921ef0fa27b0783ec0bc6aa5b524feb2ec840f952John McCall  if (Right.Type == TT_LineComment)
10902dc0e64e57b2a1786fa53a7dbd1d5c8e255eadb0Douglas Gregor    // We rely on MustBreakBefore being set correctly here as we should not
109171074fdf40a8f5b53810712102b58c27efc30759Douglas Gregor    // change the "binding" behavior of a comment.
1092fd810b1386ed29b250e7d522ea826a65c815e49dJohn McCall    return false;
1093c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor
1094c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  // Allow breaking after a trailing 'const', e.g. after a method declaration,
1095c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  // unless it is follow by ';', '{' or '='.
1096c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  if (Left.is(tok::kw_const) && Left.Parent != NULL &&
1097c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor      Left.Parent->is(tok::r_paren))
1098c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor    return Right.isNot(tok::l_brace) && Right.isNot(tok::semi) &&
1099d325daa506338ab86f9dd468b48fd010673f49a6John McCall           Right.isNot(tok::equal);
1100d325daa506338ab86f9dd468b48fd010673f49a6John McCall
110168b6b87b6beb7922fc2c8ab923ba2ce125490363John McCall  // We only break before r_brace if there was a corresponding break before
110268b6b87b6beb7922fc2c8ab923ba2ce125490363John McCall  // the l_brace, which is tracked by BreakBeforeClosingBrace.
110368b6b87b6beb7922fc2c8ab923ba2ce125490363John McCall  if (Right.is(tok::r_brace))
110468b6b87b6beb7922fc2c8ab923ba2ce125490363John McCall    return false;
110568b6b87b6beb7922fc2c8ab923ba2ce125490363John McCall
1106c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  if (Right.is(tok::r_paren) || Right.is(tok::greater))
1107d325daa506338ab86f9dd468b48fd010673f49a6John McCall    return false;
1108c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor  if (Left.is(tok::identifier) && Right.is(tok::string_literal))
1109d325daa506338ab86f9dd468b48fd010673f49a6John McCall    return true;
1110d325daa506338ab86f9dd468b48fd010673f49a6John McCall  return (isBinaryOperator(Left) && Left.isNot(tok::lessless)) ||
1111d325daa506338ab86f9dd468b48fd010673f49a6John McCall         Left.is(tok::comma) || Right.is(tok::lessless) ||
1112a789ca9b967abe47b84df83bcf4afb150856a8d9NAKAMURA Takumi         Right.is(tok::arrow) || Right.is(tok::period) ||
11137c1e98f1cb37b40e619a0c8aee8b337f037b432bDouglas Gregor         Right.is(tok::colon) || Left.is(tok::coloncolon) ||
1114d325daa506338ab86f9dd468b48fd010673f49a6John McCall         Left.is(tok::semi) || Left.is(tok::l_brace) ||
111568b6b87b6beb7922fc2c8ab923ba2ce125490363John McCall         (Left.is(tok::r_paren) && Left.Type != TT_CastRParen &&
111602cace78cf48cc26686bd5b07c78606abca13bcdJohn McCall          Right.is(tok::identifier)) ||
1117ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara         (Left.is(tok::l_paren) && !Right.is(tok::r_paren)) ||
1118635311f94e8fd4ff153130d91046ff78ffe97b06Abramo Bagnara         (Left.is(tok::l_square) && !Right.is(tok::r_square));
111916573fa9705b546b7597c273b25b85d6321e2b33Douglas Gregor}
1120af1fc7af351758b0ea0d285bdfe5640128109a4eRichard Smith
112186c3ae46250cdcc57778c27826060779a92f3815Richard Smith} // namespace format
1122b6217665c6a987f2d6c8665fd70365d7719ac4dfJohn McCall} // namespace clang
1123c22b5fff39a7520207f165fb16a27a34b944bd9cDouglas Gregor