[cfe-commits] r38925 - in /cfe/cfe/trunk/Parse: ParseDecl.cpp ParseStmt.cpp
sabre at cs.uiuc.edu
sabre at cs.uiuc.edu
Wed Jul 11 09:25:50 PDT 2007
Author: sabre
Date: Wed Jul 11 11:25:50 2007
New Revision: 38925
URL: http://llvm.org/viewvc/llvm-project?rev=38925&view=rev
Log:
Parse attributes in all places allowed.
Modified:
cfe/cfe/trunk/Parse/ParseDecl.cpp
cfe/cfe/trunk/Parse/ParseStmt.cpp
Modified: cfe/cfe/trunk/Parse/ParseDecl.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/Parse/ParseDecl.cpp?rev=38925&r1=38924&r2=38925&view=diff
==============================================================================
--- cfe/cfe/trunk/Parse/ParseDecl.cpp (original)
+++ cfe/cfe/trunk/Parse/ParseDecl.cpp Wed Jul 11 11:25:50 2007
@@ -163,6 +163,7 @@
/// specifier-qualifier-list:
/// type-specifier specifier-qualifier-list[opt]
/// type-qualifier specifier-qualifier-list[opt]
+/// [GNU] attributes specifier-qualifier-list[opt]
///
void Parser::ParseSpecifierQualifierList(DeclSpec &DS) {
/// specifier-qualifier-list is a subset of declaration-specifiers. Just
@@ -193,7 +194,7 @@
/// type-specifier declaration-specifiers[opt]
/// type-qualifier declaration-specifiers[opt]
/// [C99] function-specifier declaration-specifiers[opt]
-/// [GNU] attributes declaration-specifiers[opt] [TODO]
+/// [GNU] attributes declaration-specifiers[opt]
///
/// storage-class-specifier: [C99 6.7.1]
/// 'typedef'
@@ -254,6 +255,11 @@
// specifiers. First verify that DeclSpec's are consistent.
DS.Finish(StartLoc, Diags, getLang());
return;
+
+ // GNU attributes support.
+ case tok::kw___attribute:
+ ParseAttributes();
+ break;
// storage-class-specifier
case tok::kw_typedef:
@@ -376,6 +382,9 @@
/// struct-or-union-specifier: [C99 6.7.2.1]
/// struct-or-union identifier[opt] '{' struct-contents '}'
/// struct-or-union identifier
+/// [GNU] struct-or-union attributes[opt] identifier[opt] '{' struct-contents
+/// '}' attributes[opt]
+/// [GNU] struct-or-union attributes[opt] identifier
/// struct-or-union:
/// 'struct'
/// 'union'
@@ -394,9 +403,12 @@
/// struct-declarator-list:
/// struct-declarator
/// struct-declarator-list ',' struct-declarator
+/// [GNU] struct-declarator-list ',' attributes[opt] struct-declarator
/// struct-declarator:
/// declarator
+/// [GNU] declarator attributes[opt]
/// declarator[opt] ':' constant-expression
+/// [GNU] declarator[opt] ':' constant-expression attributes[opt]
///
void Parser::ParseStructUnionSpecifier(DeclSpec &DS) {
assert((Tok.getKind() == tok::kw_struct ||
@@ -404,7 +416,11 @@
SourceLocation Start = Tok.getLocation();
bool isUnion = Tok.getKind() == tok::kw_union;
ConsumeToken();
-
+
+ // If attributes exist after tag, parse them.
+ if (Tok.getKind() == tok::kw___attribute)
+ ParseAttributes();
+
// Must have either 'struct name' or 'struct {...}'.
if (Tok.getKind() != tok::identifier &&
Tok.getKind() != tok::l_brace) {
@@ -455,6 +471,10 @@
// Process it.
}
}
+
+ // If attributes exist after the declarator, parse them.
+ if (Tok.getKind() == tok::kw___attribute)
+ ParseAttributes();
// TODO: install declarator.
@@ -468,6 +488,10 @@
// Parse the next declarator.
DeclaratorInfo.clear();
+
+ // Attributes are only allowed on the second declarator.
+ if (Tok.getKind() == tok::kw___attribute)
+ ParseAttributes();
}
}
@@ -481,6 +505,10 @@
}
MatchRHSPunctuation(tok::r_brace, LBraceLoc, "{",diag::err_expected_rbrace);
+
+ // If attributes exist after struct contents, parse them.
+ if (Tok.getKind() == tok::kw___attribute)
+ ParseAttributes();
}
const char *PrevSpec = 0;
@@ -494,9 +522,10 @@
/// enum-specifier: [C99 6.7.2.2]
/// 'enum' identifier[opt] '{' enumerator-list '}'
/// [C99] 'enum' identifier[opt] '{' enumerator-list ',' '}'
-/// [GNU] 'enum' identifier[opt] '{' enumerator-list '}' attributes [TODO]
-/// [GNU] 'enum' identifier[opt] '{' enumerator-list ',' '}' attributes [TODO]
+/// [GNU] 'enum' attributes[opt] identifier[opt] '{' enumerator-list ',' [opt]
+/// '}' attributes[opt]
/// 'enum' identifier
+/// [GNU] 'enum' attributes[opt] identifier
/// enumerator-list:
/// enumerator
/// enumerator-list ',' enumerator
@@ -511,6 +540,9 @@
SourceLocation Start = Tok.getLocation();
ConsumeToken();
+ if (Tok.getKind() == tok::kw___attribute)
+ ParseAttributes();
+
// Must have either 'enum name' or 'enum {...}'.
if (Tok.getKind() != tok::identifier &&
Tok.getKind() != tok::l_brace) {
@@ -550,6 +582,10 @@
// Eat the }.
MatchRHSPunctuation(tok::r_brace, LBraceLoc, "{",
diag::err_expected_rbrace);
+
+ // If attributes exist after the identifier list, parse them.
+ if (Tok.getKind() == tok::kw___attribute)
+ ParseAttributes();
}
// TODO: semantic analysis on the declspec for enums.
@@ -565,6 +601,8 @@
bool Parser::isTypeSpecifierQualifier() const {
switch (Tok.getKind()) {
default: return false;
+ // GNU attributes support.
+ case tok::kw___attribute:
// type-specifiers
case tok::kw_short:
case tok::kw_long:
@@ -658,9 +696,9 @@
/// ParseTypeQualifierListOpt
/// type-qualifier-list: [C99 6.7.5]
/// type-qualifier
-/// [GNU] attributes [TODO]
+/// [GNU] attributes
/// type-qualifier-list type-qualifier
-/// [GNU] type-qualifier-list attributes [TODO]
+/// [GNU] type-qualifier-list attributes
///
void Parser::ParseTypeQualifierListOpt(DeclSpec &DS) {
SourceLocation StartLoc = Tok.getLocation();
@@ -670,11 +708,10 @@
switch (Tok.getKind()) {
default:
- // If this is not a declaration specifier token, we're done reading decl
- // specifiers. First verify that DeclSpec's are consistent.
+ // If this is not a type-qualifier token, we're done reading type
+ // qualifiers. First verify that DeclSpec's are consistent.
DS.Finish(StartLoc, Diags, getLang());
return;
- // TODO: attributes.
case tok::kw_const:
isInvalid = DS.SetTypeQual(DeclSpec::TQ_const , PrevSpec, getLang())*2;
break;
@@ -684,6 +721,10 @@
case tok::kw_restrict:
isInvalid = DS.SetTypeQual(DeclSpec::TQ_restrict, PrevSpec, getLang())*2;
break;
+
+ case tok::kw___attribute:
+ ParseAttributes();
+ break;
}
// If the specifier combination wasn't legal, issue a diagnostic.
@@ -759,7 +800,7 @@
ConsumeToken();
} else if (Tok.getKind() == tok::l_paren) {
// direct-declarator: '(' declarator ')'
- // direct-declarator: '(' attributes declarator ')' [TODO]
+ // direct-declarator: '(' attributes declarator ')'
// Example: 'char (*X)' or 'int (*XX)(void)'
ParseParenDeclarator(D);
} else if (D.mayOmitIdentifier()) {
@@ -802,9 +843,9 @@
///
/// parameter-declaration: [C99 6.7.5]
/// declaration-specifiers declarator
-/// [GNU] declaration-specifiers declarator attributes [TODO]
+/// [GNU] declaration-specifiers declarator attributes
/// declaration-specifiers abstract-declarator[opt]
-/// [GNU] declaration-specifiers abstract-declarator[opt] attributes [TODO]
+/// [GNU] declaration-specifiers abstract-declarator[opt] attributes
///
/// identifier-list: [C99 6.7.5]
/// identifier
@@ -838,8 +879,11 @@
// If this is a grouping paren, handle:
// direct-declarator: '(' declarator ')'
- // direct-declarator: '(' attributes declarator ')' [TODO]
+ // direct-declarator: '(' attributes declarator ')'
if (isGrouping) {
+ if (Tok.getKind() == tok::kw___attribute)
+ ParseAttributes();
+
ParseDeclaratorInternal(D);
// Match the ')'.
MatchRHSPunctuation(tok::r_paren, StartLoc, "(",
@@ -930,6 +974,10 @@
Declarator DeclaratorInfo(DS, Declarator::PrototypeContext);
ParseDeclarator(DeclaratorInfo);
+ // Parse GNU attributes, if present.
+ if (Tok.getKind() == tok::kw___attribute)
+ ParseAttributes();
+
// TODO: do something with the declarator, if it is valid.
// If the next token is a comma, consume it and keep reading arguments.
Modified: cfe/cfe/trunk/Parse/ParseStmt.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/Parse/ParseStmt.cpp?rev=38925&r1=38924&r2=38925&view=diff
==============================================================================
--- cfe/cfe/trunk/Parse/ParseStmt.cpp (original)
+++ cfe/cfe/trunk/Parse/ParseStmt.cpp Wed Jul 11 11:25:50 2007
@@ -178,6 +178,7 @@
///
/// labeled-statement:
/// identifier ':' statement
+/// [GNU] identifier ':' attributes[opt] statement
/// declaration (if !OnlyStatement)
/// expression[opt] ';'
///
@@ -191,6 +192,11 @@
// identifier ':' statement
if (Tok.getKind() == tok::colon) {
ConsumeToken();
+
+ // Read label attributes, if present.
+ if (Tok.getKind() == tok::kw___attribute)
+ ParseAttributes();
+
ParseStatement();
return;
}
More information about the cfe-commits
mailing list