Parse: use the EOF token method to lex inline method bodies
authorDavid Majnemer <david.majnemer@gmail.com>
Tue, 13 Jan 2015 05:06:20 +0000 (05:06 +0000)
committerDavid Majnemer <david.majnemer@gmail.com>
Tue, 13 Jan 2015 05:06:20 +0000 (05:06 +0000)
Mark the end of the method body with an EOF token, collect it once we
expect to be done with method body parsing.  No functionality change
intended.

llvm-svn: 225765

clang/lib/Parse/ParseCXXInlineMethods.cpp
clang/test/Parser/cxx-member-initializers.cpp

index 3ede029..59b491a 100644 (file)
@@ -484,10 +484,16 @@ void Parser::ParseLexedMethodDef(LexedMethod &LM) {
     Actions.ActOnReenterTemplateScope(getCurScope(), LM.D);
     ++CurTemplateDepthTracker;
   }
-  // Save the current token position.
-  SourceLocation origLoc = Tok.getLocation();
 
   assert(!LM.Toks.empty() && "Empty body!");
+  Token LastBodyToken = LM.Toks.back();
+  Token BodyEnd;
+  BodyEnd.startToken();
+  BodyEnd.setKind(tok::eof);
+  BodyEnd.setLocation(
+      LastBodyToken.getLocation().getLocWithOffset(LastBodyToken.getLength()));
+  BodyEnd.setEofData(LM.D);
+  LM.Toks.push_back(BodyEnd);
   // Append the current token at the end of the new token stream so that it
   // doesn't get lost.
   LM.Toks.push_back(Tok);
@@ -505,12 +511,11 @@ void Parser::ParseLexedMethodDef(LexedMethod &LM) {
 
   if (Tok.is(tok::kw_try)) {
     ParseFunctionTryBlock(LM.D, FnScope);
-    assert(!PP.getSourceManager().isBeforeInTranslationUnit(origLoc,
-                                                         Tok.getLocation()) &&
-           "ParseFunctionTryBlock went over the cached tokens!");
-    // There could be leftover tokens (e.g. because of an error).
-    // Skip through until we reach the original token position.
-    while (Tok.getLocation() != origLoc && Tok.isNot(tok::eof))
+
+    while (Tok.isNot(tok::eof))
+      ConsumeAnyToken();
+
+    if (Tok.is(tok::eof) && Tok.getEofData() == LM.D)
       ConsumeAnyToken();
     return;
   }
@@ -521,7 +526,11 @@ void Parser::ParseLexedMethodDef(LexedMethod &LM) {
     if (!Tok.is(tok::l_brace)) {
       FnScope.Exit();
       Actions.ActOnFinishFunctionBody(LM.D, nullptr);
-      while (Tok.getLocation() != origLoc && Tok.isNot(tok::eof))
+
+      while (Tok.isNot(tok::eof))
+        ConsumeAnyToken();
+
+      if (Tok.is(tok::eof) && Tok.getEofData() == LM.D)
         ConsumeAnyToken();
       return;
     }
@@ -541,17 +550,11 @@ void Parser::ParseLexedMethodDef(LexedMethod &LM) {
   if (LM.D)
     LM.D->getAsFunction()->setLateTemplateParsed(false);
 
-  if (Tok.getLocation() != origLoc) {
-    // Due to parsing error, we either went over the cached tokens or
-    // there are still cached tokens left. If it's the latter case skip the
-    // leftover tokens.
-    // Since this is an uncommon situation that should be avoided, use the
-    // expensive isBeforeInTranslationUnit call.
-    if (PP.getSourceManager().isBeforeInTranslationUnit(Tok.getLocation(),
-                                                        origLoc))
-      while (Tok.getLocation() != origLoc && Tok.isNot(tok::eof))
-        ConsumeAnyToken();
-  }
+  while (Tok.isNot(tok::eof))
+    ConsumeAnyToken();
+
+  if (Tok.is(tok::eof) && Tok.getEofData() == LM.D)
+    ConsumeAnyToken();
 
   if (CXXMethodDecl *MD = dyn_cast_or_null<CXXMethodDecl>(LM.D))
     Actions.ActOnFinishInlineMethodDef(MD);
index ee509b1..8e52adb 100644 (file)
@@ -66,12 +66,12 @@ namespace PR16480 {
 
     struct T { int n; };
     template<typename> struct A { int n; };
-  }; // expected-error +{{}}
+  };
 
   // FIXME: This is valid now, but may be made ill-formed by DR1607.
   struct G : X<0> {
     G() : X<0 && [](){return 0;}()>{} // expected-error +{{}}
-  }; // expected-error +{{}}
+  };
 
   struct Errs : X<0> {
     Errs(X<0>) : decltype X<0>() {} // expected-error {{expected '(' after 'decltype'}}