[cfe-commits] r53376 - in /cfe/trunk: include/clang/Parse/Parser.h lib/Parse/ParseExpr.cpp lib/Parse/ParseInit.cpp lib/Parse/ParseStmt.cpp

Argiris Kirtzidis akyrtzi at gmail.com
Wed Jul 9 15:53:07 PDT 2008


Author: akirtzidis
Date: Wed Jul  9 17:53:07 2008
New Revision: 53376

URL: http://llvm.org/viewvc/llvm-project?rev=53376&view=rev
Log:
Simplify the parser a bit by looking at the next token without consuming it (by Preprocessor::LookNext):

-Remove ParseExpressionWithLeadingIdentifier and ParseAssignmentExprWithLeadingIdentifier.
-Separate ParseLabeledStatement from ParseIdentifierStatement.

Modified:
    cfe/trunk/include/clang/Parse/Parser.h
    cfe/trunk/lib/Parse/ParseExpr.cpp
    cfe/trunk/lib/Parse/ParseInit.cpp
    cfe/trunk/lib/Parse/ParseStmt.cpp

Modified: cfe/trunk/include/clang/Parse/Parser.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Parse/Parser.h?rev=53376&r1=53375&r2=53376&view=diff

==============================================================================
--- cfe/trunk/include/clang/Parse/Parser.h (original)
+++ cfe/trunk/include/clang/Parse/Parser.h Wed Jul  9 17:53:07 2008
@@ -205,6 +205,12 @@
     if (N == 0 || Tok.is(tok::eof)) return Tok;
     return PP.LookAhead(N-1);
   }
+
+  /// NextToken - This peeks ahead one token and returns it without
+  /// consuming it.
+  const Token &NextToken() {
+    return PP.LookNext();
+  }
   
   
   /// MatchRHSPunctuation - For punctuation with a LHS and RHS (e.g. '['/']'),
@@ -369,9 +375,7 @@
   ExprResult ParseConstantExpression();
   ExprResult ParseAssignmentExpression();  // Expr that doesn't include commas.
   
-  ExprResult ParseExpressionWithLeadingIdentifier(const Token &Tok);
   ExprResult ParseExpressionWithLeadingAt(SourceLocation AtLoc);
-  ExprResult ParseAssignmentExprWithLeadingIdentifier(const Token &Tok);
 
   ExprResult ParseRHSOfBinaryExpression(ExprResult LHS, unsigned MinPrec);
   ExprResult ParseCastExpression(bool isUnaryExpression);
@@ -453,6 +457,7 @@
   StmtResult ParseStatement() { return ParseStatementOrDeclaration(true); }
   StmtResult ParseStatementOrDeclaration(bool OnlyStatement = false);
   StmtResult ParseIdentifierStatement(bool OnlyStatement);
+  StmtResult ParseLabeledStatement();
   StmtResult ParseCaseStatement();
   StmtResult ParseDefaultStatement();
   StmtResult ParseCompoundStatement(bool isStmtExpr = false);

Modified: cfe/trunk/lib/Parse/ParseExpr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Parse/ParseExpr.cpp?rev=53376&r1=53375&r2=53376&view=diff

==============================================================================
--- cfe/trunk/lib/Parse/ParseExpr.cpp (original)
+++ cfe/trunk/lib/Parse/ParseExpr.cpp Wed Jul  9 17:53:07 2008
@@ -228,69 +228,6 @@
   return ParseRHSOfBinaryExpression(LHS, prec::Conditional);
 }
 
-/// ParseExpressionWithLeadingIdentifier - This special purpose method is used
-/// in contexts where we have already consumed an identifier (which we saved in
-/// 'IdTok'), then discovered that the identifier was really the leading token
-/// of part of an expression.  For example, in "A[1]+B", we consumed "A" (which
-/// is now in 'IdTok') and the current token is "[".
-Parser::ExprResult Parser::
-ParseExpressionWithLeadingIdentifier(const Token &IdTok) {
-  // We know that 'IdTok' must correspond to this production:
-  //   primary-expression: identifier
-  
-  // Let the actions module handle the identifier.
-  ExprResult Res = Actions.ActOnIdentifierExpr(CurScope, IdTok.getLocation(),
-                                               *IdTok.getIdentifierInfo(),
-                                               Tok.is(tok::l_paren));
-  
-  // Because we have to parse an entire cast-expression before starting the
-  // ParseRHSOfBinaryExpression method (which parses any trailing binops), we
-  // need to handle the 'postfix-expression' rules.  We do this by invoking
-  // ParsePostfixExpressionSuffix to consume any postfix-expression suffixes:
-  Res = ParsePostfixExpressionSuffix(Res);
-  if (Res.isInvalid) return Res;
-
-  // At this point, the "A[1]" part of "A[1]+B" has been consumed. Once this is
-  // done, we know we don't have to do anything for cast-expression, because the
-  // only non-postfix-expression production starts with a '(' token, and we know
-  // we have an identifier.  As such, we can invoke ParseRHSOfBinaryExpression
-  // to consume any trailing operators (e.g. "+" in this example) and connected
-  // chunks of the expression.
-  return ParseRHSOfBinaryExpression(Res, prec::Comma);
-}
-
-/// ParseExpressionWithLeadingIdentifier - This special purpose method is used
-/// in contexts where we have already consumed an identifier (which we saved in
-/// 'IdTok'), then discovered that the identifier was really the leading token
-/// of part of an assignment-expression.  For example, in "A[1]+B", we consumed
-/// "A" (which is now in 'IdTok') and the current token is "[".
-Parser::ExprResult Parser::
-ParseAssignmentExprWithLeadingIdentifier(const Token &IdTok) {
-  // We know that 'IdTok' must correspond to this production:
-  //   primary-expression: identifier
-  
-  // Let the actions module handle the identifier.
-  ExprResult Res = Actions.ActOnIdentifierExpr(CurScope, IdTok.getLocation(),
-                                               *IdTok.getIdentifierInfo(),
-                                               Tok.is(tok::l_paren));
-  
-  // Because we have to parse an entire cast-expression before starting the
-  // ParseRHSOfBinaryExpression method (which parses any trailing binops), we
-  // need to handle the 'postfix-expression' rules.  We do this by invoking
-  // ParsePostfixExpressionSuffix to consume any postfix-expression suffixes:
-  Res = ParsePostfixExpressionSuffix(Res);
-  if (Res.isInvalid) return Res;
-  
-  // At this point, the "A[1]" part of "A[1]+B" has been consumed. Once this is
-  // done, we know we don't have to do anything for cast-expression, because the
-  // only non-postfix-expression production starts with a '(' token, and we know
-  // we have an identifier.  As such, we can invoke ParseRHSOfBinaryExpression
-  // to consume any trailing operators (e.g. "+" in this example) and connected
-  // chunks of the expression.
-  return ParseRHSOfBinaryExpression(Res, prec::Assignment);
-}
-
-
 /// ParseRHSOfBinaryExpression - Parse a binary expression that starts with
 /// LHS and has a precedence of at least MinPrec.
 Parser::ExprResult

Modified: cfe/trunk/lib/Parse/ParseInit.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Parse/ParseInit.cpp?rev=53376&r1=53375&r2=53376&view=diff

==============================================================================
--- cfe/trunk/lib/Parse/ParseInit.cpp (original)
+++ cfe/trunk/lib/Parse/ParseInit.cpp Wed Jul  9 17:53:07 2008
@@ -142,19 +142,18 @@
       // assignment-expression or if it is an old-style structure field
       // designator.
       // TODO: Check that this is the first designator.
-      Token Ident = Tok;
-      ConsumeToken();
       
       // If this is the gross GNU extension, handle it now.
-      if (Tok.is(tok::colon)) {
-        Diag(Ident, diag::ext_gnu_old_style_field_designator);
+      if (NextToken().is(tok::colon)) {
+        Diag(Tok, diag::ext_gnu_old_style_field_designator);
+        ConsumeToken(); // The identifier.
+        assert(Tok.is(tok::colon) && "NextToken() not working properly!");
         ConsumeToken();
         return ParseInitializer();
       }
       
-      // Otherwise, we just consumed the first token of an expression.  Parse
-      // the rest of it now.
-      return ParseAssignmentExprWithLeadingIdentifier(Ident);
+      // Otherwise, parse the assignment-expression.
+      return ParseAssignmentExpression();
     }
     }
   }

Modified: cfe/trunk/lib/Parse/ParseStmt.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Parse/ParseStmt.cpp?rev=53376&r1=53375&r2=53376&view=diff

==============================================================================
--- cfe/trunk/lib/Parse/ParseStmt.cpp (original)
+++ cfe/trunk/lib/Parse/ParseStmt.cpp Wed Jul  9 17:53:07 2008
@@ -79,8 +79,11 @@
   tok::TokenKind Kind  = Tok.getKind();
   SourceLocation AtLoc;
   switch (Kind) {
-  case tok::identifier:             // C99 6.8.1: labeled-statement
-    // identifier ':' statement
+  case tok::identifier:
+    if (NextToken().is(tok::colon)) { // C99 6.8.1: labeled-statement
+      // identifier ':' statement
+      return ParseLabeledStatement();
+    }
     // declaration                  (if !OnlyStatement)
     // expression[opt] ';'
     return ParseIdentifierStatement(OnlyStatement);
@@ -174,53 +177,61 @@
   return Res;
 }
 
-/// ParseIdentifierStatement - Because we don't have two-token lookahead, we
-/// have a bit of a quandry here.  Reading the identifier is necessary to see if
-/// there is a ':' after it.  If there is, this is a label, regardless of what
-/// else the identifier can mean.  If not, this is either part of a declaration
-/// (if the identifier is a type-name) or part of an expression.
+/// ParseLabeledStatement - We have an identifier and a ':' after it.
 ///
 ///       labeled-statement:
 ///         identifier ':' statement
 /// [GNU]   identifier ':' attributes[opt] statement
-///         declaration                  (if !OnlyStatement)
-///         expression[opt] ';'
 ///
-Parser::StmtResult Parser::ParseIdentifierStatement(bool OnlyStatement) {
+Parser::StmtResult Parser::ParseLabeledStatement() {
   assert(Tok.is(tok::identifier) && Tok.getIdentifierInfo() &&
          "Not an identifier!");
 
   Token IdentTok = Tok;  // Save the whole token.
   ConsumeToken();  // eat the identifier.
+
+  assert(Tok.is(tok::colon) && "Not a label!");
   
   // identifier ':' statement
-  if (Tok.is(tok::colon)) {
-    SourceLocation ColonLoc = ConsumeToken();
+  SourceLocation ColonLoc = ConsumeToken();
 
-    // Read label attributes, if present.
-    DeclTy *AttrList = 0;
-    if (Tok.is(tok::kw___attribute))
-      // TODO: save these somewhere.
-      AttrList = ParseAttributes();
-
-    StmtResult SubStmt = ParseStatement();
-    
-    // Broken substmt shouldn't prevent the label from being added to the AST.
-    if (SubStmt.isInvalid)
-      SubStmt = Actions.ActOnNullStmt(ColonLoc);
-    
-    return Actions.ActOnLabelStmt(IdentTok.getLocation(), 
-                                  IdentTok.getIdentifierInfo(),
-                                  ColonLoc, SubStmt.Val);
-  }
+  // Read label attributes, if present.
+  DeclTy *AttrList = 0;
+  if (Tok.is(tok::kw___attribute))
+    // TODO: save these somewhere.
+    AttrList = ParseAttributes();
+
+  StmtResult SubStmt = ParseStatement();
+  
+  // Broken substmt shouldn't prevent the label from being added to the AST.
+  if (SubStmt.isInvalid)
+    SubStmt = Actions.ActOnNullStmt(ColonLoc);
   
+  return Actions.ActOnLabelStmt(IdentTok.getLocation(), 
+                                IdentTok.getIdentifierInfo(),
+                                ColonLoc, SubStmt.Val);
+}
+  
+/// ParseIdentifierStatement - This is either part of a declaration
+/// (if the identifier is a type-name) or part of an expression.
+///
+///         declaration                  (if !OnlyStatement)
+///         expression[opt] ';'
+///
+Parser::StmtResult Parser::ParseIdentifierStatement(bool OnlyStatement) {
+  assert(Tok.is(tok::identifier) && Tok.getIdentifierInfo() &&
+         "Not an identifier!");
+
   // Check to see if this is a declaration.
   void *TypeRep;
   if (!OnlyStatement &&
-      (TypeRep = Actions.isTypeName(*IdentTok.getIdentifierInfo(), CurScope))) {
+      (TypeRep = Actions.isTypeName(*Tok.getIdentifierInfo(), CurScope))) {
     // Handle this.  Warn/disable if in middle of block and !C99.
     DeclSpec DS;
     
+    Token IdentTok = Tok;  // Save the whole token.
+    ConsumeToken();  // eat the identifier.
+
     // Add the typedef name to the start of the decl-specs.
     const char *PrevSpec = 0;
     int isInvalid = DS.SetTypeSpecType(DeclSpec::TST_typedef,
@@ -263,8 +274,8 @@
                                  DeclaratorInfo.getSourceRange().getEnd());
   }
   
-  // Otherwise, this is an expression.  Seed it with II and parse it.
-  ExprResult Res = ParseExpressionWithLeadingIdentifier(IdentTok);
+  // Otherwise, this is an expression.
+  ExprResult Res = ParseExpression();
   if (Res.isInvalid) {
     SkipUntil(tok::semi);
     return true;





More information about the cfe-commits mailing list