diff options
Diffstat (limited to 'lib/Lex/PPMacroExpansion.cpp')
-rw-r--r-- | lib/Lex/PPMacroExpansion.cpp | 456 |
1 files changed, 202 insertions, 254 deletions
diff --git a/lib/Lex/PPMacroExpansion.cpp b/lib/Lex/PPMacroExpansion.cpp index eee4342..21451f5 100644 --- a/lib/Lex/PPMacroExpansion.cpp +++ b/lib/Lex/PPMacroExpansion.cpp @@ -14,25 +14,26 @@ #include "clang/Lex/Preprocessor.h" #include "MacroArgs.h" -#include "clang/Lex/MacroInfo.h" -#include "clang/Basic/SourceManager.h" #include "clang/Basic/FileManager.h" +#include "clang/Basic/SourceManager.h" #include "clang/Basic/TargetInfo.h" -#include "clang/Lex/LexDiagnostic.h" #include "clang/Lex/CodeCompletionHandler.h" #include "clang/Lex/ExternalPreprocessorSource.h" -#include "clang/Lex/LiteralSupport.h" -#include "llvm/ADT/StringSwitch.h" +#include "clang/Lex/LexDiagnostic.h" +#include "clang/Lex/MacroInfo.h" #include "llvm/ADT/STLExtras.h" +#include "llvm/ADT/SmallString.h" +#include "llvm/ADT/StringSwitch.h" #include "llvm/Config/llvm-config.h" -#include "llvm/Support/raw_ostream.h" #include "llvm/Support/ErrorHandling.h" #include "llvm/Support/Format.h" +#include "llvm/Support/raw_ostream.h" #include <cstdio> #include <ctime> using namespace clang; -MacroInfo *Preprocessor::getMacroInfoHistory(IdentifierInfo *II) const { +MacroDirective * +Preprocessor::getMacroDirectiveHistory(const IdentifierInfo *II) const { assert(II->hadMacroDefinition() && "Identifier has not been not a macro!"); macro_iterator Pos = Macros.find(II); @@ -40,125 +41,31 @@ MacroInfo *Preprocessor::getMacroInfoHistory(IdentifierInfo *II) const { return Pos->second; } -/// setMacroInfo - Specify a macro for this identifier. -/// -void Preprocessor::setMacroInfo(IdentifierInfo *II, MacroInfo *MI) { - assert(MI && "MacroInfo should be non-zero!"); - assert(MI->getUndefLoc().isInvalid() && - "Undefined macros cannot be registered"); - - MacroInfo *&StoredMI = Macros[II]; - MI->setPreviousDefinition(StoredMI); - StoredMI = MI; - II->setHasMacroDefinition(MI->getUndefLoc().isInvalid()); - if (II->isFromAST()) - II->setChangedSinceDeserialization(); -} - -void Preprocessor::addLoadedMacroInfo(IdentifierInfo *II, MacroInfo *MI, - MacroInfo *Hint) { - assert(MI && "Missing macro?"); - assert(MI->isFromAST() && "Macro is not from an AST?"); - assert(!MI->getPreviousDefinition() && "Macro already in chain?"); - - MacroInfo *&StoredMI = Macros[II]; - - // Easy case: this is the first macro definition for this macro. - if (!StoredMI) { - StoredMI = MI; - - if (MI->isDefined()) - II->setHasMacroDefinition(true); - return; - } - - // If this macro is a definition and this identifier has been neither - // defined nor undef'd in the current translation unit, add this macro - // to the end of the chain of definitions. - if (MI->isDefined() && StoredMI->isFromAST()) { - // Simple case: if this is the first actual definition, just put it at - // th beginning. - if (!StoredMI->isDefined()) { - MI->setPreviousDefinition(StoredMI); - StoredMI = MI; - - II->setHasMacroDefinition(true); - return; - } - - // Find the end of the definition chain. - MacroInfo *Prev; - MacroInfo *PrevPrev = StoredMI; - bool Ambiguous = StoredMI->isAmbiguous(); - bool MatchedOther = false; - do { - Prev = PrevPrev; - - // If the macros are not identical, we have an ambiguity. - if (!Prev->isIdenticalTo(*MI, *this)) { - if (!Ambiguous) { - Ambiguous = true; - StoredMI->setAmbiguous(true); - } - } else { - MatchedOther = true; - } - } while ((PrevPrev = Prev->getPreviousDefinition()) && - PrevPrev->isDefined()); - - // If there are ambiguous definitions, and we didn't match any other - // definition, then mark us as ambiguous. - if (Ambiguous && !MatchedOther) - MI->setAmbiguous(true); - - // Wire this macro information into the chain. - MI->setPreviousDefinition(Prev->getPreviousDefinition()); - Prev->setPreviousDefinition(MI); - return; - } - - // The macro is not a definition; put it at the end of the list. - MacroInfo *Prev = Hint? Hint : StoredMI; - while (Prev->getPreviousDefinition()) - Prev = Prev->getPreviousDefinition(); - Prev->setPreviousDefinition(MI); -} - -void Preprocessor::makeLoadedMacroInfoVisible(IdentifierInfo *II, - MacroInfo *MI) { - assert(MI->isFromAST() && "Macro must be from the AST"); - - MacroInfo *&StoredMI = Macros[II]; - if (StoredMI == MI) { - // Easy case: this is the first macro anyway. - II->setHasMacroDefinition(MI->isDefined()); - return; - } - - // Go find the macro and pull it out of the list. - // FIXME: Yes, this is O(N), and making a pile of macros visible or hidden - // would be quadratic, but it's extremely rare. - MacroInfo *Prev = StoredMI; - while (Prev->getPreviousDefinition() != MI) - Prev = Prev->getPreviousDefinition(); - Prev->setPreviousDefinition(MI->getPreviousDefinition()); - MI->setPreviousDefinition(0); - - // Add the macro back to the list. - addLoadedMacroInfo(II, MI); - - II->setHasMacroDefinition(StoredMI->isDefined()); - if (II->isFromAST()) +void Preprocessor::appendMacroDirective(IdentifierInfo *II, MacroDirective *MD){ + assert(MD && "MacroDirective should be non-zero!"); + assert(!MD->getPrevious() && "Already attached to a MacroDirective history."); + + MacroDirective *&StoredMD = Macros[II]; + MD->setPrevious(StoredMD); + StoredMD = MD; + II->setHasMacroDefinition(MD->isDefined()); + bool isImportedMacro = isa<DefMacroDirective>(MD) && + cast<DefMacroDirective>(MD)->isImported(); + if (II->isFromAST() && !isImportedMacro) II->setChangedSinceDeserialization(); } -/// \brief Undefine a macro for this identifier. -void Preprocessor::clearMacroInfo(IdentifierInfo *II) { - assert(II->hasMacroDefinition() && "Macro is not defined!"); - assert(Macros[II]->getUndefLoc().isValid() && "Macro is still defined!"); - II->setHasMacroDefinition(false); - if (II->isFromAST()) - II->setChangedSinceDeserialization(); +void Preprocessor::setLoadedMacroDirective(IdentifierInfo *II, + MacroDirective *MD) { + assert(II && MD); + MacroDirective *&StoredMD = Macros[II]; + assert(!StoredMD && + "the macro history was modified before initializing it from a pch"); + StoredMD = MD; + // Setup the identifier as having associated macro history. + II->setHasMacroDefinition(true); + if (!MD->isDefined()) + II->setHasMacroDefinition(false); } /// RegisterBuiltinMacro - Register the specified identifier in the identifier @@ -170,7 +77,7 @@ static IdentifierInfo *RegisterBuiltinMacro(Preprocessor &PP, const char *Name){ // Mark it as being a macro that is builtin. MacroInfo *MI = PP.AllocateMacroInfo(SourceLocation()); MI->setIsBuiltinMacro(); - PP.setMacroInfo(Id, MI); + PP.appendDefMacroDirective(Id, MI); return Id; } @@ -303,7 +210,11 @@ bool Preprocessor::isNextPPTokenLParen() { /// HandleMacroExpandedIdentifier - If an identifier token is read that is to be /// expanded as a macro, handle it and return the next token as 'Identifier'. bool Preprocessor::HandleMacroExpandedIdentifier(Token &Identifier, - MacroInfo *MI) { + MacroDirective *MD) { + MacroDirective::DefInfo Def = MD->getDefinition(); + assert(Def.isValid()); + MacroInfo *MI = Def.getMacroInfo(); + // If this is a macro expansion in the "#if !defined(x)" line for the file, // then the macro could expand to different things in other contexts, we need // to disable the optimization in this case. @@ -311,7 +222,7 @@ bool Preprocessor::HandleMacroExpandedIdentifier(Token &Identifier, // If this is a builtin macro, like __LINE__ or _Pragma, handle it specially. if (MI->isBuiltinMacro()) { - if (Callbacks) Callbacks->MacroExpands(Identifier, MI, + if (Callbacks) Callbacks->MacroExpands(Identifier, MD, Identifier.getLocation()); ExpandBuiltinMacro(Identifier); return false; @@ -364,13 +275,13 @@ bool Preprocessor::HandleMacroExpandedIdentifier(Token &Identifier, // MacroExpands callbacks still happen in source order, queue this // callback to have it happen after the function macro callback. DelayedMacroExpandsCallbacks.push_back( - MacroExpandsInfo(Identifier, MI, ExpansionRange)); + MacroExpandsInfo(Identifier, MD, ExpansionRange)); } else { - Callbacks->MacroExpands(Identifier, MI, ExpansionRange); + Callbacks->MacroExpands(Identifier, MD, ExpansionRange); if (!DelayedMacroExpandsCallbacks.empty()) { for (unsigned i=0, e = DelayedMacroExpandsCallbacks.size(); i!=e; ++i) { MacroExpandsInfo &Info = DelayedMacroExpandsCallbacks[i]; - Callbacks->MacroExpands(Info.Tok, Info.MI, Info.Range); + Callbacks->MacroExpands(Info.Tok, Info.MD, Info.Range); } DelayedMacroExpandsCallbacks.clear(); } @@ -378,16 +289,17 @@ bool Preprocessor::HandleMacroExpandedIdentifier(Token &Identifier, } // If the macro definition is ambiguous, complain. - if (MI->isAmbiguous()) { + if (Def.getDirective()->isAmbiguous()) { Diag(Identifier, diag::warn_pp_ambiguous_macro) << Identifier.getIdentifierInfo(); Diag(MI->getDefinitionLoc(), diag::note_pp_ambiguous_macro_chosen) << Identifier.getIdentifierInfo(); - for (MacroInfo *PrevMI = MI->getPreviousDefinition(); - PrevMI && PrevMI->isDefined(); - PrevMI = PrevMI->getPreviousDefinition()) { - if (PrevMI->isAmbiguous()) { - Diag(PrevMI->getDefinitionLoc(), diag::note_pp_ambiguous_macro_other) + for (MacroDirective::DefInfo PrevDef = Def.getPreviousDefinition(); + PrevDef && !PrevDef.isUndefined(); + PrevDef = PrevDef.getPreviousDefinition()) { + if (PrevDef.getDirective()->isAmbiguous()) { + Diag(PrevDef.getMacroInfo()->getDefinitionLoc(), + diag::note_pp_ambiguous_macro_other) << Identifier.getIdentifierInfo(); } } @@ -455,7 +367,10 @@ bool Preprocessor::HandleMacroExpandedIdentifier(Token &Identifier, if (MacroInfo *NewMI = getMacroInfo(NewII)) if (!NewMI->isEnabled() || NewMI == MI) { Identifier.setFlag(Token::DisableExpand); - Diag(Identifier, diag::pp_disabled_macro_expansion); + // Don't warn for "#define X X" like "#define bool bool" from + // stdbool.h. + if (NewMI != MI || MI->isFunctionLike()) + Diag(Identifier, diag::pp_disabled_macro_expansion); } } @@ -497,9 +412,13 @@ MacroArgs *Preprocessor::ReadFunctionLikeMacroArgs(Token &MacroName, // argument is separated by an EOF token. Use a SmallVector so we can avoid // heap allocations in the common case. SmallVector<Token, 64> ArgTokens; + bool ContainsCodeCompletionTok = false; unsigned NumActuals = 0; while (Tok.isNot(tok::r_paren)) { + if (ContainsCodeCompletionTok && (Tok.is(tok::eof) || Tok.is(tok::eod))) + break; + assert((Tok.is(tok::l_paren) || Tok.is(tok::comma)) && "only expect argument separators here"); @@ -516,10 +435,20 @@ MacroArgs *Preprocessor::ReadFunctionLikeMacroArgs(Token &MacroName, LexUnexpandedToken(Tok); if (Tok.is(tok::eof) || Tok.is(tok::eod)) { // "#if f(<eof>" & "#if f(\n" - Diag(MacroName, diag::err_unterm_macro_invoc); - // Do not lose the EOF/EOD. Return it to the client. - MacroName = Tok; - return 0; + if (!ContainsCodeCompletionTok) { + Diag(MacroName, diag::err_unterm_macro_invoc); + Diag(MI->getDefinitionLoc(), diag::note_macro_here) + << MacroName.getIdentifierInfo(); + // Do not lose the EOF/EOD. Return it to the client. + MacroName = Tok; + return 0; + } else { + // Do not lose the EOF/EOD. + Token *Toks = new Token[1]; + Toks[0] = Tok; + EnterTokenStream(Toks, 1, true, true); + break; + } } else if (Tok.is(tok::r_paren)) { // If we found the ) token, the macro arg list is done. if (NumParens-- == 0) { @@ -550,6 +479,7 @@ MacroArgs *Preprocessor::ReadFunctionLikeMacroArgs(Token &MacroName, if (!MI->isEnabled()) Tok.setFlag(Token::DisableExpand); } else if (Tok.is(tok::code_completion)) { + ContainsCodeCompletionTok = true; if (CodeComplete) CodeComplete->CodeCompleteMacroArgument(MacroName.getIdentifierInfo(), MI, NumActuals); @@ -572,16 +502,20 @@ MacroArgs *Preprocessor::ReadFunctionLikeMacroArgs(Token &MacroName, if (ArgTokens.size() != ArgTokenStart) ArgStartLoc = ArgTokens[ArgTokenStart].getLocation(); - // Emit the diagnostic at the macro name in case there is a missing ). - // Emitting it at the , could be far away from the macro name. - Diag(ArgStartLoc, diag::err_too_many_args_in_macro_invoc); - return 0; + if (!ContainsCodeCompletionTok) { + // Emit the diagnostic at the macro name in case there is a missing ). + // Emitting it at the , could be far away from the macro name. + Diag(ArgStartLoc, diag::err_too_many_args_in_macro_invoc); + Diag(MI->getDefinitionLoc(), diag::note_macro_here) + << MacroName.getIdentifierInfo(); + return 0; + } } // Empty arguments are standard in C99 and C++0x, and are supported as an extension in // other modes. if (ArgTokens.size() == ArgTokenStart && !LangOpts.C99) - Diag(Tok, LangOpts.CPlusPlus0x ? + Diag(Tok, LangOpts.CPlusPlus11 ? diag::warn_cxx98_compat_empty_fnmacro_arg : diag::ext_empty_fnmacro_arg); @@ -593,8 +527,10 @@ MacroArgs *Preprocessor::ReadFunctionLikeMacroArgs(Token &MacroName, EOFTok.setLength(0); ArgTokens.push_back(EOFTok); ++NumActuals; - assert(NumFixedArgsLeft != 0 && "Too many arguments parsed"); - --NumFixedArgsLeft; + if (!ContainsCodeCompletionTok || NumFixedArgsLeft != 0) { + assert(NumFixedArgsLeft != 0 && "Too many arguments parsed"); + --NumFixedArgsLeft; + } } // Okay, we either found the r_paren. Check to see if we parsed too few @@ -604,6 +540,17 @@ MacroArgs *Preprocessor::ReadFunctionLikeMacroArgs(Token &MacroName, // See MacroArgs instance var for description of this. bool isVarargsElided = false; + if (ContainsCodeCompletionTok) { + // Recover from not-fully-formed macro invocation during code-completion. + Token EOFTok; + EOFTok.startToken(); + EOFTok.setKind(tok::eof); + EOFTok.setLocation(Tok.getLocation()); + EOFTok.setLength(0); + for (; NumActuals < MinArgsExpected; ++NumActuals) + ArgTokens.push_back(EOFTok); + } + if (NumActuals < MinArgsExpected) { // There are several cases where too few arguments is ok, handle them now. if (NumActuals == 0 && MinArgsExpected == 1) { @@ -619,9 +566,14 @@ MacroArgs *Preprocessor::ReadFunctionLikeMacroArgs(Token &MacroName, // Varargs where the named vararg parameter is missing: OK as extension. // #define A(x, ...) // A("blah") - Diag(Tok, diag::ext_missing_varargs_arg); - Diag(MI->getDefinitionLoc(), diag::note_macro_here) - << MacroName.getIdentifierInfo(); + // + // If the macro contains the comma pasting extension, the diagnostic + // is suppressed; we know we'll get another diagnostic later. + if (!MI->hasCommaPasting()) { + Diag(Tok, diag::ext_missing_varargs_arg); + Diag(MI->getDefinitionLoc(), diag::note_macro_here) + << MacroName.getIdentifierInfo(); + } // Remember this occurred, allowing us to elide the comma when used for // cases like: @@ -630,9 +582,11 @@ MacroArgs *Preprocessor::ReadFunctionLikeMacroArgs(Token &MacroName, // #define C(...) blah(a, ## __VA_ARGS__) // A(x) B(x) C() isVarargsElided = true; - } else { + } else if (!ContainsCodeCompletionTok) { // Otherwise, emit the error. Diag(Tok, diag::err_too_few_args_in_macro_invoc); + Diag(MI->getDefinitionLoc(), diag::note_macro_here) + << MacroName.getIdentifierInfo(); return 0; } @@ -648,10 +602,13 @@ MacroArgs *Preprocessor::ReadFunctionLikeMacroArgs(Token &MacroName, if (NumActuals == 0 && MinArgsExpected == 2) ArgTokens.push_back(Tok); - } else if (NumActuals > MinArgsExpected && !MI->isVariadic()) { + } else if (NumActuals > MinArgsExpected && !MI->isVariadic() && + !ContainsCodeCompletionTok) { // Emit the diagnostic at the macro name in case there is a missing ). // Emitting it at the , could be far away from the macro name. Diag(MacroName, diag::err_too_many_args_in_macro_invoc); + Diag(MI->getDefinitionLoc(), diag::note_macro_here) + << MacroName.getIdentifierInfo(); return 0; } @@ -745,7 +702,7 @@ static bool HasFeature(const Preprocessor &PP, const IdentifierInfo *II) { Feature = Feature.substr(2, Feature.size() - 4); return llvm::StringSwitch<bool>(Feature) - .Case("address_sanitizer", LangOpts.SanitizeAddress) + .Case("address_sanitizer", LangOpts.Sanitize.Address) .Case("attribute_analyzer_noreturn", true) .Case("attribute_availability", true) .Case("attribute_availability_with_message", true) @@ -767,6 +724,8 @@ static bool HasFeature(const Preprocessor &PP, const IdentifierInfo *II) { .Case("cxx_exceptions", LangOpts.Exceptions) .Case("cxx_rtti", LangOpts.RTTI) .Case("enumerator_attributes", true) + .Case("memory_sanitizer", LangOpts.Sanitize.Memory) + .Case("thread_sanitizer", LangOpts.Sanitize.Thread) // Objective-C features .Case("objc_arr", LangOpts.ObjCAutoRefCount) // FIXME: REMOVE? .Case("objc_arc", LangOpts.ObjCAutoRefCount) @@ -776,6 +735,7 @@ static bool HasFeature(const Preprocessor &PP, const IdentifierInfo *II) { .Case("objc_instancetype", LangOpts.ObjC2) .Case("objc_modules", LangOpts.ObjC2 && LangOpts.Modules) .Case("objc_nonfragile_abi", LangOpts.ObjCRuntime.isNonFragile()) + .Case("objc_property_explicit_atomic", true) // Does clang support explicit "atomic" keyword? .Case("objc_weak_class", LangOpts.ObjCRuntime.hasWeakClassImport()) .Case("ownership_holds", true) .Case("ownership_returns", true) @@ -792,41 +752,41 @@ static bool HasFeature(const Preprocessor &PP, const IdentifierInfo *II) { .Case("c_generic_selections", LangOpts.C11) .Case("c_static_assert", LangOpts.C11) // C++11 features - .Case("cxx_access_control_sfinae", LangOpts.CPlusPlus0x) - .Case("cxx_alias_templates", LangOpts.CPlusPlus0x) - .Case("cxx_alignas", LangOpts.CPlusPlus0x) - .Case("cxx_atomic", LangOpts.CPlusPlus0x) - .Case("cxx_attributes", LangOpts.CPlusPlus0x) - .Case("cxx_auto_type", LangOpts.CPlusPlus0x) - .Case("cxx_constexpr", LangOpts.CPlusPlus0x) - .Case("cxx_decltype", LangOpts.CPlusPlus0x) - .Case("cxx_decltype_incomplete_return_types", LangOpts.CPlusPlus0x) - .Case("cxx_default_function_template_args", LangOpts.CPlusPlus0x) - .Case("cxx_defaulted_functions", LangOpts.CPlusPlus0x) - .Case("cxx_delegating_constructors", LangOpts.CPlusPlus0x) - .Case("cxx_deleted_functions", LangOpts.CPlusPlus0x) - .Case("cxx_explicit_conversions", LangOpts.CPlusPlus0x) - .Case("cxx_generalized_initializers", LangOpts.CPlusPlus0x) - .Case("cxx_implicit_moves", LangOpts.CPlusPlus0x) + .Case("cxx_access_control_sfinae", LangOpts.CPlusPlus11) + .Case("cxx_alias_templates", LangOpts.CPlusPlus11) + .Case("cxx_alignas", LangOpts.CPlusPlus11) + .Case("cxx_atomic", LangOpts.CPlusPlus11) + .Case("cxx_attributes", LangOpts.CPlusPlus11) + .Case("cxx_auto_type", LangOpts.CPlusPlus11) + .Case("cxx_constexpr", LangOpts.CPlusPlus11) + .Case("cxx_decltype", LangOpts.CPlusPlus11) + .Case("cxx_decltype_incomplete_return_types", LangOpts.CPlusPlus11) + .Case("cxx_default_function_template_args", LangOpts.CPlusPlus11) + .Case("cxx_defaulted_functions", LangOpts.CPlusPlus11) + .Case("cxx_delegating_constructors", LangOpts.CPlusPlus11) + .Case("cxx_deleted_functions", LangOpts.CPlusPlus11) + .Case("cxx_explicit_conversions", LangOpts.CPlusPlus11) + .Case("cxx_generalized_initializers", LangOpts.CPlusPlus11) + .Case("cxx_implicit_moves", LangOpts.CPlusPlus11) //.Case("cxx_inheriting_constructors", false) - .Case("cxx_inline_namespaces", LangOpts.CPlusPlus0x) - .Case("cxx_lambdas", LangOpts.CPlusPlus0x) - .Case("cxx_local_type_template_args", LangOpts.CPlusPlus0x) - .Case("cxx_nonstatic_member_init", LangOpts.CPlusPlus0x) - .Case("cxx_noexcept", LangOpts.CPlusPlus0x) - .Case("cxx_nullptr", LangOpts.CPlusPlus0x) - .Case("cxx_override_control", LangOpts.CPlusPlus0x) - .Case("cxx_range_for", LangOpts.CPlusPlus0x) - .Case("cxx_raw_string_literals", LangOpts.CPlusPlus0x) - .Case("cxx_reference_qualified_functions", LangOpts.CPlusPlus0x) - .Case("cxx_rvalue_references", LangOpts.CPlusPlus0x) - .Case("cxx_strong_enums", LangOpts.CPlusPlus0x) - .Case("cxx_static_assert", LangOpts.CPlusPlus0x) - .Case("cxx_trailing_return", LangOpts.CPlusPlus0x) - .Case("cxx_unicode_literals", LangOpts.CPlusPlus0x) - .Case("cxx_unrestricted_unions", LangOpts.CPlusPlus0x) - .Case("cxx_user_literals", LangOpts.CPlusPlus0x) - .Case("cxx_variadic_templates", LangOpts.CPlusPlus0x) + .Case("cxx_inline_namespaces", LangOpts.CPlusPlus11) + .Case("cxx_lambdas", LangOpts.CPlusPlus11) + .Case("cxx_local_type_template_args", LangOpts.CPlusPlus11) + .Case("cxx_nonstatic_member_init", LangOpts.CPlusPlus11) + .Case("cxx_noexcept", LangOpts.CPlusPlus11) + .Case("cxx_nullptr", LangOpts.CPlusPlus11) + .Case("cxx_override_control", LangOpts.CPlusPlus11) + .Case("cxx_range_for", LangOpts.CPlusPlus11) + .Case("cxx_raw_string_literals", LangOpts.CPlusPlus11) + .Case("cxx_reference_qualified_functions", LangOpts.CPlusPlus11) + .Case("cxx_rvalue_references", LangOpts.CPlusPlus11) + .Case("cxx_strong_enums", LangOpts.CPlusPlus11) + .Case("cxx_static_assert", LangOpts.CPlusPlus11) + .Case("cxx_trailing_return", LangOpts.CPlusPlus11) + .Case("cxx_unicode_literals", LangOpts.CPlusPlus11) + .Case("cxx_unrestricted_unions", LangOpts.CPlusPlus11) + .Case("cxx_user_literals", LangOpts.CPlusPlus11) + .Case("cxx_variadic_templates", LangOpts.CPlusPlus11) // Type traits .Case("has_nothrow_assign", LangOpts.CPlusPlus) .Case("has_nothrow_copy", LangOpts.CPlusPlus) @@ -840,10 +800,6 @@ static bool HasFeature(const Preprocessor &PP, const IdentifierInfo *II) { .Case("is_base_of", LangOpts.CPlusPlus) .Case("is_class", LangOpts.CPlusPlus) .Case("is_convertible_to", LangOpts.CPlusPlus) - // __is_empty is available only if the horrible - // "struct __is_empty" parsing hack hasn't been needed in this - // translation unit. If it has, __is_empty reverts to a normal - // identifier and __has_feature(is_empty) evaluates false. .Case("is_empty", LangOpts.CPlusPlus) .Case("is_enum", LangOpts.CPlusPlus) .Case("is_final", LangOpts.CPlusPlus) @@ -926,9 +882,15 @@ static bool EvaluateHasIncludeCommon(Token &Tok, IdentifierInfo *II, Preprocessor &PP, const DirectoryLookup *LookupFrom) { // Save the location of the current token. If a '(' is later found, use - // that location. If no, use the end of this location instead. + // that location. If not, use the end of this location instead. SourceLocation LParenLoc = Tok.getLocation(); + // These expressions are only allowed within a preprocessor directive. + if (!PP.isParsingIfOrElifDirective()) { + PP.Diag(LParenLoc, diag::err_pp_directive_required) << II->getName(); + return false; + } + // Get '('. PP.LexNonComment(Tok); @@ -946,8 +908,14 @@ static bool EvaluateHasIncludeCommon(Token &Tok, // Save '(' location for possible missing ')' message. LParenLoc = Tok.getLocation(); - // Get the file name. - PP.getCurrentLexer()->LexIncludeFilename(Tok); + if (PP.getCurrentLexer()) { + // Get the file name. + PP.getCurrentLexer()->LexIncludeFilename(Tok); + } else { + // We're in a macro, so we can't use LexIncludeFilename; just + // grab the next token. + PP.Lex(Tok); + } } // Reserve a buffer to get the spelling. @@ -1223,15 +1191,15 @@ void Preprocessor::ExpandBuiltinMacro(Token &Tok) { IdentifierInfo *FeatureII = 0; // Read the '('. - Lex(Tok); + LexUnexpandedToken(Tok); if (Tok.is(tok::l_paren)) { // Read the identifier - Lex(Tok); + LexUnexpandedToken(Tok); if (Tok.is(tok::identifier) || Tok.is(tok::kw_const)) { FeatureII = Tok.getIdentifierInfo(); // Read the ')'. - Lex(Tok); + LexUnexpandedToken(Tok); if (Tok.is(tok::r_paren)) IsValid = true; } @@ -1275,69 +1243,49 @@ void Preprocessor::ExpandBuiltinMacro(Token &Tok) { bool IsValid = false; bool Value = false; // Read the '('. - Lex(Tok); + LexUnexpandedToken(Tok); do { - if (Tok.is(tok::l_paren)) { - // Read the string. - Lex(Tok); - - // We need at least one string literal. - if (!Tok.is(tok::string_literal)) { - StartLoc = Tok.getLocation(); - IsValid = false; - // Eat tokens until ')'. - do Lex(Tok); while (!(Tok.is(tok::r_paren) || Tok.is(tok::eod))); - break; - } - - // String concatenation allows multiple strings, which can even come - // from macro expansion. - SmallVector<Token, 4> StrToks; - while (Tok.is(tok::string_literal)) { - // Complain about, and drop, any ud-suffix. - if (Tok.hasUDSuffix()) - Diag(Tok, diag::err_invalid_string_udl); - StrToks.push_back(Tok); + if (Tok.isNot(tok::l_paren)) { + Diag(StartLoc, diag::err_warning_check_malformed); + break; + } + + LexUnexpandedToken(Tok); + std::string WarningName; + SourceLocation StrStartLoc = Tok.getLocation(); + if (!FinishLexStringLiteral(Tok, WarningName, "'__has_warning'", + /*MacroExpansion=*/false)) { + // Eat tokens until ')'. + while (Tok.isNot(tok::r_paren) && Tok.isNot(tok::eod) && + Tok.isNot(tok::eof)) LexUnexpandedToken(Tok); - } - - // Is the end a ')'? - if (!(IsValid = Tok.is(tok::r_paren))) - break; - - // Concatenate and parse the strings. - StringLiteralParser Literal(&StrToks[0], StrToks.size(), *this); - assert(Literal.isAscii() && "Didn't allow wide strings in"); - if (Literal.hadError) - break; - if (Literal.Pascal) { - Diag(Tok, diag::warn_pragma_diagnostic_invalid); - break; - } - - StringRef WarningName(Literal.GetString()); - - if (WarningName.size() < 3 || WarningName[0] != '-' || - WarningName[1] != 'W') { - Diag(StrToks[0].getLocation(), diag::warn_has_warning_invalid_option); - break; - } - - // Finally, check if the warning flags maps to a diagnostic group. - // We construct a SmallVector here to talk to getDiagnosticIDs(). - // Although we don't use the result, this isn't a hot path, and not - // worth special casing. - llvm::SmallVector<diag::kind, 10> Diags; - Value = !getDiagnostics().getDiagnosticIDs()-> - getDiagnosticsInGroup(WarningName.substr(2), Diags); + break; + } + + // Is the end a ')'? + if (!(IsValid = Tok.is(tok::r_paren))) { + Diag(StartLoc, diag::err_warning_check_malformed); + break; + } + + if (WarningName.size() < 3 || WarningName[0] != '-' || + WarningName[1] != 'W') { + Diag(StrStartLoc, diag::warn_has_warning_invalid_option); + break; } + + // Finally, check if the warning flags maps to a diagnostic group. + // We construct a SmallVector here to talk to getDiagnosticIDs(). + // Although we don't use the result, this isn't a hot path, and not + // worth special casing. + SmallVector<diag::kind, 10> Diags; + Value = !getDiagnostics().getDiagnosticIDs()-> + getDiagnosticsInGroup(WarningName.substr(2), Diags); } while (false); - - if (!IsValid) - Diag(StartLoc, diag::err_warning_check_malformed); OS << (int)Value; - Tok.setKind(tok::numeric_constant); + if (IsValid) + Tok.setKind(tok::numeric_constant); } else if (II == Ident__building_module) { // The argument to this builtin should be an identifier. The // builtin evaluates to 1 when that identifier names the module we are |