diff options
Diffstat (limited to 'clang/lib/Parse/ParseDeclCXX.cpp')
-rw-r--r-- | clang/lib/Parse/ParseDeclCXX.cpp | 44 |
1 files changed, 32 insertions, 12 deletions
diff --git a/clang/lib/Parse/ParseDeclCXX.cpp b/clang/lib/Parse/ParseDeclCXX.cpp index 9369f0f56c9..c814775c77e 100644 --- a/clang/lib/Parse/ParseDeclCXX.cpp +++ b/clang/lib/Parse/ParseDeclCXX.cpp @@ -3790,6 +3790,28 @@ IdentifierInfo *Parser::TryParseCXX11AttributeIdentifier(SourceLocation &Loc) { } return nullptr; + case tok::numeric_constant: { + // If we got a numeric constant, check to see if it comes from a macro that + // corresponds to the predefined __clang__ macro. If it does, warn the user + // and recover by pretending they said _Clang instead. + if (Tok.getLocation().isMacroID()) { + SmallString<8> ExpansionBuf; + SourceLocation ExpansionLoc = + PP.getSourceManager().getExpansionLoc(Tok.getLocation()); + StringRef Spelling = PP.getSpelling(ExpansionLoc, ExpansionBuf); + if (Spelling == "__clang__") { + SourceRange TokRange( + ExpansionLoc, + PP.getSourceManager().getExpansionLoc(Tok.getEndLoc())); + Diag(Tok, diag::warn_wrong_clang_attr_namespace) + << FixItHint::CreateReplacement(TokRange, "_Clang"); + Loc = ConsumeToken(); + return &PP.getIdentifierTable().get("_Clang"); + } + } + return nullptr; + } + case tok::ampamp: // 'and' case tok::pipe: // 'bitor' case tok::pipepipe: // 'or' @@ -3865,24 +3887,22 @@ bool Parser::ParseCXX11AttributeArgs(IdentifierInfo *AttrName, // Eat the left paren, then skip to the ending right paren. ConsumeParen(); SkipUntil(tok::r_paren); - return false;
- }
-
- if (ScopeName &&
- (ScopeName->getName() == "gnu" || ScopeName->getName() == "__gnu__")) {
- // GNU-scoped attributes have some special cases to handle GNU-specific
- // behaviors.
- ParseGNUAttributeArgs(AttrName, AttrNameLoc, Attrs, EndLoc, ScopeName,
+ return false; + } + + if (ScopeName && (ScopeName->isStr("gnu") || ScopeName->isStr("__gnu__"))) { + // GNU-scoped attributes have some special cases to handle GNU-specific + // behaviors. + ParseGNUAttributeArgs(AttrName, AttrNameLoc, Attrs, EndLoc, ScopeName, ScopeLoc, Syntax, nullptr); return true; } unsigned NumArgs; // Some Clang-scoped attributes have some special parsing behavior. - if (ScopeName && ScopeName->getName() == "clang") - NumArgs = - ParseClangAttributeArgs(AttrName, AttrNameLoc, Attrs, EndLoc, ScopeName, - ScopeLoc, Syntax); + if (ScopeName && (ScopeName->isStr("clang") || ScopeName->isStr("_Clang"))) + NumArgs = ParseClangAttributeArgs(AttrName, AttrNameLoc, Attrs, EndLoc, + ScopeName, ScopeLoc, Syntax); else NumArgs = ParseAttributeArgsCommon(AttrName, AttrNameLoc, Attrs, EndLoc, |