r199632 - Make the Linux support for finding libc++ somewhat less braindead.

Chandler Carruth chandlerc at gmail.com
Mon Jan 20 01:42:24 PST 2014


Author: chandlerc
Date: Mon Jan 20 03:42:24 2014
New Revision: 199632

URL: http://llvm.org/viewvc/llvm-project?rev=199632&view=rev
Log:
Make the Linux support for finding libc++ somewhat less braindead.

Now instead of just looking in the system root for it, we also look
relative to the clang binary's directory. This should "just work" in
almost all cases. I've added test cases accordingly.

This is probably *very* worthwhile to backport to the 3.4 branch so that
folks can check it out, build it, and use that as their host compiler
going forward.

Modified:
    cfe/trunk/lib/Driver/ToolChains.cpp
    cfe/trunk/test/Driver/linux-header-search.cpp

Modified: cfe/trunk/lib/Driver/ToolChains.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Driver/ToolChains.cpp?rev=199632&r1=199631&r2=199632&view=diff
==============================================================================
--- cfe/trunk/lib/Driver/ToolChains.cpp (original)
+++ cfe/trunk/lib/Driver/ToolChains.cpp Mon Jan 20 03:42:24 2014
@@ -2945,9 +2945,24 @@ void Linux::AddClangCXXStdlibIncludeArgs
 
   // Check if libc++ has been enabled and provide its include paths if so.
   if (GetCXXStdlibType(DriverArgs) == ToolChain::CST_Libcxx) {
-    // libc++ is always installed at a fixed path on Linux currently.
-    addSystemInclude(DriverArgs, CC1Args,
-                     getDriver().SysRoot + "/usr/include/c++/v1");
+    const std::string LibCXXIncludePathCandidates[] = {
+      // The primary location is within the Clang installation.
+      // FIXME: We shouldn't hard code 'v1' here to make Clang future proof to
+      // newer ABI versions.
+      getDriver().Dir + "/../include/c++/v1",
+
+      // We also check the system as for a long time this is the only place Clang looked.
+      // FIXME: We should really remove this. It doesn't make any sense.
+      getDriver().SysRoot + "/usr/include/c++/v1"
+    };
+    for (unsigned i = 0; i < llvm::array_lengthof(LibCXXIncludePathCandidates);
+         ++i) {
+      if (!llvm::sys::fs::exists(LibCXXIncludePathCandidates[i]))
+        continue;
+      // Add the first candidate that exists.
+      addSystemInclude(DriverArgs, CC1Args, LibCXXIncludePathCandidates[i]);
+      break;
+    }
     return;
   }
 
@@ -2971,7 +2986,7 @@ void Linux::AddClangCXXStdlibIncludeArgs
                                MIPSABIDirSuffix, DriverArgs, CC1Args))
     return;
 
-  const std::string IncludePathCandidates[] = {
+  const std::string LibStdCXXIncludePathCandidates[] = {
     // Gentoo is weird and places its headers inside the GCC install, so if the
     // first attempt to find the headers fails, try these patterns.
     InstallDir.str() + "/include/g++-v" + Version.MajorStr + "." +
@@ -2984,8 +2999,9 @@ void Linux::AddClangCXXStdlibIncludeArgs
     LibDir.str() + "/../include/c++",
   };
 
-  for (unsigned i = 0; i < llvm::array_lengthof(IncludePathCandidates); ++i) {
-    if (addLibStdCXXIncludePaths(IncludePathCandidates[i],
+  for (unsigned i = 0; i < llvm::array_lengthof(LibStdCXXIncludePathCandidates);
+       ++i) {
+    if (addLibStdCXXIncludePaths(LibStdCXXIncludePathCandidates[i],
                                  TripleStr + MIPSABIDirSuffix + BiarchSuffix,
                                  DriverArgs, CC1Args))
       break;

Modified: cfe/trunk/test/Driver/linux-header-search.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Driver/linux-header-search.cpp?rev=199632&r1=199631&r2=199632&view=diff
==============================================================================
--- cfe/trunk/test/Driver/linux-header-search.cpp (original)
+++ cfe/trunk/test/Driver/linux-header-search.cpp Mon Jan 20 03:42:24 2014
@@ -1,6 +1,29 @@
 // General tests that the header search paths detected by the driver and passed
 // to CC1 are sane.
 //
+// Test a simulated installation of libc++ on Linux, both through sysroot and
+// the installation path of Clang.
+// RUN: %clang -no-canonical-prefixes %s -### -fsyntax-only 2>&1 \
+// RUN:     -target x86_64-unknown-linux-gnu \
+// RUN:     -stdlib=libc++ \
+// RUN:     -ccc-install-dir %S/Inputs/basic_linux_tree/usr/bin \
+// RUN:     --sysroot=%S/Inputs/basic_linux_libcxx_tree \
+// RUN:   | FileCheck --check-prefix=CHECK-BASIC-LIBCXX-SYSROOT %s
+// CHECK-BASIC-LIBCXX-SYSROOT: "{{[^"]*}}clang{{[^"]*}}" "-cc1"
+// CHECK-BASIC-LIBCXX-SYSROOT: "-isysroot" "[[SYSROOT:[^"]+]]"
+// CHECK-BASIC-LIBCXX-SYSROOT: "-internal-isystem" "[[SYSROOT]]/usr/include/c++/v1"
+// CHECK-BASIC-LIBCXX-SYSROOT: "-internal-isystem" "[[SYSROOT]]/usr/local/include"
+// RUN: %clang -no-canonical-prefixes %s -### -fsyntax-only 2>&1 \
+// RUN:     -target x86_64-unknown-linux-gnu \
+// RUN:     -stdlib=libc++ \
+// RUN:     -ccc-install-dir %S/Inputs/basic_linux_libcxx_tree/usr/bin \
+// RUN:     --sysroot=%S/Inputs/basic_linux_libcxx_tree \
+// RUN:   | FileCheck --check-prefix=CHECK-BASIC-LIBCXX-INSTALL %s
+// CHECK-BASIC-LIBCXX-INSTALL: "{{[^"]*}}clang{{[^"]*}}" "-cc1"
+// CHECK-BASIC-LIBCXX-INSTALL: "-isysroot" "[[SYSROOT:[^"]+]]"
+// CHECK-BASIC-LIBCXX-INSTALL: "-internal-isystem" "[[SYSROOT]]/usr/bin/../include/c++/v1"
+// CHECK-BASIC-LIBCXX-INSTALL: "-internal-isystem" "[[SYSROOT]]/usr/local/include"
+//
 // Test a very broken version of multiarch that shipped in Ubuntu 11.04.
 // RUN: %clang -no-canonical-prefixes %s -### -fsyntax-only 2>&1 \
 // RUN:     -target i386-unknown-linux \





More information about the cfe-commits mailing list