mgrang created this revision.
mgrang added reviewers: asb, apazos.
mgrang added a project: clang.
Herald added subscribers: cfe-commits, hintonda, niosHD, sabuasal, 
jordy.potman.lists, simoncook, johnrusso, rbar, mgorny.

Currently we are invoking riscv-gcc to link. This causes all flags passed to 
clang to be passed down to gcc as well.
As a result we run into errors for flags not recognzied by gcc.


Repository:
  rC Clang

https://reviews.llvm.org/D42673

Files:
  lib/Driver/CMakeLists.txt
  lib/Driver/Driver.cpp
  lib/Driver/ToolChains/RISCV.cpp
  lib/Driver/ToolChains/RISCV.h

Index: lib/Driver/ToolChains/RISCV.h
===================================================================
--- /dev/null
+++ lib/Driver/ToolChains/RISCV.h
@@ -0,0 +1,59 @@
+//===--- RISCV.h - RISCV ToolChain Implementations --------------*- C++ -*-===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_RISCV_H
+#define LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_RISCV_H
+
+#include "Gnu.h"
+#include "clang/Driver/ToolChain.h"
+
+namespace clang {
+namespace driver {
+namespace toolchains {
+
+class LLVM_LIBRARY_VISIBILITY RISCVToolChain : public Generic_ELF {
+public:
+  RISCVToolChain(const Driver &D, const llvm::Triple &Triple,
+                 const llvm::opt::ArgList &Args);
+
+  bool IsIntegratedAssemblerDefault() const override { return true; }
+  void
+  AddClangSystemIncludeArgs(const llvm::opt::ArgList &DriverArgs,
+                            llvm::opt::ArgStringList &CC1Args) const override;
+
+protected:
+  Tool *buildLinker() const override;
+};
+
+} // end namespace toolchains
+
+namespace tools {
+namespace RISCV {
+class LLVM_LIBRARY_VISIBILITY Linker : public GnuTool {
+public:
+  Linker(const ToolChain &TC)
+      : GnuTool("RISCV::Linker",
+                TC.getTriple().isArch64Bit() ? "riscv64-unknown-elf-ld"
+                                             //: "riscv32-unknown-elf-ld",
+                                             : "riscv32-unknown-linux-gnu-ld",
+                TC) {}
+  bool hasIntegratedCPP() const override { return false; }
+  bool isLinkJob() const override { return true; }
+  void ConstructJob(Compilation &C, const JobAction &JA,
+                    const InputInfo &Output, const InputInfoList &Inputs,
+                    const llvm::opt::ArgList &TCArgs,
+                    const char *LinkingOutput) const override;
+};
+} // end namespace RISCV
+} // end namespace tools
+
+} // end namespace driver
+} // end namespace clang
+
+#endif // LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_RISCV_H
Index: lib/Driver/ToolChains/RISCV.cpp
===================================================================
--- /dev/null
+++ lib/Driver/ToolChains/RISCV.cpp
@@ -0,0 +1,102 @@
+//===--- RISCV.cpp - RISCV ToolChain Implementations ------------*- C++ -*-===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#include "RISCV.h"
+#include "CommonArgs.h"
+#include "InputInfo.h"
+#include "clang/Driver/Compilation.h"
+#include "clang/Driver/Options.h"
+#include "llvm/Option/ArgList.h"
+#include "llvm/Support/Path.h"
+
+using namespace clang::driver;
+using namespace clang::driver::toolchains;
+using namespace clang::driver::tools;
+using namespace clang;
+using namespace llvm::opt;
+
+/// RISCV Toolchain
+RISCVToolChain::RISCVToolChain(const Driver &D, const llvm::Triple &Triple,
+                               const ArgList &Args)
+    : Generic_ELF(D, Triple, Args) {
+  GCCInstallation.init(Triple, Args);
+  getFilePaths().push_back(D.SysRoot + "/lib");
+  if (GCCInstallation.isValid()) {
+    getFilePaths().push_back(GCCInstallation.getInstallPath().str());
+    getProgramPaths().push_back(
+        (GCCInstallation.getParentLibPath() + "/../bin").str());
+  }
+}
+
+Tool *RISCVToolChain::buildLinker() const {
+  return new tools::RISCV::Linker(*this);
+}
+
+void RISCVToolChain::AddClangSystemIncludeArgs(const ArgList &DriverArgs,
+                                               ArgStringList &CC1Args) const {
+  if (DriverArgs.hasArg(options::OPT_nostdinc))
+    return;
+
+  if (!DriverArgs.hasArg(options::OPT_nostdlibinc)) {
+    SmallString<128> Dir(getDriver().SysRoot);
+    llvm::sys::path::append(Dir, "include");
+    addSystemInclude(DriverArgs, CC1Args, Dir.str());
+  }
+}
+
+void RISCV::Linker::ConstructJob(Compilation &C, const JobAction &JA,
+                                 const InputInfo &Output,
+                                 const InputInfoList &Inputs,
+                                 const ArgList &Args,
+                                 const char *LinkingOutput) const {
+  const ToolChain &ToolChain = getToolChain();
+  const Driver &D = ToolChain.getDriver();
+  ArgStringList CmdArgs;
+
+  if (!D.SysRoot.empty())
+    CmdArgs.push_back(Args.MakeArgString("--sysroot=" + D.SysRoot));
+
+  std::string Linker = getToolChain().GetProgramPath(getShortName());
+
+  bool WantCRTs =
+      !Args.hasArg(options::OPT_nostdlib, options::OPT_nostartfiles);
+
+  if (WantCRTs) {
+    CmdArgs.push_back(Args.MakeArgString(ToolChain.GetFilePath("crt0.o")));
+    CmdArgs.push_back(Args.MakeArgString(ToolChain.GetFilePath("crtbegin.o")));
+  }
+
+  Args.AddAllArgs(CmdArgs, options::OPT_L);
+  ToolChain.AddFilePathLibArgs(Args, CmdArgs);
+  Args.AddAllArgs(CmdArgs,
+                  {options::OPT_T_Group, options::OPT_e, options::OPT_s,
+                   options::OPT_t, options::OPT_Z_Flag, options::OPT_r});
+
+  AddLinkerInputs(ToolChain, Inputs, Args, CmdArgs, JA);
+
+  // TODO: add C++ includes and libs if compiling C++.
+
+  if (!Args.hasArg(options::OPT_nostdlib) &&
+      !Args.hasArg(options::OPT_nodefaultlibs)) {
+    CmdArgs.push_back("--start-group");
+    CmdArgs.push_back("-lc");
+    CmdArgs.push_back("-lgloss");
+    CmdArgs.push_back("--end-group");
+    CmdArgs.push_back("-lgcc");
+  }
+
+  if (WantCRTs)
+    CmdArgs.push_back(Args.MakeArgString(ToolChain.GetFilePath("crtend.o")));
+
+  CmdArgs.push_back("-o");
+  CmdArgs.push_back(Output.getFilename());
+  C.addCommand(llvm::make_unique<Command>(JA, *this, Args.MakeArgString(Linker),
+                                          CmdArgs, Inputs));
+}
+// RISCV tools end.
Index: lib/Driver/Driver.cpp
===================================================================
--- lib/Driver/Driver.cpp
+++ lib/Driver/Driver.cpp
@@ -36,6 +36,7 @@
 #include "ToolChains/NetBSD.h"
 #include "ToolChains/OpenBSD.h"
 #include "ToolChains/PS4CPU.h"
+#include "ToolChains/RISCV.h"
 #include "ToolChains/Solaris.h"
 #include "ToolChains/TCE.h"
 #include "ToolChains/WebAssembly.h"
@@ -4200,6 +4201,10 @@
       case llvm::Triple::avr:
         TC = llvm::make_unique<toolchains::AVRToolChain>(*this, Target, Args);
         break;
+      case llvm::Triple::riscv32:
+      case llvm::Triple::riscv64:
+        TC = llvm::make_unique<toolchains::RISCVToolChain>(*this, Target, Args);
+        break;
       default:
         if (Target.getVendor() == llvm::Triple::Myriad)
           TC = llvm::make_unique<toolchains::MyriadToolChain>(*this, Target,
Index: lib/Driver/CMakeLists.txt
===================================================================
--- lib/Driver/CMakeLists.txt
+++ lib/Driver/CMakeLists.txt
@@ -56,6 +56,7 @@
   ToolChains/NetBSD.cpp
   ToolChains/OpenBSD.cpp
   ToolChains/PS4CPU.cpp
+  ToolChains/RISCV.cpp
   ToolChains/Solaris.cpp
   ToolChains/TCE.cpp
   ToolChains/WebAssembly.cpp
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to