]> granicus.if.org Git - clang/commitdiff
[WebAssembly] Support -stdlib=libc++ switch
authorSam Clegg <sbc@chromium.org>
Fri, 12 Jan 2018 17:54:49 +0000 (17:54 +0000)
committerSam Clegg <sbc@chromium.org>
Fri, 12 Jan 2018 17:54:49 +0000 (17:54 +0000)
Referenced implementation from Fuchsia and Darwin Toolchain.
Still only support CST_Libcxx.  Now checks that the argument
is really '-stdlib=libc++', and display error.

Also, now will pass -lc++ and -lc++abi to the linker.

Patch by Patrick Cheng!

Differential Revision: https://reviews.llvm.org/D41937

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@322382 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Driver/ToolChains/WebAssembly.cpp
lib/Driver/ToolChains/WebAssembly.h
test/Driver/wasm-toolchain.cpp [new file with mode: 0644]

index 42de430cb197e3ca77c515a96324e5501a647d9e..94f7279bbdbaf95d1eccf6fa397292d3980f6773 100644 (file)
@@ -11,6 +11,7 @@
 #include "CommonArgs.h"
 #include "clang/Driver/Compilation.h"
 #include "clang/Driver/Driver.h"
+#include "clang/Driver/DriverDiagnostic.h"
 #include "clang/Driver/Options.h"
 #include "llvm/Option/ArgList.h"
 
@@ -117,6 +118,12 @@ ToolChain::RuntimeLibType WebAssembly::GetDefaultRuntimeLibType() const {
 }
 
 ToolChain::CXXStdlibType WebAssembly::GetCXXStdlibType(const ArgList &Args) const {
+  if (Arg *A = Args.getLastArg(options::OPT_stdlib_EQ)) {
+    StringRef Value = A->getValue();
+    if (Value != "libc++")
+      getDriver().Diag(diag::err_drv_invalid_stdlib_name)
+          << A->getAsString(Args);
+  }
   return ToolChain::CST_Libcxx;
 }
 
@@ -134,6 +141,19 @@ void WebAssembly::AddClangCXXStdlibIncludeArgs(const ArgList &DriverArgs,
                      getDriver().SysRoot + "/include/c++/v1");
 }
 
+void WebAssembly::AddCXXStdlibLibArgs(const llvm::opt::ArgList &Args,
+                                      llvm::opt::ArgStringList &CmdArgs) const {
+
+  switch (GetCXXStdlibType(Args)) {
+  case ToolChain::CST_Libcxx:
+    CmdArgs.push_back("-lc++");
+    CmdArgs.push_back("-lc++abi");
+    break;
+  case ToolChain::CST_Libstdcxx:
+    llvm_unreachable("invalid stdlib name");
+  }
+}
+
 std::string WebAssembly::getThreadModel() const {
   // The WebAssembly MVP does not yet support threads; for now, use the
   // "single" threading model, which lowers atomics to non-atomic operations.
index 8784e12dfb0ecff74bdac20379626cd32c3e2dbd..cdbb34ff919f2110a1570c918350d4543139047c 100644 (file)
@@ -62,6 +62,8 @@ private:
   void AddClangCXXStdlibIncludeArgs(
       const llvm::opt::ArgList &DriverArgs,
       llvm::opt::ArgStringList &CC1Args) const override;
+  void AddCXXStdlibLibArgs(const llvm::opt::ArgList &Args,
+                           llvm::opt::ArgStringList &CmdArgs) const override;
   std::string getThreadModel() const override;
 
   const char *getDefaultLinker() const override {
diff --git a/test/Driver/wasm-toolchain.cpp b/test/Driver/wasm-toolchain.cpp
new file mode 100644 (file)
index 0000000..799e027
--- /dev/null
@@ -0,0 +1,36 @@
+// A basic clang -cc1 command-line. WebAssembly is somewhat special in
+// enabling -ffunction-sections, -fdata-sections, and -fvisibility=hidden by
+// default.
+
+// RUN: %clang++ %s -### -no-canonical-prefixes -target wasm32-unknown-unknown 2>&1 | FileCheck -check-prefix=CC1 %s
+// CC1: clang{{.*}} "-cc1" "-triple" "wasm32-unknown-unknown" {{.*}} "-fvisibility" "hidden" {{.*}} "-ffunction-sections" "-fdata-sections"
+
+// Ditto, but ensure that a user -fno-function-sections disables the
+// default -ffunction-sections.
+
+// RUN: %clang++ %s -### -target wasm32-unknown-unknown -fno-function-sections 2>&1 | FileCheck -check-prefix=NO_FUNCTION_SECTIONS %s
+// NO_FUNCTION_SECTIONS-NOT: function-sections
+
+// Ditto, but ensure that a user -fno-data-sections disables the
+// default -fdata-sections.
+
+// RUN: %clang++ %s -### -target wasm32-unknown-unknown -fno-data-sections 2>&1 | FileCheck -check-prefix=NO_DATA_SECTIONS %s
+// NO_DATA_SECTIONS-NOT: data-sections
+
+// Ditto, but ensure that a user -fvisibility=default disables the default
+// -fvisibility=hidden.
+
+// RUN: %clang++ %s -### -target wasm32-unknown-unknown -fvisibility=default 2>&1 | FileCheck -check-prefix=FVISIBILITY_DEFAULT %s
+// FVISIBILITY_DEFAULT-NOT: hidden
+
+// A basic C++ link command-line.
+
+// RUN: %clang++ -### -no-canonical-prefixes -target wasm32-unknown-unknown --sysroot=/foo --stdlib=c++ %s 2>&1 | FileCheck -check-prefix=LINK %s
+// LINK: clang{{.*}}" "-cc1" {{.*}} "-o" "[[temp:[^"]*]]"
+// LINK: lld{{.*}}" "-flavor" "wasm" "-L/foo/lib" "crt1.o" "[[temp]]" "-lc++" "-lc++abi" "-lc" "{{.*[/\\]}}libclang_rt.builtins-wasm32.a" "-o" "a.out"
+
+// A basic C++ link command-line with optimization.
+
+// RUN: %clang++ -### -O2 -no-canonical-prefixes -target wasm32-unknown-unknown --sysroot=/foo %s --stdlib=c++ 2>&1 | FileCheck -check-prefix=LINK_OPT %s
+// LINK_OPT: clang{{.*}}" "-cc1" {{.*}} "-o" "[[temp:[^"]*]]"
+// LINK_OPT: lld{{.*}}" "-flavor" "wasm" "-L/foo/lib" "crt1.o" "[[temp]]" "-lc++" "-lc++abi" "-lc" "{{.*[/\\]}}libclang_rt.builtins-wasm32.a" "-o" "a.out"