Index: clang/lib/Basic/CMakeLists.txt =================================================================== --- clang/lib/Basic/CMakeLists.txt +++ clang/lib/Basic/CMakeLists.txt @@ -75,6 +75,7 @@ Targets/ARM.cpp Targets/AVR.cpp Targets/BPF.cpp + Targets/CSKY.cpp Targets/Hexagon.cpp Targets/Lanai.cpp Targets/Le64.cpp Index: clang/lib/Basic/Targets.cpp =================================================================== --- clang/lib/Basic/Targets.cpp +++ clang/lib/Basic/Targets.cpp @@ -19,6 +19,7 @@ #include "Targets/ARM.h" #include "Targets/AVR.h" #include "Targets/BPF.h" +#include "Targets/CSKY.h" #include "Targets/Hexagon.h" #include "Targets/Lanai.h" #include "Targets/Le64.h" @@ -656,6 +657,14 @@ case llvm::Triple::ve: return new LinuxTargetInfo(Triple, Opts); + + case llvm::Triple::csky: + switch (os) { + case llvm::Triple::Linux: + return new LinuxTargetInfo(Triple, Opts); + default: + return new CSKYTargetInfo(Triple, Opts); + } } } } // namespace targets Index: clang/lib/Basic/Targets/CSKY.h =================================================================== --- /dev/null +++ clang/lib/Basic/Targets/CSKY.h @@ -0,0 +1,101 @@ +//===--- CSKY.h - Declare CSKY target feature support -----------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file declares CSKY TargetInfo objects. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_CLANG_LIB_BASIC_TARGETS_CSKY_H +#define LLVM_CLANG_LIB_BASIC_TARGETS_CSKY_H + +#include "clang/Basic/MacroBuilder.h" +#include "clang/Basic/TargetInfo.h" +#include "llvm/Support/CSKYTargetParser.h" + +namespace clang { +namespace targets { + +class LLVM_LIBRARY_VISIBILITY CSKYTargetInfo : public TargetInfo { +protected: + std::string ABI; + llvm::CSKY::ArchKind Arch = llvm::CSKY::ArchKind::INVALID; + std::string CPU; + + bool HardFloat; + bool VDSPV2; + bool VDSPV1; + bool DSPV2; + bool is3E3R1; + +public: + CSKYTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) + : TargetInfo(Triple) { + NoAsmVariants = true; + LongLongAlign = 32; + SuitableAlign = 32; + DoubleAlign = LongDoubleAlign = 32; + SizeType = UnsignedInt; + PtrDiffType = SignedInt; + IntPtrType = SignedInt; + WCharType = SignedInt; + WIntType = UnsignedInt; + + UseZeroLengthBitfieldAlignment = true; + MaxAtomicPromoteWidth = MaxAtomicInlineWidth = 32; + resetDataLayout("e-m:e-S32-p:32:32-i32:32:32-i64:32:32-f32:32:32-f64:32:32-" + "v64:32:32-v128:32:32-a:0:32-Fi32-n32"); + + setABI("abiv2"); + } + + StringRef getABI() const override { return ABI; } + bool setABI(const std::string &Name) override { + if (Name == "abiv2" || Name == "abiv1") { + ABI = Name; + return true; + } + return false; + } + + bool setCPU(const std::string &Name) override; + + bool isValidCPUName(StringRef Name) const override; + + virtual unsigned getMinGlobalAlign(uint64_t) const override; + + ArrayRef getTargetBuiltins() const override; + + BuiltinVaListKind getBuiltinVaListKind() const override { + return VoidPtrBuiltinVaList; + } + + bool validateAsmConstraint(const char *&Name, + TargetInfo::ConstraintInfo &info) const override; + + const char *getClobbers() const override { return ""; } + + void getTargetDefines(const LangOptions &Opts, + MacroBuilder &Builder) const override; + bool handleTargetFeatures(std::vector &Features, + DiagnosticsEngine &Diags) override; + + /// Whether target allows to overalign ABI-specified preferred alignment + bool allowsLargerPreferedTypeAlignment() const override { return false; } + + bool hasBitIntType() const override { return true; } + +protected: + ArrayRef getGCCRegNames() const override; + + ArrayRef getGCCRegAliases() const override; +}; + +} // namespace targets +} // namespace clang + +#endif // LLVM_CLANG_LIB_BASIC_TARGETS_CSKY_H Index: clang/lib/Basic/Targets/CSKY.cpp =================================================================== --- /dev/null +++ clang/lib/Basic/Targets/CSKY.cpp @@ -0,0 +1,295 @@ +//===--- CSKY.cpp - Implement CSKY target feature support -----------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file implements CSKY TargetInfo objects. +// +//===----------------------------------------------------------------------===// + +#include "CSKY.h" + +using namespace clang; +using namespace clang::targets; + +bool CSKYTargetInfo::isValidCPUName(StringRef Name) const { + return llvm::CSKY::parseCPUArch(Name) != llvm::CSKY::ArchKind::INVALID; +} + +bool CSKYTargetInfo::setCPU(const std::string &Name) { + llvm::CSKY::ArchKind archKind = llvm::CSKY::parseCPUArch(Name); + bool isValid = (archKind != llvm::CSKY::ArchKind::INVALID); + + if (isValid) { + CPU = Name; + Arch = archKind; + } + + return isValid; +} + +void CSKYTargetInfo::getTargetDefines(const LangOptions &Opts, + MacroBuilder &Builder) const { + Builder.defineMacro("__ELF__"); + Builder.defineMacro("__csky__", "2"); + Builder.defineMacro("__CSKY__", "2"); + Builder.defineMacro("__ckcore__", "2"); + Builder.defineMacro("__CKCORE__", "2"); + + Builder.defineMacro("__CSKYABI__", ABI == "abiv2" ? "2" : "1"); + Builder.defineMacro("__cskyabi__", ABI == "abiv2" ? "2" : "1"); + + StringRef ArchName = "ck810"; + StringRef CPUName = "ck810f"; + + if (Arch != llvm::CSKY::ArchKind::INVALID) { + ArchName = llvm::CSKY::getArchName(Arch); + CPUName = CPU; + } + + Builder.defineMacro("__" + ArchName.upper() + "__"); + Builder.defineMacro("__" + ArchName.lower() + "__"); + Builder.defineMacro("__" + CPUName.upper() + "__"); + Builder.defineMacro("__" + CPUName.lower() + "__"); + + // TODO: Add support for BE if BE was supported later + StringRef endian = "__cskyLE__"; + + Builder.defineMacro(endian); + Builder.defineMacro(endian.upper()); + Builder.defineMacro(endian.lower()); + + if (DSPV2) { + StringRef dspv2 = "__CSKY_DSPV2__"; + Builder.defineMacro(dspv2); + Builder.defineMacro(dspv2.lower()); + } + + if (VDSPV2) { + StringRef vdspv2 = "__CSKY_VDSPV2__"; + Builder.defineMacro(vdspv2); + Builder.defineMacro(vdspv2.lower()); + + if (HardFloat) { + StringRef vdspv2_f = "__CSKY_VDSPV2_F__"; + Builder.defineMacro(vdspv2_f); + Builder.defineMacro(vdspv2_f.lower()); + } + } + if (VDSPV1) { + StringRef vdspv1_64 = "__CSKY_VDSP64__"; + StringRef vdspv1_128 = "__CSKY_VDSP128__"; + + Builder.defineMacro(vdspv1_64); + Builder.defineMacro(vdspv1_64.lower()); + Builder.defineMacro(vdspv1_128); + Builder.defineMacro(vdspv1_128.lower()); + } + if (is3E3R1) { + StringRef is3e3r1 = "__CSKY_3E3R1__"; + Builder.defineMacro(is3e3r1); + Builder.defineMacro(is3e3r1.lower()); + } +} + +bool CSKYTargetInfo::handleTargetFeatures(std::vector &Features, + DiagnosticsEngine &Diags) { + HardFloat = false; + VDSPV2 = false; + VDSPV1 = false; + DSPV2 = false; + is3E3R1 = false; + + for (const auto &Feature : Features) { + if (Feature == "+hard-float") + HardFloat = true; + if (Feature == "+vdspv2") + VDSPV2 = true; + if (Feature == "+dspv2") + DSPV2 = true; + if (Feature == "+vdspv1") + VDSPV1 = true; + if (Feature == "+3e3r1") + is3E3R1 = true; + } + + return true; +} + +ArrayRef CSKYTargetInfo::getTargetBuiltins() const { + return ArrayRef(); +} + +ArrayRef CSKYTargetInfo::getGCCRegNames() const { + static const char *const GCCRegNames[] = { + // Integer registers + "r0", + "r1", + "r2", + "r3", + "r4", + "r5", + "r6", + "r7", + "r8", + "r9", + "r10", + "r11", + "r12", + "r13", + "r14", + "r15", + "r16", + "r17", + "r18", + "r19", + "r20", + "r21", + "r22", + "r23", + "r24", + "r25", + "r26", + "r27", + "r28", + "r29", + "r30", + "r31", + + // Floating point registers + "fr0", + "fr1", + "fr2", + "fr3", + "fr4", + "fr5", + "fr6", + "fr7", + "fr8", + "fr9", + "fr10", + "fr11", + "fr12", + "fr13", + "fr14", + "fr15", + "fr16", + "fr17", + "fr18", + "fr19", + "fr20", + "fr21", + "fr22", + "fr23", + "fr24", + "fr25", + "fr26", + "fr27", + "fr28", + "fr29", + "fr30", + "fr31", + + }; + return llvm::makeArrayRef(GCCRegNames); +} + +ArrayRef CSKYTargetInfo::getGCCRegAliases() const { + static const TargetInfo::GCCRegAlias GCCRegAliases[] = { + {{"a0"}, "r0"}, + {{"a1"}, "r1"}, + {{"a2"}, "r2"}, + {{"a3"}, "r3"}, + {{"l0"}, "r4"}, + {{"l1"}, "r5"}, + {{"l2"}, "r6"}, + {{"l3"}, "r7"}, + {{"l4"}, "r8"}, + {{"l5"}, "r9"}, + {{"l6"}, "r10"}, + {{"l7"}, "r11"}, + {{"t0"}, "r12"}, + {{"t1"}, "r13"}, + {{"sp"}, "r14"}, + {{"lr"}, "r15"}, + {{"l8"}, "r16"}, + {{"l9"}, "r17"}, + {{"t2"}, "r18"}, + {{"t3"}, "r19"}, + {{"t4"}, "r20"}, + {{"t5"}, "r21"}, + {{"t6"}, "r22"}, + {{"t7", "fp"}, "r23"}, + {{"t8", "top"}, "r24"}, + {{"t9", "bsp"}, "r25"}, + {{"r26"}, "r26"}, + {{"r27"}, "r27"}, + {{"gb", "rgb", "rdb"}, "r28"}, + {{"tb", "rtb"}, "r29"}, + {{"svbr"}, "r30"}, + {{"tls"}, "r31"}, + + {{"vr0"}, "fr0"}, + {{"vr1"}, "fr1"}, + {{"vr2"}, "fr2"}, + {{"vr3"}, "fr3"}, + {{"vr4"}, "fr4"}, + {{"vr5"}, "fr5"}, + {{"vr6"}, "fr6"}, + {{"vr7"}, "fr7"}, + {{"vr8"}, "fr8"}, + {{"vr9"}, "fr9"}, + {{"vr10"}, "fr10"}, + {{"vr11"}, "fr11"}, + {{"vr12"}, "fr12"}, + {{"vr13"}, "fr13"}, + {{"vr14"}, "fr14"}, + {{"vr15"}, "fr15"}, + {{"vr16"}, "fr16"}, + {{"vr17"}, "fr17"}, + {{"vr18"}, "fr18"}, + {{"vr19"}, "fr19"}, + {{"vr20"}, "fr20"}, + {{"vr21"}, "fr21"}, + {{"vr22"}, "fr22"}, + {{"vr23"}, "fr23"}, + {{"vr24"}, "fr24"}, + {{"vr25"}, "fr25"}, + {{"vr26"}, "fr26"}, + {{"vr27"}, "fr27"}, + {{"vr28"}, "fr28"}, + {{"vr29"}, "fr29"}, + {{"vr30"}, "fr30"}, + {{"vr31"}, "fr31"}, + + }; + return llvm::makeArrayRef(GCCRegAliases); +} + +bool CSKYTargetInfo::validateAsmConstraint( + const char *&Name, TargetInfo::ConstraintInfo &Info) const { + switch (*Name) { + default: + return false; + case 'a': + case 'b': + case 'c': + case 'y': + case 'l': + case 'h': + case 'w': + case 'v': // A floating-point and vector register. + case 'z': + Info.setAllowsRegister(); + return true; + } +} + +unsigned CSKYTargetInfo::getMinGlobalAlign(uint64_t Size) const { + if (Size >= 32) + return 32; + return 0; +} Index: clang/lib/Driver/CMakeLists.txt =================================================================== --- clang/lib/Driver/CMakeLists.txt +++ clang/lib/Driver/CMakeLists.txt @@ -27,6 +27,7 @@ ToolChain.cpp ToolChains/Arch/AArch64.cpp ToolChains/Arch/ARM.cpp + ToolChains/Arch/CSKY.cpp ToolChains/Arch/M68k.cpp ToolChains/Arch/Mips.cpp ToolChains/Arch/PPC.cpp @@ -46,6 +47,7 @@ ToolChains/CommonArgs.cpp ToolChains/Contiki.cpp ToolChains/CrossWindows.cpp + ToolChains/CSKYToolChain.cpp ToolChains/Cuda.cpp ToolChains/Darwin.cpp ToolChains/DragonFly.cpp Index: clang/lib/Driver/Driver.cpp =================================================================== --- clang/lib/Driver/Driver.cpp +++ clang/lib/Driver/Driver.cpp @@ -13,6 +13,7 @@ #include "ToolChains/AVR.h" #include "ToolChains/Ananas.h" #include "ToolChains/BareMetal.h" +#include "ToolChains/CSKYToolChain.h" #include "ToolChains/Clang.h" #include "ToolChains/CloudABI.h" #include "ToolChains/Contiki.h" @@ -5704,6 +5705,9 @@ case llvm::Triple::spirv64: TC = std::make_unique(*this, Target, Args); break; + case llvm::Triple::csky: + TC = std::make_unique(*this, Target, Args); + break; default: if (Target.getVendor() == llvm::Triple::Myriad) TC = std::make_unique(*this, Target, Index: clang/lib/Driver/ToolChains/Arch/CSKY.h =================================================================== --- /dev/null +++ clang/lib/Driver/ToolChains/Arch/CSKY.h @@ -0,0 +1,46 @@ +//===--- CSKY.h - CSKY-specific Tool Helpers ------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_ARCH_CSKY_H +#define LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_ARCH_CSKY_H + +#include "clang/Driver/Driver.h" +#include "llvm/ADT/StringRef.h" +#include "llvm/Option/ArgList.h" +#include "llvm/Option/Option.h" +#include +#include + +namespace clang { +namespace driver { +namespace tools { +namespace csky { + +enum class FloatABI { + Invalid, + Soft, + SoftFP, + Hard, +}; + +FloatABI getCSKYFloatABI(const Driver &D, const llvm::opt::ArgList &Args); + +void getCSKYTargetFeatures(const Driver &D, const llvm::Triple &Triple, + const llvm::opt::ArgList &Args, + llvm::opt::ArgStringList &CmdArgs, + std::vector &Features); + +llvm::StringRef getCSKYArchName(const Driver &D, const llvm::opt::ArgList &Args, + const llvm::Triple &Triple); + +} // end namespace csky +} // namespace tools +} // end namespace driver +} // end namespace clang + +#endif // LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_ARCH_CSKY_H Index: clang/lib/Driver/ToolChains/Arch/CSKY.cpp =================================================================== --- /dev/null +++ clang/lib/Driver/ToolChains/Arch/CSKY.cpp @@ -0,0 +1,142 @@ +//===--- CSKY.cpp - CSKY Helpers for Tools --------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "CSKY.h" +#include "ToolChains/CommonArgs.h" +#include "clang/Basic/CharInfo.h" +#include "clang/Driver/Driver.h" +#include "clang/Driver/DriverDiagnostic.h" +#include "clang/Driver/Options.h" +#include "llvm/ADT/Optional.h" +#include "llvm/ADT/StringSwitch.h" +#include "llvm/Option/ArgList.h" +#include "llvm/Support/CSKYTargetParser.h" +#include "llvm/Support/Host.h" +#include "llvm/Support/TargetParser.h" +#include "llvm/Support/raw_ostream.h" + +using namespace clang::driver; +using namespace clang::driver::tools; +using namespace clang; +using namespace llvm::opt; + +llvm::StringRef csky::getCSKYArchName(const Driver &D, const ArgList &Args, + const llvm::Triple &Triple) { + if (const Arg *A = Args.getLastArg(options::OPT_march_EQ)) { + llvm::CSKY::ArchKind ArchKind = llvm::CSKY::parseArch(A->getValue()); + + if (ArchKind == llvm::CSKY::ArchKind::INVALID) { + D.Diag(clang::diag::err_drv_invalid_arch_name) << A->getAsString(Args); + return StringRef(); + } + return A->getValue(); + } + + if (const Arg *A = Args.getLastArg(clang::driver::options::OPT_mcpu_EQ)) { + llvm::CSKY::ArchKind ArchKind = llvm::CSKY::parseCPUArch(A->getValue()); + if (ArchKind == llvm::CSKY::ArchKind::INVALID) { + D.Diag(clang::diag::err_drv_clang_unsupported) << A->getAsString(Args); + return StringRef(); + } + return llvm::CSKY::getArchName(ArchKind); + } + + return StringRef(); +} + +csky::FloatABI csky::getCSKYFloatABI(const Driver &D, const ArgList &Args) { + csky::FloatABI ABI = FloatABI::Soft; + if (Arg *A = + Args.getLastArg(options::OPT_msoft_float, options::OPT_mhard_float, + options::OPT_mfloat_abi_EQ)) { + if (A->getOption().matches(options::OPT_msoft_float)) { + ABI = FloatABI::Soft; + } else if (A->getOption().matches(options::OPT_mhard_float)) { + ABI = FloatABI::Hard; + } else { + ABI = llvm::StringSwitch(A->getValue()) + .Case("soft", FloatABI::Soft) + .Case("softfp", FloatABI::SoftFP) + .Case("hard", FloatABI::Hard) + .Default(FloatABI::Invalid); + if (ABI == FloatABI::Invalid) { + D.Diag(diag::err_drv_invalid_mfloat_abi) << A->getAsString(Args); + ABI = FloatABI::Soft; + } + } + } + + return ABI; +} + +// Handle -mfpu=. +static llvm::CSKY::CSKYFPUKind +getCSKYFPUFeatures(const Driver &D, const Arg *A, const ArgList &Args, + StringRef FPU, std::vector &Features) { + + llvm::CSKY::CSKYFPUKind FPUID = + llvm::StringSwitch(FPU) + .Case("auto", llvm::CSKY::FK_AUTO) + .Case("fpv2", llvm::CSKY::FK_FPV2) + .Case("fpv2_divd", llvm::CSKY::FK_FPV2_DIVD) + .Case("fpv2_sf", llvm::CSKY::FK_FPV2_SF) + .Case("fpv3", llvm::CSKY::FK_FPV3) + .Case("fpv3_hf", llvm::CSKY::FK_FPV3_HF) + .Case("fpv3_hsf", llvm::CSKY::FK_FPV3_HSF) + .Case("fpv3_sdf", llvm::CSKY::FK_FPV3_SDF) + .Default(llvm::CSKY::FK_INVALID); + + if (!llvm::CSKY::getFPUFeatures(FPUID, Features)) { + D.Diag(clang::diag::err_drv_clang_unsupported) << A->getAsString(Args); + return llvm::CSKY::FK_INVALID; + } + + return FPUID; +} + +void csky::getCSKYTargetFeatures(const Driver &D, const llvm::Triple &Triple, + const ArgList &Args, ArgStringList &CmdArgs, + std::vector &Features) { + + llvm::StringRef archName = getCSKYArchName(D, Args, Triple); + llvm::CSKY::ArchKind archKind = llvm::CSKY::parseArch(archName); + llvm::StringRef cpuName = + (archKind == llvm::CSKY::ArchKind::INVALID) ? StringRef() : archName; + + if (const Arg *A = Args.getLastArg(clang::driver::options::OPT_mcpu_EQ)) { + llvm::CSKY::ArchKind Kind = llvm::CSKY::parseCPUArch(A->getValue()); + if (Kind != archKind) { + D.Diag(clang::diag::err_drv_clang_unsupported) << A->getAsString(Args); + return; + } + cpuName = A->getValue(); + } + if (!cpuName.empty()) { + CmdArgs.push_back("-target-cpu"); + CmdArgs.push_back(Args.MakeArgString(cpuName)); + } + + csky::FloatABI FloatABI = csky::getCSKYFloatABI(D, Args); + + if (FloatABI == csky::FloatABI::Hard) { + Features.push_back("+hard-float-abi"); + Features.push_back("+hard-float"); + } else if (FloatABI == csky::FloatABI::SoftFP) { + Features.push_back("+hard-float"); + } + + if (const Arg *FPUArg = Args.getLastArg(options::OPT_mfpu_EQ)) + getCSKYFPUFeatures(D, FPUArg, Args, FPUArg->getValue(), Features); + else if (FloatABI != csky::FloatABI::Soft && archName.empty()) + llvm::CSKY::getFPUFeatures(llvm::CSKY::FK_AUTO, Features); + + if (!cpuName.empty() && archKind != llvm::CSKY::ArchKind::INVALID) { + uint64_t Extension = llvm::CSKY::getDefaultExtensions(cpuName); + llvm::CSKY::getExtensionFeatures(Extension, Features); + } +} Index: clang/lib/Driver/ToolChains/CSKYToolChain.h =================================================================== --- /dev/null +++ clang/lib/Driver/ToolChains/CSKYToolChain.h @@ -0,0 +1,64 @@ +//===--- CSKYToolchain.h - CSKY ToolChain Implementations -----*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_CSKYTOOLCHAIN_H +#define LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_CSKYTOOLCHAIN_H + +#include "Gnu.h" +#include "clang/Driver/ToolChain.h" + +namespace clang { +namespace driver { +namespace toolchains { + +class LLVM_LIBRARY_VISIBILITY CSKYToolChain : public Generic_ELF { +public: + CSKYToolChain(const Driver &D, const llvm::Triple &Triple, + const llvm::opt::ArgList &Args); + + bool IsIntegratedAssemblerDefault() const override { return true; } + void addClangTargetOptions(const llvm::opt::ArgList &DriverArgs, + llvm::opt::ArgStringList &CC1Args, + Action::OffloadKind) const override; + RuntimeLibType GetDefaultRuntimeLibType() const override; + UnwindLibType GetUnwindLibType(const llvm::opt::ArgList &Args) const override; + void + AddClangSystemIncludeArgs(const llvm::opt::ArgList &DriverArgs, + llvm::opt::ArgStringList &CC1Args) const override; + void + addLibStdCxxIncludePaths(const llvm::opt::ArgList &DriverArgs, + llvm::opt::ArgStringList &CC1Args) const override; + +protected: + Tool *buildLinker() const override; + +private: + std::string computeSysRoot() const override; +}; + +} // end namespace toolchains + +namespace tools { +namespace CSKY { +class LLVM_LIBRARY_VISIBILITY Linker : public Tool { +public: + Linker(const ToolChain &TC) : Tool("CSKY::Linker", "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 CSKY +} // end namespace tools + +} // end namespace driver +} // end namespace clang + +#endif // LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_CSKYTOOLCHAIN_H Index: clang/lib/Driver/ToolChains/CSKYToolChain.cpp =================================================================== --- /dev/null +++ clang/lib/Driver/ToolChains/CSKYToolChain.cpp @@ -0,0 +1,204 @@ +//===--- CSKYToolchain.cpp - CSKY ToolChain Implementations ---*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "CSKYToolChain.h" +#include "CommonArgs.h" +#include "clang/Driver/Compilation.h" +#include "clang/Driver/InputInfo.h" +#include "clang/Driver/Options.h" +#include "llvm/Option/ArgList.h" +#include "llvm/Support/FileSystem.h" +#include "llvm/Support/Path.h" +#include "llvm/Support/raw_ostream.h" + +using namespace clang::driver; +using namespace clang::driver::toolchains; +using namespace clang::driver::tools; +using namespace clang; +using namespace llvm::opt; + +static void addMultilibsFilePaths(const Driver &D, const MultilibSet &Multilibs, + const Multilib &Multilib, + StringRef InstallPath, + ToolChain::path_list &Paths) { + if (const auto &PathsCallback = Multilibs.filePathsCallback()) + for (const auto &Path : PathsCallback(Multilib)) + addPathIfExists(D, InstallPath + Path, Paths); +} + +/// CSKY Toolchain +CSKYToolChain::CSKYToolChain(const Driver &D, const llvm::Triple &Triple, + const ArgList &Args) + : Generic_ELF(D, Triple, Args) { + GCCInstallation.init(Triple, Args); + if (GCCInstallation.isValid()) { + Multilibs = GCCInstallation.getMultilibs(); + SelectedMultilib = GCCInstallation.getMultilib(); + path_list &Paths = getFilePaths(); + // Add toolchain/multilib specific file paths. + addMultilibsFilePaths(D, Multilibs, SelectedMultilib, + GCCInstallation.getInstallPath(), Paths); + getFilePaths().push_back(GCCInstallation.getInstallPath().str() + + SelectedMultilib.osSuffix()); + ToolChain::path_list &PPaths = getProgramPaths(); + // Multilib cross-compiler GCC installations put ld in a triple-prefixed + // directory off of the parent of the GCC installation. + PPaths.push_back(Twine(GCCInstallation.getParentLibPath() + "/../" + + GCCInstallation.getTriple().str() + "/bin") + .str()); + PPaths.push_back((GCCInstallation.getParentLibPath() + "/../bin").str()); + } else { + getProgramPaths().push_back(D.Dir); + } + getFilePaths().push_back(computeSysRoot() + "/lib" + + SelectedMultilib.osSuffix()); +} + +Tool *CSKYToolChain::buildLinker() const { + return new tools::CSKY::Linker(*this); +} + +ToolChain::RuntimeLibType CSKYToolChain::GetDefaultRuntimeLibType() const { + return GCCInstallation.isValid() ? ToolChain::RLT_Libgcc + : ToolChain::RLT_CompilerRT; +} + +ToolChain::UnwindLibType +CSKYToolChain::GetUnwindLibType(const llvm::opt::ArgList &Args) const { + return ToolChain::UNW_None; +} + +void CSKYToolChain::addClangTargetOptions(const llvm::opt::ArgList &DriverArgs, + llvm::opt::ArgStringList &CC1Args, + Action::OffloadKind) const { + CC1Args.push_back("-nostdsysteminc"); +} + +void CSKYToolChain::AddClangSystemIncludeArgs(const ArgList &DriverArgs, + ArgStringList &CC1Args) const { + if (DriverArgs.hasArg(options::OPT_nostdinc)) + return; + + if (!DriverArgs.hasArg(options::OPT_nostdlibinc)) { + SmallString<128> Dir(computeSysRoot()); + llvm::sys::path::append(Dir, "include"); + addSystemInclude(DriverArgs, CC1Args, Dir.str()); + SmallString<128> Dir2(computeSysRoot()); + llvm::sys::path::append(Dir2, "sys-include"); + addSystemInclude(DriverArgs, CC1Args, Dir2.str()); + } +} + +void CSKYToolChain::addLibStdCxxIncludePaths( + const llvm::opt::ArgList &DriverArgs, + llvm::opt::ArgStringList &CC1Args) const { + const GCCVersion &Version = GCCInstallation.getVersion(); + StringRef TripleStr = GCCInstallation.getTriple().str(); + const Multilib &Multilib = GCCInstallation.getMultilib(); + addLibStdCXXIncludePaths(computeSysRoot() + "/include/c++/" + Version.Text, + TripleStr, Multilib.includeSuffix(), DriverArgs, + CC1Args); +} + +std::string CSKYToolChain::computeSysRoot() const { + if (!getDriver().SysRoot.empty()) + return getDriver().SysRoot; + + SmallString<128> SysRootDir; + if (GCCInstallation.isValid()) { + StringRef LibDir = GCCInstallation.getParentLibPath(); + StringRef TripleStr = GCCInstallation.getTriple().str(); + llvm::sys::path::append(SysRootDir, LibDir, "..", TripleStr); + } else { + // Use the triple as provided to the driver. Unlike the parsed triple + // this has not been normalized to always contain every field. + llvm::sys::path::append(SysRootDir, getDriver().Dir, "..", + getDriver().getTargetTriple()); + } + + if (!llvm::sys::fs::exists(SysRootDir)) + return std::string(); + + return std::string(SysRootDir.str()); +} + +void CSKY::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)); + + CmdArgs.push_back("-m"); + CmdArgs.push_back("cskyelf"); + + std::string Linker = getToolChain().GetLinkerPath(); + + bool WantCRTs = + !Args.hasArg(options::OPT_nostdlib, options::OPT_nostartfiles); + + const char *crtbegin, *crtend; + auto RuntimeLib = ToolChain.GetRuntimeLibType(Args); + if (RuntimeLib == ToolChain::RLT_Libgcc) { + crtbegin = "crtbegin.o"; + crtend = "crtend.o"; + } else { + assert(RuntimeLib == ToolChain::RLT_CompilerRT); + crtbegin = ToolChain.getCompilerRTArgString(Args, "crtbegin", + ToolChain::FT_Object); + crtend = + ToolChain.getCompilerRTArgString(Args, "crtend", ToolChain::FT_Object); + } + + if (WantCRTs) { + CmdArgs.push_back(Args.MakeArgString(ToolChain.GetFilePath("crt0.o"))); + CmdArgs.push_back(Args.MakeArgString(ToolChain.GetFilePath("crti.o"))); + CmdArgs.push_back(Args.MakeArgString(ToolChain.GetFilePath(crtbegin))); + } + + 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)) { + if (ToolChain.ShouldLinkCXXStdlib(Args)) + ToolChain.AddCXXStdlibLibArgs(Args, CmdArgs); + CmdArgs.push_back("--start-group"); + CmdArgs.push_back("-lc"); + if (Args.hasArg(options::OPT_msim)) + CmdArgs.push_back("-lsemi"); + else + CmdArgs.push_back("-lnosys"); + CmdArgs.push_back("--end-group"); + AddRunTimeLibs(ToolChain, ToolChain.getDriver(), CmdArgs, Args); + } + + if (WantCRTs) { + CmdArgs.push_back(Args.MakeArgString(ToolChain.GetFilePath(crtend))); + CmdArgs.push_back(Args.MakeArgString(ToolChain.GetFilePath("crtn.o"))); + } + + CmdArgs.push_back("-o"); + CmdArgs.push_back(Output.getFilename()); + C.addCommand(std::make_unique( + JA, *this, ResponseFileSupport::AtFileCurCP(), Args.MakeArgString(Linker), + CmdArgs, Inputs, Output)); +} +// CSKY tools end. Index: clang/lib/Driver/ToolChains/Clang.cpp =================================================================== --- clang/lib/Driver/ToolChains/Clang.cpp +++ clang/lib/Driver/ToolChains/Clang.cpp @@ -10,6 +10,7 @@ #include "AMDGPU.h" #include "Arch/AArch64.h" #include "Arch/ARM.h" +#include "Arch/CSKY.h" #include "Arch/M68k.h" #include "Arch/Mips.h" #include "Arch/PPC.h" @@ -378,6 +379,9 @@ case llvm::Triple::ve: ve::getVETargetFeatures(D, Args, Features); break; + case llvm::Triple::csky: + csky::getCSKYTargetFeatures(D, Triple, Args, CmdArgs, Features); + break; } for (auto Feature : unifyTargetFeatures(Features)) { @@ -542,6 +546,7 @@ case llvm::Triple::riscv64: case llvm::Triple::amdgcn: case llvm::Triple::r600: + case llvm::Triple::csky: return !areOptimizationsEnabled(Args); default: break; Index: clang/lib/Driver/ToolChains/CommonArgs.cpp =================================================================== --- clang/lib/Driver/ToolChains/CommonArgs.cpp +++ clang/lib/Driver/ToolChains/CommonArgs.cpp @@ -424,6 +424,7 @@ return TargetCPUName; } + case llvm::Triple::csky: case llvm::Triple::riscv32: case llvm::Triple::riscv64: if (const Arg *A = Args.getLastArg(options::OPT_mcpu_EQ)) Index: clang/lib/Driver/ToolChains/Gnu.cpp =================================================================== --- clang/lib/Driver/ToolChains/Gnu.cpp +++ clang/lib/Driver/ToolChains/Gnu.cpp @@ -8,6 +8,7 @@ #include "Gnu.h" #include "Arch/ARM.h" +#include "Arch/CSKY.h" #include "Arch/Mips.h" #include "Arch/PPC.h" #include "Arch/RISCV.h" @@ -299,6 +300,8 @@ return "elf_x86_64"; case llvm::Triple::ve: return "elf64ve"; + case llvm::Triple::csky: + return "cskyelf_linux"; default: return nullptr; } @@ -1577,6 +1580,67 @@ return false; } +static void findCSKYMultilibs(const Driver &D, const llvm::Triple &TargetTriple, + StringRef Path, const ArgList &Args, + DetectedMultilibs &Result) { + FilterNonExistent NonExistent(Path, "/crtbegin.o", D.getVFS()); + + tools::csky::FloatABI TheFloatABI = tools::csky::getCSKYFloatABI(D, Args); + StringRef ARCHName = tools::csky::getCSKYArchName(D, Args, TargetTriple); + if (ARCHName.empty()) + ARCHName = "ck810"; + + bool isBigEndian = false; + + Multilib::flags_list Flags; + addMultilibFlag(TheFloatABI == tools::csky::FloatABI::Hard, "hard-fp", Flags); + addMultilibFlag(TheFloatABI == tools::csky::FloatABI::SoftFP, "soft-fp", + Flags); + addMultilibFlag(TheFloatABI == tools::csky::FloatABI::Soft, "soft", Flags); + addMultilibFlag(ARCHName == "ck801", "march=ck801", Flags); + addMultilibFlag(ARCHName == "ck802", "march=ck802", Flags); + addMultilibFlag(ARCHName == "ck803", "march=ck803", Flags); + addMultilibFlag(ARCHName == "ck804", "march=ck804", Flags); + addMultilibFlag(ARCHName == "ck805", "march=ck805", Flags); + addMultilibFlag(ARCHName == "ck807", "march=ck807", Flags); + addMultilibFlag(ARCHName == "ck810", "march=ck810", Flags); + addMultilibFlag(ARCHName == "ck810v", "march=ck810v", Flags); + addMultilibFlag(ARCHName == "ck860", "march=ck860", Flags); + addMultilibFlag(ARCHName == "ck860v", "march=ck860v", Flags); + + if (Arg *A = Args.getLastArg(options::OPT_mlittle_endian, + options::OPT_mbig_endian)) + isBigEndian = !A->getOption().matches(options::OPT_mlittle_endian); + addMultilibFlag(isBigEndian, "EB", Flags); + + auto HardFloat = makeMultilib("/hard-fp").flag("+hard-fp"); + auto SoftFpFloat = makeMultilib("/soft-fp").flag("+soft-fp"); + auto SoftFloat = makeMultilib("").flag("+soft"); + auto Arch801 = makeMultilib("/ck801").flag("+march=ck801"); + auto Arch802 = makeMultilib("/ck802").flag("+march=ck802"); + auto Arch803 = makeMultilib("/ck803").flag("+march=ck803"); + // CK804 use the same library as CK803 + auto Arch804 = makeMultilib("/ck803").flag("+march=ck804"); + auto Arch805 = makeMultilib("/ck805").flag("+march=ck805"); + auto Arch807 = makeMultilib("/ck807").flag("+march=ck807"); + auto Arch810 = makeMultilib("").flag("+march=ck810"); + auto Arch810v = makeMultilib("/ck810v").flag("+march=ck810v"); + auto Arch860 = makeMultilib("/ck860").flag("+march=ck860"); + auto Arch860v = makeMultilib("/ck860v").flag("+march=ck860v"); + auto BigEndian = makeMultilib("/big").flag("+EB"); + + MultilibSet CSKYMultilibs = + MultilibSet() + .Maybe(BigEndian) + .Either({Arch801, Arch802, Arch803, Arch804, Arch805, Arch807, + Arch810, Arch810v, Arch860, Arch860v}) + .Either(HardFloat, SoftFpFloat, SoftFloat) + .FilterOut(NonExistent); + + if (CSKYMultilibs.select(Flags, Result.SelectedMultilib)) + Result.Multilibs = CSKYMultilibs; +} + static void findRISCVBareMetalMultilibs(const Driver &D, const llvm::Triple &TargetTriple, StringRef Path, const ArgList &Args, @@ -2095,6 +2159,10 @@ static const char *const AVRLibDirs[] = {"/lib"}; static const char *const AVRTriples[] = {"avr"}; + static const char *const CSKYLibDirs[] = {"/lib"}; + static const char *const CSKYTriples[] = { + "csky-linux-gnuabiv2", "csky-linux-uclibcabiv2", "csky-elf-noneabiv2"}; + static const char *const X86_64LibDirs[] = {"/lib64", "/lib"}; static const char *const X86_64Triples[] = { "x86_64-linux-gnu", "x86_64-unknown-linux-gnu", @@ -2329,6 +2397,10 @@ LibDirs.append(begin(AVRLibDirs), end(AVRLibDirs)); TripleAliases.append(begin(AVRTriples), end(AVRTriples)); break; + case llvm::Triple::csky: + LibDirs.append(begin(CSKYLibDirs), end(CSKYLibDirs)); + TripleAliases.append(begin(CSKYTriples), end(CSKYTriples)); + break; case llvm::Triple::x86_64: if (TargetTriple.isX32()) { LibDirs.append(begin(X32LibDirs), end(X32LibDirs)); @@ -2478,6 +2550,8 @@ if (isArmOrThumbArch(TargetArch) && TargetTriple.isAndroid()) { // It should also work without multilibs in a simplified toolchain. findAndroidArmMultilibs(D, TargetTriple, Path, Args, Detected); + } else if (TargetTriple.isCSKY()) { + findCSKYMultilibs(D, TargetTriple, Path, Args, Detected); } else if (TargetTriple.isMIPS()) { if (!findMIPSMultilibs(D, TargetTriple, Path, Args, Detected)) return false; @@ -2738,6 +2812,7 @@ case llvm::Triple::avr: case llvm::Triple::bpfel: case llvm::Triple::bpfeb: + case llvm::Triple::csky: case llvm::Triple::thumb: case llvm::Triple::thumbeb: case llvm::Triple::ppc: Index: clang/lib/Driver/ToolChains/Linux.cpp =================================================================== --- clang/lib/Driver/ToolChains/Linux.cpp +++ clang/lib/Driver/ToolChains/Linux.cpp @@ -221,8 +221,12 @@ const bool IsMips = Triple.isMIPS(); const bool IsHexagon = Arch == llvm::Triple::hexagon; const bool IsRISCV = Triple.isRISCV(); + const bool IsCSKY = Triple.isCSKY(); - if (IsMips && !SysRoot.empty()) + if (IsCSKY) + SysRoot = SysRoot + SelectedMultilib.osSuffix(); + + if ((IsMips || IsCSKY) && !SysRoot.empty()) ExtraOpts.push_back("--sysroot=" + SysRoot); // Do not use 'gnu' hash style for Mips targets because .gnu.hash @@ -361,6 +365,21 @@ return AndroidSysRootPath; } + if (getTriple().isCSKY()) { + // CSKY toolchains use different names for sysroot folder. + if (!GCCInstallation.isValid()) + return std::string(); + // GCCInstallation.getInstallPath() = + // $GCCToolchainPath/lib/gcc/csky-linux-gnuabiv2/6.3.0 + // Path = $GCCToolchainPath/csky-linux-gnuabiv2/libc + std::string Path = (GCCInstallation.getInstallPath() + "/../../../../" + + GCCInstallation.getTriple().str() + "/libc") + .str(); + if (getVFS().exists(Path)) + return Path; + return std::string(); + } + if (!GCCInstallation.isValid() || !getTriple().isMIPS()) return std::string(); @@ -537,6 +556,11 @@ } case llvm::Triple::ve: return "/opt/nec/ve/lib/ld-linux-ve.so.1"; + case llvm::Triple::csky: { + LibDir = "lib"; + Loader = "ld.so.1"; + break; + } } if (Distro == Distro::Exherbo && Index: clang/test/Driver/csky-arch-error.c =================================================================== --- /dev/null +++ clang/test/Driver/csky-arch-error.c @@ -0,0 +1,8 @@ +// RUN: %clang -target csky-unknown-elf -march=csky -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck -check-prefix=CSKY %s +// CSKY: error: invalid arch name '-march=csky' + +// RUN: %clang -target csky-unknown-elf -march=CK810 -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck -check-prefix=CSKY-UPPER %s +// CSKY-UPPER: error: invalid arch name '-march=CK810' + Index: clang/test/Driver/csky-arch.c =================================================================== --- /dev/null +++ clang/test/Driver/csky-arch.c @@ -0,0 +1,31 @@ +// RUN: %clang -target csky-unknown-elf -march=ck801 -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck %s +// RUN: %clang -target csky-unknown-elf -march=ck802 -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck %s +// RUN: %clang -target csky-unknown-elf -march=ck803 -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck %s +// RUN: %clang -target csky-unknown-elf -march=ck803s -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck %s +// RUN: %clang -target csky-unknown-elf -march=ck804 -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck %s +// RUN: %clang -target csky-unknown-elf -march=ck805 -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck %s +// RUN: %clang -target csky-unknown-elf -march=ck807 -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck %s +// RUN: %clang -target csky-unknown-elf -march=ck810 -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck %s +// RUN: %clang -target csky-unknown-elf -march=ck810v -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck %s +// RUN: %clang -target csky-unknown-elf -march=ck860 -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck %s +// RUN: %clang -target csky-unknown-elf -march=ck860v -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck %s + +// Testing specific messages and unsupported extensions. +// RUN: %clang -target csky-unknown-elf -march=ck810 -### %s \ +// RUN: -fsyntax-only 2>&1 | FileCheck -check-prefixes=CHECK,CSKY-TARGET %s + +// CHECK-NOT: error: invalid arch name ' +// CSKY-TARGET: "-triple" "csky-unknown-unknown-elf" + + Index: clang/test/Driver/csky-cpus.c =================================================================== --- /dev/null +++ clang/test/Driver/csky-cpus.c @@ -0,0 +1,15 @@ +// Check target CPUs are correctly passed. + +// RUN: %clang -target csky -### -c %s 2>&1 -mcpu=ck810 | FileCheck -check-prefix=MCPU-CK810 %s +// MCPU-CK810: "-target-cpu" "ck810" + +// RUN: %clang -target csky -### -c %s 2>&1 -mcpu=ck860 | FileCheck -check-prefix=MCPU-CK860 %s +// MCPU-CK860: "-target-cpu" "ck860" + +// Check failed cases + +// RUN: %clang -target csky -### -c %s 2>&1 -mcpu=generic1 | FileCheck -check-prefix=FAIL-MCPU-NAME %s +// FAIL-MCPU-NAME: error: the clang compiler does not support '-mcpu=generic1' + +// RUN: %clang -target csky -### -c %s 2>&1 -mcpu=generic -march=ck860 | FileCheck -check-prefix=MISMATCH-ARCH %s +// MISMATCH-ARCH: error: the clang compiler does not support '-mcpu=generic' Index: clang/test/Driver/csky-toolchain.c =================================================================== --- /dev/null +++ clang/test/Driver/csky-toolchain.c @@ -0,0 +1,43 @@ +// A basic clang -cc1 command-line, and simple environment check. + +// RUN: %clang %s -### -no-canonical-prefixes -target csky 2>&1 | FileCheck -check-prefix=CC1 %s +// CC1: clang{{.*}} "-cc1" "-triple" "csky" + +// Test interaction with -fuse-ld=lld, if lld is available. +// RUN: %clang %s -### -no-canonical-prefixes -target csky -fuse-ld=lld 2>&1 | FileCheck -check-prefix=LLD %s +// LLD: {{(error: invalid linker name in argument '-fuse-ld=lld')|(ld.lld)}} + +// In the below tests, --rtlib=platform is used so that the driver ignores +// the configure-time CLANG_DEFAULT_RTLIB option when choosing the runtime lib + +// RUN: %clang %s -### -no-canonical-prefixes -fuse-ld=ld -target csky-unknown-linux-gnu --rtlib=platform \ +// RUN: --gcc-toolchain=%S/Inputs/multilib_csky_linux_sdk 2>&1 | FileCheck -check-prefix=C-CSKY-LINUX-MULTI %s + +// C-CSKY-LINUX-MULTI: "{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/bin{{/|\\\\}}ld" +// C-CSKY-LINUX-MULTI: "--sysroot={{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc" +// C-CSKY-LINUX-MULTI: "-m" "cskyelf_linux" +// C-CSKY-LINUX-MULTI: "-dynamic-linker" "/lib/ld.so.1" +// C-CSKY-LINUX-MULTI: "{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc/usr/lib/../lib/crt1.o" +// C-CSKY-LINUX-MULTI: "{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/crti.o" +// C-CSKY-LINUX-MULTI: "{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/crtbegin.o" +// C-CSKY-LINUX-MULTI: "-L{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0" +// C-CSKY-LINUX-MULTI: "-L{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc/lib/../lib" +// C-CSKY-LINUX-MULTI: "-L{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc/usr/lib/../lib" +// C-CSKY-LINUX-MULTI: "-L{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc/lib" +// C-CSKY-LINUX-MULTI: "-L{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc/usr/lib" + +// RUN: %clang %s -### -no-canonical-prefixes -fuse-ld=ld -target csky-unknown-linux-gnu --rtlib=platform -march=ck860v \ +// RUN: --gcc-toolchain=%S/Inputs/multilib_csky_linux_sdk 2>&1 | FileCheck -check-prefix=C-CSKY-LINUX-CK860V %s + +// C-CSKY-LINUX-CK860V: "{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/bin{{/|\\\\}}ld" +// C-CSKY-LINUX-CK860V: "--sysroot={{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc/ck860v" +// C-CSKY-LINUX-CK860V: "-m" "cskyelf_linux" +// C-CSKY-LINUX-CK860V: "-dynamic-linker" "/lib/ld.so.1" +// C-CSKY-LINUX-CK860V: "{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc/ck860v/usr/lib/../lib/crt1.o" +// C-CSKY-LINUX-CK860V: "{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/ck860v/crti.o" +// C-CSKY-LINUX-CK860V: "{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/ck860v/crtbegin.o" +// C-CSKY-LINUX-CK860V: "-L{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/ck860v" +// C-CSKY-LINUX-CK860V: "-L{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc/ck860v/lib/../lib" +// C-CSKY-LINUX-CK860V: "-L{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc/ck860v/usr/lib/../lib" +// C-CSKY-LINUX-CK860V: "-L{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc/ck860v/lib" +// C-CSKY-LINUX-CK860V: "-L{{.*}}/Inputs/multilib_csky_linux_sdk/lib/gcc/csky-linux-gnuabiv2/6.3.0/../../..{{/|\\\\}}..{{/|\\\\}}csky-linux-gnuabiv2/libc/ck860v/usr/lib" Index: clang/test/Preprocessor/csky-target-features.c =================================================================== --- /dev/null +++ clang/test/Preprocessor/csky-target-features.c @@ -0,0 +1,17 @@ +// RUN: %clang -target csky-unknown-linux-gnu -x c -E -dM %s \ +// RUN: -o - | FileCheck %s + +// CHECK: __CK810F__ 1 +// CHECK: __CK810__ 1 +// CHECK: __CKCORE__ 2 +// CHECK: __CSKYABI__ 2 +// CHECK: __CSKYLE__ 1 +// CHECK: __CSKY__ 2 + +// CHECK: __ck810__ 1 +// CHECK: __ck810f__ 1 +// CHECK: __ckcore__ 2 +// CHECK: __cskyLE__ 1 +// CHECK: __csky__ 2 +// CHECK: __cskyabi__ 2 +// CHECK: __cskyle__ 1 Index: clang/test/Preprocessor/init-csky.c =================================================================== --- /dev/null +++ clang/test/Preprocessor/init-csky.c @@ -0,0 +1,212 @@ +// RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple=csky < /dev/null \ +// RUN: | FileCheck -match-full-lines -check-prefix=CSKY %s +// RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple=csky-unknown-linux < /dev/null \ +// RUN: | FileCheck -match-full-lines -check-prefixes=CSKY,CSKY-LINUX %s +// RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple=csky \ +// RUN: -fforce-enable-int128 < /dev/null | FileCheck -match-full-lines \ +// RUN: -check-prefixes=CSKY,CSKY-INT128 %s +// CSKY: #define _ILP32 1 +// CSKY: #define __ATOMIC_ACQUIRE 2 +// CSKY: #define __ATOMIC_ACQ_REL 4 +// CSKY: #define __ATOMIC_CONSUME 1 +// CSKY: #define __ATOMIC_RELAXED 0 +// CSKY: #define __ATOMIC_RELEASE 3 +// CSKY: #define __ATOMIC_SEQ_CST 5 +// CSKY: #define __BIGGEST_ALIGNMENT__ 4 +// CSKY: #define __BYTE_ORDER__ __ORDER_LITTLE_ENDIAN__ +// CSKY: #define __CHAR16_TYPE__ unsigned short +// CSKY: #define __CHAR32_TYPE__ unsigned int +// CSKY: #define __CHAR_BIT__ 8 +// CSKY: #define __DBL_DECIMAL_DIG__ 17 +// CSKY: #define __DBL_DENORM_MIN__ 4.9406564584124654e-324 +// CSKY: #define __DBL_DIG__ 15 +// CSKY: #define __DBL_EPSILON__ 2.2204460492503131e-16 +// CSKY: #define __DBL_HAS_DENORM__ 1 +// CSKY: #define __DBL_HAS_INFINITY__ 1 +// CSKY: #define __DBL_HAS_QUIET_NAN__ 1 +// CSKY: #define __DBL_MANT_DIG__ 53 +// CSKY: #define __DBL_MAX_10_EXP__ 308 +// CSKY: #define __DBL_MAX_EXP__ 1024 +// CSKY: #define __DBL_MAX__ 1.7976931348623157e+308 +// CSKY: #define __DBL_MIN_10_EXP__ (-307) +// CSKY: #define __DBL_MIN_EXP__ (-1021) +// CSKY: #define __DBL_MIN__ 2.2250738585072014e-308 +// CSKY: #define __DECIMAL_DIG__ __LDBL_DECIMAL_DIG__ +// CSKY: #define __ELF__ 1 +// CSKY: #define __FINITE_MATH_ONLY__ 0 +// CSKY: #define __FLT_DECIMAL_DIG__ 9 +// CSKY: #define __FLT_DENORM_MIN__ 1.40129846e-45F +// CSKY: #define __FLT_DIG__ 6 +// CSKY: #define __FLT_EPSILON__ 1.19209290e-7F +// CSKY: #define __FLT_HAS_DENORM__ 1 +// CSKY: #define __FLT_HAS_INFINITY__ 1 +// CSKY: #define __FLT_HAS_QUIET_NAN__ 1 +// CSKY: #define __FLT_MANT_DIG__ 24 +// CSKY: #define __FLT_MAX_10_EXP__ 38 +// CSKY: #define __FLT_MAX_EXP__ 128 +// CSKY: #define __FLT_MAX__ 3.40282347e+38F +// CSKY: #define __FLT_MIN_10_EXP__ (-37) +// CSKY: #define __FLT_MIN_EXP__ (-125) +// CSKY: #define __FLT_MIN__ 1.17549435e-38F +// CSKY: #define __FLT_RADIX__ 2 +// CSKY: #define __GCC_ATOMIC_BOOL_LOCK_FREE 2 +// CSKY: #define __GCC_ATOMIC_CHAR16_T_LOCK_FREE 2 +// CSKY: #define __GCC_ATOMIC_CHAR32_T_LOCK_FREE 2 +// CSKY: #define __GCC_ATOMIC_CHAR_LOCK_FREE 2 +// CSKY: #define __GCC_ATOMIC_INT_LOCK_FREE 2 +// CSKY: #define __GCC_ATOMIC_LLONG_LOCK_FREE 1 +// CSKY: #define __GCC_ATOMIC_LONG_LOCK_FREE 2 +// CSKY: #define __GCC_ATOMIC_POINTER_LOCK_FREE 2 +// CSKY: #define __GCC_ATOMIC_SHORT_LOCK_FREE 2 +// CSKY: #define __GCC_ATOMIC_TEST_AND_SET_TRUEVAL 1 +// CSKY: #define __GCC_ATOMIC_WCHAR_T_LOCK_FREE 2 +// CSKY: #define __GNUC_MINOR__ {{.*}} +// CSKY: #define __GNUC_PATCHLEVEL__ {{.*}} +// CSKY: #define __GNUC_STDC_INLINE__ 1 +// CSKY: #define __GNUC__ {{.*}} +// CSKY: #define __GXX_ABI_VERSION {{.*}} +// CSKY: #define __ILP32__ 1 +// CSKY: #define __INT16_C_SUFFIX__ +// CSKY: #define __INT16_MAX__ 32767 +// CSKY: #define __INT16_TYPE__ short +// CSKY: #define __INT32_C_SUFFIX__ +// CSKY: #define __INT32_MAX__ 2147483647 +// CSKY: #define __INT32_TYPE__ int +// CSKY: #define __INT64_C_SUFFIX__ LL +// CSKY: #define __INT64_MAX__ 9223372036854775807LL +// CSKY: #define __INT64_TYPE__ long long int +// CSKY: #define __INT8_C_SUFFIX__ +// CSKY: #define __INT8_MAX__ 127 +// CSKY: #define __INT8_TYPE__ signed char +// CSKY: #define __INTMAX_C_SUFFIX__ LL +// CSKY: #define __INTMAX_MAX__ 9223372036854775807LL +// CSKY: #define __INTMAX_TYPE__ long long int +// CSKY: #define __INTMAX_WIDTH__ 64 +// CSKY: #define __INTPTR_MAX__ 2147483647 +// CSKY: #define __INTPTR_TYPE__ int +// CSKY: #define __INTPTR_WIDTH__ 32 +// TODO: C-SKY GCC defines INT_FAST16 as int +// CSKY: #define __INT_FAST16_MAX__ 32767 +// CSKY: #define __INT_FAST16_TYPE__ short +// CSKY: #define __INT_FAST32_MAX__ 2147483647 +// CSKY: #define __INT_FAST32_TYPE__ int +// CSKY: #define __INT_FAST64_MAX__ 9223372036854775807LL +// CSKY: #define __INT_FAST64_TYPE__ long long int +// TODO: C-SKY GCC defines INT_FAST8 as int +// CSKY: #define __INT_FAST8_MAX__ 127 +// CSKY: #define __INT_FAST8_TYPE__ signed char +// CSKY: #define __INT_LEAST16_MAX__ 32767 +// CSKY: #define __INT_LEAST16_TYPE__ short +// CSKY: #define __INT_LEAST32_MAX__ 2147483647 +// CSKY: #define __INT_LEAST32_TYPE__ int +// CSKY: #define __INT_LEAST64_MAX__ 9223372036854775807LL +// CSKY: #define __INT_LEAST64_TYPE__ long long int +// CSKY: #define __INT_LEAST8_MAX__ 127 +// CSKY: #define __INT_LEAST8_TYPE__ signed char +// CSKY: #define __INT_MAX__ 2147483647 +// CSKY: #define __LDBL_DECIMAL_DIG__ 17 +// CSKY: #define __LDBL_DENORM_MIN__ 4.9406564584124654e-324L +// CSKY: #define __LDBL_DIG__ 15 +// CSKY: #define __LDBL_EPSILON__ 2.2204460492503131e-16L +// CSKY: #define __LDBL_HAS_DENORM__ 1 +// CSKY: #define __LDBL_HAS_INFINITY__ 1 +// CSKY: #define __LDBL_HAS_QUIET_NAN__ 1 +// CSKY: #define __LDBL_MANT_DIG__ 53 +// CSKY: #define __LDBL_MAX_10_EXP__ 308 +// CSKY: #define __LDBL_MAX_EXP__ 1024 +// CSKY: #define __LDBL_MAX__ 1.7976931348623157e+308L +// CSKY: #define __LDBL_MIN_10_EXP__ (-307) +// CSKY: #define __LDBL_MIN_EXP__ (-1021) +// CSKY: #define __LDBL_MIN__ 2.2250738585072014e-308L +// CSKY: #define __LITTLE_ENDIAN__ 1 +// CSKY: #define __LONG_LONG_MAX__ 9223372036854775807LL +// CSKY: #define __LONG_MAX__ 2147483647L +// CSKY: #define __NO_INLINE__ 1 +// CSKY: #define __POINTER_WIDTH__ 32 +// CSKY: #define __PRAGMA_REDEFINE_EXTNAME 1 +// CSKY: #define __PTRDIFF_MAX__ 2147483647 +// CSKY: #define __PTRDIFF_TYPE__ int +// CSKY: #define __PTRDIFF_WIDTH__ 32 +// CSKY: #define __SCHAR_MAX__ 127 +// CSKY: #define __SHRT_MAX__ 32767 +// CSKY: #define __SIG_ATOMIC_MAX__ 2147483647 +// CSKY: #define __SIG_ATOMIC_WIDTH__ 32 +// CSKY: #define __SIZEOF_DOUBLE__ 8 +// CSKY: #define __SIZEOF_FLOAT__ 4 +// CSKY-INT128: #define __SIZEOF_INT128__ 16 +// CSKY: #define __SIZEOF_INT__ 4 +// CSKY: #define __SIZEOF_LONG_DOUBLE__ 8 +// CSKY: #define __SIZEOF_LONG_LONG__ 8 +// CSKY: #define __SIZEOF_LONG__ 4 +// CSKY: #define __SIZEOF_POINTER__ 4 +// CSKY: #define __SIZEOF_PTRDIFF_T__ 4 +// CSKY: #define __SIZEOF_SHORT__ 2 +// CSKY: #define __SIZEOF_SIZE_T__ 4 +// CSKY: #define __SIZEOF_WCHAR_T__ 4 +// CSKY: #define __SIZEOF_WINT_T__ 4 +// CSKY: #define __SIZE_MAX__ 4294967295U +// CSKY: #define __SIZE_TYPE__ unsigned int +// CSKY: #define __SIZE_WIDTH__ 32 +// CSKY: #define __STDC_HOSTED__ 0 +// CSKY: #define __STDC_UTF_16__ 1 +// CSKY: #define __STDC_UTF_32__ 1 +// CSKY: #define __STDC_VERSION__ 201710L +// CSKY: #define __STDC__ 1 +// CSKY: #define __UINT16_C_SUFFIX__ +// CSKY: #define __UINT16_MAX__ 65535 +// CSKY: #define __UINT16_TYPE__ unsigned short +// CSKY: #define __UINT32_C_SUFFIX__ U +// CSKY: #define __UINT32_MAX__ 4294967295U +// CSKY: #define __UINT32_TYPE__ unsigned int +// CSKY: #define __UINT64_C_SUFFIX__ ULL +// CSKY: #define __UINT64_MAX__ 18446744073709551615ULL +// CSKY: #define __UINT64_TYPE__ long long unsigned int +// CSKY: #define __UINT8_C_SUFFIX__ +// CSKY: #define __UINT8_MAX__ 255 +// CSKY: #define __UINT8_TYPE__ unsigned char +// CSKY: #define __UINTMAX_C_SUFFIX__ ULL +// CSKY: #define __UINTMAX_MAX__ 18446744073709551615ULL +// CSKY: #define __UINTMAX_TYPE__ long long unsigned int +// CSKY: #define __UINTMAX_WIDTH__ 64 +// CSKY: #define __UINTPTR_MAX__ 4294967295U +// CSKY: #define __UINTPTR_TYPE__ unsigned int +// CSKY: #define __UINTPTR_WIDTH__ 32 +// TODO: C-SKY GCC defines UINT_FAST16 to be unsigned int +// CSKY: #define __UINT_FAST16_MAX__ 65535 +// CSKY: #define __UINT_FAST16_TYPE__ unsigned short +// CSKY: #define __UINT_FAST32_MAX__ 4294967295U +// CSKY: #define __UINT_FAST32_TYPE__ unsigned int +// CSKY: #define __UINT_FAST64_MAX__ 18446744073709551615ULL +// CSKY: #define __UINT_FAST64_TYPE__ long long unsigned int +// TODO: C-SKY GCC defines UINT_FAST8 to be unsigned int +// CSKY: #define __UINT_FAST8_MAX__ 255 +// CSKY: #define __UINT_FAST8_TYPE__ unsigned char +// CSKY: #define __UINT_LEAST16_MAX__ 65535 +// CSKY: #define __UINT_LEAST16_TYPE__ unsigned short +// CSKY: #define __UINT_LEAST32_MAX__ 4294967295U +// CSKY: #define __UINT_LEAST32_TYPE__ unsigned int +// CSKY: #define __UINT_LEAST64_MAX__ 18446744073709551615ULL +// CSKY: #define __UINT_LEAST64_TYPE__ long long unsigned int +// CSKY: #define __UINT_LEAST8_MAX__ 255 +// CSKY: #define __UINT_LEAST8_TYPE__ unsigned char +// CSKY: #define __USER_LABEL_PREFIX__ +// CSKY: #define __WCHAR_MAX__ 2147483647 +// CSKY: #define __WCHAR_TYPE__ int +// CSKY: #define __WCHAR_WIDTH__ 32 +// CSKY: #define __WINT_TYPE__ unsigned int +// CSKY: #define __WINT_UNSIGNED__ 1 +// CSKY: #define __WINT_WIDTH__ 32 +// CSKY: #define __ck810__ 1 +// CSKY: #define __ck810f__ 1 +// CSKY: #define __ckcore__ 2 +// CSKY: #define __cskyLE__ 1 +// CSKY: #define __csky__ 2 +// CSKY: #define __cskyabi__ 2 +// CSKY: #define __cskyle__ 1 +// CSKY-LINUX: #define __gnu_linux__ 1 +// CSKY-LINUX: #define __linux 1 +// CSKY-LINUX: #define __linux__ 1 +// CSKY-LINUX: #define __unix 1 +// CSKY-LINUX: #define __unix__ 1 +// CSKY-LINUX: #define linux 1 +// CSKY-LINUX: #define unix 1 Index: llvm/lib/Target/CSKY/CSKY.h =================================================================== --- llvm/lib/Target/CSKY/CSKY.h +++ llvm/lib/Target/CSKY/CSKY.h @@ -19,6 +19,7 @@ namespace llvm { class CSKYTargetMachine; class FunctionPass; +class PassRegistry; FunctionPass *createCSKYISelDag(CSKYTargetMachine &TM); FunctionPass *createCSKYConstantIslandPass();