diff options
author | Joao Matos <ripzonetriton@gmail.com> | 2012-08-31 18:45:21 +0000 |
---|---|---|
committer | Joao Matos <ripzonetriton@gmail.com> | 2012-08-31 18:45:21 +0000 |
commit | 6666ed4ed2e2bc13da5ac5d0a4947019137d45be (patch) | |
tree | aa69fbfff54188e6a8e772240a87e40e6b927b76 /lib/Parse/ParseDeclCXX.cpp | |
parent | a89f719ad3a7134e3eec7c9e03aa0e22031c0de9 (diff) |
Improved MSVC __interface support by adding first class support for it, instead of aliasing to "struct" which had some incorrect behaviour. Patch by David Robins.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@163013 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Parse/ParseDeclCXX.cpp')
-rw-r--r-- | lib/Parse/ParseDeclCXX.cpp | 72 |
1 files changed, 37 insertions, 35 deletions
diff --git a/lib/Parse/ParseDeclCXX.cpp b/lib/Parse/ParseDeclCXX.cpp index 42ec6b0205..e5740112bb 100644 --- a/lib/Parse/ParseDeclCXX.cpp +++ b/lib/Parse/ParseDeclCXX.cpp @@ -1031,12 +1031,14 @@ void Parser::ParseClassSpecifier(tok::TokenKind TagTokKind, const ParsedTemplateInfo &TemplateInfo, AccessSpecifier AS, bool EnteringContext, DeclSpecContext DSC) { - DeclSpec::TST TagType; - if (TagTokKind == tok::kw_struct) - TagType = DeclSpec::TST_struct; - else if (TagTokKind == tok::kw_class) - TagType = DeclSpec::TST_class; - else { + DeclSpec::TST TagType;
+ if (TagTokKind == tok::kw_struct)
+ TagType = DeclSpec::TST_struct;
+ else if (TagTokKind == tok::kw___interface)
+ TagType = DeclSpec::TST_interface;
+ else if (TagTokKind == tok::kw_class)
+ TagType = DeclSpec::TST_class;
+ else {
assert(TagTokKind == tok::kw_union && "Not a class specifier"); TagType = DeclSpec::TST_union; } @@ -1148,13 +1150,14 @@ void Parser::ParseClassSpecifier(tok::TokenKind TagTokKind, } Diag(NameLoc, diag::err_explicit_spec_non_template) - << (TemplateInfo.Kind == ParsedTemplateInfo::ExplicitInstantiation) - << (TagType == DeclSpec::TST_class? 0 - : TagType == DeclSpec::TST_struct? 1 - : 2) - << Name - << SourceRange(LAngleLoc, RAngleLoc); - + << (TemplateInfo.Kind == ParsedTemplateInfo::ExplicitInstantiation)
+ << (TagType == DeclSpec::TST_class? 0
+ : TagType == DeclSpec::TST_struct? 1
+ : TagType == DeclSpec::TST_interface? 2
+ : 3)
+ << Name
+ << SourceRange(LAngleLoc, RAngleLoc);
+
// Strip off the last template parameter list if it was empty, since // we've removed its template argument list. if (TemplateParams && TemplateInfo.LastParameterListWasEmpty) { @@ -1240,14 +1243,13 @@ void Parser::ParseClassSpecifier(tok::TokenKind TagTokKind, (Tok.is(tok::semi) || (Tok.isAtStartOfLine() && !isValidAfterTypeSpecifier(false)))) { TUK = DS.isFriendSpecified() ? Sema::TUK_Friend : Sema::TUK_Declaration; - if (Tok.isNot(tok::semi)) { - // A semicolon was missing after this declaration. Diagnose and recover. - ExpectAndConsume(tok::semi, diag::err_expected_semi_after_tagdecl, - TagType == DeclSpec::TST_class ? "class" : - TagType == DeclSpec::TST_struct ? "struct" : "union"); - PP.EnterToken(Tok); - Tok.setKind(tok::semi); - } + if (Tok.isNot(tok::semi)) {
+ // A semicolon was missing after this declaration. Diagnose and recover.
+ ExpectAndConsume(tok::semi, diag::err_expected_semi_after_tagdecl,
+ DeclSpec::getSpecifierName(TagType));
+ PP.EnterToken(Tok);
+ Tok.setKind(tok::semi);
+ }
} else TUK = Sema::TUK_Reference; @@ -1466,14 +1468,13 @@ void Parser::ParseClassSpecifier(tok::TokenKind TagTokKind, // Also enforce C++ [temp]p3: // In a template-declaration which defines a class, no declarator // is permitted. - if (TUK == Sema::TUK_Definition && - (TemplateInfo.Kind || !isValidAfterTypeSpecifier(false))) { - ExpectAndConsume(tok::semi, diag::err_expected_semi_after_tagdecl, - TagType == DeclSpec::TST_class ? "class" : - TagType == DeclSpec::TST_struct ? "struct" : "union"); - // Push this token back into the preprocessor and change our current token - // to ';' so that the rest of the code recovers as though there were an - // ';' after the definition. + if (TUK == Sema::TUK_Definition &&
+ (TemplateInfo.Kind || !isValidAfterTypeSpecifier(false))) {
+ ExpectAndConsume(tok::semi, diag::err_expected_semi_after_tagdecl,
+ DeclSpec::getSpecifierName(TagType));
+ // Push this token back into the preprocessor and change our current token
+ // to ';' so that the rest of the code recovers as though there were an
+ // ';' after the definition.
PP.EnterToken(Tok); Tok.setKind(tok::semi); } @@ -2236,12 +2237,13 @@ ExprResult Parser::ParseCXXMemberInitializer(Decl *D, bool IsFunction, /// member-declaration member-specification[opt] /// access-specifier ':' member-specification[opt] /// -void Parser::ParseCXXMemberSpecification(SourceLocation RecordLoc, - unsigned TagType, Decl *TagDecl) { - assert((TagType == DeclSpec::TST_struct || - TagType == DeclSpec::TST_union || - TagType == DeclSpec::TST_class) && "Invalid TagType!"); - +void Parser::ParseCXXMemberSpecification(SourceLocation RecordLoc,
+ unsigned TagType, Decl *TagDecl) {
+ assert((TagType == DeclSpec::TST_struct ||
+ TagType == DeclSpec::TST_interface ||
+ TagType == DeclSpec::TST_union ||
+ TagType == DeclSpec::TST_class) && "Invalid TagType!");
+
PrettyDeclStackTraceEntry CrashInfo(Actions, TagDecl, RecordLoc, "parsing struct/union/class body"); |