[cfe-commits] r38828 - in /cfe/cfe/trunk: Parse/ParseDecl.cpp include/clang/Basic/DiagnosticKinds.def include/clang/Parse/Parser.h

sabre at cs.uiuc.edu sabre at cs.uiuc.edu
Wed Jul 11 09:24:59 PDT 2007


Author: sabre
Date: Wed Jul 11 11:24:59 2007
New Revision: 38828

URL: http://llvm.org/viewvc/llvm-project?rev=38828&view=rev
Log:
Parse array declarators, tested by Parser/declarators.c

Modified:
    cfe/cfe/trunk/Parse/ParseDecl.cpp
    cfe/cfe/trunk/include/clang/Basic/DiagnosticKinds.def
    cfe/cfe/trunk/include/clang/Parse/Parser.h

Modified: cfe/cfe/trunk/Parse/ParseDecl.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/Parse/ParseDecl.cpp?rev=38828&r1=38827&r2=38828&view=diff

==============================================================================
--- cfe/cfe/trunk/Parse/ParseDecl.cpp (original)
+++ cfe/cfe/trunk/Parse/ParseDecl.cpp Wed Jul 11 11:24:59 2007
@@ -311,11 +311,11 @@
 ///         identifier
 ///         '(' declarator ')'
 /// [GNU]   '(' attributes declarator ')'
-/// [C90]   direct-declarator [ constant-expression[opt] ] 
-/// [C99]   direct-declarator [ type-qual-list[opt] assignment-expr[opt] ]
-/// [C99]   direct-declarator [ 'static' type-qual-list[opt] assignment-expr ]
-/// [C99]   direct-declarator [ type-qual-list 'static' assignment-expr ]
-/// [C99]   direct-declarator [ type-qual-list[opt] * ]
+/// [C90]   direct-declarator '[' constant-expression[opt] ']'
+/// [C99]   direct-declarator '[' type-qual-list[opt] assignment-expr[opt] ']'
+/// [C99]   direct-declarator '[' 'static' type-qual-list[opt] assign-expr ']'
+/// [C99]   direct-declarator '[' type-qual-list 'static' assignment-expr ']'
+/// [C99]   direct-declarator '[' type-qual-list[opt] '*' ']'
 ///         direct-declarator '(' parameter-type-list ')'
 ///         direct-declarator '(' identifier-list[opt] ')'
 /// [GNU]   direct-declarator '(' parameter-forward-declarations
@@ -357,7 +357,7 @@
     if (Tok.getKind() == tok::l_paren) {
       ParseParenDeclarator(D);
     } else if (Tok.getKind() == tok::l_square) {
-      assert(0 && "Unimp!");
+      ParseBracketDeclarator(D);
     } else {
       break;
     }
@@ -486,8 +486,8 @@
 
         // Check to see if this is "void(...)" which is not allowed.
         if (!ReadArg) {
-          // Otherwise, parse parameter type list.  If it starts with an ellipsis, 
-          // diagnose the malformed function.
+          // Otherwise, parse parameter type list.  If it starts with an
+          // ellipsis,  diagnose the malformed function.
           Diag(Tok, diag::err_ellipsis_first_arg);
           isVariadic = false;       // Treat this like 'void()'.
         }
@@ -527,3 +527,56 @@
   ConsumeParen();
 }
 
+
+/// [C90]   direct-declarator '[' constant-expression[opt] ']'
+/// [C99]   direct-declarator '[' type-qual-list[opt] assignment-expr[opt] ']'
+/// [C99]   direct-declarator '[' 'static' type-qual-list[opt] assign-expr ']'
+/// [C99]   direct-declarator '[' type-qual-list 'static' assignment-expr ']'
+/// [C99]   direct-declarator '[' type-qual-list[opt] '*' ']'
+void Parser::ParseBracketDeclarator(Declarator &D) {
+  SourceLocation StartLoc = Tok.getLocation();
+  ConsumeSquare();
+  
+  // If valid, this location is the position where we read the 'static' keyword.
+  SourceLocation StaticLoc;
+  if (Tok.getKind() == tok::kw_static) {
+    StaticLoc = Tok.getLocation();
+    ConsumeToken();
+  }
+  
+  // If there is a type-qualifier-list, read it now.
+  DeclSpec DS;
+  ParseTypeQualifierListOpt(DS);
+  // TODO: do something with DS.
+  
+  // If we haven't already read 'static', check to see if there is one after the
+  // type-qualifier-list.
+  if (!StaticLoc.isValid() && Tok.getKind() == tok::kw_static) {
+    StaticLoc = Tok.getLocation();
+    ConsumeToken();
+  }
+  
+  // Handle "direct-declarator [ type-qual-list[opt] * ]".
+  // Check that the ']' token is present to avoid incorrectly parsing
+  // expressions starting with '*' as [*].
+  bool isStar = false;
+  if (Tok.getKind() == tok::star /*FIXME: && nexttok == tok::r_square*/) {
+    if (StaticLoc.isValid())
+      Diag(StaticLoc, diag::err_unspecified_vla_size_with_static);
+    StaticLoc = SourceLocation();  // Drop the static.
+    isStar = true;
+    ConsumeToken();
+  } else if (Tok.getKind() != tok::r_square) {
+    // Parse the assignment-expression now.
+    assert(0 && "expr parsing not impl yet!");
+  }
+  
+  ConsumeSquare();
+  
+  // If C99 isn't enabled, emit an ext-warn if the arg list wasn't empty and if
+  // it was not a constant expression.
+  if (!getLang().C99) {
+    // TODO: check C90 array constant exprness.
+  }
+}
+

Modified: cfe/cfe/trunk/include/clang/Basic/DiagnosticKinds.def
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/include/clang/Basic/DiagnosticKinds.def?rev=38828&r1=38827&r2=38828&view=diff

==============================================================================
--- cfe/cfe/trunk/include/clang/Basic/DiagnosticKinds.def (original)
+++ cfe/cfe/trunk/include/clang/Basic/DiagnosticKinds.def Wed Jul 11 11:24:59 2007
@@ -271,5 +271,7 @@
      "'__thread %s' is invalid")
 DIAG(err_ellipsis_first_arg, ERROR,
      "ISO C requires a named argument before '...'")
+DIAG(err_unspecified_vla_size_with_static, ERROR,
+     "'static' may not be used with an unspecified variable length array size")
 
 #undef DIAG

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

==============================================================================
--- cfe/cfe/trunk/include/clang/Parse/Parser.h (original)
+++ cfe/cfe/trunk/include/clang/Parse/Parser.h Wed Jul 11 11:24:59 2007
@@ -68,6 +68,8 @@
     assert(Tok.getKind() != tok::string_literal &&
            Tok.getKind() != tok::l_paren &&
            Tok.getKind() != tok::r_paren &&
+           Tok.getKind() != tok::l_square &&
+           Tok.getKind() != tok::r_square &&
            "Should consume special tokens with Consume*Token");
     PP.Lex(Tok);
   }
@@ -80,6 +82,14 @@
     PP.Lex(Tok);
   }
 
+  /// ConsumeSquare -  This consume method keeps the bracket count up-to-date.
+  ///
+  void ConsumeSquare() {
+    assert((Tok.getKind() == tok::l_square ||
+            Tok.getKind() == tok::r_square) && "wrong consume method");
+    PP.Lex(Tok);
+  }
+  
 private:
   //===--------------------------------------------------------------------===//
   // C99 6.9: External Definitions.
@@ -96,7 +106,7 @@
   void ParseTypeQualifierListOpt(DeclSpec &DS);
   void ParseDirectDeclarator(Declarator &D);
   void ParseParenDeclarator(Declarator &D);
-  
+  void ParseBracketDeclarator(Declarator &D);
 };
 
 }  // end namespace clang





More information about the cfe-commits mailing list