diff options
-rw-r--r-- | include/clang/Basic/TokenKinds.def | 1 | ||||
-rw-r--r-- | lib/Basic/IdentifierTable.cpp | 2 | ||||
-rw-r--r-- | lib/Lex/PPDirectives.cpp | 6 | ||||
-rw-r--r-- | tools/clang-cc/clang-cc.cpp | 61 |
4 files changed, 55 insertions, 15 deletions
diff --git a/include/clang/Basic/TokenKinds.def b/include/clang/Basic/TokenKinds.def index 81a4c2f302..f1b6f42433 100644 --- a/include/clang/Basic/TokenKinds.def +++ b/include/clang/Basic/TokenKinds.def @@ -59,6 +59,7 @@ PPKEYWORD(defined) // C99 6.10.2 - Source File Inclusion. PPKEYWORD(include) +PPKEYWORD(__include_macros) // C99 6.10.3 - Macro Replacement. PPKEYWORD(define) diff --git a/lib/Basic/IdentifierTable.cpp b/lib/Basic/IdentifierTable.cpp index c002b3f110..78758d7188 100644 --- a/lib/Basic/IdentifierTable.cpp +++ b/lib/Basic/IdentifierTable.cpp @@ -207,6 +207,8 @@ tok::PPKeywordKind IdentifierInfo::getPPKeywordID() const { CASE( 8, 'u', 'a', unassert); CASE(12, 'i', 'c', include_next); + + CASE(16, '_', 'i', __include_macros); #undef CASE #undef HASH } diff --git a/lib/Lex/PPDirectives.cpp b/lib/Lex/PPDirectives.cpp index c5dc7abd08..a60d9ba4e1 100644 --- a/lib/Lex/PPDirectives.cpp +++ b/lib/Lex/PPDirectives.cpp @@ -528,8 +528,10 @@ TryAgain: // C99 6.10.2 - Source File Inclusion. case tok::pp_include: - return HandleIncludeDirective(Result); // Handle #include. - + return HandleIncludeDirective(Result); // Handle #include. + case tok::pp___include_macros: + return HandleIncludeDirective(Result); // Handle #__include_macros. + // C99 6.10.3 - Macro Replacement. case tok::pp_define: return HandleDefineDirective(Result); diff --git a/tools/clang-cc/clang-cc.cpp b/tools/clang-cc/clang-cc.cpp index 13e4389159..d5c44cd078 100644 --- a/tools/clang-cc/clang-cc.cpp +++ b/tools/clang-cc/clang-cc.cpp @@ -48,6 +48,7 @@ #include "llvm/ADT/OwningPtr.h" #include "llvm/ADT/SmallPtrSet.h" #include "llvm/ADT/StringExtras.h" +#include "llvm/ADT/STLExtras.h" #include "llvm/Config/config.h" #include "llvm/Support/CommandLine.h" #include "llvm/Support/ManagedStatic.h" @@ -966,6 +967,9 @@ U_macros("U", llvm::cl::value_desc("macro"), llvm::cl::Prefix, static llvm::cl::list<std::string> ImplicitIncludes("include", llvm::cl::value_desc("file"), llvm::cl::desc("Include file before parsing")); +static llvm::cl::list<std::string> +ImplicitMacroIncludes("imacros", llvm::cl::value_desc("file"), + llvm::cl::desc("Include macros from file before parsing")); static llvm::cl::opt<std::string> ImplicitIncludePTH("include-pth", llvm::cl::value_desc("file"), @@ -1012,9 +1016,18 @@ static void AddImplicitInclude(std::vector<char> &Buf, const std::string &File){ Buf.push_back('\n'); } +static void AddImplicitIncludeMacros(std::vector<char> &Buf, + const std::string &File) { + const char *Inc = "#__include_macros \""; + Buf.insert(Buf.end(), Inc, Inc+strlen(Inc)); + Buf.insert(Buf.end(), File.begin(), File.end()); + Buf.push_back('"'); + Buf.push_back('\n'); +} + /// AddImplicitIncludePTH - Add an implicit #include using the original file /// used to generate a PTH cache. -static void AddImplicitIncludePTH(std::vector<char> &Buf, Preprocessor & PP) { +static void AddImplicitIncludePTH(std::vector<char> &Buf, Preprocessor &PP) { PTHManager *P = PP.getPTHManager(); assert(P && "No PTHManager."); const char *OriginalFile = P->getOriginalSourceFile(); @@ -1083,19 +1096,41 @@ static bool InitializePreprocessor(Preprocessor &PP, // FIXME: Read any files specified by -imacros. - // Add implicit #includes from -include and -include-pth. - bool handledPTH = ImplicitIncludePTH.empty(); - for (unsigned i = 0, e = ImplicitIncludes.size(); i != e; ++i) { - if (!handledPTH && - ImplicitIncludePTH.getPosition() < ImplicitIncludes.getPosition(i)) { - AddImplicitIncludePTH(PredefineBuffer, PP); - handledPTH = true; - } - - AddImplicitInclude(PredefineBuffer, ImplicitIncludes[i]); + if (!ImplicitIncludePTH.empty() || !ImplicitIncludes.empty() || + !ImplicitMacroIncludes.empty()) { + // We want to add these paths to the predefines buffer in order, make a temporary + // vector to sort by their occurrence. + llvm::SmallVector<std::pair<unsigned, std::string*>, 8> OrderedPaths; + + if (!ImplicitIncludePTH.empty()) + OrderedPaths.push_back(std::make_pair(ImplicitIncludePTH.getPosition(), + &ImplicitIncludePTH)); + for (unsigned i = 0, e = ImplicitIncludes.size(); i != e; ++i) + OrderedPaths.push_back(std::make_pair(ImplicitIncludes.getPosition(i), + &ImplicitIncludes[i])); + for (unsigned i = 0, e = ImplicitMacroIncludes.size(); i != e; ++i) + OrderedPaths.push_back(std::make_pair(ImplicitMacroIncludes + .getPosition(i), + &ImplicitMacroIncludes[i])); + llvm::array_pod_sort(OrderedPaths.begin(), OrderedPaths.end()); + + // Now that they are ordered by position, add to the predefines buffer. + for (unsigned i = 0, e = OrderedPaths.size(); i != e; ++i) { + std::string *Ptr = OrderedPaths[i].second; + if (!ImplicitIncludes.empty() && + Ptr >= &ImplicitIncludes[0] && + Ptr <= &ImplicitIncludes[ImplicitIncludes.size()-1]) { + AddImplicitInclude(PredefineBuffer, *Ptr); + } else if (Ptr == &ImplicitIncludePTH) { + AddImplicitIncludePTH(PredefineBuffer, PP); + } else { + assert(Ptr >= &ImplicitMacroIncludes[0] && + Ptr <= &ImplicitMacroIncludes[ImplicitMacroIncludes.size()-1] && + "String must have been in -imacros?"); + AddImplicitIncludeMacros(PredefineBuffer, *Ptr); + } + } } - if (!handledPTH && !ImplicitIncludePTH.empty()) - AddImplicitIncludePTH(PredefineBuffer, PP); // Null terminate PredefinedBuffer and add it. PredefineBuffer.push_back(0); |