ParseDeclCXX.cpp revision 49f40bd0c9c9de5e74727774fec429b47d36303a
18f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner//===--- ParseDeclCXX.cpp - C++ Declaration Parsing -----------------------===//
28f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner//
38f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner//                     The LLVM Compiler Infrastructure
48f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner//
50bc735ffcfb223c0186419547abaa5c84482663eChris Lattner// This file is distributed under the University of Illinois Open Source
60bc735ffcfb223c0186419547abaa5c84482663eChris Lattner// License. See LICENSE.TXT for details.
78f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner//
88f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner//===----------------------------------------------------------------------===//
98f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner//
108f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner//  This file implements the C++ Declaration portions of the Parser interfaces.
118f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner//
128f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner//===----------------------------------------------------------------------===//
138f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner
140c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson#include "clang/Basic/OperatorKinds.h"
151b7f89846f10681ce3cbe89ef5d60691d55bd918Douglas Gregor#include "clang/Parse/Parser.h"
16500d3297d2a21edeac4d46cbcbe21bc2352c2a28Chris Lattner#include "clang/Parse/ParseDiagnostic.h"
17e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor#include "clang/Parse/DeclSpec.h"
188f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner#include "clang/Parse/Scope.h"
19bc8d56496a6ecdba14769df03d75c001184f8c54Chris Lattner#include "ExtensionRAIIObject.h"
208f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattnerusing namespace clang;
218f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner
228f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner/// ParseNamespace - We know that the current token is a namespace keyword. This
238f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner/// may either be a top level namespace or a block-level namespace alias.
248f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///
258f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///       namespace-definition: [C++ 7.3: basic.namespace]
268f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///         named-namespace-definition
278f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///         unnamed-namespace-definition
288f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///
298f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///       unnamed-namespace-definition:
308f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///         'namespace' attributes[opt] '{' namespace-body '}'
318f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///
328f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///       named-namespace-definition:
338f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///         original-namespace-definition
348f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///         extension-namespace-definition
358f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///
368f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///       original-namespace-definition:
378f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///         'namespace' identifier attributes[opt] '{' namespace-body '}'
388f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///
398f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///       extension-namespace-definition:
408f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///         'namespace' original-namespace-name '{' namespace-body '}'
411eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump///
428f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///       namespace-alias-definition:  [C++ 7.3.2: namespace.alias]
438f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///         'namespace' identifier '=' qualified-namespace-specifier ';'
448f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner///
4597144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris LattnerParser::DeclPtrTy Parser::ParseNamespace(unsigned Context,
4697144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner                                         SourceLocation &DeclEnd) {
4704d6666eee19bbf25bdfcb8e79eb8b00ace03f0cChris Lattner  assert(Tok.is(tok::kw_namespace) && "Not a namespace!");
488f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner  SourceLocation NamespaceLoc = ConsumeToken();  // eat the 'namespace'.
491eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
5049f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor  if (Tok.is(tok::code_completion)) {
5149f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor    Actions.CodeCompleteNamespaceDecl(CurScope);
5249f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor    ConsumeToken();
5349f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor  }
5449f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor
558f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner  SourceLocation IdentLoc;
568f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner  IdentifierInfo *Ident = 0;
576a588dd230c14a364d222d6057bbcf11afbd9ffdDouglas Gregor
586a588dd230c14a364d222d6057bbcf11afbd9ffdDouglas Gregor  Token attrTok;
591eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
6004d6666eee19bbf25bdfcb8e79eb8b00ace03f0cChris Lattner  if (Tok.is(tok::identifier)) {
618f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner    Ident = Tok.getIdentifierInfo();
628f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner    IdentLoc = ConsumeToken();  // eat the identifier.
638f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner  }
641eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
658f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner  // Read label attributes, if present.
66b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris Lattner  Action::AttrTy *AttrList = 0;
676a588dd230c14a364d222d6057bbcf11afbd9ffdDouglas Gregor  if (Tok.is(tok::kw___attribute)) {
686a588dd230c14a364d222d6057bbcf11afbd9ffdDouglas Gregor    attrTok = Tok;
696a588dd230c14a364d222d6057bbcf11afbd9ffdDouglas Gregor
708f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner    // FIXME: save these somewhere.
718f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner    AttrList = ParseAttributes();
726a588dd230c14a364d222d6057bbcf11afbd9ffdDouglas Gregor  }
731eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
746a588dd230c14a364d222d6057bbcf11afbd9ffdDouglas Gregor  if (Tok.is(tok::equal)) {
756a588dd230c14a364d222d6057bbcf11afbd9ffdDouglas Gregor    if (AttrList)
766a588dd230c14a364d222d6057bbcf11afbd9ffdDouglas Gregor      Diag(attrTok, diag::err_unexpected_namespace_attributes_alias);
776a588dd230c14a364d222d6057bbcf11afbd9ffdDouglas Gregor
7897144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner    return ParseNamespaceAlias(NamespaceLoc, IdentLoc, Ident, DeclEnd);
796a588dd230c14a364d222d6057bbcf11afbd9ffdDouglas Gregor  }
801eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
815144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner  if (Tok.isNot(tok::l_brace)) {
821eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    Diag(Tok, Ident ? diag::err_expected_lbrace :
835144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner         diag::err_expected_ident_lbrace);
845144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner    return DeclPtrTy();
855144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner  }
861eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
875144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner  SourceLocation LBrace = ConsumeBrace();
882d1c5d313cd0c229cc614e74baa4c5756a4b46f4Argyrios Kyrtzidis
895144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner  // Enter a scope for the namespace.
905144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner  ParseScope NamespaceScope(this, Scope::DeclScope);
912d1c5d313cd0c229cc614e74baa4c5756a4b46f4Argyrios Kyrtzidis
925144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner  DeclPtrTy NamespcDecl =
935144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner    Actions.ActOnStartNamespaceDef(CurScope, IdentLoc, Ident, LBrace);
942d1c5d313cd0c229cc614e74baa4c5756a4b46f4Argyrios Kyrtzidis
955144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner  PrettyStackTraceActionsDecl CrashInfo(NamespcDecl, NamespaceLoc, Actions,
965144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner                                        PP.getSourceManager(),
975144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner                                        "parsing namespace");
981eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
995144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner  while (Tok.isNot(tok::r_brace) && Tok.isNot(tok::eof))
1005144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner    ParseExternalDeclaration();
1011eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1025144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner  // Leave the namespace scope.
1035144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner  NamespaceScope.Exit();
1048ba5d792032f475eb653ca6340eb51068df0fa90Argyrios Kyrtzidis
10597144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner  SourceLocation RBraceLoc = MatchRHSPunctuation(tok::r_brace, LBrace);
10697144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner  Actions.ActOnFinishNamespaceDef(NamespcDecl, RBraceLoc);
1072d1c5d313cd0c229cc614e74baa4c5756a4b46f4Argyrios Kyrtzidis
10897144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner  DeclEnd = RBraceLoc;
1095144832ae62cf97543b274d4bb88d5f74d0f7a20Chris Lattner  return NamespcDecl;
1108f08cb7d0b97786b17ef05e05caa55aad4d6bd39Chris Lattner}
111c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner
112f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson/// ParseNamespaceAlias - Parse the part after the '=' in a namespace
113f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson/// alias definition.
114f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson///
11503bd5a1e9a54b62b10ae8aeb6eb5245e2031d98bAnders CarlssonParser::DeclPtrTy Parser::ParseNamespaceAlias(SourceLocation NamespaceLoc,
1161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                              SourceLocation AliasLoc,
11797144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner                                              IdentifierInfo *Alias,
11897144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner                                              SourceLocation &DeclEnd) {
119f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson  assert(Tok.is(tok::equal) && "Not equal token");
1201eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
121f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson  ConsumeToken(); // eat the '='.
1221eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
12349f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor  if (Tok.is(tok::code_completion)) {
12449f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor    Actions.CodeCompleteNamespaceAliasDecl(CurScope);
12549f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor    ConsumeToken();
12649f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor  }
12749f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor
128f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson  CXXScopeSpec SS;
129f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson  // Parse (optional) nested-name-specifier.
1302dd078ae50ff7be1fb25ebeedde45e9ab691a4f0Douglas Gregor  ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/0, false);
131f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson
132f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson  if (SS.isInvalid() || Tok.isNot(tok::identifier)) {
133f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson    Diag(Tok, diag::err_expected_namespace_name);
134f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson    // Skip to end of the definition and eat the ';'.
135f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson    SkipUntil(tok::semi);
136b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris Lattner    return DeclPtrTy();
137f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson  }
138f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson
139f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson  // Parse identifier.
14003bd5a1e9a54b62b10ae8aeb6eb5245e2031d98bAnders Carlsson  IdentifierInfo *Ident = Tok.getIdentifierInfo();
14103bd5a1e9a54b62b10ae8aeb6eb5245e2031d98bAnders Carlsson  SourceLocation IdentLoc = ConsumeToken();
1421eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
143f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson  // Eat the ';'.
14497144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner  DeclEnd = Tok.getLocation();
1456869d8ea1bb7d191b5b290f5a55ee74f2174829aChris Lattner  ExpectAndConsume(tok::semi, diag::err_expected_semi_after_namespace_name,
1466869d8ea1bb7d191b5b290f5a55ee74f2174829aChris Lattner                   "", tok::semi);
1471eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1481eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  return Actions.ActOnNamespaceAliasDef(CurScope, NamespaceLoc, AliasLoc, Alias,
14903bd5a1e9a54b62b10ae8aeb6eb5245e2031d98bAnders Carlsson                                        SS, IdentLoc, Ident);
150f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson}
151f67606ae2febe3bb0718f05040c6c4bc2c2c3276Anders Carlsson
152c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner/// ParseLinkage - We know that the current token is a string_literal
153c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner/// and just before that, that extern was seen.
154c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner///
155c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner///       linkage-specification: [C++ 7.5p2: dcl.link]
156c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner///         'extern' string-literal '{' declaration-seq[opt] '}'
157c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner///         'extern' string-literal declaration
158c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner///
159b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris LattnerParser::DeclPtrTy Parser::ParseLinkage(unsigned Context) {
160c19923dda3d28f67aab4726cd40bb07032758383Douglas Gregor  assert(Tok.is(tok::string_literal) && "Not a string literal!");
161c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner  llvm::SmallVector<char, 8> LangBuffer;
162c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner  // LangBuffer is guaranteed to be big enough.
163c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner  LangBuffer.resize(Tok.getLength());
164c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner  const char *LangBufPtr = &LangBuffer[0];
165c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner  unsigned StrSize = PP.getSpelling(Tok, LangBufPtr);
166c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner
167c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner  SourceLocation Loc = ConsumeStringToken();
168c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner
169074149e11baf5f7db12f84efd5c34ba6e35d5cdfDouglas Gregor  ParseScope LinkageScope(this, Scope::DeclScope);
1701eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  DeclPtrTy LinkageSpec
1711eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    = Actions.ActOnStartLinkageSpecification(CurScope,
172074149e11baf5f7db12f84efd5c34ba6e35d5cdfDouglas Gregor                                             /*FIXME: */SourceLocation(),
173074149e11baf5f7db12f84efd5c34ba6e35d5cdfDouglas Gregor                                             Loc, LangBufPtr, StrSize,
1741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                       Tok.is(tok::l_brace)? Tok.getLocation()
175074149e11baf5f7db12f84efd5c34ba6e35d5cdfDouglas Gregor                                                           : SourceLocation());
176074149e11baf5f7db12f84efd5c34ba6e35d5cdfDouglas Gregor
177074149e11baf5f7db12f84efd5c34ba6e35d5cdfDouglas Gregor  if (Tok.isNot(tok::l_brace)) {
178074149e11baf5f7db12f84efd5c34ba6e35d5cdfDouglas Gregor    ParseDeclarationOrFunctionDefinition();
1791eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    return Actions.ActOnFinishLinkageSpecification(CurScope, LinkageSpec,
180074149e11baf5f7db12f84efd5c34ba6e35d5cdfDouglas Gregor                                                   SourceLocation());
1811eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  }
182f44515a49b549171dc3ee9faa6281b72609da563Douglas Gregor
183f44515a49b549171dc3ee9faa6281b72609da563Douglas Gregor  SourceLocation LBrace = ConsumeBrace();
184f44515a49b549171dc3ee9faa6281b72609da563Douglas Gregor  while (Tok.isNot(tok::r_brace) && Tok.isNot(tok::eof)) {
185074149e11baf5f7db12f84efd5c34ba6e35d5cdfDouglas Gregor    ParseExternalDeclaration();
186f44515a49b549171dc3ee9faa6281b72609da563Douglas Gregor  }
187c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner
188f44515a49b549171dc3ee9faa6281b72609da563Douglas Gregor  SourceLocation RBrace = MatchRHSPunctuation(tok::r_brace, LBrace);
189074149e11baf5f7db12f84efd5c34ba6e35d5cdfDouglas Gregor  return Actions.ActOnFinishLinkageSpecification(CurScope, LinkageSpec, RBrace);
190c6fdc34ac0183bfa03d65f317c78b7bdac52897eChris Lattner}
191e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
192f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor/// ParseUsingDirectiveOrDeclaration - Parse C++ using using-declaration or
193f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor/// using-directive. Assumes that current token is 'using'.
19497144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris LattnerParser::DeclPtrTy Parser::ParseUsingDirectiveOrDeclaration(unsigned Context,
19597144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner                                                     SourceLocation &DeclEnd) {
196f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  assert(Tok.is(tok::kw_using) && "Not using token");
197f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor
198f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  // Eat 'using'.
199f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  SourceLocation UsingLoc = ConsumeToken();
200f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor
20149f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor  if (Tok.is(tok::code_completion)) {
20249f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor    Actions.CodeCompleteUsing(CurScope);
20349f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor    ConsumeToken();
20449f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor  }
20549f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor
2062f27477a29b6f5365ee545c1cac666cc8b95f518Chris Lattner  if (Tok.is(tok::kw_namespace))
207f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor    // Next token after 'using' is 'namespace' so it must be using-directive
20897144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner    return ParseUsingDirective(Context, UsingLoc, DeclEnd);
2092f27477a29b6f5365ee545c1cac666cc8b95f518Chris Lattner
2102f27477a29b6f5365ee545c1cac666cc8b95f518Chris Lattner  // Otherwise, it must be using-declaration.
21197144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner  return ParseUsingDeclaration(Context, UsingLoc, DeclEnd);
212f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor}
213f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor
214f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor/// ParseUsingDirective - Parse C++ using-directive, assumes
215f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor/// that current token is 'namespace' and 'using' was already parsed.
216f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor///
217f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor///       using-directive: [C++ 7.3.p4: namespace.udir]
218f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor///        'using' 'namespace' ::[opt] nested-name-specifier[opt]
219f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor///                 namespace-name ;
220f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor/// [GNU] using-directive:
221f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor///        'using' 'namespace' ::[opt] nested-name-specifier[opt]
222f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor///                 namespace-name attributes[opt] ;
223f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor///
224b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris LattnerParser::DeclPtrTy Parser::ParseUsingDirective(unsigned Context,
22597144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner                                              SourceLocation UsingLoc,
22697144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner                                              SourceLocation &DeclEnd) {
227f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  assert(Tok.is(tok::kw_namespace) && "Not 'namespace' token");
228f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor
229f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  // Eat 'namespace'.
230f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  SourceLocation NamespcLoc = ConsumeToken();
231f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor
23249f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor  if (Tok.is(tok::code_completion)) {
23349f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor    Actions.CodeCompleteUsingDirective(CurScope);
23449f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor    ConsumeToken();
23549f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor  }
23649f40bd0c9c9de5e74727774fec429b47d36303aDouglas Gregor
237f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  CXXScopeSpec SS;
238f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  // Parse (optional) nested-name-specifier.
2392dd078ae50ff7be1fb25ebeedde45e9ab691a4f0Douglas Gregor  ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/0, false);
240f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor
241f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  AttributeList *AttrList = 0;
242f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  IdentifierInfo *NamespcName = 0;
243f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  SourceLocation IdentLoc = SourceLocation();
244f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor
245f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  // Parse namespace-name.
246823c44e6d73141f642e207980b4021ddcf09897bChris Lattner  if (SS.isInvalid() || Tok.isNot(tok::identifier)) {
247f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor    Diag(Tok, diag::err_expected_namespace_name);
248f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor    // If there was invalid namespace name, skip to end of decl, and eat ';'.
249f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor    SkipUntil(tok::semi);
250f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor    // FIXME: Are there cases, when we would like to call ActOnUsingDirective?
251b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris Lattner    return DeclPtrTy();
252f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  }
2531eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
254823c44e6d73141f642e207980b4021ddcf09897bChris Lattner  // Parse identifier.
255823c44e6d73141f642e207980b4021ddcf09897bChris Lattner  NamespcName = Tok.getIdentifierInfo();
256823c44e6d73141f642e207980b4021ddcf09897bChris Lattner  IdentLoc = ConsumeToken();
2571eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
258823c44e6d73141f642e207980b4021ddcf09897bChris Lattner  // Parse (optional) attributes (most likely GNU strong-using extension).
259823c44e6d73141f642e207980b4021ddcf09897bChris Lattner  if (Tok.is(tok::kw___attribute))
260823c44e6d73141f642e207980b4021ddcf09897bChris Lattner    AttrList = ParseAttributes();
2611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
262823c44e6d73141f642e207980b4021ddcf09897bChris Lattner  // Eat ';'.
26397144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner  DeclEnd = Tok.getLocation();
2646869d8ea1bb7d191b5b290f5a55ee74f2174829aChris Lattner  ExpectAndConsume(tok::semi,
2656869d8ea1bb7d191b5b290f5a55ee74f2174829aChris Lattner                   AttrList ? diag::err_expected_semi_after_attribute_list :
2666869d8ea1bb7d191b5b290f5a55ee74f2174829aChris Lattner                   diag::err_expected_semi_after_namespace_name, "", tok::semi);
267f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor
268f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor  return Actions.ActOnUsingDirective(CurScope, UsingLoc, NamespcLoc, SS,
269823c44e6d73141f642e207980b4021ddcf09897bChris Lattner                                      IdentLoc, NamespcName, AttrList);
270f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor}
271f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor
272f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor/// ParseUsingDeclaration - Parse C++ using-declaration. Assumes that
273f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor/// 'using' was already seen.
274f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor///
275f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor///     using-declaration: [C++ 7.3.p3: namespace.udecl]
276f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor///       'using' 'typename'[opt] ::[opt] nested-name-specifier
2779cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor///               unqualified-id
2789cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor///       'using' :: unqualified-id
279f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor///
280b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris LattnerParser::DeclPtrTy Parser::ParseUsingDeclaration(unsigned Context,
28197144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner                                                SourceLocation UsingLoc,
282595adc1795cc2c079ef5876100e01acd10a0504aAnders Carlsson                                                SourceLocation &DeclEnd,
283595adc1795cc2c079ef5876100e01acd10a0504aAnders Carlsson                                                AccessSpecifier AS) {
2849cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  CXXScopeSpec SS;
2859cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  bool IsTypeName;
2869cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor
2879cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  // Ignore optional 'typename'.
2889cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  if (Tok.is(tok::kw_typename)) {
2899cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    ConsumeToken();
2909cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    IsTypeName = true;
2919cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  }
2929cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  else
2939cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    IsTypeName = false;
2949cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor
2959cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  // Parse nested-name-specifier.
2962dd078ae50ff7be1fb25ebeedde45e9ab691a4f0Douglas Gregor  ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/0, false);
2979cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor
2989cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  AttributeList *AttrList = 0;
2999cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor
3009cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  // Check nested-name specifier.
3019cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  if (SS.isInvalid()) {
3029cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    SkipUntil(tok::semi);
3039cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    return DeclPtrTy();
3049cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  }
3059cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  if (Tok.is(tok::annot_template_id)) {
30673b39cf02eaa346c6d7a76c32bf13759de7516dbAnders Carlsson    // C++0x N2914 [namespace.udecl]p5:
3071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    // A using-declaration shall not name a template-id.
30873b39cf02eaa346c6d7a76c32bf13759de7516dbAnders Carlsson    Diag(Tok, diag::err_using_decl_can_not_refer_to_template_spec);
3099cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    SkipUntil(tok::semi);
3109cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    return DeclPtrTy();
3119cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  }
3121eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
3130c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson  IdentifierInfo *TargetName = 0;
3140c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson  OverloadedOperatorKind Op = OO_None;
3150c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson  SourceLocation IdentLoc;
3161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
3170c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson  if (Tok.is(tok::kw_operator)) {
3180c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson    IdentLoc = Tok.getLocation();
3190c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson
3200c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson    Op = TryParseOperatorFunctionId();
3210c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson    if (!Op) {
3220c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson      // If there was an invalid operator, skip to end of decl, and eat ';'.
3230c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson      SkipUntil(tok::semi);
3240c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson      return DeclPtrTy();
3250c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson    }
3260c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson  } else if (Tok.is(tok::identifier)) {
3270c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson    // Parse identifier.
3280c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson    TargetName = Tok.getIdentifierInfo();
3290c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson    IdentLoc = ConsumeToken();
3300c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson  } else {
3310c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson    // FIXME: Use a better diagnostic here.
3329cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    Diag(Tok, diag::err_expected_ident_in_using);
3330c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson
3349cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    // If there was invalid identifier, skip to end of decl, and eat ';'.
3359cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    SkipUntil(tok::semi);
3369cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    return DeclPtrTy();
3379cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  }
3381eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
3399cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  // Parse (optional) attributes (most likely GNU strong-using extension).
3409cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  if (Tok.is(tok::kw___attribute))
3419cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    AttrList = ParseAttributes();
3421eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
3439cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  // Eat ';'.
3449cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  DeclEnd = Tok.getLocation();
3459cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  ExpectAndConsume(tok::semi, diag::err_expected_semi_after,
3469cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor                   AttrList ? "attributes list" : "namespace name", tok::semi);
3479cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor
348595adc1795cc2c079ef5876100e01acd10a0504aAnders Carlsson  return Actions.ActOnUsingDeclaration(CurScope, AS, UsingLoc, SS,
3490c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson                                       IdentLoc, TargetName, Op,
3500c6139d0c2497c4e8780340e0dc097de041f248eAnders Carlsson                                       AttrList, IsTypeName);
351f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor}
352f780abc21c39cd4731b9e38f2d2d9f7d1510bd7bDouglas Gregor
353511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson/// ParseStaticAssertDeclaration - Parse C++0x static_assert-declaratoion.
354511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson///
355511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson///      static_assert-declaration:
356511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson///        static_assert ( constant-expression  ,  string-literal  ) ;
357511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson///
35897144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris LattnerParser::DeclPtrTy Parser::ParseStaticAssertDeclaration(SourceLocation &DeclEnd){
359511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  assert(Tok.is(tok::kw_static_assert) && "Not a static_assert declaration");
360511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  SourceLocation StaticAssertLoc = ConsumeToken();
3611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
362511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  if (Tok.isNot(tok::l_paren)) {
363511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson    Diag(Tok, diag::err_expected_lparen);
364b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris Lattner    return DeclPtrTy();
365511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  }
3661eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
367511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  SourceLocation LParenLoc = ConsumeParen();
368e0762c92110dfdcdd207db461a4ea17afd168f1eDouglas Gregor
369511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  OwningExprResult AssertExpr(ParseConstantExpression());
370511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  if (AssertExpr.isInvalid()) {
371511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson    SkipUntil(tok::semi);
372b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris Lattner    return DeclPtrTy();
373511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  }
3741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
375ad5f960f9e42568a87bf5e03dce7ad878f9ba6daAnders Carlsson  if (ExpectAndConsume(tok::comma, diag::err_expected_comma, "", tok::semi))
376b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris Lattner    return DeclPtrTy();
377ad5f960f9e42568a87bf5e03dce7ad878f9ba6daAnders Carlsson
378511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  if (Tok.isNot(tok::string_literal)) {
379511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson    Diag(Tok, diag::err_expected_string_literal);
380511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson    SkipUntil(tok::semi);
381b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris Lattner    return DeclPtrTy();
382511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  }
3831eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
384511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  OwningExprResult AssertMessage(ParseStringLiteralExpression());
3851eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  if (AssertMessage.isInvalid())
386b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris Lattner    return DeclPtrTy();
387511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson
38894b15fbc3a10cdfb1639528a8a773b66a1e7cd9eAnders Carlsson  MatchRHSPunctuation(tok::r_paren, LParenLoc);
3891eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
39097144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner  DeclEnd = Tok.getLocation();
391511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  ExpectAndConsume(tok::semi, diag::err_expected_semi_after_static_assert);
392511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson
3931eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  return Actions.ActOnStaticAssertDeclaration(StaticAssertLoc, move(AssertExpr),
39494b15fbc3a10cdfb1639528a8a773b66a1e7cd9eAnders Carlsson                                              move(AssertMessage));
395511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson}
396511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson
3976fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson/// ParseDecltypeSpecifier - Parse a C++0x decltype specifier.
3986fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson///
3996fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson/// 'decltype' ( expression )
4006fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson///
4016fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlssonvoid Parser::ParseDecltypeSpecifier(DeclSpec &DS) {
4026fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  assert(Tok.is(tok::kw_decltype) && "Not a decltype specifier");
4036fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson
4046fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  SourceLocation StartLoc = ConsumeToken();
4056fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  SourceLocation LParenLoc = Tok.getLocation();
4061eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
4071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  if (ExpectAndConsume(tok::l_paren, diag::err_expected_lparen_after,
4086fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson                       "decltype")) {
4096fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson    SkipUntil(tok::r_paren);
4106fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson    return;
4116fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  }
4121eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
4136fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  // Parse the expression
4141eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
4156fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  // C++0x [dcl.type.simple]p4:
4166fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  //   The operand of the decltype specifier is an unevaluated operand.
4176fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  EnterExpressionEvaluationContext Unevaluated(Actions,
4186fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson                                               Action::Unevaluated);
4196fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  OwningExprResult Result = ParseExpression();
4206fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  if (Result.isInvalid()) {
4216fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson    SkipUntil(tok::r_paren);
4226fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson    return;
4236fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  }
4241eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
4256fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  // Match the ')'
4266fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  SourceLocation RParenLoc;
4276fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  if (Tok.is(tok::r_paren))
4286fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson    RParenLoc = ConsumeParen();
4296fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  else
4306fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson    MatchRHSPunctuation(tok::r_paren, LParenLoc);
4311eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
4326fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  if (RParenLoc.isInvalid())
4336fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson    return;
4346fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson
4356fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  const char *PrevSpec = 0;
436fec54013fcd0eb72642741584ca04c1bc292bef8John McCall  unsigned DiagID;
4376fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson  // Check for duplicate type specifiers (e.g. "int decltype(a)").
4381eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  if (DS.SetTypeSpecType(DeclSpec::TST_decltype, StartLoc, PrevSpec,
439fec54013fcd0eb72642741584ca04c1bc292bef8John McCall                         DiagID, Result.release()))
440fec54013fcd0eb72642741584ca04c1bc292bef8John McCall    Diag(StartLoc, DiagID) << PrevSpec;
4416fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson}
4426fd634f4ac59f5923cffadadb99d19f23c18707aAnders Carlsson
44342a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor/// ParseClassName - Parse a C++ class-name, which names a class. Note
44442a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor/// that we only check that the result names a type; semantic analysis
44542a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor/// will need to verify that the type names a class. The result is
4467f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor/// either a type or NULL, depending on whether a type name was
44742a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor/// found.
44842a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor///
44942a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor///       class-name: [C++ 9.1]
45042a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor///         identifier
4517f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor///         simple-template-id
4521eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump///
45331a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas GregorParser::TypeResult Parser::ParseClassName(SourceLocation &EndLocation,
454d33c868d386ef47c2942e2dbff0d9955a8591fa9Fariborz Jahanian                                          const CXXScopeSpec *SS,
455d33c868d386ef47c2942e2dbff0d9955a8591fa9Fariborz Jahanian                                          bool DestrExpected) {
4567f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor  // Check whether we have a template-id that names a type.
4577f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor  if (Tok.is(tok::annot_template_id)) {
4581eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    TemplateIdAnnotation *TemplateId
4597f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor      = static_cast<TemplateIdAnnotation *>(Tok.getAnnotationValue());
460c45c232440dfafedca1a3773b904fb42609b1b19Douglas Gregor    if (TemplateId->Kind == TNK_Type_template) {
46131a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas Gregor      AnnotateTemplateIdTokenAsType(SS);
4627f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor
4637f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor      assert(Tok.is(tok::annot_typename) && "template-id -> type failed");
4647f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor      TypeTy *Type = Tok.getAnnotationValue();
4657f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor      EndLocation = Tok.getAnnotationEndLoc();
4667f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor      ConsumeToken();
46731a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas Gregor
46831a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas Gregor      if (Type)
46931a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas Gregor        return Type;
47031a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas Gregor      return true;
4717f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor    }
4727f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor
4737f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor    // Fall through to produce an error below.
4747f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor  }
4757f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor
47642a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor  if (Tok.isNot(tok::identifier)) {
4771ab3b96de160e4fbffec2a776e284a48a3bb543dChris Lattner    Diag(Tok, diag::err_expected_class_name);
47831a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas Gregor    return true;
47942a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor  }
48042a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor
48142a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor  // We have an identifier; check whether it is actually a type.
4821eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  TypeTy *Type = Actions.getTypeName(*Tok.getIdentifierInfo(),
48342c39f39184c5ce9d7f489e5dcb7eec770728a9aDouglas Gregor                                     Tok.getLocation(), CurScope, SS,
48442c39f39184c5ce9d7f489e5dcb7eec770728a9aDouglas Gregor                                     true);
48542a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor  if (!Type) {
4861eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    Diag(Tok, DestrExpected ? diag::err_destructor_class_name
487d33c868d386ef47c2942e2dbff0d9955a8591fa9Fariborz Jahanian                            : diag::err_expected_class_name);
48831a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas Gregor    return true;
48942a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor  }
49042a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor
49142a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor  // Consume the identifier.
4927f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor  EndLocation = ConsumeToken();
49342a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor  return Type;
49442a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor}
49542a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor
496e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// ParseClassSpecifier - Parse a C++ class-specifier [C++ class] or
497e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// elaborated-type-specifier [C++ dcl.type.elab]; we can't tell which
498e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// until we reach the start of a definition or see a token that
499e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// cannot start a definition.
500e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///
501e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///       class-specifier: [C++ class]
502e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         class-head '{' member-specification[opt] '}'
503e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         class-head '{' member-specification[opt] '}' attributes[opt]
504e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///       class-head:
505e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         class-key identifier[opt] base-clause[opt]
506e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         class-key nested-name-specifier identifier base-clause[opt]
507e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         class-key nested-name-specifier[opt] simple-template-id
508e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///                          base-clause[opt]
509e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// [GNU]   class-key attributes[opt] identifier[opt] base-clause[opt]
5101eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// [GNU]   class-key attributes[opt] nested-name-specifier
511e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///                          identifier base-clause[opt]
5121eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// [GNU]   class-key attributes[opt] nested-name-specifier[opt]
513e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///                          simple-template-id base-clause[opt]
514e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///       class-key:
515e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         'class'
516e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         'struct'
517e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         'union'
518e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///
519e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///       elaborated-type-specifier: [C++ dcl.type.elab]
5201eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump///         class-key ::[opt] nested-name-specifier[opt] identifier
5211eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump///         class-key ::[opt] nested-name-specifier[opt] 'template'[opt]
5221eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump///                          simple-template-id
523e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///
524e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///  Note that the C++ class-specifier and elaborated-type-specifier,
525e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///  together, subsume the C99 struct-or-union-specifier:
526e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///
527e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///       struct-or-union-specifier: [C99 6.7.2.1]
528e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         struct-or-union identifier[opt] '{' struct-contents '}'
529e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         struct-or-union identifier
530e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// [GNU]   struct-or-union attributes[opt] identifier[opt] '{' struct-contents
531e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///                                                         '}' attributes[opt]
532e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// [GNU]   struct-or-union attributes[opt] identifier
533e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///       struct-or-union:
534e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         'struct'
535e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         'union'
5364c97d762d8c5a84f6554e5bfb31d28c90df64158Chris Lattnervoid Parser::ParseClassSpecifier(tok::TokenKind TagTokKind,
5374c97d762d8c5a84f6554e5bfb31d28c90df64158Chris Lattner                                 SourceLocation StartLoc, DeclSpec &DS,
5384d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor                                 const ParsedTemplateInfo &TemplateInfo,
53906c0fecd197fef21e265a41bca8dc5022de1f864Douglas Gregor                                 AccessSpecifier AS) {
5404c97d762d8c5a84f6554e5bfb31d28c90df64158Chris Lattner  DeclSpec::TST TagType;
5414c97d762d8c5a84f6554e5bfb31d28c90df64158Chris Lattner  if (TagTokKind == tok::kw_struct)
5424c97d762d8c5a84f6554e5bfb31d28c90df64158Chris Lattner    TagType = DeclSpec::TST_struct;
5434c97d762d8c5a84f6554e5bfb31d28c90df64158Chris Lattner  else if (TagTokKind == tok::kw_class)
5444c97d762d8c5a84f6554e5bfb31d28c90df64158Chris Lattner    TagType = DeclSpec::TST_class;
5454c97d762d8c5a84f6554e5bfb31d28c90df64158Chris Lattner  else {
5464c97d762d8c5a84f6554e5bfb31d28c90df64158Chris Lattner    assert(TagTokKind == tok::kw_union && "Not a class specifier");
5474c97d762d8c5a84f6554e5bfb31d28c90df64158Chris Lattner    TagType = DeclSpec::TST_union;
5484c97d762d8c5a84f6554e5bfb31d28c90df64158Chris Lattner  }
549e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
550374929f7e88f6c7a96382b3eb4201b721c418372Douglas Gregor  if (Tok.is(tok::code_completion)) {
551374929f7e88f6c7a96382b3eb4201b721c418372Douglas Gregor    // Code completion for a struct, class, or union name.
552374929f7e88f6c7a96382b3eb4201b721c418372Douglas Gregor    Actions.CodeCompleteTag(CurScope, TagType);
553374929f7e88f6c7a96382b3eb4201b721c418372Douglas Gregor    ConsumeToken();
554374929f7e88f6c7a96382b3eb4201b721c418372Douglas Gregor  }
555374929f7e88f6c7a96382b3eb4201b721c418372Douglas Gregor
556e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  AttributeList *Attr = 0;
557e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  // If attributes exist after tag, parse them.
558e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  if (Tok.is(tok::kw___attribute))
559e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    Attr = ParseAttributes();
560e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
561f59e17ecf06ac60065e2d02058bd6f21f5d216ccSteve Naroff  // If declspecs exist after tag, parse them.
562290eeb0ec2b6b91f3621e05ef541deb257fbea73Eli Friedman  if (Tok.is(tok::kw___declspec))
563290eeb0ec2b6b91f3621e05ef541deb257fbea73Eli Friedman    Attr = ParseMicrosoftDeclSpec(Attr);
5641eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
565b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor  if (TagType == DeclSpec::TST_struct && Tok.is(tok::kw___is_pod)) {
566b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    // GNU libstdc++ 4.2 uses __is_pod as the name of a struct template, but
567b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    // __is_pod is a keyword in GCC >= 4.3. Therefore, when we see the
5681eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    // token sequence "struct __is_pod", make __is_pod into a normal
569b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    // identifier rather than a keyword, to allow libstdc++ 4.2 to work
570b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    // properly.
571b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    Tok.getIdentifierInfo()->setTokenID(tok::identifier);
572b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    Tok.setKind(tok::identifier);
573b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor  }
574b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor
575b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor  if (TagType == DeclSpec::TST_struct && Tok.is(tok::kw___is_empty)) {
576b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    // GNU libstdc++ 4.2 uses __is_empty as the name of a struct template, but
577b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    // __is_empty is a keyword in GCC >= 4.3. Therefore, when we see the
5781eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    // token sequence "struct __is_empty", make __is_empty into a normal
579b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    // identifier rather than a keyword, to allow libstdc++ 4.2 to work
580b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    // properly.
581b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    Tok.getIdentifierInfo()->setTokenID(tok::identifier);
582b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor    Tok.setKind(tok::identifier);
583b117a60f7684261ddc8c8f14e8ef8a827e6af814Douglas Gregor  }
5841eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
585eb83ecde1a822b1c38cd060a85a08c1ac9f82cf8Argyrios Kyrtzidis  // Parse the (optional) nested-name-specifier.
586eb83ecde1a822b1c38cd060a85a08c1ac9f82cf8Argyrios Kyrtzidis  CXXScopeSpec SS;
5871eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  if (getLang().CPlusPlus &&
5882dd078ae50ff7be1fb25ebeedde45e9ab691a4f0Douglas Gregor      ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/0, true))
58939a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor    if (Tok.isNot(tok::identifier) && Tok.isNot(tok::annot_template_id))
590eb83ecde1a822b1c38cd060a85a08c1ac9f82cf8Argyrios Kyrtzidis      Diag(Tok, diag::err_expected_ident);
591cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor
592cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor  // Parse the (optional) class name or simple-template-id.
593e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  IdentifierInfo *Name = 0;
594e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  SourceLocation NameLoc;
59539a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor  TemplateIdAnnotation *TemplateId = 0;
596e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  if (Tok.is(tok::identifier)) {
597e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    Name = Tok.getIdentifierInfo();
598e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    NameLoc = ConsumeToken();
59939a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor  } else if (Tok.is(tok::annot_template_id)) {
60039a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor    TemplateId = static_cast<TemplateIdAnnotation *>(Tok.getAnnotationValue());
60139a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor    NameLoc = ConsumeToken();
602cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor
603c45c232440dfafedca1a3773b904fb42609b1b19Douglas Gregor    if (TemplateId->Kind != TNK_Type_template) {
60439a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor      // The template-name in the simple-template-id refers to
60539a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor      // something other than a class template. Give an appropriate
60639a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor      // error message and skip to the ';'.
60739a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor      SourceRange Range(NameLoc);
60839a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor      if (SS.isNotEmpty())
60939a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor        Range.setBegin(SS.getBeginLoc());
61039a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor
61139a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor      Diag(TemplateId->LAngleLoc, diag::err_template_spec_syntax_non_template)
61239a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor        << Name << static_cast<int>(TemplateId->Kind) << Range;
6131eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
61439a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor      DS.SetTypeSpecError();
61539a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor      SkipUntil(tok::semi, false, true);
61639a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor      TemplateId->Destroy();
61739a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor      return;
618cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor    }
619e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  }
620e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
62167d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall  // There are four options here.  If we have 'struct foo;', then this
62267d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall  // is either a forward declaration or a friend declaration, which
62367d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall  // have to be treated differently.  If we have 'struct foo {...' or
62439a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor  // 'struct foo :...' then this is a definition. Otherwise we have
625e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  // something like 'struct foo xyz', a reference.
6260f434ecbead44c1f4d5f9dda088f9827fa0dc40fJohn McCall  Action::TagUseKind TUK;
627e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  if (Tok.is(tok::l_brace) || (getLang().CPlusPlus && Tok.is(tok::colon)))
6280f434ecbead44c1f4d5f9dda088f9827fa0dc40fJohn McCall    TUK = Action::TUK_Definition;
62967d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall  else if (Tok.is(tok::semi))
63067d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall    TUK = DS.isFriendSpecified() ? Action::TUK_Friend : Action::TUK_Declaration;
631e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  else
6320f434ecbead44c1f4d5f9dda088f9827fa0dc40fJohn McCall    TUK = Action::TUK_Reference;
633e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
6340f434ecbead44c1f4d5f9dda088f9827fa0dc40fJohn McCall  if (!Name && !TemplateId && TUK != Action::TUK_Definition) {
635e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    // We have a declaration or reference to an anonymous class.
6361ab3b96de160e4fbffec2a776e284a48a3bb543dChris Lattner    Diag(StartLoc, diag::err_anon_type_definition)
6371ab3b96de160e4fbffec2a776e284a48a3bb543dChris Lattner      << DeclSpec::getSpecifierName(TagType);
638e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
639e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    // Skip the rest of this declarator, up until the comma or semicolon.
640e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    SkipUntil(tok::comma, true);
64139a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor
64239a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor    if (TemplateId)
64339a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor      TemplateId->Destroy();
644e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    return;
645e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  }
646e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
647ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  // Create the tag portion of the class or class template.
648c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall  Action::DeclResult TagOrTempResult = true; // invalid
649c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall  Action::TypeResult TypeResult = true; // invalid
6504d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor  TemplateParameterLists *TemplateParams = TemplateInfo.TemplateParams;
6514d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor
6520f434ecbead44c1f4d5f9dda088f9827fa0dc40fJohn McCall  // FIXME: When TUK == TUK_Reference and we have a template-id, we need
6534d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor  // to turn that template-id into a type.
6544d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor
655402abb55fc2e0cdda5fb1ac90009b1f5f6774906Douglas Gregor  bool Owned = false;
656f1bbbb49f06a7462476cd88166fccda5feb15cabJohn McCall  if (TemplateId) {
6574d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor    // Explicit specialization, class template partial specialization,
6584d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor    // or explicit instantiation.
6591eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    ASTTemplateArgsPtr TemplateArgsPtr(Actions,
66039a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor                                       TemplateId->getTemplateArgs(),
66139a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor                                       TemplateId->getTemplateArgIsType(),
66239a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor                                       TemplateId->NumArgs);
6634d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor    if (TemplateInfo.Kind == ParsedTemplateInfo::ExplicitInstantiation &&
6640f434ecbead44c1f4d5f9dda088f9827fa0dc40fJohn McCall        TUK == Action::TUK_Declaration) {
6654d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor      // This is an explicit instantiation of a class template.
6664d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor      TagOrTempResult
6671eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump        = Actions.ActOnExplicitInstantiation(CurScope,
66845f965581935791a018df829a14dff53c1dd8f47Douglas Gregor                                             TemplateInfo.ExternLoc,
6691eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                             TemplateInfo.TemplateLoc,
6704d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor                                             TagType,
6711eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                             StartLoc,
6724d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor                                             SS,
6731eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                     TemplateTy::make(TemplateId->Template),
6741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                             TemplateId->TemplateNameLoc,
6751eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                             TemplateId->LAngleLoc,
6764d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor                                             TemplateArgsPtr,
6774d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor                                      TemplateId->getTemplateArgLocations(),
6781eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                             TemplateId->RAngleLoc,
6794d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor                                             Attr);
680f1bbbb49f06a7462476cd88166fccda5feb15cabJohn McCall    } else if (TUK == Action::TUK_Reference || TUK == Action::TUK_Friend) {
681c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall      TypeResult
6826b2becfc434b0bdced8560802c4d0e03148c61b8John McCall        = Actions.ActOnTemplateIdType(TemplateTy::make(TemplateId->Template),
6836b2becfc434b0bdced8560802c4d0e03148c61b8John McCall                                      TemplateId->TemplateNameLoc,
6846b2becfc434b0bdced8560802c4d0e03148c61b8John McCall                                      TemplateId->LAngleLoc,
6856b2becfc434b0bdced8560802c4d0e03148c61b8John McCall                                      TemplateArgsPtr,
6866b2becfc434b0bdced8560802c4d0e03148c61b8John McCall                                      TemplateId->getTemplateArgLocations(),
6876b2becfc434b0bdced8560802c4d0e03148c61b8John McCall                                      TemplateId->RAngleLoc);
6886b2becfc434b0bdced8560802c4d0e03148c61b8John McCall
689c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall      TypeResult = Actions.ActOnTagTemplateIdType(TypeResult, TUK,
690c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall                                                  TagType, StartLoc);
6914d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor    } else {
6924d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor      // This is an explicit specialization or a class template
6934d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor      // partial specialization.
6944d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor      TemplateParameterLists FakedParamLists;
6954d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor
6964d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor      if (TemplateInfo.Kind == ParsedTemplateInfo::ExplicitInstantiation) {
6974d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        // This looks like an explicit instantiation, because we have
6984d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        // something like
6994d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        //
7004d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        //   template class Foo<X>
7014d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        //
7023f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor        // but it actually has a definition. Most likely, this was
7034d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        // meant to be an explicit specialization, but the user forgot
7044d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        // the '<>' after 'template'.
7050f434ecbead44c1f4d5f9dda088f9827fa0dc40fJohn McCall        assert(TUK == Action::TUK_Definition && "Expected a definition here");
7064d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor
7071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump        SourceLocation LAngleLoc
7084d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor          = PP.getLocForEndOfToken(TemplateInfo.TemplateLoc);
7091eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump        Diag(TemplateId->TemplateNameLoc,
7104d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor             diag::err_explicit_instantiation_with_definition)
7114d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor          << SourceRange(TemplateInfo.TemplateLoc)
7124d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor          << CodeModificationHint::CreateInsertion(LAngleLoc, "<>");
7134d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor
7144d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        // Create a fake template parameter list that contains only
7154d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        // "template<>", so that we treat this construct as a class
7164d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        // template specialization.
7174d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        FakedParamLists.push_back(
7181eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump          Actions.ActOnTemplateParameterList(0, SourceLocation(),
7194d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor                                             TemplateInfo.TemplateLoc,
7201eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                             LAngleLoc,
7211eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                             0, 0,
7224d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor                                             LAngleLoc));
7234d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor        TemplateParams = &FakedParamLists;
7244d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor      }
7254d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor
7264d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor      // Build the class template specialization.
7274d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor      TagOrTempResult
7280f434ecbead44c1f4d5f9dda088f9827fa0dc40fJohn McCall        = Actions.ActOnClassTemplateSpecialization(CurScope, TagType, TUK,
72939a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor                       StartLoc, SS,
7301eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                       TemplateTy::make(TemplateId->Template),
7311eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                       TemplateId->TemplateNameLoc,
7321eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                       TemplateId->LAngleLoc,
73339a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor                       TemplateArgsPtr,
73439a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor                       TemplateId->getTemplateArgLocations(),
7351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                       TemplateId->RAngleLoc,
73639a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor                       Attr,
7371eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                       Action::MultiTemplateParamsArg(Actions,
738cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor                                    TemplateParams? &(*TemplateParams)[0] : 0,
739cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor                                 TemplateParams? TemplateParams->size() : 0));
7404d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor    }
74139a8de10c18365bde7062d8959b7ed525449c561Douglas Gregor    TemplateId->Destroy();
7423f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor  } else if (TemplateInfo.Kind == ParsedTemplateInfo::ExplicitInstantiation &&
7430f434ecbead44c1f4d5f9dda088f9827fa0dc40fJohn McCall             TUK == Action::TUK_Declaration) {
7443f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor    // Explicit instantiation of a member of a class template
7453f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor    // specialization, e.g.,
7463f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor    //
7473f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor    //   template struct Outer<int>::Inner;
7483f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor    //
7493f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor    TagOrTempResult
7501eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      = Actions.ActOnExplicitInstantiation(CurScope,
75145f965581935791a018df829a14dff53c1dd8f47Douglas Gregor                                           TemplateInfo.ExternLoc,
7521eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                           TemplateInfo.TemplateLoc,
7531eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                           TagType, StartLoc, SS, Name,
7543f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor                                           NameLoc, Attr);
7553f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor  } else {
7563f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor    if (TemplateInfo.Kind == ParsedTemplateInfo::ExplicitInstantiation &&
7570f434ecbead44c1f4d5f9dda088f9827fa0dc40fJohn McCall        TUK == Action::TUK_Definition) {
7583f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor      // FIXME: Diagnose this particular error.
7593f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor    }
7603f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor
761c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall    bool IsDependent = false;
762c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall
7633f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor    // Declaration or definition of a class type
7641eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    TagOrTempResult = Actions.ActOnTag(CurScope, TagType, TUK, StartLoc, SS,
7657cdbc5832084f45721693dfb1d93284c3e08efeeDouglas Gregor                                       Name, NameLoc, Attr, AS,
7661eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                                  Action::MultiTemplateParamsArg(Actions,
7677cdbc5832084f45721693dfb1d93284c3e08efeeDouglas Gregor                                    TemplateParams? &(*TemplateParams)[0] : 0,
7687cdbc5832084f45721693dfb1d93284c3e08efeeDouglas Gregor                                    TemplateParams? TemplateParams->size() : 0),
769c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall                                       Owned, IsDependent);
770c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall
771c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall    // If ActOnTag said the type was dependent, try again with the
772c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall    // less common call.
773c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall    if (IsDependent)
774c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall      TypeResult = Actions.ActOnDependentTag(CurScope, TagType, TUK,
775c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall                                             SS, Name, StartLoc, NameLoc);
7763f5b61c394f4f205bcb4d316eb2a7a0a68b8af86Douglas Gregor  }
777e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
778e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  // Parse the optional base clause (C++ only).
77922bd905673a73ccb9b5e45a7038ec060c9650ffeChris Lattner  if (getLang().CPlusPlus && Tok.is(tok::colon))
780212e81cc5151b3c42346e43cfd42499a53ffd39aDouglas Gregor    ParseBaseClause(TagOrTempResult.get());
781e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
782e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  // If there is a body, parse it and inform the actions module.
783e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  if (Tok.is(tok::l_brace))
78407952324dda0e758c17f8bc3015793c65c51c48cArgyrios Kyrtzidis    if (getLang().CPlusPlus)
785212e81cc5151b3c42346e43cfd42499a53ffd39aDouglas Gregor      ParseCXXMemberSpecification(StartLoc, TagType, TagOrTempResult.get());
78607952324dda0e758c17f8bc3015793c65c51c48cArgyrios Kyrtzidis    else
787212e81cc5151b3c42346e43cfd42499a53ffd39aDouglas Gregor      ParseStructUnionBody(StartLoc, TagType, TagOrTempResult.get());
7880f434ecbead44c1f4d5f9dda088f9827fa0dc40fJohn McCall  else if (TUK == Action::TUK_Definition) {
789e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    // FIXME: Complain that we have a base-specifier list but no
790e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    // definition.
7911ab3b96de160e4fbffec2a776e284a48a3bb543dChris Lattner    Diag(Tok, diag::err_expected_lbrace);
792e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  }
793e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
794c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall  void *Result;
795c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall  if (!TypeResult.isInvalid()) {
796c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall    TagType = DeclSpec::TST_typename;
797c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall    Result = TypeResult.get();
798c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall    Owned = false;
799c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall  } else if (!TagOrTempResult.isInvalid()) {
800c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall    Result = TagOrTempResult.get().getAs<void>();
801c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall  } else {
802ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor    DS.SetTypeSpecError();
80366e9977ddd6b197317d149213b76a9af0d3df4deAnders Carlsson    return;
80466e9977ddd6b197317d149213b76a9af0d3df4deAnders Carlsson  }
8051eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
806fec54013fcd0eb72642741584ca04c1bc292bef8John McCall  const char *PrevSpec = 0;
807fec54013fcd0eb72642741584ca04c1bc292bef8John McCall  unsigned DiagID;
808c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall
809fec54013fcd0eb72642741584ca04c1bc292bef8John McCall  if (DS.SetTypeSpecType(TagType, StartLoc, PrevSpec, DiagID,
810c4e7019d5c9034a2d84ee4695f8e98dc025ac131John McCall                         Result, Owned))
811fec54013fcd0eb72642741584ca04c1bc292bef8John McCall    Diag(StartLoc, DiagID) << PrevSpec;
812e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor}
813e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
8141eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// ParseBaseClause - Parse the base-clause of a C++ class [C++ class.derived].
815e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///
816e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///       base-clause : [C++ class.derived]
817e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         ':' base-specifier-list
818e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///       base-specifier-list:
819e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         base-specifier '...'[opt]
820e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         base-specifier-list ',' base-specifier '...'[opt]
821b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris Lattnervoid Parser::ParseBaseClause(DeclPtrTy ClassDecl) {
822e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  assert(Tok.is(tok::colon) && "Not a base clause");
823e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  ConsumeToken();
824e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
825f8268ae3196002bbab6adb830302e79b0f368f13Douglas Gregor  // Build up an array of parsed base specifiers.
826f8268ae3196002bbab6adb830302e79b0f368f13Douglas Gregor  llvm::SmallVector<BaseTy *, 8> BaseInfo;
827f8268ae3196002bbab6adb830302e79b0f368f13Douglas Gregor
828e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  while (true) {
829e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    // Parse a base-specifier.
830f8268ae3196002bbab6adb830302e79b0f368f13Douglas Gregor    BaseResult Result = ParseBaseSpecifier(ClassDecl);
8315ac8aff3d7431dc7e4d64d960574a10c9f7e0078Douglas Gregor    if (Result.isInvalid()) {
832e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor      // Skip the rest of this base specifier, up until the comma or
833e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor      // opening brace.
834f8268ae3196002bbab6adb830302e79b0f368f13Douglas Gregor      SkipUntil(tok::comma, tok::l_brace, true, true);
835f8268ae3196002bbab6adb830302e79b0f368f13Douglas Gregor    } else {
836f8268ae3196002bbab6adb830302e79b0f368f13Douglas Gregor      // Add this to our array of base specifiers.
8375ac8aff3d7431dc7e4d64d960574a10c9f7e0078Douglas Gregor      BaseInfo.push_back(Result.get());
838e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    }
839e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
840e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    // If the next token is a comma, consume it and keep reading
841e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    // base-specifiers.
842e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    if (Tok.isNot(tok::comma)) break;
8431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
844e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    // Consume the comma.
845e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    ConsumeToken();
846e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  }
847f8268ae3196002bbab6adb830302e79b0f368f13Douglas Gregor
848f8268ae3196002bbab6adb830302e79b0f368f13Douglas Gregor  // Attach the base specifiers
849beaaccd8e2a8748f77b66e2b330fb9136937e14cJay Foad  Actions.ActOnBaseSpecifiers(ClassDecl, BaseInfo.data(), BaseInfo.size());
850e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor}
851e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
852e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// ParseBaseSpecifier - Parse a C++ base-specifier. A base-specifier is
853e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// one entry in the base class list of a class specifier, for example:
854e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///    class foo : public bar, virtual private baz {
855e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// 'public bar' and 'virtual private baz' are each base-specifiers.
856e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///
857e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///       base-specifier: [C++ class.derived]
858e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         ::[opt] nested-name-specifier[opt] class-name
859e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         'virtual' access-specifier[opt] ::[opt] nested-name-specifier[opt]
860e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///                        class-name
861e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         access-specifier 'virtual'[opt] ::[opt] nested-name-specifier[opt]
862e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///                        class-name
863b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris LattnerParser::BaseResult Parser::ParseBaseSpecifier(DeclPtrTy ClassDecl) {
864e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  bool IsVirtual = false;
865e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  SourceLocation StartLoc = Tok.getLocation();
866e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
867e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  // Parse the 'virtual' keyword.
868e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  if (Tok.is(tok::kw_virtual))  {
869e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    ConsumeToken();
870e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    IsVirtual = true;
871e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  }
872e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
873e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  // Parse an (optional) access specifier.
874e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  AccessSpecifier Access = getAccessSpecifierIfPresent();
875e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  if (Access)
876e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    ConsumeToken();
8771eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
878e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  // Parse the 'virtual' keyword (again!), in case it came after the
879e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  // access specifier.
880e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  if (Tok.is(tok::kw_virtual))  {
881e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    SourceLocation VirtualLoc = ConsumeToken();
882e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    if (IsVirtual) {
883e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor      // Complain about duplicate 'virtual'
8841ab3b96de160e4fbffec2a776e284a48a3bb543dChris Lattner      Diag(VirtualLoc, diag::err_dup_virtual)
88531a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas Gregor        << CodeModificationHint::CreateRemoval(SourceRange(VirtualLoc));
886e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    }
887e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
888e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor    IsVirtual = true;
889e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  }
890e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
891eb83ecde1a822b1c38cd060a85a08c1ac9f82cf8Argyrios Kyrtzidis  // Parse optional '::' and optional nested-name-specifier.
892eb83ecde1a822b1c38cd060a85a08c1ac9f82cf8Argyrios Kyrtzidis  CXXScopeSpec SS;
8932dd078ae50ff7be1fb25ebeedde45e9ab691a4f0Douglas Gregor  ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/0, true);
894e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
895e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  // The location of the base class itself.
896e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  SourceLocation BaseLoc = Tok.getLocation();
89742a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor
89842a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor  // Parse the class-name.
8997f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor  SourceLocation EndLocation;
90031a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas Gregor  TypeResult BaseType = ParseClassName(EndLocation, &SS);
90131a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas Gregor  if (BaseType.isInvalid())
90242a552f8200ba5948661aee0106fce0c04e39818Douglas Gregor    return true;
9031eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
9041eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  // Find the complete source range for the base-specifier.
9057f43d6764797ab21216421aeb00f4ec314d503d1Douglas Gregor  SourceRange Range(StartLoc, EndLocation);
9061eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
907e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  // Notify semantic analysis that we have parsed a complete
908e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  // base-specifier.
909a55e52c0802cae3b7c366a05c461d3d15074c1a3Sebastian Redl  return Actions.ActOnBaseSpecifier(ClassDecl, Range, IsVirtual, Access,
91031a19b6989bbf326d2de5ae12e712e2a65ca9c34Douglas Gregor                                    BaseType.get(), BaseLoc);
911e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor}
912e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor
913e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// getAccessSpecifierIfPresent - Determine whether the next token is
914e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor/// a C++ access-specifier.
915e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///
916e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///       access-specifier: [C++ class.derived]
917e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         'private'
918e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         'protected'
919e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor///         'public'
9201eb4433ac451dc16f4133a88af2d002ac26c58efMike StumpAccessSpecifier Parser::getAccessSpecifierIfPresent() const {
921e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  switch (Tok.getKind()) {
922e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  default: return AS_none;
923e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  case tok::kw_private: return AS_private;
924e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  case tok::kw_protected: return AS_protected;
925e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  case tok::kw_public: return AS_public;
926e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor  }
927e37ac4ff1620ed2d7026f52baccbfa022d79ced1Douglas Gregor}
9284cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
929d33133cdc1af466f9c276249b2621be03867888bEli Friedmanvoid Parser::HandleMemberFunctionDefaultArgs(Declarator& DeclaratorInfo,
930d33133cdc1af466f9c276249b2621be03867888bEli Friedman                                             DeclPtrTy ThisDecl) {
931d33133cdc1af466f9c276249b2621be03867888bEli Friedman  // We just declared a member function. If this member function
932d33133cdc1af466f9c276249b2621be03867888bEli Friedman  // has any default arguments, we'll need to parse them later.
933d33133cdc1af466f9c276249b2621be03867888bEli Friedman  LateParsedMethodDeclaration *LateMethod = 0;
9341eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  DeclaratorChunk::FunctionTypeInfo &FTI
935d33133cdc1af466f9c276249b2621be03867888bEli Friedman    = DeclaratorInfo.getTypeObject(0).Fun;
936d33133cdc1af466f9c276249b2621be03867888bEli Friedman  for (unsigned ParamIdx = 0; ParamIdx < FTI.NumArgs; ++ParamIdx) {
937d33133cdc1af466f9c276249b2621be03867888bEli Friedman    if (LateMethod || FTI.ArgInfo[ParamIdx].DefaultArgTokens) {
938d33133cdc1af466f9c276249b2621be03867888bEli Friedman      if (!LateMethod) {
939d33133cdc1af466f9c276249b2621be03867888bEli Friedman        // Push this method onto the stack of late-parsed method
940d33133cdc1af466f9c276249b2621be03867888bEli Friedman        // declarations.
941d33133cdc1af466f9c276249b2621be03867888bEli Friedman        getCurrentClass().MethodDecls.push_back(
942d33133cdc1af466f9c276249b2621be03867888bEli Friedman                                LateParsedMethodDeclaration(ThisDecl));
943d33133cdc1af466f9c276249b2621be03867888bEli Friedman        LateMethod = &getCurrentClass().MethodDecls.back();
944d83d04041f64a2c89123d227fa8003b482391279Douglas Gregor        LateMethod->TemplateScope = CurScope->isTemplateParamScope();
945d33133cdc1af466f9c276249b2621be03867888bEli Friedman
946d33133cdc1af466f9c276249b2621be03867888bEli Friedman        // Add all of the parameters prior to this one (they don't
947d33133cdc1af466f9c276249b2621be03867888bEli Friedman        // have default arguments).
948d33133cdc1af466f9c276249b2621be03867888bEli Friedman        LateMethod->DefaultArgs.reserve(FTI.NumArgs);
949d33133cdc1af466f9c276249b2621be03867888bEli Friedman        for (unsigned I = 0; I < ParamIdx; ++I)
950d33133cdc1af466f9c276249b2621be03867888bEli Friedman          LateMethod->DefaultArgs.push_back(
951d33133cdc1af466f9c276249b2621be03867888bEli Friedman                    LateParsedDefaultArgument(FTI.ArgInfo[ParamIdx].Param));
952d33133cdc1af466f9c276249b2621be03867888bEli Friedman      }
953d33133cdc1af466f9c276249b2621be03867888bEli Friedman
954d33133cdc1af466f9c276249b2621be03867888bEli Friedman      // Add this parameter to the list of parameters (it or may
955d33133cdc1af466f9c276249b2621be03867888bEli Friedman      // not have a default argument).
956d33133cdc1af466f9c276249b2621be03867888bEli Friedman      LateMethod->DefaultArgs.push_back(
957d33133cdc1af466f9c276249b2621be03867888bEli Friedman        LateParsedDefaultArgument(FTI.ArgInfo[ParamIdx].Param,
958d33133cdc1af466f9c276249b2621be03867888bEli Friedman                                  FTI.ArgInfo[ParamIdx].DefaultArgTokens));
959d33133cdc1af466f9c276249b2621be03867888bEli Friedman    }
960d33133cdc1af466f9c276249b2621be03867888bEli Friedman  }
961d33133cdc1af466f9c276249b2621be03867888bEli Friedman}
962d33133cdc1af466f9c276249b2621be03867888bEli Friedman
9634cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis/// ParseCXXClassMemberDeclaration - Parse a C++ class member declaration.
9644cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///
9654cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///       member-declaration:
9664cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         decl-specifier-seq[opt] member-declarator-list[opt] ';'
9674cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         function-definition ';'[opt]
9684cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         ::[opt] nested-name-specifier template[opt] unqualified-id ';'[TODO]
9694cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         using-declaration                                            [TODO]
970511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson/// [C++0x] static_assert-declaration
9715aeccdbb4bdc94e48c04cacc59fa812af32109b2Anders Carlsson///         template-declaration
972bc8d56496a6ecdba14769df03d75c001184f8c54Chris Lattner/// [GNU]   '__extension__' member-declaration
9734cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///
9744cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///       member-declarator-list:
9754cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         member-declarator
9764cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         member-declarator-list ',' member-declarator
9774cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///
9784cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///       member-declarator:
9794cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         declarator pure-specifier[opt]
9804cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         declarator constant-initializer[opt]
9814cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         identifier[opt] ':' constant-expression
9824cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///
983e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl///       pure-specifier:
9844cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         '= 0'
9854cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///
9864cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///       constant-initializer:
9874cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         '=' constant-expression
9884cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///
98937b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregorvoid Parser::ParseCXXClassMemberDeclaration(AccessSpecifier AS,
99037b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregor                                       const ParsedTemplateInfo &TemplateInfo) {
991511d7aba3b12853fdb88729a0313b80a60eab8adAnders Carlsson  // static_assert-declaration
992682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner  if (Tok.is(tok::kw_static_assert)) {
99337b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregor    // FIXME: Check for templates
99497144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner    SourceLocation DeclEnd;
99597144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner    ParseStaticAssertDeclaration(DeclEnd);
996682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner    return;
997682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner  }
9981eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
999682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner  if (Tok.is(tok::kw_template)) {
10001eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    assert(!TemplateInfo.TemplateParams &&
100137b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregor           "Nested template improperly parsed?");
100297144fc41a9419bf6d74fc9450e8ef3f6e11f7e0Chris Lattner    SourceLocation DeclEnd;
10031eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    ParseDeclarationStartingWithTemplate(Declarator::MemberContext, DeclEnd,
10044d9a16f36d3b768672d50e6d02000f982ae448d7Douglas Gregor                                         AS);
1005682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner    return;
1006682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner  }
10075aeccdbb4bdc94e48c04cacc59fa812af32109b2Anders Carlsson
1008bc8d56496a6ecdba14769df03d75c001184f8c54Chris Lattner  // Handle:  member-declaration ::= '__extension__' member-declaration
1009bc8d56496a6ecdba14769df03d75c001184f8c54Chris Lattner  if (Tok.is(tok::kw___extension__)) {
1010bc8d56496a6ecdba14769df03d75c001184f8c54Chris Lattner    // __extension__ silences extension warnings in the subexpression.
1011bc8d56496a6ecdba14769df03d75c001184f8c54Chris Lattner    ExtensionRAIIObject O(Diags);  // Use RAII to do this.
1012bc8d56496a6ecdba14769df03d75c001184f8c54Chris Lattner    ConsumeToken();
101337b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregor    return ParseCXXClassMemberDeclaration(AS, TemplateInfo);
1014bc8d56496a6ecdba14769df03d75c001184f8c54Chris Lattner  }
10159cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor
10169cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  if (Tok.is(tok::kw_using)) {
101737b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregor    // FIXME: Check for template aliases
10181eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
10199cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    // Eat 'using'.
10209cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    SourceLocation UsingLoc = ConsumeToken();
10219cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor
10229cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    if (Tok.is(tok::kw_namespace)) {
10239cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor      Diag(UsingLoc, diag::err_using_namespace_in_class);
10249cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor      SkipUntil(tok::semi, true, true);
10259cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    }
10269cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    else {
10279cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor      SourceLocation DeclEnd;
10289cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor      // Otherwise, it must be using-declaration.
1029595adc1795cc2c079ef5876100e01acd10a0504aAnders Carlsson      ParseUsingDeclaration(Declarator::MemberContext, UsingLoc, DeclEnd, AS);
10309cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    }
10319cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor    return;
10329cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor  }
10339cfbe48a7a20a217fdb2920b29b67ae7941cb116Douglas Gregor
10344cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  SourceLocation DSStart = Tok.getLocation();
10354cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // decl-specifier-seq:
10364cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // Parse the common declaration-specifiers piece.
10374cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  DeclSpec DS;
103837b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregor  ParseDeclarationSpecifiers(DS, TemplateInfo, AS, DSC_class);
10394cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
1040dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  Action::MultiTemplateParamsArg TemplateParams(Actions,
1041dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall      TemplateInfo.TemplateParams? TemplateInfo.TemplateParams->data() : 0,
1042dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall      TemplateInfo.TemplateParams? TemplateInfo.TemplateParams->size() : 0);
1043dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
10444cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  if (Tok.is(tok::semi)) {
10454cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    ConsumeToken();
104667d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall
10474111181534e8257f592b6b7db57694af7cd04b06Anders Carlsson    if (DS.isFriendSpecified()) {
1048dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall      Actions.ActOnFriendTypeDecl(CurScope, DS, move(TemplateParams));
10494111181534e8257f592b6b7db57694af7cd04b06Anders Carlsson    } else
1050682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner      Actions.ParsedFreeStandingDeclSpec(CurScope, DS);
105167d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall
105267d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall    return;
10534cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  }
105407952324dda0e758c17f8bc3015793c65c51c48cArgyrios Kyrtzidis
10554cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  Declarator DeclaratorInfo(DS, Declarator::MemberContext);
10564cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
10573a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis  if (Tok.isNot(tok::colon)) {
10583a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis    // Parse the first declarator.
10593a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis    ParseDeclarator(DeclaratorInfo);
10603a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis    // Error parsing the declarator?
106110bd36882406cdf4805e35add1ce2f11ab9ae152Douglas Gregor    if (!DeclaratorInfo.hasName()) {
10623a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis      // If so, skip until the semi-colon or a }.
10634cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      SkipUntil(tok::r_brace, true);
10643a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis      if (Tok.is(tok::semi))
10653a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis        ConsumeToken();
1066682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner      return;
10674cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    }
10684cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
10693a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis    // function-definition:
10707ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor    if (Tok.is(tok::l_brace)
1071d3a413d3b8eb39bcee5944bc545d9997c1abe492Sebastian Redl        || (DeclaratorInfo.isFunctionDeclarator() &&
1072d3a413d3b8eb39bcee5944bc545d9997c1abe492Sebastian Redl            (Tok.is(tok::colon) || Tok.is(tok::kw_try)))) {
10733a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis      if (!DeclaratorInfo.isFunctionDeclarator()) {
10743a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis        Diag(Tok, diag::err_func_def_no_params);
10753a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis        ConsumeBrace();
10763a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis        SkipUntil(tok::r_brace, true);
1077682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner        return;
10783a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis      }
10793a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis
10803a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis      if (DS.getStorageClassSpec() == DeclSpec::SCS_typedef) {
10813a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis        Diag(Tok, diag::err_function_declared_typedef);
10823a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis        // This recovery skips the entire function body. It would be nice
10833a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis        // to simply call ParseCXXInlineMethodDef() below, however Sema
10843a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis        // assumes the declarator represents a function, not a typedef.
10853a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis        ConsumeBrace();
10863a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis        SkipUntil(tok::r_brace, true);
1087682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner        return;
10883a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis      }
10894cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
109037b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregor      ParseCXXInlineMethodDef(AS, DeclaratorInfo, TemplateInfo);
1091682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner      return;
10923a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis    }
10934cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  }
10944cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
10954cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // member-declarator-list:
10964cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  //   member-declarator
10974cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  //   member-declarator-list ',' member-declarator
10984cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
1099682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner  llvm::SmallVector<DeclPtrTy, 8> DeclsInGroup;
110015faa7fdfb496489dec9470aa5eb699b29ecdaccSebastian Redl  OwningExprResult BitfieldSize(Actions);
110115faa7fdfb496489dec9470aa5eb699b29ecdaccSebastian Redl  OwningExprResult Init(Actions);
1102e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl  bool Deleted = false;
11034cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
11044cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  while (1) {
11054cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
11064cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // member-declarator:
11074cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    //   declarator pure-specifier[opt]
11084cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    //   declarator constant-initializer[opt]
11094cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    //   identifier[opt] ':' constant-expression
11104cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
11114cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    if (Tok.is(tok::colon)) {
11124cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      ConsumeToken();
11130e9eabca263e8922bec0e2b38c8670eba9a39a1fSebastian Redl      BitfieldSize = ParseConstantExpression();
11140e9eabca263e8922bec0e2b38c8670eba9a39a1fSebastian Redl      if (BitfieldSize.isInvalid())
11154cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis        SkipUntil(tok::comma, true, true);
11164cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    }
11171eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
11184cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // pure-specifier:
11194cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    //   '= 0'
11204cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    //
11214cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // constant-initializer:
11224cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    //   '=' constant-expression
1123e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl    //
1124e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl    // defaulted/deleted function-definition:
1125e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl    //   '=' 'default'                          [TODO]
1126e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl    //   '=' 'delete'
11274cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
11284cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    if (Tok.is(tok::equal)) {
11294cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      ConsumeToken();
1130e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl      if (getLang().CPlusPlus0x && Tok.is(tok::kw_delete)) {
1131e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl        ConsumeToken();
1132e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl        Deleted = true;
1133e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl      } else {
1134e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl        Init = ParseInitializer();
1135e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl        if (Init.isInvalid())
1136e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl          SkipUntil(tok::comma, true, true);
1137e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl      }
11384cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    }
11394cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
11404cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // If attributes exist after the declarator, parse them.
1141ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl    if (Tok.is(tok::kw___attribute)) {
1142ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl      SourceLocation Loc;
1143ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl      AttributeList *AttrList = ParseAttributes(&Loc);
1144ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl      DeclaratorInfo.AddAttributes(AttrList, Loc);
1145ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl    }
11464cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
114707952324dda0e758c17f8bc3015793c65c51c48cArgyrios Kyrtzidis    // NOTE: If Sema is the Action module and declarator is an instance field,
1148682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner    // this call will *not* return the created decl; It will return null.
114907952324dda0e758c17f8bc3015793c65c51c48cArgyrios Kyrtzidis    // See Sema::ActOnCXXMemberDeclarator for details.
115067d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall
115167d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall    DeclPtrTy ThisDecl;
115267d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall    if (DS.isFriendSpecified()) {
1153bbbcdd9cc06b6078939129330ecc9bda3310984dJohn McCall      // TODO: handle initializers, bitfields, 'delete'
1154bbbcdd9cc06b6078939129330ecc9bda3310984dJohn McCall      ThisDecl = Actions.ActOnFriendFunctionDecl(CurScope, DeclaratorInfo,
1155bbbcdd9cc06b6078939129330ecc9bda3310984dJohn McCall                                                 /*IsDefinition*/ false,
1156bbbcdd9cc06b6078939129330ecc9bda3310984dJohn McCall                                                 move(TemplateParams));
115737b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregor    } else {
115867d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall      ThisDecl = Actions.ActOnCXXMemberDeclarator(CurScope, AS,
115967d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall                                                  DeclaratorInfo,
116037b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregor                                                  move(TemplateParams),
116167d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall                                                  BitfieldSize.release(),
116267d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall                                                  Init.release(),
116367d1a67f3db2f1aa69083c5c94164d6e0ee05b32John McCall                                                  Deleted);
116437b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregor    }
1165682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner    if (ThisDecl)
1166682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner      DeclsInGroup.push_back(ThisDecl);
11674cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
116872b505b7904b3c9320a1312998800ba76e4f5841Douglas Gregor    if (DeclaratorInfo.isFunctionDeclarator() &&
11691eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump        DeclaratorInfo.getDeclSpec().getStorageClassSpec()
117072b505b7904b3c9320a1312998800ba76e4f5841Douglas Gregor          != DeclSpec::SCS_typedef) {
1171d33133cdc1af466f9c276249b2621be03867888bEli Friedman      HandleMemberFunctionDefaultArgs(DeclaratorInfo, ThisDecl);
117272b505b7904b3c9320a1312998800ba76e4f5841Douglas Gregor    }
117372b505b7904b3c9320a1312998800ba76e4f5841Douglas Gregor
11744cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // If we don't have a comma, it is either the end of the list (a ';')
11754cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // or an error, bail out.
11764cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    if (Tok.isNot(tok::comma))
11774cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      break;
11781eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
11794cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // Consume the comma.
11804cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    ConsumeToken();
11811eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
11824cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // Parse the next declarator.
11834cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    DeclaratorInfo.clear();
118415faa7fdfb496489dec9470aa5eb699b29ecdaccSebastian Redl    BitfieldSize = 0;
118515faa7fdfb496489dec9470aa5eb699b29ecdaccSebastian Redl    Init = 0;
1186e2b6833d445c7a4ce64f1816c05f176ba1740acaSebastian Redl    Deleted = false;
11871eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
11884cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // Attributes are only allowed on the second declarator.
1189ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl    if (Tok.is(tok::kw___attribute)) {
1190ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl      SourceLocation Loc;
1191ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl      AttributeList *AttrList = ParseAttributes(&Loc);
1192ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl      DeclaratorInfo.AddAttributes(AttrList, Loc);
1193ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl    }
11944cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
11953a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis    if (Tok.isNot(tok::colon))
11963a9fdb4742b21c0a3c27f18c5e4e94bab6f9e64cArgyrios Kyrtzidis      ParseDeclarator(DeclaratorInfo);
11974cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  }
11984cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
11994cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  if (Tok.is(tok::semi)) {
12004cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    ConsumeToken();
1201c1dc653b08226c1d8e1732f9d8b03b82869900bcEli Friedman    Actions.FinalizeDeclaratorGroup(CurScope, DS, DeclsInGroup.data(),
1202682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner                                    DeclsInGroup.size());
1203682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner    return;
12044cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  }
12054cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
12064cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  Diag(Tok, diag::err_expected_semi_decl_list);
12074cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // Skip to end of block or statement
12084cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  SkipUntil(tok::r_brace, true, true);
12094cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  if (Tok.is(tok::semi))
12104cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    ConsumeToken();
1211682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner  return;
12124cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis}
12134cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
12144cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis/// ParseCXXMemberSpecification - Parse the class definition.
12154cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///
12164cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///       member-specification:
12174cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         member-declaration member-specification[opt]
12184cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///         access-specifier ':' member-specification[opt]
12194cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis///
12204cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidisvoid Parser::ParseCXXMemberSpecification(SourceLocation RecordLoc,
1221b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris Lattner                                         unsigned TagType, DeclPtrTy TagDecl) {
122231fc07df7f0fc89ebf83ca05a20b29de45a7598dSanjiv Gupta  assert((TagType == DeclSpec::TST_struct ||
12234cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis         TagType == DeclSpec::TST_union  ||
122431fc07df7f0fc89ebf83ca05a20b29de45a7598dSanjiv Gupta         TagType == DeclSpec::TST_class) && "Invalid TagType!");
12254cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
122649f28ca787d8db7cac3c8898334f70ea55374c98Chris Lattner  PrettyStackTraceActionsDecl CrashInfo(TagDecl, RecordLoc, Actions,
122749f28ca787d8db7cac3c8898334f70ea55374c98Chris Lattner                                        PP.getSourceManager(),
122849f28ca787d8db7cac3c8898334f70ea55374c98Chris Lattner                                        "parsing struct/union/class body");
12291eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
12304cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  SourceLocation LBraceLoc = ConsumeBrace();
12314cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
12326569d68745c8213709740337d2be52b031384f58Douglas Gregor  // Determine whether this is a top-level (non-nested) class.
12331eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  bool TopLevelClass = ClassStack.empty() ||
12346569d68745c8213709740337d2be52b031384f58Douglas Gregor    CurScope->isInCXXInlineMethodScope();
12354cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
12364cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // Enter a scope for the class.
12373218c4bb3b5d7250f12420de6db7ef3e3f805a75Douglas Gregor  ParseScope ClassScope(this, Scope::ClassScope|Scope::DeclScope);
12384cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
12396569d68745c8213709740337d2be52b031384f58Douglas Gregor  // Note that we are parsing a new (potentially-nested) class definition.
12406569d68745c8213709740337d2be52b031384f58Douglas Gregor  ParsingClassDefinition ParsingDef(*this, TagDecl, TopLevelClass);
12416569d68745c8213709740337d2be52b031384f58Douglas Gregor
1242ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  if (TagDecl)
1243ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor    Actions.ActOnTagStartDefinition(CurScope, TagDecl);
1244ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  else {
1245ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor    SkipUntil(tok::r_brace, false, false);
1246ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor    return;
1247ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  }
12484cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
12494cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // C++ 11p3: Members of a class defined with the keyword class are private
12504cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // by default. Members of a class defined with the keywords struct or union
12514cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // are public by default.
12524cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  AccessSpecifier CurAS;
12534cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  if (TagType == DeclSpec::TST_class)
12544cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    CurAS = AS_private;
12554cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  else
12564cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    CurAS = AS_public;
12574cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
12584cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // While we still have something to read, read the member-declarations.
12594cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  while (Tok.isNot(tok::r_brace) && Tok.isNot(tok::eof)) {
12604cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // Each iteration of this loop reads one member-declaration.
12611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
12624cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // Check for extraneous top-level semicolon.
12634cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    if (Tok.is(tok::semi)) {
12644cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      Diag(Tok, diag::ext_extra_struct_semi);
12654cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      ConsumeToken();
12664cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      continue;
12674cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    }
12684cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
12694cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    AccessSpecifier AS = getAccessSpecifierIfPresent();
12704cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    if (AS != AS_none) {
12714cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      // Current token is a C++ access specifier.
12724cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      CurAS = AS;
12734cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      ConsumeToken();
12744cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      ExpectAndConsume(tok::colon, diag::err_expected_colon);
12754cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis      continue;
12764cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    }
12774cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
127837b372b76a3fafe77186d7e6079e5642e2017478Douglas Gregor    // FIXME: Make sure we don't have a template here.
12791eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
12804cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // Parse all the comma separated declarators.
12814cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    ParseCXXClassMemberDeclaration(CurAS);
12824cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  }
12831eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
12844cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  SourceLocation RBraceLoc = MatchRHSPunctuation(tok::r_brace, LBraceLoc);
12851eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
12864cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  AttributeList *AttrList = 0;
12874cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // If attributes exist after class contents, parse them.
12884cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  if (Tok.is(tok::kw___attribute))
12894cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    AttrList = ParseAttributes(); // FIXME: where should I put them?
12904cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
12914cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  Actions.ActOnFinishCXXMemberSpecification(CurScope, RecordLoc, TagDecl,
12924cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis                                            LBraceLoc, RBraceLoc);
12934cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
12944cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // C++ 9.2p2: Within the class member-specification, the class is regarded as
12954cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // complete within function bodies, default arguments,
12964cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // exception-specifications, and constructor ctor-initializers (including
12974cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // such things in nested classes).
12984cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  //
129972b505b7904b3c9320a1312998800ba76e4f5841Douglas Gregor  // FIXME: Only function bodies and constructor ctor-initializers are
130072b505b7904b3c9320a1312998800ba76e4f5841Douglas Gregor  // parsed correctly, fix the rest.
13016569d68745c8213709740337d2be52b031384f58Douglas Gregor  if (TopLevelClass) {
13024cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis    // We are not inside a nested class. This class and its nested classes
130372b505b7904b3c9320a1312998800ba76e4f5841Douglas Gregor    // are complete and we can parse the delayed portions of method
130472b505b7904b3c9320a1312998800ba76e4f5841Douglas Gregor    // declarations and the lexed inline method definitions.
13056569d68745c8213709740337d2be52b031384f58Douglas Gregor    ParseLexedMethodDeclarations(getCurrentClass());
13066569d68745c8213709740337d2be52b031384f58Douglas Gregor    ParseLexedMethodDefs(getCurrentClass());
13074cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  }
13084cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
13094cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis  // Leave the class scope.
13106569d68745c8213709740337d2be52b031384f58Douglas Gregor  ParsingDef.Pop();
13118935b8b49053122ddd3ab4cd59af0fe5eb9c23cfDouglas Gregor  ClassScope.Exit();
13124cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis
131307a5b282fbe719986df9ed05543081ea0ed94aa5Argyrios Kyrtzidis  Actions.ActOnTagFinishDefinition(CurScope, TagDecl, RBraceLoc);
13144cc18a4d5222e04bd568b1e3e4d86127dbbcdf3fArgyrios Kyrtzidis}
13157ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor
13167ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// ParseConstructorInitializer - Parse a C++ constructor initializer,
13177ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// which explicitly initializes the members or base classes of a
13187ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// class (C++ [class.base.init]). For example, the three initializers
13197ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// after the ':' in the Derived constructor below:
13207ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor///
13217ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// @code
13227ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// class Base { };
13237ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// class Derived : Base {
13247ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor///   int x;
13257ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor///   float f;
13267ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// public:
13277ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor///   Derived(float f) : Base(), x(17), f(f) { }
13287ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// };
13297ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// @endcode
13307ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor///
13311eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// [C++]  ctor-initializer:
13321eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump///          ':' mem-initializer-list
13337ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor///
13341eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// [C++]  mem-initializer-list:
13351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump///          mem-initializer
13361eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump///          mem-initializer , mem-initializer-list
1337b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris Lattnervoid Parser::ParseConstructorInitializer(DeclPtrTy ConstructorDecl) {
13387ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  assert(Tok.is(tok::colon) && "Constructor initializer always starts with ':'");
13397ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor
13407ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  SourceLocation ColonLoc = ConsumeToken();
13411eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
13427ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  llvm::SmallVector<MemInitTy*, 4> MemInitializers;
13431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
13447ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  do {
13457ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor    MemInitResult MemInit = ParseMemInitializer(ConstructorDecl);
13465ac8aff3d7431dc7e4d64d960574a10c9f7e0078Douglas Gregor    if (!MemInit.isInvalid())
13475ac8aff3d7431dc7e4d64d960574a10c9f7e0078Douglas Gregor      MemInitializers.push_back(MemInit.get());
13487ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor
13497ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor    if (Tok.is(tok::comma))
13507ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor      ConsumeToken();
13517ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor    else if (Tok.is(tok::l_brace))
13527ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor      break;
13537ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor    else {
13547ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor      // Skip over garbage, until we get to '{'.  Don't eat the '{'.
1355d3a413d3b8eb39bcee5944bc545d9997c1abe492Sebastian Redl      Diag(Tok.getLocation(), diag::err_expected_lbrace_or_comma);
13567ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor      SkipUntil(tok::l_brace, true, true);
13577ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor      break;
13587ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor    }
13597ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  } while (true);
13607ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor
13611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  Actions.ActOnMemInitializers(ConstructorDecl, ColonLoc,
1362beaaccd8e2a8748f77b66e2b330fb9136937e14cJay Foad                               MemInitializers.data(), MemInitializers.size());
13637ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor}
13647ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor
13657ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// ParseMemInitializer - Parse a C++ member initializer, which is
13667ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// part of a constructor initializer that explicitly initializes one
13677ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// member or base class (C++ [class.base.init]). See
13687ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// ParseConstructorInitializer for an example.
13697ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor///
13707ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// [C++] mem-initializer:
13717ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor///         mem-initializer-id '(' expression-list[opt] ')'
13721eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump///
13737ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor/// [C++] mem-initializer-id:
13747ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor///         '::'[opt] nested-name-specifier[opt] class-name
13757ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor///         identifier
1376b28317a8e5e0e2953d1e5406d753d6c3c7f1e7d2Chris LattnerParser::MemInitResult Parser::ParseMemInitializer(DeclPtrTy ConstructorDecl) {
1377bcfad54a43e5570e09daddd976bd4545933e75b1Fariborz Jahanian  // parse '::'[opt] nested-name-specifier[opt]
1378bcfad54a43e5570e09daddd976bd4545933e75b1Fariborz Jahanian  CXXScopeSpec SS;
13792dd078ae50ff7be1fb25ebeedde45e9ab691a4f0Douglas Gregor  ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/0, false);
1380961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian  TypeTy *TemplateTypeTy = 0;
1381961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian  if (Tok.is(tok::annot_template_id)) {
1382961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian    TemplateIdAnnotation *TemplateId
1383961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian      = static_cast<TemplateIdAnnotation *>(Tok.getAnnotationValue());
1384961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian    if (TemplateId->Kind == TNK_Type_template) {
1385961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian      AnnotateTemplateIdTokenAsType(&SS);
1386961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian      assert(Tok.is(tok::annot_typename) && "template-id -> type failed");
1387961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian      TemplateTypeTy = Tok.getAnnotationValue();
1388961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian    }
1389961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian    // FIXME. May need to check for TNK_Dependent_template as well.
1390961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian  }
1391961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian  if (!TemplateTypeTy && Tok.isNot(tok::identifier)) {
13921ab3b96de160e4fbffec2a776e284a48a3bb543dChris Lattner    Diag(Tok, diag::err_expected_member_or_base_name);
13937ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor    return true;
13947ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  }
13951eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
13967ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  // Get the identifier. This may be a member name or a class name,
13977ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  // but we'll let the semantic analysis determine which it is.
1398961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian  IdentifierInfo *II = Tok.is(tok::identifier) ? Tok.getIdentifierInfo() : 0;
13997ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  SourceLocation IdLoc = ConsumeToken();
14007ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor
14017ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  // Parse the '('.
14027ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  if (Tok.isNot(tok::l_paren)) {
14031ab3b96de160e4fbffec2a776e284a48a3bb543dChris Lattner    Diag(Tok, diag::err_expected_lparen);
14047ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor    return true;
14057ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  }
14067ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  SourceLocation LParenLoc = ConsumeParen();
14077ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor
14087ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  // Parse the optional expression-list.
1409a55e52c0802cae3b7c366a05c461d3d15074c1a3Sebastian Redl  ExprVector ArgExprs(Actions);
14107ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  CommaLocsTy CommaLocs;
14117ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  if (Tok.isNot(tok::r_paren) && ParseExpressionList(ArgExprs, CommaLocs)) {
14127ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor    SkipUntil(tok::r_paren);
14137ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor    return true;
14147ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  }
14157ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor
14167ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor  SourceLocation RParenLoc = MatchRHSPunctuation(tok::r_paren, LParenLoc);
14177ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor
1418961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian  return Actions.ActOnMemInitializer(ConstructorDecl, CurScope, SS, II,
1419961743326fd18776f897bf4461345dba680ef637Fariborz Jahanian                                     TemplateTypeTy, IdLoc,
1420a55e52c0802cae3b7c366a05c461d3d15074c1a3Sebastian Redl                                     LParenLoc, ArgExprs.take(),
1421beaaccd8e2a8748f77b66e2b330fb9136937e14cJay Foad                                     ArgExprs.size(), CommaLocs.data(),
1422beaaccd8e2a8748f77b66e2b330fb9136937e14cJay Foad                                     RParenLoc);
14237ad8390f7992ab7f19b1460c5f0b9d96f165c4e9Douglas Gregor}
14240fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor
14250fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor/// ParseExceptionSpecification - Parse a C++ exception-specification
14260fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor/// (C++ [except.spec]).
14270fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor///
1428a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor///       exception-specification:
1429a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor///         'throw' '(' type-id-list [opt] ')'
1430a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor/// [MS]    'throw' '(' '...' ')'
14311eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump///
1432a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor///       type-id-list:
1433a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor///         type-id
1434a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor///         type-id-list ',' type-id
14350fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor///
14367dc813462dd9fd3f6f4296f896a12de14264fef8Sebastian Redlbool Parser::ParseExceptionSpecification(SourceLocation &EndLoc,
1437ef65f06e8e440aec541442cfd73a8a836e9bc842Sebastian Redl                                         llvm::SmallVector<TypeTy*, 2>
1438ef65f06e8e440aec541442cfd73a8a836e9bc842Sebastian Redl                                             &Exceptions,
1439ef65f06e8e440aec541442cfd73a8a836e9bc842Sebastian Redl                                         llvm::SmallVector<SourceRange, 2>
1440ef65f06e8e440aec541442cfd73a8a836e9bc842Sebastian Redl                                             &Ranges,
14417dc813462dd9fd3f6f4296f896a12de14264fef8Sebastian Redl                                         bool &hasAnyExceptionSpec) {
14420fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor  assert(Tok.is(tok::kw_throw) && "expected throw");
14431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
14440fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor  SourceLocation ThrowLoc = ConsumeToken();
14451eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
14460fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor  if (!Tok.is(tok::l_paren)) {
14470fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor    return Diag(Tok, diag::err_expected_lparen_after) << "throw";
14480fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor  }
14490fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor  SourceLocation LParenLoc = ConsumeParen();
14500fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor
1451a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor  // Parse throw(...), a Microsoft extension that means "this function
1452a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor  // can throw anything".
1453a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor  if (Tok.is(tok::ellipsis)) {
14547dc813462dd9fd3f6f4296f896a12de14264fef8Sebastian Redl    hasAnyExceptionSpec = true;
1455a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor    SourceLocation EllipsisLoc = ConsumeToken();
1456a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor    if (!getLang().Microsoft)
1457a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor      Diag(EllipsisLoc, diag::ext_ellipsis_exception_spec);
1458ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl    EndLoc = MatchRHSPunctuation(tok::r_paren, LParenLoc);
1459a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor    return false;
1460a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor  }
1461a4745616ebe36ba7699f18618382e764aa8183a1Douglas Gregor
14620fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor  // Parse the sequence of type-ids.
1463ef65f06e8e440aec541442cfd73a8a836e9bc842Sebastian Redl  SourceRange Range;
14640fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor  while (Tok.isNot(tok::r_paren)) {
1465ef65f06e8e440aec541442cfd73a8a836e9bc842Sebastian Redl    TypeResult Res(ParseTypeName(&Range));
1466ef65f06e8e440aec541442cfd73a8a836e9bc842Sebastian Redl    if (!Res.isInvalid()) {
14677dc813462dd9fd3f6f4296f896a12de14264fef8Sebastian Redl      Exceptions.push_back(Res.get());
1468ef65f06e8e440aec541442cfd73a8a836e9bc842Sebastian Redl      Ranges.push_back(Range);
1469ef65f06e8e440aec541442cfd73a8a836e9bc842Sebastian Redl    }
14700fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor    if (Tok.is(tok::comma))
14710fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor      ConsumeToken();
14727dc813462dd9fd3f6f4296f896a12de14264fef8Sebastian Redl    else
14730fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor      break;
14740fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor  }
14750fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor
1476ab197baec16bacade82325fb274cf6b992ac5d8aSebastian Redl  EndLoc = MatchRHSPunctuation(tok::r_paren, LParenLoc);
14770fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor  return false;
14780fe7bea6fca9737c6c145aaa4a2ad3abe595782aDouglas Gregor}
14796569d68745c8213709740337d2be52b031384f58Douglas Gregor
14806569d68745c8213709740337d2be52b031384f58Douglas Gregor/// \brief We have just started parsing the definition of a new class,
14816569d68745c8213709740337d2be52b031384f58Douglas Gregor/// so push that class onto our stack of classes that is currently
14826569d68745c8213709740337d2be52b031384f58Douglas Gregor/// being parsed.
14836569d68745c8213709740337d2be52b031384f58Douglas Gregorvoid Parser::PushParsingClass(DeclPtrTy ClassDecl, bool TopLevelClass) {
14841eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  assert((TopLevelClass || !ClassStack.empty()) &&
14856569d68745c8213709740337d2be52b031384f58Douglas Gregor         "Nested class without outer class");
14866569d68745c8213709740337d2be52b031384f58Douglas Gregor  ClassStack.push(new ParsingClass(ClassDecl, TopLevelClass));
14876569d68745c8213709740337d2be52b031384f58Douglas Gregor}
14886569d68745c8213709740337d2be52b031384f58Douglas Gregor
14896569d68745c8213709740337d2be52b031384f58Douglas Gregor/// \brief Deallocate the given parsed class and all of its nested
14906569d68745c8213709740337d2be52b031384f58Douglas Gregor/// classes.
14916569d68745c8213709740337d2be52b031384f58Douglas Gregorvoid Parser::DeallocateParsedClasses(Parser::ParsingClass *Class) {
14926569d68745c8213709740337d2be52b031384f58Douglas Gregor  for (unsigned I = 0, N = Class->NestedClasses.size(); I != N; ++I)
14936569d68745c8213709740337d2be52b031384f58Douglas Gregor    DeallocateParsedClasses(Class->NestedClasses[I]);
14946569d68745c8213709740337d2be52b031384f58Douglas Gregor  delete Class;
14956569d68745c8213709740337d2be52b031384f58Douglas Gregor}
14966569d68745c8213709740337d2be52b031384f58Douglas Gregor
14976569d68745c8213709740337d2be52b031384f58Douglas Gregor/// \brief Pop the top class of the stack of classes that are
14986569d68745c8213709740337d2be52b031384f58Douglas Gregor/// currently being parsed.
14996569d68745c8213709740337d2be52b031384f58Douglas Gregor///
15006569d68745c8213709740337d2be52b031384f58Douglas Gregor/// This routine should be called when we have finished parsing the
15016569d68745c8213709740337d2be52b031384f58Douglas Gregor/// definition of a class, but have not yet popped the Scope
15026569d68745c8213709740337d2be52b031384f58Douglas Gregor/// associated with the class's definition.
15036569d68745c8213709740337d2be52b031384f58Douglas Gregor///
15046569d68745c8213709740337d2be52b031384f58Douglas Gregor/// \returns true if the class we've popped is a top-level class,
15056569d68745c8213709740337d2be52b031384f58Douglas Gregor/// false otherwise.
15066569d68745c8213709740337d2be52b031384f58Douglas Gregorvoid Parser::PopParsingClass() {
15076569d68745c8213709740337d2be52b031384f58Douglas Gregor  assert(!ClassStack.empty() && "Mismatched push/pop for class parsing");
15081eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
15096569d68745c8213709740337d2be52b031384f58Douglas Gregor  ParsingClass *Victim = ClassStack.top();
15106569d68745c8213709740337d2be52b031384f58Douglas Gregor  ClassStack.pop();
15116569d68745c8213709740337d2be52b031384f58Douglas Gregor  if (Victim->TopLevelClass) {
15126569d68745c8213709740337d2be52b031384f58Douglas Gregor    // Deallocate all of the nested classes of this class,
15136569d68745c8213709740337d2be52b031384f58Douglas Gregor    // recursively: we don't need to keep any of this information.
15146569d68745c8213709740337d2be52b031384f58Douglas Gregor    DeallocateParsedClasses(Victim);
15156569d68745c8213709740337d2be52b031384f58Douglas Gregor    return;
15161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  }
15176569d68745c8213709740337d2be52b031384f58Douglas Gregor  assert(!ClassStack.empty() && "Missing top-level class?");
15186569d68745c8213709740337d2be52b031384f58Douglas Gregor
15196569d68745c8213709740337d2be52b031384f58Douglas Gregor  if (Victim->MethodDecls.empty() && Victim->MethodDefs.empty() &&
15206569d68745c8213709740337d2be52b031384f58Douglas Gregor      Victim->NestedClasses.empty()) {
15216569d68745c8213709740337d2be52b031384f58Douglas Gregor    // The victim is a nested class, but we will not need to perform
15226569d68745c8213709740337d2be52b031384f58Douglas Gregor    // any processing after the definition of this class since it has
15236569d68745c8213709740337d2be52b031384f58Douglas Gregor    // no members whose handling was delayed. Therefore, we can just
15246569d68745c8213709740337d2be52b031384f58Douglas Gregor    // remove this nested class.
15256569d68745c8213709740337d2be52b031384f58Douglas Gregor    delete Victim;
15266569d68745c8213709740337d2be52b031384f58Douglas Gregor    return;
15276569d68745c8213709740337d2be52b031384f58Douglas Gregor  }
15286569d68745c8213709740337d2be52b031384f58Douglas Gregor
15296569d68745c8213709740337d2be52b031384f58Douglas Gregor  // This nested class has some members that will need to be processed
15306569d68745c8213709740337d2be52b031384f58Douglas Gregor  // after the top-level class is completely defined. Therefore, add
15316569d68745c8213709740337d2be52b031384f58Douglas Gregor  // it to the list of nested classes within its parent.
15326569d68745c8213709740337d2be52b031384f58Douglas Gregor  assert(CurScope->isClassScope() && "Nested class outside of class scope?");
15336569d68745c8213709740337d2be52b031384f58Douglas Gregor  ClassStack.top()->NestedClasses.push_back(Victim);
15346569d68745c8213709740337d2be52b031384f58Douglas Gregor  Victim->TemplateScope = CurScope->getParent()->isTemplateParamScope();
15356569d68745c8213709740337d2be52b031384f58Douglas Gregor}
1536