From a97740d995e7fbb88fa6626cfabfc087d4cb1474 Mon Sep 17 00:00:00 2001 From: chenli Date: Wed, 9 Aug 2023 17:07:59 +0800 Subject: [PATCH] [LoongArch] Backport patches and add the triple for anolis os --- 0001-backport-LoongArch-patches.patch | 1564 ++++++++++++++++++ 0002-LoongArch-fix-symbol-lookup-error.patch | 834 ++++++++++ clang.spec | 9 +- 3 files changed, 2406 insertions(+), 1 deletion(-) create mode 100644 0001-backport-LoongArch-patches.patch create mode 100644 0002-LoongArch-fix-symbol-lookup-error.patch diff --git a/0001-backport-LoongArch-patches.patch b/0001-backport-LoongArch-patches.patch new file mode 100644 index 0000000..ae53c0f --- /dev/null +++ b/0001-backport-LoongArch-patches.patch @@ -0,0 +1,1564 @@ +diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst +index 8d67ff904..d36046916 100644 +--- a/clang/docs/ReleaseNotes.rst ++++ b/clang/docs/ReleaseNotes.rst +@@ -1047,6 +1047,9 @@ LoongArch Support + - Support extended options: ``-msoft-float``, ``-msingle-float``, ``-mdouble-float`` and ``mfpu=``. + See `LoongArch toolchain conventions `_. + ++- Patchable function entry (``-fpatchable-function-entry``) is now supported ++ on LoongArch. ++ + RISC-V Support + ^^^^^^^^^^^^^^ + - ``sifive-7-rv32`` and ``sifive-7-rv64`` are no longer supported for ``-mcpu``. +diff --git a/clang/include/clang/Basic/Attr.td b/clang/include/clang/Basic/Attr.td +index d449a2fe7..28f94eebc 100644 +--- a/clang/include/clang/Basic/Attr.td ++++ b/clang/include/clang/Basic/Attr.td +@@ -792,7 +792,8 @@ def XRayLogArgs : InheritableAttr { + def PatchableFunctionEntry + : InheritableAttr, + TargetSpecificAttr> { ++ ["aarch64", "aarch64_be", "loongarch32", "loongarch64", "riscv32", ++ "riscv64", "x86", "x86_64"]>> { + let Spellings = [GCC<"patchable_function_entry">]; + let Subjects = SubjectList<[Function, ObjCMethod]>; + let Args = [UnsignedArgument<"Count">, DefaultIntArgument<"Offset", 0>]; +diff --git a/clang/include/clang/Basic/AttrDocs.td b/clang/include/clang/Basic/AttrDocs.td +index 6d7a3ffd2..8861a9fce 100644 +--- a/clang/include/clang/Basic/AttrDocs.td ++++ b/clang/include/clang/Basic/AttrDocs.td +@@ -5315,7 +5315,7 @@ takes precedence over the command line option ``-fpatchable-function-entry=N,M`` + ``M`` defaults to 0 if omitted. + + This attribute is only supported on +-aarch64/aarch64-be/riscv32/riscv64/i386/x86-64 targets. ++aarch64/aarch64-be/loongarch32/loongarch64/riscv32/riscv64/i386/x86-64 targets. + }]; + } + +diff --git a/clang/include/clang/Basic/DiagnosticDriverKinds.td b/clang/include/clang/Basic/DiagnosticDriverKinds.td +index f3d43b2e0..10bab1c46 100644 +--- a/clang/include/clang/Basic/DiagnosticDriverKinds.td ++++ b/clang/include/clang/Basic/DiagnosticDriverKinds.td +@@ -715,6 +715,9 @@ def warn_drv_sarif_format_unstable : Warning< + def err_drv_riscv_unsupported_with_linker_relaxation : Error< + "%0 is unsupported with RISC-V linker relaxation (-mrelax)">; + ++def warn_drv_loongarch_conflicting_implied_val : Warning< ++ "ignoring '%0' as it conflicts with that implied by '%1' (%2)">, ++ InGroup; + def err_drv_loongarch_invalid_mfpu_EQ : Error< + "invalid argument '%0' to -mfpu=; must be one of: 64, 32, none, 0 (alias for none)">; + } +diff --git a/clang/include/clang/Driver/Options.td b/clang/include/clang/Driver/Options.td +index 652c15afc..fcbdcb5ec 100644 +--- a/clang/include/clang/Driver/Options.td ++++ b/clang/include/clang/Driver/Options.td +@@ -3583,12 +3583,14 @@ def mcmodel_EQ_medany : Flag<["-"], "mcmodel=medany">, Group, + def menable_experimental_extensions : Flag<["-"], "menable-experimental-extensions">, Group, + HelpText<"Enable use of experimental RISC-V extensions.">; + +-def munaligned_access : Flag<["-"], "munaligned-access">, Group, +- HelpText<"Allow memory accesses to be unaligned (AArch32/AArch64 only)">; +-def mno_unaligned_access : Flag<["-"], "mno-unaligned-access">, Group, +- HelpText<"Force all memory accesses to be aligned (AArch32/AArch64 only)">; ++def munaligned_access : Flag<["-"], "munaligned-access">, Group, ++ HelpText<"Allow memory accesses to be unaligned (AArch32/AArch64/LoongArch only)">; ++def mno_unaligned_access : Flag<["-"], "mno-unaligned-access">, Group, ++ HelpText<"Force all memory accesses to be aligned (AArch32/AArch64/LoongArch only)">; + def mstrict_align : Flag<["-"], "mstrict-align">, Alias, Flags<[CC1Option,HelpHidden]>, + HelpText<"Force all memory accesses to be aligned (same as mno-unaligned-access)">; ++def mno_strict_align : Flag<["-"], "mno-strict-align">, Alias, Flags<[CC1Option,HelpHidden]>, ++ HelpText<"Allow memory accesses to be unaligned (same as munaligned-access)">; + def mno_thumb : Flag<["-"], "mno-thumb">, Group; + def mrestrict_it: Flag<["-"], "mrestrict-it">, Group, + HelpText<"Disallow generation of complex IT blocks.">; +diff --git a/clang/lib/Basic/Targets/LoongArch.cpp b/clang/lib/Basic/Targets/LoongArch.cpp +index 2079c89e3..96ef29620 100644 +--- a/clang/lib/Basic/Targets/LoongArch.cpp ++++ b/clang/lib/Basic/Targets/LoongArch.cpp +@@ -14,8 +14,8 @@ + #include "clang/Basic/Diagnostic.h" + #include "clang/Basic/MacroBuilder.h" + #include "clang/Basic/TargetBuiltins.h" +-#include "llvm/Support/TargetParser.h" + #include "llvm/Support/raw_ostream.h" ++#include "llvm/TargetParser/LoongArchTargetParser.h" + + using namespace clang; + using namespace clang::targets; +@@ -31,34 +31,79 @@ ArrayRef LoongArchTargetInfo::getGCCRegNames() const { + "$f0", "$f1", "$f2", "$f3", "$f4", "$f5", "$f6", "$f7", "$f8", "$f9", + "$f10", "$f11", "$f12", "$f13", "$f14", "$f15", "$f16", "$f17", "$f18", + "$f19", "$f20", "$f21", "$f22", "$f23", "$f24", "$f25", "$f26", "$f27", +- "$f28", "$f29", "$f30", "$f31"}; ++ "$f28", "$f29", "$f30", "$f31", ++ // Condition flag registers. ++ "$fcc0", "$fcc1", "$fcc2", "$fcc3", "$fcc4", "$fcc5", "$fcc6", "$fcc7"}; + return llvm::ArrayRef(GCCRegNames); + } + + ArrayRef + LoongArchTargetInfo::getGCCRegAliases() const { + static const TargetInfo::GCCRegAlias GCCRegAliases[] = { +- {{"$zero"}, "$r0"}, {{"$ra"}, "$r1"}, {{"$tp"}, "$r2"}, +- {{"$sp"}, "$r3"}, {{"$a0"}, "$r4"}, {{"$a1"}, "$r5"}, +- {{"$a2"}, "$r6"}, {{"$a3"}, "$r7"}, {{"$a4"}, "$r8"}, +- {{"$a5"}, "$r9"}, {{"$a6"}, "$r10"}, {{"$a7"}, "$r11"}, +- {{"$t0"}, "$r12"}, {{"$t1"}, "$r13"}, {{"$t2"}, "$r14"}, +- {{"$t3"}, "$r15"}, {{"$t4"}, "$r16"}, {{"$t5"}, "$r17"}, +- {{"$t6"}, "$r18"}, {{"$t7"}, "$r19"}, {{"$t8"}, "$r20"}, +- {{"$fp", "$s9"}, "$r22"}, {{"$s0"}, "$r23"}, {{"$s1"}, "$r24"}, +- {{"$s2"}, "$r25"}, {{"$s3"}, "$r26"}, {{"$s4"}, "$r27"}, +- {{"$s5"}, "$r28"}, {{"$s6"}, "$r29"}, {{"$s7"}, "$r30"}, +- {{"$s8"}, "$r31"}, {{"$fa0"}, "$f0"}, {{"$fa1"}, "$f1"}, +- {{"$fa2"}, "$f2"}, {{"$fa3"}, "$f3"}, {{"$fa4"}, "$f4"}, +- {{"$fa5"}, "$f5"}, {{"$fa6"}, "$f6"}, {{"$fa7"}, "$f7"}, +- {{"$ft0"}, "$f8"}, {{"$ft1"}, "$f9"}, {{"$ft2"}, "$f10"}, +- {{"$ft3"}, "$f11"}, {{"$ft4"}, "$f12"}, {{"$ft5"}, "$f13"}, +- {{"$ft6"}, "$f14"}, {{"$ft7"}, "$f15"}, {{"$ft8"}, "$f16"}, +- {{"$ft9"}, "$f17"}, {{"$ft10"}, "$f18"}, {{"$ft11"}, "$f19"}, +- {{"$ft12"}, "$f20"}, {{"$ft13"}, "$f21"}, {{"$ft14"}, "$f22"}, +- {{"$ft15"}, "$f23"}, {{"$fs0"}, "$f24"}, {{"$fs1"}, "$f25"}, +- {{"$fs2"}, "$f26"}, {{"$fs3"}, "$f27"}, {{"$fs4"}, "$f28"}, +- {{"$fs5"}, "$f29"}, {{"$fs6"}, "$f30"}, {{"$fs7"}, "$f31"}, ++ {{"zero", "$zero", "r0"}, "$r0"}, ++ {{"ra", "$ra", "r1"}, "$r1"}, ++ {{"tp", "$tp", "r2"}, "$r2"}, ++ {{"sp", "$sp", "r3"}, "$r3"}, ++ {{"a0", "$a0", "r4"}, "$r4"}, ++ {{"a1", "$a1", "r5"}, "$r5"}, ++ {{"a2", "$a2", "r6"}, "$r6"}, ++ {{"a3", "$a3", "r7"}, "$r7"}, ++ {{"a4", "$a4", "r8"}, "$r8"}, ++ {{"a5", "$a5", "r9"}, "$r9"}, ++ {{"a6", "$a6", "r10"}, "$r10"}, ++ {{"a7", "$a7", "r11"}, "$r11"}, ++ {{"t0", "$t0", "r12"}, "$r12"}, ++ {{"t1", "$t1", "r13"}, "$r13"}, ++ {{"t2", "$t2", "r14"}, "$r14"}, ++ {{"t3", "$t3", "r15"}, "$r15"}, ++ {{"t4", "$t4", "r16"}, "$r16"}, ++ {{"t5", "$t5", "r17"}, "$r17"}, ++ {{"t6", "$t6", "r18"}, "$r18"}, ++ {{"t7", "$t7", "r19"}, "$r19"}, ++ {{"t8", "$t8", "r20"}, "$r20"}, ++ {{"r21"}, "$r21"}, ++ {{"s9", "$s9", "r22", "fp", "$fp"}, "$r22"}, ++ {{"s0", "$s0", "r23"}, "$r23"}, ++ {{"s1", "$s1", "r24"}, "$r24"}, ++ {{"s2", "$s2", "r25"}, "$r25"}, ++ {{"s3", "$s3", "r26"}, "$r26"}, ++ {{"s4", "$s4", "r27"}, "$r27"}, ++ {{"s5", "$s5", "r28"}, "$r28"}, ++ {{"s6", "$s6", "r29"}, "$r29"}, ++ {{"s7", "$s7", "r30"}, "$r30"}, ++ {{"s8", "$s8", "r31"}, "$r31"}, ++ {{"$fa0"}, "$f0"}, ++ {{"$fa1"}, "$f1"}, ++ {{"$fa2"}, "$f2"}, ++ {{"$fa3"}, "$f3"}, ++ {{"$fa4"}, "$f4"}, ++ {{"$fa5"}, "$f5"}, ++ {{"$fa6"}, "$f6"}, ++ {{"$fa7"}, "$f7"}, ++ {{"$ft0"}, "$f8"}, ++ {{"$ft1"}, "$f9"}, ++ {{"$ft2"}, "$f10"}, ++ {{"$ft3"}, "$f11"}, ++ {{"$ft4"}, "$f12"}, ++ {{"$ft5"}, "$f13"}, ++ {{"$ft6"}, "$f14"}, ++ {{"$ft7"}, "$f15"}, ++ {{"$ft8"}, "$f16"}, ++ {{"$ft9"}, "$f17"}, ++ {{"$ft10"}, "$f18"}, ++ {{"$ft11"}, "$f19"}, ++ {{"$ft12"}, "$f20"}, ++ {{"$ft13"}, "$f21"}, ++ {{"$ft14"}, "$f22"}, ++ {{"$ft15"}, "$f23"}, ++ {{"$fs0"}, "$f24"}, ++ {{"$fs1"}, "$f25"}, ++ {{"$fs2"}, "$f26"}, ++ {{"$fs3"}, "$f27"}, ++ {{"$fs4"}, "$f28"}, ++ {{"$fs5"}, "$f29"}, ++ {{"$fs6"}, "$f30"}, ++ {{"$fs7"}, "$f31"}, + }; + return llvm::ArrayRef(GCCRegAliases); + } +@@ -143,7 +188,15 @@ void LoongArchTargetInfo::getTargetDefines(const LangOptions &Opts, + else + Builder.defineMacro("__loongarch_frlen", "0"); + +- // TODO: define __loongarch_arch and __loongarch_tune. ++ // Define __loongarch_arch. ++ StringRef ArchName = getCPU(); ++ Builder.defineMacro("__loongarch_arch", Twine('"') + ArchName + Twine('"')); ++ ++ // Define __loongarch_tune. ++ StringRef TuneCPU = getTargetOpts().TuneCPU; ++ if (TuneCPU.empty()) ++ TuneCPU = ArchName; ++ Builder.defineMacro("__loongarch_tune", Twine('"') + TuneCPU + Twine('"')); + + StringRef ABI = getABI(); + if (ABI == "lp64d" || ABI == "lp64f" || ABI == "lp64s") +@@ -215,3 +268,12 @@ bool LoongArchTargetInfo::handleTargetFeatures( + } + return true; + } ++ ++bool LoongArchTargetInfo::isValidCPUName(StringRef Name) const { ++ return llvm::LoongArch::isValidCPUName(Name); ++} ++ ++void LoongArchTargetInfo::fillValidCPUList( ++ SmallVectorImpl &Values) const { ++ llvm::LoongArch::fillValidCPUList(Values); ++} +diff --git a/clang/lib/Basic/Targets/LoongArch.h b/clang/lib/Basic/Targets/LoongArch.h +index 646c8d071..46ce56b43 100644 +--- a/clang/lib/Basic/Targets/LoongArch.h ++++ b/clang/lib/Basic/Targets/LoongArch.h +@@ -24,6 +24,7 @@ namespace targets { + class LLVM_LIBRARY_VISIBILITY LoongArchTargetInfo : public TargetInfo { + protected: + std::string ABI; ++ std::string CPU; + bool HasFeatureD; + bool HasFeatureF; + +@@ -40,6 +41,15 @@ public: + WIntType = UnsignedInt; + } + ++ bool setCPU(const std::string &Name) override { ++ if (!isValidCPUName(Name)) ++ return false; ++ CPU = Name; ++ return true; ++ } ++ ++ StringRef getCPU() const { return CPU; } ++ + StringRef getABI() const override { return ABI; } + + void getTargetDefines(const LangOptions &Opts, +@@ -80,6 +90,9 @@ public: + const std::vector &FeaturesVec) const override; + + bool hasFeature(StringRef Feature) const override; ++ ++ bool isValidCPUName(StringRef Name) const override; ++ void fillValidCPUList(SmallVectorImpl &Values) const override; + }; + + class LLVM_LIBRARY_VISIBILITY LoongArch32TargetInfo +diff --git a/clang/lib/CodeGen/TargetInfo.cpp b/clang/lib/CodeGen/TargetInfo.cpp +index 9e2d7a85d..442138715 100644 +--- a/clang/lib/CodeGen/TargetInfo.cpp ++++ b/clang/lib/CodeGen/TargetInfo.cpp +@@ -548,12 +548,13 @@ TargetCodeGenInfo::getLLVMSyncScopeID(const LangOptions &LangOpts, + return Ctx.getOrInsertSyncScopeID(""); /* default sync scope */ + } + +-static bool isEmptyRecord(ASTContext &Context, QualType T, bool AllowArrays); ++static bool isEmptyRecord(ASTContext &Context, QualType T, bool AllowArrays, ++ bool AsIfNoUniqueAddr = false); + + /// isEmptyField - Return true iff a the field is "empty", that is it + /// is an unnamed bit-field or an (array of) empty record(s). + static bool isEmptyField(ASTContext &Context, const FieldDecl *FD, +- bool AllowArrays) { ++ bool AllowArrays, bool AsIfNoUniqueAddr = false) { + if (FD->isUnnamedBitfield()) + return true; + +@@ -587,16 +588,19 @@ static bool isEmptyField(ASTContext &Context, const FieldDecl *FD, + // not arrays of records, so we must also check whether we stripped off an + // array type above. + if (isa(RT->getDecl()) && +- (WasArray || !FD->hasAttr())) ++ (WasArray || (!AsIfNoUniqueAddr && !FD->hasAttr()))) + return false; + +- return isEmptyRecord(Context, FT, AllowArrays); ++ return isEmptyRecord(Context, FT, AllowArrays, AsIfNoUniqueAddr); + } + + /// isEmptyRecord - Return true iff a structure contains only empty + /// fields. Note that a structure with a flexible array member is not +-/// considered empty. +-static bool isEmptyRecord(ASTContext &Context, QualType T, bool AllowArrays) { ++/// considered empty. If AsIfNoUniqueAddr is true, then C++ record fields are ++/// considered empty if the [[no_unique_address]] attribute would have made ++/// them empty. ++static bool isEmptyRecord(ASTContext &Context, QualType T, bool AllowArrays, ++ bool AsIfNoUniqueAddr) { + const RecordType *RT = T->getAs(); + if (!RT) + return false; +@@ -607,11 +611,11 @@ static bool isEmptyRecord(ASTContext &Context, QualType T, bool AllowArrays) { + // If this is a C++ record, check the bases first. + if (const CXXRecordDecl *CXXRD = dyn_cast(RD)) + for (const auto &I : CXXRD->bases()) +- if (!isEmptyRecord(Context, I.getType(), true)) ++ if (!isEmptyRecord(Context, I.getType(), true, AsIfNoUniqueAddr)) + return false; + + for (const auto *I : RD->fields()) +- if (!isEmptyField(Context, I, AllowArrays)) ++ if (!isEmptyField(Context, I, AllowArrays, AsIfNoUniqueAddr)) + return false; + return true; + } +@@ -11883,6 +11887,13 @@ bool LoongArchABIInfo::detectFARsEligibleStructHelper( + if (const ConstantArrayType *ATy = getContext().getAsConstantArrayType(Ty)) { + uint64_t ArraySize = ATy->getSize().getZExtValue(); + QualType EltTy = ATy->getElementType(); ++ // Non-zero-length arrays of empty records make the struct ineligible to be ++ // passed via FARs in C++. ++ if (const auto *RTy = EltTy->getAs()) { ++ if (ArraySize != 0 && isa(RTy->getDecl()) && ++ isEmptyRecord(getContext(), EltTy, true, true)) ++ return false; ++ } + CharUnits EltSize = getContext().getTypeSizeInChars(EltTy); + for (uint64_t i = 0; i < ArraySize; ++i) { + if (!detectFARsEligibleStructHelper(EltTy, CurOff, Field1Ty, Field1Off, +@@ -11898,7 +11909,7 @@ bool LoongArchABIInfo::detectFARsEligibleStructHelper( + // copy constructor are not eligible for the FP calling convention. + if (getRecordArgABI(Ty, CGT.getCXXABI())) + return false; +- if (isEmptyRecord(getContext(), Ty, true)) ++ if (isEmptyRecord(getContext(), Ty, true, true)) + return true; + const RecordDecl *RD = RTy->getDecl(); + // Unions aren't eligible unless they're empty (which is caught above). +@@ -11957,6 +11968,8 @@ bool LoongArchABIInfo::detectFARsEligibleStruct( + if (!detectFARsEligibleStructHelper(Ty, CharUnits::Zero(), Field1Ty, + Field1Off, Field2Ty, Field2Off)) + return false; ++ if (!Field1Ty) ++ return false; + // Not really a candidate if we have a single int but no float. + if (Field1Ty && !Field2Ty && !Field1Ty->isFloatingPointTy()) + return false; +diff --git a/clang/lib/Driver/ToolChains/Arch/LoongArch.cpp b/clang/lib/Driver/ToolChains/Arch/LoongArch.cpp +index 576677a5f..f5d4018a4 100644 +--- a/clang/lib/Driver/ToolChains/Arch/LoongArch.cpp ++++ b/clang/lib/Driver/ToolChains/Arch/LoongArch.cpp +@@ -7,11 +7,13 @@ + //===----------------------------------------------------------------------===// + + #include "LoongArch.h" ++#include "ToolChains/CommonArgs.h" + #include "clang/Basic/DiagnosticDriver.h" + #include "clang/Driver/Driver.h" + #include "clang/Driver/DriverDiagnostic.h" + #include "clang/Driver/Options.h" +-#include "llvm/Support/LoongArchTargetParser.h" ++#include "llvm/TargetParser/Host.h" ++#include "llvm/TargetParser/LoongArchTargetParser.h" + + using namespace clang::driver; + using namespace clang::driver::tools; +@@ -25,32 +27,75 @@ StringRef loongarch::getLoongArchABI(const Driver &D, const ArgList &Args, + "Unexpected triple"); + bool IsLA32 = Triple.getArch() == llvm::Triple::loongarch32; + ++ // Record -mabi value for later use. ++ const Arg *MABIArg = Args.getLastArg(options::OPT_mabi_EQ); ++ StringRef MABIValue; ++ if (MABIArg) { ++ MABIValue = MABIArg->getValue(); ++ } ++ ++ // Parse -mfpu value for later use. ++ const Arg *MFPUArg = Args.getLastArg(options::OPT_mfpu_EQ); ++ int FPU = -1; ++ if (MFPUArg) { ++ StringRef V = MFPUArg->getValue(); ++ if (V == "64") ++ FPU = 64; ++ else if (V == "32") ++ FPU = 32; ++ else if (V == "0" || V == "none") ++ FPU = 0; ++ else ++ D.Diag(diag::err_drv_loongarch_invalid_mfpu_EQ) << V; ++ } ++ + // Check -m*-float firstly since they have highest priority. + if (const Arg *A = Args.getLastArg(options::OPT_mdouble_float, + options::OPT_msingle_float, + options::OPT_msoft_float)) { +- if (A->getOption().matches(options::OPT_mdouble_float)) +- return IsLA32 ? "ilp32d" : "lp64d"; +- if (A->getOption().matches(options::OPT_msingle_float)) +- return IsLA32 ? "ilp32f" : "lp64f"; +- if (A->getOption().matches(options::OPT_msoft_float)) +- return IsLA32 ? "ilp32s" : "lp64s"; ++ StringRef ImpliedABI; ++ int ImpliedFPU = -1; ++ if (A->getOption().matches(options::OPT_mdouble_float)) { ++ ImpliedABI = IsLA32 ? "ilp32d" : "lp64d"; ++ ImpliedFPU = 64; ++ } ++ if (A->getOption().matches(options::OPT_msingle_float)) { ++ ImpliedABI = IsLA32 ? "ilp32f" : "lp64f"; ++ ImpliedFPU = 32; ++ } ++ if (A->getOption().matches(options::OPT_msoft_float)) { ++ ImpliedABI = IsLA32 ? "ilp32s" : "lp64s"; ++ ImpliedFPU = 0; ++ } ++ ++ // Check `-mabi=` and `-mfpu=` settings and report if they conflict with ++ // the higher-priority settings implied by -m*-float. ++ // ++ // ImpliedABI and ImpliedFPU are guaranteed to have valid values because ++ // one of the match arms must match if execution can arrive here at all. ++ if (!MABIValue.empty() && ImpliedABI != MABIValue) ++ D.Diag(diag::warn_drv_loongarch_conflicting_implied_val) ++ << MABIArg->getAsString(Args) << A->getAsString(Args) << ImpliedABI; ++ ++ if (FPU != -1 && ImpliedFPU != FPU) ++ D.Diag(diag::warn_drv_loongarch_conflicting_implied_val) ++ << MFPUArg->getAsString(Args) << A->getAsString(Args) << ImpliedFPU; ++ ++ return ImpliedABI; + } + + // If `-mabi=` is specified, use it. +- if (const Arg *A = Args.getLastArg(options::OPT_mabi_EQ)) +- return A->getValue(); ++ if (!MABIValue.empty()) ++ return MABIValue; + + // Select abi based on -mfpu=xx. +- if (const Arg *A = Args.getLastArg(options::OPT_mfpu_EQ)) { +- StringRef FPU = A->getValue(); +- if (FPU == "64") +- return IsLA32 ? "ilp32d" : "lp64d"; +- if (FPU == "32") +- return IsLA32 ? "ilp32f" : "lp64f"; +- if (FPU == "0" || FPU == "none") +- return IsLA32 ? "ilp32s" : "lp64s"; +- D.Diag(diag::err_drv_loongarch_invalid_mfpu_EQ) << FPU; ++ switch (FPU) { ++ case 64: ++ return IsLA32 ? "ilp32d" : "lp64d"; ++ case 32: ++ return IsLA32 ? "ilp32f" : "lp64f"; ++ case 0: ++ return IsLA32 ? "ilp32s" : "lp64s"; + } + + // Choose a default based on the triple. +@@ -61,25 +106,11 @@ void loongarch::getLoongArchTargetFeatures(const Driver &D, + const llvm::Triple &Triple, + const ArgList &Args, + std::vector &Features) { +- StringRef ArchName; +- llvm::LoongArch::ArchKind ArchKind = llvm::LoongArch::ArchKind::AK_INVALID; +- if (const Arg *A = Args.getLastArg(options::OPT_march_EQ)) { +- ArchKind = llvm::LoongArch::parseArch(A->getValue()); +- if (ArchKind == llvm::LoongArch::ArchKind::AK_INVALID) { +- D.Diag(clang::diag::err_drv_invalid_arch_name) << A->getAsString(Args); +- return; +- } ++ std::string ArchName; ++ if (const Arg *A = Args.getLastArg(options::OPT_march_EQ)) + ArchName = A->getValue(); +- } +- +- // TODO: handle -march=native and -mtune=xx. +- +- // Select a default arch name. +- if (ArchName.empty() && Triple.getArch() == llvm::Triple::loongarch64) +- ArchName = "loongarch64"; +- +- if (!ArchName.empty()) +- llvm::LoongArch::getArchFeatures(ArchName, Features); ++ ArchName = postProcessTargetCPUString(ArchName, Triple); ++ llvm::LoongArch::getArchFeatures(ArchName, Features); + + // Select floating-point features determined by -mdouble-float, + // -msingle-float, -msoft-float and -mfpu. +@@ -112,4 +143,31 @@ void loongarch::getLoongArchTargetFeatures(const Driver &D, + D.Diag(diag::err_drv_loongarch_invalid_mfpu_EQ) << FPU; + } + } ++ ++ // Select the `ual` feature determined by -m[no-]unaligned-access ++ // or the alias -m[no-]strict-align. ++ AddTargetFeature(Args, Features, options::OPT_munaligned_access, ++ options::OPT_mno_unaligned_access, "ual"); ++} ++ ++std::string loongarch::postProcessTargetCPUString(const std::string &CPU, ++ const llvm::Triple &Triple) { ++ std::string CPUString = CPU; ++ if (CPUString == "native") { ++ CPUString = llvm::sys::getHostCPUName(); ++ if (CPUString == "generic") ++ CPUString = llvm::LoongArch::getDefaultArch(Triple.isLoongArch64()); ++ } ++ if (CPUString.empty()) ++ CPUString = llvm::LoongArch::getDefaultArch(Triple.isLoongArch64()); ++ return CPUString; ++} ++ ++std::string loongarch::getLoongArchTargetCPU(const llvm::opt::ArgList &Args, ++ const llvm::Triple &Triple) { ++ std::string CPU; ++ // If we have -march, use that. ++ if (const Arg *A = Args.getLastArg(options::OPT_march_EQ)) ++ CPU = A->getValue(); ++ return postProcessTargetCPUString(CPU, Triple); + } +diff --git a/clang/lib/Driver/ToolChains/Arch/LoongArch.h b/clang/lib/Driver/ToolChains/Arch/LoongArch.h +index 0084474e7..d8280cd83 100644 +--- a/clang/lib/Driver/ToolChains/Arch/LoongArch.h ++++ b/clang/lib/Driver/ToolChains/Arch/LoongArch.h +@@ -23,6 +23,12 @@ void getLoongArchTargetFeatures(const Driver &D, const llvm::Triple &Triple, + + StringRef getLoongArchABI(const Driver &D, const llvm::opt::ArgList &Args, + const llvm::Triple &Triple); ++ ++std::string postProcessTargetCPUString(const std::string &CPU, ++ const llvm::Triple &Triple); ++ ++std::string getLoongArchTargetCPU(const llvm::opt::ArgList &Args, ++ const llvm::Triple &Triple); + } // end namespace loongarch + } // end namespace tools + } // end namespace driver +diff --git a/clang/lib/Driver/ToolChains/Clang.cpp b/clang/lib/Driver/ToolChains/Clang.cpp +index 77554aa2c..e5c3b1087 100644 +--- a/clang/lib/Driver/ToolChains/Clang.cpp ++++ b/clang/lib/Driver/ToolChains/Clang.cpp +@@ -54,6 +54,7 @@ + #include "llvm/Support/Path.h" + #include "llvm/Support/Process.h" + #include "llvm/Support/YAMLParser.h" ++#include "llvm/TargetParser/LoongArchTargetParser.h" + #include + + using namespace clang::driver; +@@ -1833,10 +1834,20 @@ void Clang::AddAArch64TargetArgs(const ArgList &Args, + + void Clang::AddLoongArchTargetArgs(const ArgList &Args, + ArgStringList &CmdArgs) const { ++ const llvm::Triple &Triple = getToolChain().getTriple(); ++ + CmdArgs.push_back("-target-abi"); +- CmdArgs.push_back(loongarch::getLoongArchABI(getToolChain().getDriver(), Args, +- getToolChain().getTriple()) +- .data()); ++ CmdArgs.push_back( ++ loongarch::getLoongArchABI(getToolChain().getDriver(), Args, Triple) ++ .data()); ++ ++ // Handle -mtune. ++ if (const Arg *A = Args.getLastArg(options::OPT_mtune_EQ)) { ++ std::string TuneCPU = A->getValue(); ++ TuneCPU = loongarch::postProcessTargetCPUString(TuneCPU, Triple); ++ CmdArgs.push_back("-tune-cpu"); ++ CmdArgs.push_back(Args.MakeArgString(TuneCPU)); ++ } + } + + void Clang::AddMIPSTargetArgs(const ArgList &Args, +@@ -6235,7 +6246,8 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA, + if (Arg *A = Args.getLastArg(options::OPT_fpatchable_function_entry_EQ)) { + StringRef S0 = A->getValue(), S = S0; + unsigned Size, Offset = 0; +- if (!Triple.isAArch64() && !Triple.isRISCV() && !Triple.isX86()) ++ if (!Triple.isAArch64() && !Triple.isLoongArch() && !Triple.isRISCV() && ++ !Triple.isX86()) + D.Diag(diag::err_drv_unsupported_opt_for_target) + << A->getAsString(Args) << TripleStr; + else if (S.consumeInteger(10, Size) || +@@ -7863,6 +7875,14 @@ void ClangAs::AddX86TargetArgs(const ArgList &Args, + } + } + ++void ClangAs::AddLoongArchTargetArgs(const ArgList &Args, ++ ArgStringList &CmdArgs) const { ++ CmdArgs.push_back("-target-abi"); ++ CmdArgs.push_back(loongarch::getLoongArchABI(getToolChain().getDriver(), Args, ++ getToolChain().getTriple()) ++ .data()); ++} ++ + void ClangAs::AddRISCVTargetArgs(const ArgList &Args, + ArgStringList &CmdArgs) const { + const llvm::Triple &Triple = getToolChain().getTriple(); +@@ -8054,6 +8074,11 @@ void ClangAs::ConstructJob(Compilation &C, const JobAction &JA, + } + break; + ++ case llvm::Triple::loongarch32: ++ case llvm::Triple::loongarch64: ++ AddLoongArchTargetArgs(Args, CmdArgs); ++ break; ++ + case llvm::Triple::riscv32: + case llvm::Triple::riscv64: + AddRISCVTargetArgs(Args, CmdArgs); +diff --git a/clang/lib/Driver/ToolChains/Clang.h b/clang/lib/Driver/ToolChains/Clang.h +index a7625dba6..3c373bdee 100644 +--- a/clang/lib/Driver/ToolChains/Clang.h ++++ b/clang/lib/Driver/ToolChains/Clang.h +@@ -125,6 +125,8 @@ class LLVM_LIBRARY_VISIBILITY ClangAs : public Tool { + public: + ClangAs(const ToolChain &TC) + : Tool("clang::as", "clang integrated assembler", TC) {} ++ void AddLoongArchTargetArgs(const llvm::opt::ArgList &Args, ++ llvm::opt::ArgStringList &CmdArgs) const; + void AddMIPSTargetArgs(const llvm::opt::ArgList &Args, + llvm::opt::ArgStringList &CmdArgs) const; + void AddX86TargetArgs(const llvm::opt::ArgList &Args, +diff --git a/clang/lib/Driver/ToolChains/CommonArgs.cpp b/clang/lib/Driver/ToolChains/CommonArgs.cpp +index 34640b3c4..b462e2fe1 100644 +--- a/clang/lib/Driver/ToolChains/CommonArgs.cpp ++++ b/clang/lib/Driver/ToolChains/CommonArgs.cpp +@@ -455,6 +455,10 @@ std::string tools::getCPUName(const Driver &D, const ArgList &Args, + case llvm::Triple::wasm32: + case llvm::Triple::wasm64: + return std::string(getWebAssemblyTargetCPU(Args)); ++ ++ case llvm::Triple::loongarch32: ++ case llvm::Triple::loongarch64: ++ return loongarch::getLoongArchTargetCPU(Args, T); + } + } + +diff --git a/clang/lib/Driver/ToolChains/Gnu.cpp b/clang/lib/Driver/ToolChains/Gnu.cpp +index 4f2340316..001ead153 100644 +--- a/clang/lib/Driver/ToolChains/Gnu.cpp ++++ b/clang/lib/Driver/ToolChains/Gnu.cpp +@@ -9,6 +9,7 @@ + #include "Gnu.h" + #include "Arch/ARM.h" + #include "Arch/CSKY.h" ++#include "Arch/LoongArch.h" + #include "Arch/Mips.h" + #include "Arch/PPC.h" + #include "Arch/RISCV.h" +@@ -855,6 +856,13 @@ void tools::gnutools::Assembler::ConstructJob(Compilation &C, + + break; + } ++ // TODO: handle loongarch32. ++ case llvm::Triple::loongarch64: { ++ StringRef ABIName = ++ loongarch::getLoongArchABI(D, Args, getToolChain().getTriple()); ++ CmdArgs.push_back(Args.MakeArgString("-mabi=" + ABIName)); ++ break; ++ } + case llvm::Triple::mips: + case llvm::Triple::mipsel: + case llvm::Triple::mips64: +@@ -2261,7 +2269,8 @@ void Generic_GCC::GCCInstallationDetector::AddDefaultGCCPrefixes( + + static const char *const LoongArch64LibDirs[] = {"/lib64", "/lib"}; + static const char *const LoongArch64Triples[] = { +- "loongarch64-linux-gnu", "loongarch64-unknown-linux-gnu"}; ++ "loongarch64-linux-gnu", "loongarch64-unknown-linux-gnu", ++ "loongarch64-anolis-linux"}; + + static const char *const M68kLibDirs[] = {"/lib"}; + static const char *const M68kTriples[] = { +diff --git a/clang/test/CodeGen/LoongArch/abi-lp64d-empty-structs.c b/clang/test/CodeGen/LoongArch/abi-lp64d-empty-structs.c +new file mode 100644 +index 000000000..fb90bf556 +--- /dev/null ++++ b/clang/test/CodeGen/LoongArch/abi-lp64d-empty-structs.c +@@ -0,0 +1,89 @@ ++// RUN: %clang_cc1 -triple loongarch64 -target-feature +f -target-feature +d -target-abi lp64d -emit-llvm %s -o - | \ ++// RUN: FileCheck --check-prefix=CHECK-C %s ++// RUN: %clang_cc1 -triple loongarch64 -target-feature +f -target-feature +d -target-abi lp64d -emit-llvm %s -o - -x c++ | \ ++// RUN: FileCheck --check-prefix=CHECK-CXX %s ++ ++// Fields containing empty structs or unions are ignored when flattening ++// structs to examine whether the structs can be passed via FARs, even in C++. ++// But there is an exception that non-zero-length array of empty structures are ++// not ignored in C++. These rules are not documented in psABI ++// but they match GCC behaviours. ++ ++#include ++ ++struct empty { struct { struct { } e; }; }; ++struct s1 { struct empty e; float f; }; ++ ++// CHECK-C: define{{.*}} float @test_s1(float {{.*}}) ++// CHECK-CXX: define{{.*}} float @_Z7test_s12s1(float {{.*}}) ++struct s1 test_s1(struct s1 a) { ++ return a; ++} ++ ++struct s2 { struct empty e; int32_t i; float f; }; ++ ++// CHECK-C: define{{.*}} { i32, float } @test_s2(i32 {{.*}}, float {{.*}}) ++// CHECK-CXX: define{{.*}} { i32, float } @_Z7test_s22s2(i32 {{.*}}, float {{.*}}) ++struct s2 test_s2(struct s2 a) { ++ return a; ++} ++ ++struct s3 { struct empty e; float f; float g; }; ++ ++// CHECK-C: define{{.*}} { float, float } @test_s3(float {{.*}}, float {{.*}}) ++// CHECK-CXX: define{{.*}} { float, float } @_Z7test_s32s3(float {{.*}}, float {{.*}}) ++struct s3 test_s3(struct s3 a) { ++ return a; ++} ++ ++struct s4 { struct empty e; float __complex__ c; }; ++ ++// CHECK-C: define{{.*}} { float, float } @test_s4(float {{.*}}, float {{.*}}) ++// CHECK-CXX: define{{.*}} { float, float } @_Z7test_s42s4(float {{.*}}, float {{.*}}) ++struct s4 test_s4(struct s4 a) { ++ return a; ++} ++ ++// An array of empty fields isn't ignored in C++ (this isn't explicit in the ++// psABI, but matches observed g++ behaviour). ++ ++struct s5 { struct empty e[1]; float f; }; ++ ++// CHECK-C: define{{.*}} float @test_s5(float {{.*}}) ++// CHECK-CXX: define{{.*}} i64 @_Z7test_s52s5(i64 {{.*}}) ++struct s5 test_s5(struct s5 a) { ++ return a; ++} ++ ++struct empty_arr { struct { struct { } e[1]; }; }; ++struct s6 { struct empty_arr e; float f; }; ++ ++// CHECK-C: define{{.*}} float @test_s6(float {{.*}}) ++// CHECK-CXX: define{{.*}} i64 @_Z7test_s62s6(i64 {{.*}}) ++struct s6 test_s6(struct s6 a) { ++ return a; ++} ++ ++struct s7 { struct empty e[0]; float f; }; ++ ++// CHECK-C: define{{.*}} float @test_s7(float {{.*}}) ++// CHECK-CXX: define{{.*}} float @_Z7test_s72s7(float {{.*}}) ++struct s7 test_s7(struct s7 a) { ++ return a; ++} ++ ++struct empty_arr0 { struct { struct { } e[0]; }; }; ++struct s8 { struct empty_arr0 e; float f; }; ++ ++// CHECK-C: define{{.*}} float @test_s8(float {{.*}}) ++// CHECK-CXX: define{{.*}} float @_Z7test_s82s8(float {{.*}}) ++struct s8 test_s8(struct s8 a) { ++ return a; ++} ++ ++// CHECK-C: define{{.*}} void @test_s9() ++// CHECK-CXX: define{{.*}} i64 @_Z7test_s92s9(i64 {{.*}}) ++struct s9 { struct empty e; }; ++struct s9 test_s9(struct s9 a) { ++ return a; ++} +diff --git a/clang/test/CodeGen/LoongArch/inline-asm-gcc-regs-error.c b/clang/test/CodeGen/LoongArch/inline-asm-gcc-regs-error.c +index 39450c465..c5ecf0c92 100644 +--- a/clang/test/CodeGen/LoongArch/inline-asm-gcc-regs-error.c ++++ b/clang/test/CodeGen/LoongArch/inline-asm-gcc-regs-error.c +@@ -11,12 +11,10 @@ void test(void) { + + /// Names not prefixed with '$' are invalid. + +-// CHECK: :[[#@LINE+1]]:24: error: unknown register name 'r4' in asm +- register int a3 asm ("r4"); +-// CHECK: :[[#@LINE+1]]:24: error: unknown register name 'a0' in asm +- register int a4 asm ("a0"); + // CHECK: :[[#@LINE+1]]:26: error: unknown register name 'f0' in asm + register float a5 asm ("f0"); + // CHECK: :[[#@LINE+1]]:26: error: unknown register name 'fa0' in asm + register float a6 asm ("fa0"); ++// CHECK: :[[#@LINE+1]]:15: error: unknown register name 'fcc0' in asm ++ asm ("" ::: "fcc0"); + } +diff --git a/clang/test/CodeGen/LoongArch/inline-asm-gcc-regs.c b/clang/test/CodeGen/LoongArch/inline-asm-gcc-regs.c +index 067645366..e1015f6fc 100644 +--- a/clang/test/CodeGen/LoongArch/inline-asm-gcc-regs.c ++++ b/clang/test/CodeGen/LoongArch/inline-asm-gcc-regs.c +@@ -7,56 +7,72 @@ + // CHECK: call void asm sideeffect "", "{$r0}"(i32 undef) + void test_r0() { + register int a asm ("$r0"); ++ register int b asm ("r0"); + asm ("" :: "r" (a)); ++ asm ("" :: "r" (b)); + } + + // CHECK-LABEL: @test_r12 + // CHECK: call void asm sideeffect "", "{$r12}"(i32 undef) + void test_r12() { + register int a asm ("$r12"); ++ register int b asm ("r12"); + asm ("" :: "r" (a)); ++ asm ("" :: "r" (b)); + } + + // CHECK-LABEL: @test_r31 + // CHECK: call void asm sideeffect "", "{$r31}"(i32 undef) + void test_r31() { + register int a asm ("$r31"); ++ register int b asm ("r31"); + asm ("" :: "r" (a)); ++ asm ("" :: "r" (b)); + } + + // CHECK-LABEL: @test_zero + // CHECK: call void asm sideeffect "", "{$r0}"(i32 undef) + void test_zero() { + register int a asm ("$zero"); ++ register int b asm ("zero"); + asm ("" :: "r" (a)); ++ asm ("" :: "r" (b)); + } + + // CHECK-LABEL: @test_a0 + // CHECK: call void asm sideeffect "", "{$r4}"(i32 undef) + void test_a0() { + register int a asm ("$a0"); ++ register int b asm ("a0"); + asm ("" :: "r" (a)); ++ asm ("" :: "r" (b)); + } + + // CHECK-LABEL: @test_t1 + // CHECK: call void asm sideeffect "", "{$r13}"(i32 undef) + void test_t1() { + register int a asm ("$t1"); ++ register int b asm ("t1"); + asm ("" :: "r" (a)); ++ asm ("" :: "r" (b)); + } + + // CHECK-LABEL: @test_fp + // CHECK: call void asm sideeffect "", "{$r22}"(i32 undef) + void test_fp() { + register int a asm ("$fp"); ++ register int b asm ("fp"); + asm ("" :: "r" (a)); ++ asm ("" :: "r" (b)); + } + + // CHECK-LABEL: @test_s2 + // CHECK: call void asm sideeffect "", "{$r25}"(i32 undef) + void test_s2() { + register int a asm ("$s2"); ++ register int b asm ("s2"); + asm ("" :: "r" (a)); ++ asm ("" :: "r" (b)); + } + + // CHECK-LABEL: @test_f0 +@@ -100,3 +116,11 @@ void test_fs2() { + register float a asm ("$fs2"); + asm ("" :: "f" (a)); + } ++ ++// CHECK-LABEL: @test_fcc ++// CHECK: call void asm sideeffect "", "~{$fcc0}"() ++// CHECK: call void asm sideeffect "", "~{$fcc7}"() ++void test_fcc() { ++ asm ("" ::: "$fcc0"); ++ asm ("" ::: "$fcc7"); ++} +diff --git a/clang/test/Driver/fpatchable-function-entry.c b/clang/test/Driver/fpatchable-function-entry.c +index da7370a4d..4d0d60958 100644 +--- a/clang/test/Driver/fpatchable-function-entry.c ++++ b/clang/test/Driver/fpatchable-function-entry.c +@@ -2,6 +2,8 @@ + // RUN: %clang -target x86_64 %s -fpatchable-function-entry=1 -c -### 2>&1 | FileCheck %s + // RUN: %clang -target aarch64 %s -fpatchable-function-entry=1 -c -### 2>&1 | FileCheck %s + // RUN: %clang -target aarch64 %s -fpatchable-function-entry=1,0 -c -### 2>&1 | FileCheck %s ++// RUN: %clang -target loongarch32 %s -fpatchable-function-entry=1,0 -c -### 2>&1 | FileCheck %s ++// RUN: %clang -target loongarch64 %s -fpatchable-function-entry=1,0 -c -### 2>&1 | FileCheck %s + // RUN: %clang -target riscv32 %s -fpatchable-function-entry=1,0 -c -### 2>&1 | FileCheck %s + // RUN: %clang -target riscv64 %s -fpatchable-function-entry=1,0 -c -### 2>&1 | FileCheck %s + // CHECK: "-fpatchable-function-entry=1" +diff --git a/clang/test/Driver/loongarch-as.s b/clang/test/Driver/loongarch-as.s +new file mode 100644 +index 000000000..6f6d87f6a +--- /dev/null ++++ b/clang/test/Driver/loongarch-as.s +@@ -0,0 +1,15 @@ ++/// This file checks options are correctly passed to as for LoongArch targets. ++ ++/// Check `-mabi`. ++// RUN: %clang --target=loongarch64 -### -fno-integrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=lp64d --check-prefix=ABI %s ++// RUN: %clang --target=loongarch64 -mabi=lp64d -### -fno-integrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=lp64d --check-prefix=ABI %s ++// RUN: %clang --target=loongarch64 -mabi=lp64f -### -fno-integrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=lp64f --check-prefix=ABI %s ++// RUN: %clang --target=loongarch64 -mabi=lp64s -### -fno-integrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=lp64s --check-prefix=ABI %s ++ ++// ALL: as ++ ++// ABI: "-mabi=[[ABI]]" +diff --git a/clang/test/Driver/loongarch-default-features.c b/clang/test/Driver/loongarch-default-features.c +index 027d8cdb7..3cdf3ba3d 100644 +--- a/clang/test/Driver/loongarch-default-features.c ++++ b/clang/test/Driver/loongarch-default-features.c +@@ -2,7 +2,7 @@ + // RUN: %clang --target=loongarch64 -S -emit-llvm %s -o - | FileCheck %s --check-prefix=LA64 + + // LA32: "target-features"="+32bit" +-// LA64: "target-features"="+64bit,+d,+f" ++// LA64: "target-features"="+64bit,+d,+f,+ual" + + int foo(void) { + return 3; +diff --git a/clang/test/Driver/loongarch-ias.s b/clang/test/Driver/loongarch-ias.s +new file mode 100644 +index 000000000..6fec9e6e1 +--- /dev/null ++++ b/clang/test/Driver/loongarch-ias.s +@@ -0,0 +1,23 @@ ++/// This file checks options are correctly passed to cc1as for LoongArch targets. ++ ++/// Check `-target-abi`. ++// RUN: %clang --target=loongarch32 -### -fintegrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=ilp32d --check-prefix=ABI %s ++// RUN: %clang --target=loongarch32 -mabi=ilp32d -### -fintegrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=ilp32d --check-prefix=ABI %s ++// RUN: %clang --target=loongarch32 -mabi=ilp32f -### -fintegrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=ilp32f --check-prefix=ABI %s ++// RUN: %clang --target=loongarch32 -mabi=ilp32s -### -fintegrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=ilp32s --check-prefix=ABI %s ++// RUN: %clang --target=loongarch64 -### -fintegrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=lp64d --check-prefix=ABI %s ++// RUN: %clang --target=loongarch64 -mabi=lp64d -### -fintegrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=lp64d --check-prefix=ABI %s ++// RUN: %clang --target=loongarch64 -mabi=lp64f -### -fintegrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=lp64f --check-prefix=ABI %s ++// RUN: %clang --target=loongarch64 -mabi=lp64s -### -fintegrated-as -c %s 2>&1 | \ ++// RUN: FileCheck -DABI=lp64s --check-prefix=ABI %s ++ ++// ALL: -cc1as ++ ++// ABI: "-target-abi" "[[ABI]]" +diff --git a/clang/test/Driver/loongarch-march-error.c b/clang/test/Driver/loongarch-march-error.c +index f447de655..6bfaa18b0 100644 +--- a/clang/test/Driver/loongarch-march-error.c ++++ b/clang/test/Driver/loongarch-march-error.c +@@ -1,7 +1,7 @@ + // RUN: not %clang --target=loongarch64 -march=loongarch -fsyntax-only %s 2>&1 | \ +-// RUN: FileCheck --check-prefix=LOONGARCH %s +-// LOONGARCH: error: invalid arch name '-march=loongarch' +- ++// RUN: FileCheck -DCPU=loongarch %s + // RUN: not %clang --target=loongarch64 -march=LA464 -fsyntax-only %s 2>&1 | \ +-// RUN: FileCheck --check-prefix=LA464-UPPER %s +-// LA464-UPPER: error: invalid arch name '-march=LA464' ++// RUN: FileCheck -DCPU=LA464 %s ++ ++// CHECK: error: unknown target CPU '[[CPU]]' ++// CHECK-NEXT: note: valid target CPU values are: {{.*}} +diff --git a/clang/test/Driver/loongarch-march.c b/clang/test/Driver/loongarch-march.c +index 6416f4274..9214130cd 100644 +--- a/clang/test/Driver/loongarch-march.c ++++ b/clang/test/Driver/loongarch-march.c +@@ -7,18 +7,20 @@ + // RUN: %clang --target=loongarch64 -march=la464 -S -emit-llvm %s -o - | \ + // RUN: FileCheck %s --check-prefix=IR-LA464 + ++// CC1-LOONGARCH64: "-target-cpu" "loongarch64" + // CC1-LOONGARCH64-NOT: "-target-feature" +-// CC1-LOONGARCH64: "-target-feature" "+64bit" "-target-feature" "+f" "-target-feature" "+d" ++// CC1-LOONGARCH64: "-target-feature" "+64bit" "-target-feature" "+f" "-target-feature" "+d" "-target-feature" "+ual" + // CC1-LOONGARCH64-NOT: "-target-feature" + // CC1-LOONGARCH64: "-target-abi" "lp64d" + ++// CC1-LA464: "-target-cpu" "la464" + // CC1-LA464-NOT: "-target-feature" +-// CC1-LA464: "-target-feature" "+64bit" "-target-feature" "+f" "-target-feature" "+d" "-target-feature" "+lsx" "-target-feature" "+lasx" ++// CC1-LA464: "-target-feature" "+64bit" "-target-feature" "+f" "-target-feature" "+d" "-target-feature" "+lsx" "-target-feature" "+lasx" "-target-feature" "+ual" + // CC1-LA464-NOT: "-target-feature" + // CC1-LA464: "-target-abi" "lp64d" + +-// IR-LOONGARCH64: attributes #[[#]] ={{.*}}"target-features"="+64bit,+d,+f" +-// IR-LA464: attributes #[[#]] ={{.*}}"target-features"="+64bit,+d,+f,+lasx,+lsx" ++// IR-LOONGARCH64: attributes #[[#]] ={{.*}}"target-cpu"="loongarch64" {{.*}}"target-features"="+64bit,+d,+f,+ual" ++// IR-LA464: attributes #[[#]] ={{.*}}"target-cpu"="la464" {{.*}}"target-features"="+64bit,+d,+f,+lasx,+lsx,+ual" + + int foo(void) { + return 3; +diff --git a/clang/test/Driver/loongarch-mdouble-float.c b/clang/test/Driver/loongarch-mdouble-float.c +index 63bc1c911..caa9ab42c 100644 +--- a/clang/test/Driver/loongarch-mdouble-float.c ++++ b/clang/test/Driver/loongarch-mdouble-float.c +@@ -1,19 +1,23 @@ + // RUN: %clang --target=loongarch64 -mdouble-float -fsyntax-only %s -### 2>&1 | \ + // RUN: FileCheck %s --check-prefix=CC1 ++// RUN: %clang --target=loongarch64 -mdouble-float -mfpu=64 -mabi=lp64d -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefixes=CC1,NOWARN + // RUN: %clang --target=loongarch64 -mdouble-float -mfpu=0 -mabi=lp64s -fsyntax-only %s -### 2>&1 | \ +-// RUN: FileCheck %s --check-prefixes=CC1,WARN ++// RUN: FileCheck %s --check-prefixes=CC1,WARN,WARN-FPU0 ++// RUN: %clang --target=loongarch64 -mdouble-float -mfpu=none -mabi=lp64s -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefixes=CC1,WARN,WARN-FPUNONE + // RUN: %clang --target=loongarch64 -mdouble-float -S -emit-llvm %s -o - | \ + // RUN: FileCheck %s --check-prefix=IR + +-// WARN: warning: argument unused during compilation: '-mfpu=0' +-// WARN: warning: argument unused during compilation: '-mabi=lp64s' ++// NOWARN-NOT: warning: ++// WARN: warning: ignoring '-mabi=lp64s' as it conflicts with that implied by '-mdouble-float' (lp64d) ++// WARN-FPU0: warning: ignoring '-mfpu=0' as it conflicts with that implied by '-mdouble-float' (64) ++// WARN-FPUNONE: warning: ignoring '-mfpu=none' as it conflicts with that implied by '-mdouble-float' (64) + +-// CC1-NOT: "-target-feature" +-// CC1: "-target-feature" "+64bit" "-target-feature" "+f" "-target-feature" "+d" +-// CC1-NOT: "-target-feature" ++// CC1: "-target-feature" "+f"{{.*}} "-target-feature" "+d" + // CC1: "-target-abi" "lp64d" + +-// IR: attributes #[[#]] ={{.*}}"target-features"="+64bit,+d,+f" ++// IR: attributes #[[#]] ={{.*}}"target-features"="{{(.*,)?}}+d,{{(.*,)?}}+f{{(,.*)?}}" + + int foo(void) { + return 3; +diff --git a/clang/test/Driver/loongarch-mfpu.c b/clang/test/Driver/loongarch-mfpu.c +index 7fc7d45a7..753057d70 100644 +--- a/clang/test/Driver/loongarch-mfpu.c ++++ b/clang/test/Driver/loongarch-mfpu.c +@@ -16,24 +16,18 @@ + // RUN: %clang --target=loongarch64 -mfpu=none -S -emit-llvm %s -o - | \ + // RUN: FileCheck %s --check-prefix=IR-FPU0 + +-// CC1-FPU64-NOT: "-target-feature" +-// CC1-FPU64: "-target-feature" "+64bit" "-target-feature" "+f" "-target-feature" "+d" +-// CC1-FPU64-NOT: "-target-feature" ++// CC1-FPU64: "-target-feature" "+f"{{.*}} "-target-feature" "+d" + // CC1-FPU64: "-target-abi" "lp64d" + +-// CC1-FPU32-NOT: "-target-feature" +-// CC1-FPU32: "-target-feature" "+64bit" "-target-feature" "+f" "-target-feature" "-d" +-// CC1-FPU32-NOT: "-target-feature" ++// CC1-FPU32: "-target-feature" "+f"{{.*}} "-target-feature" "-d" + // CC1-FPU32: "-target-abi" "lp64f" + +-// CC1-FPU0-NOT: "-target-feature" +-// CC1-FPU0: "-target-feature" "+64bit" "-target-feature" "-f" "-target-feature" "-d" +-// CC1-FPU0-NOT: "-target-feature" ++// CC1-FPU0: "-target-feature" "-f"{{.*}} "-target-feature" "-d" + // CC1-FPU0: "-target-abi" "lp64s" + +-// IR-FPU64: attributes #[[#]] ={{.*}}"target-features"="+64bit,+d,+f" +-// IR-FPU32: attributes #[[#]] ={{.*}}"target-features"="+64bit,+f,-d" +-// IR-FPU0: attributes #[[#]] ={{.*}}"target-features"="+64bit,-d,-f" ++// IR-FPU64: attributes #[[#]] ={{.*}}"target-features"="{{(.*,)?}}+d,{{(.*,)?}}+f{{(,.*)?}}" ++// IR-FPU32: attributes #[[#]] ={{.*}}"target-features"="{{(.*,)?}}+f,{{(.*,)?}}-d{{(,.*)?}}" ++// IR-FPU0: attributes #[[#]] ={{.*}}"target-features"="{{(.*,)?}}-d,{{(.*,)?}}-f{{(,.*)?}}" + + int foo(void) { + return 3; +diff --git a/clang/test/Driver/loongarch-msingle-float.c b/clang/test/Driver/loongarch-msingle-float.c +index 5deff8655..bd9b3e8a8 100644 +--- a/clang/test/Driver/loongarch-msingle-float.c ++++ b/clang/test/Driver/loongarch-msingle-float.c +@@ -1,19 +1,20 @@ + // RUN: %clang --target=loongarch64 -msingle-float -fsyntax-only %s -### 2>&1 | \ + // RUN: FileCheck %s --check-prefix=CC1 +-// RUN: %clang --target=loongarch64 -msingle-float -mfpu=0 -mabi=lp64s -fsyntax-only %s -### 2>&1 | \ ++// RUN: %clang --target=loongarch64 -msingle-float -mfpu=32 -mabi=lp64f -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefixes=CC1,NOWARN ++// RUN: %clang --target=loongarch64 -msingle-float -mfpu=64 -mabi=lp64s -fsyntax-only %s -### 2>&1 | \ + // RUN: FileCheck %s --check-prefixes=CC1,WARN + // RUN: %clang --target=loongarch64 -msingle-float -S -emit-llvm %s -o - | \ + // RUN: FileCheck %s --check-prefix=IR + +-// WARN: warning: argument unused during compilation: '-mfpu=0' +-// WARN: warning: argument unused during compilation: '-mabi=lp64s' ++// NOWARN-NOT: warning: ++// WARN: warning: ignoring '-mabi=lp64s' as it conflicts with that implied by '-msingle-float' (lp64f) ++// WARN: warning: ignoring '-mfpu=64' as it conflicts with that implied by '-msingle-float' (32) + +-// CC1-NOT: "-target-feature" +-// CC1: "-target-feature" "+64bit" "-target-feature" "+f" "-target-feature" "-d" +-// CC1-NOT: "-target-feature" ++// CC1: "-target-feature" "+f"{{.*}} "-target-feature" "-d" + // CC1: "-target-abi" "lp64f" + +-// IR: attributes #[[#]] ={{.*}}"target-features"="+64bit,+f,-d" ++// IR: attributes #[[#]] ={{.*}}"target-features"="{{(.*,)?}}+f,{{(.*,)?}}-d" + + int foo(void) { + return 3; +diff --git a/clang/test/Driver/loongarch-msoft-float.c b/clang/test/Driver/loongarch-msoft-float.c +index fd200377a..0e5121ac8 100644 +--- a/clang/test/Driver/loongarch-msoft-float.c ++++ b/clang/test/Driver/loongarch-msoft-float.c +@@ -1,19 +1,20 @@ + // RUN: %clang --target=loongarch64 -msoft-float -fsyntax-only %s -### 2>&1 | \ + // RUN: FileCheck %s --check-prefix=CC1 ++// RUN: %clang --target=loongarch64 -msoft-float -mfpu=0 -mabi=lp64s -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefixes=CC1,NOWARN + // RUN: %clang --target=loongarch64 -msoft-float -mfpu=64 -mabi=lp64d -fsyntax-only %s -### 2>&1 | \ + // RUN: FileCheck %s --check-prefixes=CC1,WARN + // RUN: %clang --target=loongarch64 -msoft-float -S -emit-llvm %s -o - | \ + // RUN: FileCheck %s --check-prefix=IR + +-// WARN: warning: argument unused during compilation: '-mfpu=64' +-// WARN: warning: argument unused during compilation: '-mabi=lp64d' ++// NOWARN-NOT: warning: ++// WARN: warning: ignoring '-mabi=lp64d' as it conflicts with that implied by '-msoft-float' (lp64s) ++// WARN: warning: ignoring '-mfpu=64' as it conflicts with that implied by '-msoft-float' (0) + +-// CC1-NOT: "-target-feature" +-// CC1: "-target-feature" "+64bit" "-target-feature" "-f" "-target-feature" "-d" +-// CC1-NOT: "-target-feature" ++// CC1: "-target-feature" "-f"{{.*}} "-target-feature" "-d" + // CC1: "-target-abi" "lp64s" + +-// IR: attributes #[[#]] ={{.*}}"target-features"="+64bit,-d,-f" ++// IR: attributes #[[#]] ={{.*}}"target-features"="{{(.*,)?}}-d,{{(.*,)?}}-f{{(,.*)?}}" + + int foo(void) { + return 3; +diff --git a/clang/test/Driver/loongarch-mtune.c b/clang/test/Driver/loongarch-mtune.c +new file mode 100644 +index 000000000..6f3f39e9b +--- /dev/null ++++ b/clang/test/Driver/loongarch-mtune.c +@@ -0,0 +1,34 @@ ++// RUN: %clang --target=loongarch64 -mtune=loongarch64 -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1ARG -DCPU=loongarch64 ++// RUN: %clang --target=loongarch64 -mtune=loongarch64 -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IRATTR -DCPU=loongarch64 ++ ++// RUN: %clang --target=loongarch64 -mtune=la464 -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1ARG -DCPU=la464 ++// RUN: %clang --target=loongarch64 -mtune=la464 -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IRATTR -DCPU=la464 ++ ++// RUN: %clang --target=loongarch64 -mtune=invalidcpu -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1ARG -DCPU=invalidcpu ++// RUN: not %clang --target=loongarch64 -mtune=invalidcpu -S -emit-llvm %s -o /dev/null 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=ERROR -DCPU=invalidcpu ++ ++// RUN: %clang --target=loongarch64 -mtune=generic -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1ARG -DCPU=generic ++// RUN: not %clang --target=loongarch64 -mtune=generic -S -emit-llvm %s -o /dev/null 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=ERROR -DCPU=generic ++ ++// RUN: %clang --target=loongarch64 -mtune=generic-la64 -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1ARG -DCPU=generic-la64 ++// RUN: not %clang --target=loongarch64 -mtune=generic-la64 -S -emit-llvm %s -o /dev/null 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=ERROR -DCPU=generic-la64 ++ ++// CC1ARG: "-tune-cpu" "[[CPU]]" ++// IRATTR: "tune-cpu"="[[CPU]]" ++ ++// ERROR: error: unknown target CPU '[[CPU]]' ++// ERROR-NEXT: note: valid target CPU values are: {{.*}} ++ ++int foo(void) { ++ return 3; ++} +diff --git a/clang/test/Driver/loongarch-munaligned-access.c b/clang/test/Driver/loongarch-munaligned-access.c +new file mode 100644 +index 000000000..44edb2eb1 +--- /dev/null ++++ b/clang/test/Driver/loongarch-munaligned-access.c +@@ -0,0 +1,61 @@ ++/// Test -m[no-]unaligned-access and -m[no-]strict-align options. ++ ++// RUN: %clang --target=loongarch64 -munaligned-access -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-unaligned-access -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-NO-UNALIGNED ++// RUN: %clang --target=loongarch64 -mstrict-align -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-NO-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-strict-align -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-UNALIGNED ++// RUN: %clang --target=loongarch64 -munaligned-access -mno-unaligned-access -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-NO-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-unaligned-access -munaligned-access -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-UNALIGNED ++// RUN: %clang --target=loongarch64 -mstrict-align -mno-strict-align -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-strict-align -mstrict-align -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-NO-UNALIGNED ++// RUN: %clang --target=loongarch64 -munaligned-access -mstrict-align -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-NO-UNALIGNED ++// RUN: %clang --target=loongarch64 -mstrict-align -munaligned-access -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-unaligned-access -mno-strict-align -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-strict-align -mno-unaligned-access -fsyntax-only %s -### 2>&1 | \ ++// RUN: FileCheck %s --check-prefix=CC1-NO-UNALIGNED ++ ++// RUN: %clang --target=loongarch64 -munaligned-access -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-unaligned-access -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-NO-UNALIGNED ++// RUN: %clang --target=loongarch64 -mstrict-align -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-NO-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-strict-align -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-UNALIGNED ++// RUN: %clang --target=loongarch64 -munaligned-access -mno-unaligned-access -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-NO-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-unaligned-access -munaligned-access -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-UNALIGNED ++// RUN: %clang --target=loongarch64 -mstrict-align -mno-strict-align -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-strict-align -mstrict-align -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-NO-UNALIGNED ++// RUN: %clang --target=loongarch64 -munaligned-access -mstrict-align -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-NO-UNALIGNED ++// RUN: %clang --target=loongarch64 -mstrict-align -munaligned-access -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-unaligned-access -mno-strict-align -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-UNALIGNED ++// RUN: %clang --target=loongarch64 -mno-strict-align -mno-unaligned-access -S -emit-llvm %s -o - | \ ++// RUN: FileCheck %s --check-prefix=IR-NO-UNALIGNED ++ ++// CC1-UNALIGNED: "-target-feature" "+ual" ++// CC1-NO-UNALIGNED: "-target-feature" "-ual" ++ ++// IR-UNALIGNED: attributes #[[#]] ={{.*}}"target-features"="{{(.*,)?}}+ual{{(,.*)?}}" ++// IR-NO-UNALIGNED: attributes #[[#]] ={{.*}}"target-features"="{{(.*,)?}}-ual{{(,.*)?}}" ++ ++int foo(void) { ++ return 3; ++} +diff --git a/clang/test/Driver/munaligned-access-unused.c b/clang/test/Driver/munaligned-access-unused.c +new file mode 100644 +index 000000000..c8cbe4e0d +--- /dev/null ++++ b/clang/test/Driver/munaligned-access-unused.c +@@ -0,0 +1,8 @@ ++/// Check -m[no-]unaligned-access and -m[no-]strict-align are warned unused on a target that does not support them. ++ ++// RUN: %clang --target=x86_64 -munaligned-access -fsyntax-only %s -### 2>&1 | FileCheck %s -DOPTION=unaligned-access ++// RUN: %clang --target=x86_64 -mno-unaligned-access -fsyntax-only %s -### 2>&1 | FileCheck %s -DOPTION=no-unaligned-access ++// RUN: %clang --target=x86_64 -mstrict-align -fsyntax-only %s -### 2>&1 | FileCheck %s -DOPTION=strict-align ++// RUN: %clang --target=x86_64 -mno-strict-align -fsyntax-only %s -### 2>&1 | FileCheck %s -DOPTION=no-strict-align ++ ++// CHECK: warning: argument unused during compilation: '-m[[OPTION]]' [-Wunused-command-line-argument] +diff --git a/clang/test/Preprocessor/init-loongarch.c b/clang/test/Preprocessor/init-loongarch.c +index 686c96813..4ef42a921 100644 +--- a/clang/test/Preprocessor/init-loongarch.c ++++ b/clang/test/Preprocessor/init-loongarch.c +@@ -3,16 +3,16 @@ + // RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple loongarch32-unknown-linux /dev/null \ + // RUN: | FileCheck --match-full-lines --check-prefixes=LA32,LA32-LINUX %s + // RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple loongarch32 \ +-// RUN: -fforce-enable-int128 /dev/null | FileCheck --match-full-lines \ +-// RUN: --check-prefixes=LA32,LA32-INT128 %s ++// RUN: -fforce-enable-int128 /dev/null | FileCheck --match-full-lines \ ++// RUN: --check-prefixes=LA32,LA32-INT128 %s + + // RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple loongarch64 /dev/null \ + // RUN: | FileCheck --match-full-lines --check-prefix=LA64 %s + // RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple loongarch64-unknown-linux /dev/null \ + // RUN: | FileCheck --match-full-lines --check-prefixes=LA64,LA64-LINUX %s + // RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple loongarch64 \ +-// RUN: -fforce-enable-int128 /dev/null | FileCheck --match-full-lines \ +-// RUN: --check-prefixes=LA64,LA64-INT128 %s ++// RUN: -fforce-enable-int128 /dev/null | FileCheck --match-full-lines \ ++// RUN: --check-prefixes=LA64,LA64-INT128 %s + + //// Note that common macros are tested in init.c, such as __VERSION__. So they're not listed here. + +@@ -650,141 +650,160 @@ + // LA64-LINUX: #define unix 1 + + +-/// Check various macros prefixed with "__loongarch_" in different cases. +-/// "__loongarch__"" is not listed here as it has been checked above. ++/// Check __loongarch_{double,single,hard,soft}_float, __loongarch_{gr,fr}len, __loongarch_lp64. + + // RUN: %clang --target=loongarch32 -mfpu=64 -mabi=ilp32d -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU64-ILP32D %s ++// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU64-ILP32D %s + // RUN: %clang --target=loongarch32 -mdouble-float -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU64-ILP32D %s +-// LA32-FPU64-ILP32D: __loongarch_double_float 1 +-// LA32-FPU64-ILP32D-NEXT: __loongarch_frlen 64 +-// LA32-FPU64-ILP32D-NEXT: __loongarch_grlen 32 +-// LA32-FPU64-ILP32D-NEXT: __loongarch_hard_float 1 +-// LA32-FPU64-ILP32D-NOT: __loongarch_lp64 +-// LA32-FPU64-ILP32D-NOT: __loongarch_single_float +-// LA32-FPU64-ILP32D-NOT: __loongarch_soft_float ++// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU64-ILP32D %s ++// LA32-FPU64-ILP32D: #define __loongarch_double_float 1 ++// LA32-FPU64-ILP32D: #define __loongarch_frlen 64 ++// LA32-FPU64-ILP32D: #define __loongarch_grlen 32 ++// LA32-FPU64-ILP32D: #define __loongarch_hard_float 1 ++// LA32-FPU64-ILP32D-NOT: #define __loongarch_lp64 ++// LA32-FPU64-ILP32D-NOT: #define __loongarch_single_float ++// LA32-FPU64-ILP32D-NOT: #define __loongarch_soft_float + + // RUN: %clang --target=loongarch32 -mfpu=64 -mabi=ilp32f -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU64-ILP32F %s +-// LA32-FPU64-ILP32F-NOT: __loongarch_double_float +-// LA32-FPU64-ILP32F: __loongarch_frlen 64 +-// LA32-FPU64-ILP32F-NEXT: __loongarch_grlen 32 +-// LA32-FPU64-ILP32F-NEXT: __loongarch_hard_float 1 +-// LA32-FPU64-ILP32F-NOT: __loongarch_lp64 +-// LA32-FPU64-ILP32F-NEXT: __loongarch_single_float 1 +-// LA32-FPU64-ILP32F-NOT: __loongarch_soft_float ++// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU64-ILP32F %s ++// LA32-FPU64-ILP32F-NOT: #define __loongarch_double_float ++// LA32-FPU64-ILP32F: #define __loongarch_frlen 64 ++// LA32-FPU64-ILP32F: #define __loongarch_grlen 32 ++// LA32-FPU64-ILP32F: #define __loongarch_hard_float 1 ++// LA32-FPU64-ILP32F-NOT: #define __loongarch_lp64 ++// LA32-FPU64-ILP32F: #define __loongarch_single_float 1 ++// LA32-FPU64-ILP32F-NOT: #define __loongarch_soft_float + + // RUN: %clang --target=loongarch32 -mfpu=64 -mabi=ilp32s -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU64-ILP32S %s +-// LA32-FPU64-ILP32S-NOT: __loongarch_double_float +-// LA32-FPU64-ILP32S: __loongarch_frlen 64 +-// LA32-FPU64-ILP32S-NEXT: __loongarch_grlen 32 +-// LA32-FPU64-ILP32S-NOT: __loongarch_hard_float +-// LA32-FPU64-ILP32S-NOT: __loongarch_lp64 +-// LA32-FPU64-ILP32S-NOT: __loongarch_single_float +-// LA32-FPU64-ILP32S-NEXT: __loongarch_soft_float 1 ++// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU64-ILP32S %s ++// LA32-FPU64-ILP32S-NOT: #define __loongarch_double_float ++// LA32-FPU64-ILP32S: #define __loongarch_frlen 64 ++// LA32-FPU64-ILP32S: #define __loongarch_grlen 32 ++// LA32-FPU64-ILP32S-NOT: #define __loongarch_hard_float ++// LA32-FPU64-ILP32S-NOT: #define __loongarch_lp64 ++// LA32-FPU64-ILP32S-NOT: #define __loongarch_single_float ++// LA32-FPU64-ILP32S: #define __loongarch_soft_float 1 + + // RUN: %clang --target=loongarch32 -mfpu=32 -mabi=ilp32f -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU32-ILP32F %s ++// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU32-ILP32F %s + // RUN: %clang --target=loongarch32 -msingle-float -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU32-ILP32F %s +-// LA32-FPU32-ILP32F-NOT: __loongarch_double_float +-// LA32-FPU32-ILP32F: __loongarch_frlen 32 +-// LA32-FPU32-ILP32F-NEXT: __loongarch_grlen 32 +-// LA32-FPU32-ILP32F-NEXT: __loongarch_hard_float 1 +-// LA32-FPU32-ILP32F-NOT: __loongarch_lp64 +-// LA32-FPU32-ILP32F-NEXT: __loongarch_single_float 1 +-// LA32-FPU32-ILP32F-NOT: __loongarch_soft_float ++// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU32-ILP32F %s ++// LA32-FPU32-ILP32F-NOT: #define __loongarch_double_float ++// LA32-FPU32-ILP32F: #define __loongarch_frlen 32 ++// LA32-FPU32-ILP32F: #define __loongarch_grlen 32 ++// LA32-FPU32-ILP32F: #define __loongarch_hard_float 1 ++// LA32-FPU32-ILP32F-NOT: #define __loongarch_lp64 ++// LA32-FPU32-ILP32F: #define __loongarch_single_float 1 ++// LA32-FPU32-ILP32F-NOT: #define __loongarch_soft_float + + // RUN: %clang --target=loongarch32 -mfpu=32 -mabi=ilp32s -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU32-ILP32S %s +-// LA32-FPU32-ILP32S-NOT: __loongarch_double_float +-// LA32-FPU32-ILP32S: __loongarch_frlen 32 +-// LA32-FPU32-ILP32S-NEXT: __loongarch_grlen 32 +-// LA32-FPU32-ILP32S-NOT: __loongarch_hard_float +-// LA32-FPU32-ILP32S-NOT: __loongarch_lp64 +-// LA32-FPU32-ILP32S-NOT: __loongarch_single_float +-// LA32-FPU32-ILP32S-NEXT: __loongarch_soft_float 1 ++// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU32-ILP32S %s ++// LA32-FPU32-ILP32S-NOT: #define __loongarch_double_float ++// LA32-FPU32-ILP32S: #define __loongarch_frlen 32 ++// LA32-FPU32-ILP32S: #define __loongarch_grlen 32 ++// LA32-FPU32-ILP32S-NOT: #define __loongarch_hard_float ++// LA32-FPU32-ILP32S-NOT: #define __loongarch_lp64 ++// LA32-FPU32-ILP32S-NOT: #define __loongarch_single_float ++// LA32-FPU32-ILP32S: #define __loongarch_soft_float 1 + + // RUN: %clang --target=loongarch32 -mfpu=0 -mabi=ilp32s -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU0-ILP32S %s ++// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU0-ILP32S %s + // RUN: %clang --target=loongarch32 -mfpu=none -mabi=ilp32s -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU0-ILP32S %s ++// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU0-ILP32S %s + // RUN: %clang --target=loongarch32 -msoft-float -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU0-ILP32S %s +-// LA32-FPU0-ILP32S-NOT: __loongarch_double_float +-// LA32-FPU0-ILP32S: __loongarch_frlen 0 +-// LA32-FPU0-ILP32S-NEXT: __loongarch_grlen 32 +-// LA32-FPU0-ILP32S-NOT: __loongarch_hard_float +-// LA32-FPU0-ILP32S-NOT: __loongarch_lp64 +-// LA32-FPU0-ILP32S-NOT: __loongarch_single_float +-// LA32-FPU0-ILP32S-NEXT: __loongarch_soft_float 1 ++// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU0-ILP32S %s ++// LA32-FPU0-ILP32S-NOT: #define __loongarch_double_float ++// LA32-FPU0-ILP32S: #define __loongarch_frlen 0 ++// LA32-FPU0-ILP32S: #define __loongarch_grlen 32 ++// LA32-FPU0-ILP32S-NOT: #define __loongarch_hard_float ++// LA32-FPU0-ILP32S-NOT: #define __loongarch_lp64 ++// LA32-FPU0-ILP32S-NOT: #define __loongarch_single_float ++// LA32-FPU0-ILP32S: #define __loongarch_soft_float 1 + + // RUN: %clang --target=loongarch64 -mfpu=64 -mabi=lp64d -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU64-LP64D %s ++// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU64-LP64D %s + // RUN: %clang --target=loongarch64 -mdouble-float -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU64-LP64D %s +-// LA64-FPU64-LP64D: __loongarch_double_float 1 +-// LA64-FPU64-LP64D-NEXT: __loongarch_frlen 64 +-// LA64-FPU64-LP64D-NEXT: __loongarch_grlen 64 +-// LA64-FPU64-LP64D-NEXT: __loongarch_hard_float 1 +-// LA64-FPU64-LP64D-NEXT: __loongarch_lp64 1 +-// LA64-FPU64-LP64D-NOT: __loongarch_single_float +-// LA64-FPU64-LP64D-NOT: __loongarch_soft_float ++// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU64-LP64D %s ++// LA64-FPU64-LP64D: #define __loongarch_double_float 1 ++// LA64-FPU64-LP64D: #define __loongarch_frlen 64 ++// LA64-FPU64-LP64D: #define __loongarch_grlen 64 ++// LA64-FPU64-LP64D: #define __loongarch_hard_float 1 ++// LA64-FPU64-LP64D: #define __loongarch_lp64 1 ++// LA64-FPU64-LP64D-NOT: #define __loongarch_single_float ++// LA64-FPU64-LP64D-NOT: #define __loongarch_soft_float + + // RUN: %clang --target=loongarch64 -mfpu=64 -mabi=lp64f -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU64-LP64F %s +-// LA64-FPU64-LP64F-NOT: __loongarch_double_float +-// LA64-FPU64-LP64F: __loongarch_frlen 64 +-// LA64-FPU64-LP64F-NEXT: __loongarch_grlen 64 +-// LA64-FPU64-LP64F-NEXT: __loongarch_hard_float 1 +-// LA64-FPU64-LP64F-NEXT: __loongarch_lp64 1 +-// LA64-FPU64-LP64F-NEXT: __loongarch_single_float 1 +-// LA64-FPU64-LP64F-NOT: __loongarch_soft_float ++// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU64-LP64F %s ++// LA64-FPU64-LP64F-NOT: #define __loongarch_double_float ++// LA64-FPU64-LP64F: #define __loongarch_frlen 64 ++// LA64-FPU64-LP64F: #define __loongarch_grlen 64 ++// LA64-FPU64-LP64F: #define __loongarch_hard_float 1 ++// LA64-FPU64-LP64F: #define __loongarch_lp64 1 ++// LA64-FPU64-LP64F: #define __loongarch_single_float 1 ++// LA64-FPU64-LP64F-NOT: #define __loongarch_soft_float + + // RUN: %clang --target=loongarch64 -mfpu=64 -mabi=lp64s -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU64-LP64S %s +-// LA64-FPU64-LP64S-NOT: __loongarch_double_float +-// LA64-FPU64-LP64S: __loongarch_frlen 64 +-// LA64-FPU64-LP64S-NEXT: __loongarch_grlen 64 +-// LA64-FPU64-LP64S-NOT: __loongarch_hard_float +-// LA64-FPU64-LP64S-NEXT: __loongarch_lp64 1 +-// LA64-FPU64-LP64S-NOT: __loongarch_single_float +-// LA64-FPU64-LP64S-NEXT: __loongarch_soft_float 1 ++// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU64-LP64S %s ++// LA64-FPU64-LP64S-NOT: #define __loongarch_double_float ++// LA64-FPU64-LP64S: #define __loongarch_frlen 64 ++// LA64-FPU64-LP64S: #define __loongarch_grlen 64 ++// LA64-FPU64-LP64S-NOT: #define __loongarch_hard_float ++// LA64-FPU64-LP64S: #define __loongarch_lp64 1 ++// LA64-FPU64-LP64S-NOT: #define __loongarch_single_float ++// LA64-FPU64-LP64S: #define __loongarch_soft_float 1 + + // RUN: %clang --target=loongarch64 -mfpu=32 -mabi=lp64f -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU32-LP64F %s ++// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU32-LP64F %s + // RUN: %clang --target=loongarch64 -msingle-float -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU32-LP64F %s +-// LA64-FPU32-LP64F-NOT: __loongarch_double_float +-// LA64-FPU32-LP64F: __loongarch_frlen 32 +-// LA64-FPU32-LP64F-NEXT: __loongarch_grlen 64 +-// LA64-FPU32-LP64F-NEXT: __loongarch_hard_float 1 +-// LA64-FPU32-LP64F-NEXT: __loongarch_lp64 1 +-// LA64-FPU32-LP64F-NEXT: __loongarch_single_float 1 +-// LA64-FPU32-LP64F-NOT: __loongarch_soft_float ++// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU32-LP64F %s ++// LA64-FPU32-LP64F-NOT: #define __loongarch_double_float ++// LA64-FPU32-LP64F: #define __loongarch_frlen 32 ++// LA64-FPU32-LP64F: #define __loongarch_grlen 64 ++// LA64-FPU32-LP64F: #define __loongarch_hard_float 1 ++// LA64-FPU32-LP64F: #define __loongarch_lp64 1 ++// LA64-FPU32-LP64F: #define __loongarch_single_float 1 ++// LA64-FPU32-LP64F-NOT: #define __loongarch_soft_float + + // RUN: %clang --target=loongarch64 -mfpu=32 -mabi=lp64s -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU32-LP64S %s +-// LA64-FPU32-LP64S-NOT: __loongarch_double_float +-// LA64-FPU32-LP64S: __loongarch_frlen 32 +-// LA64-FPU32-LP64S-NEXT: __loongarch_grlen 64 +-// LA64-FPU32-LP64S-NOT: __loongarch_hard_float +-// LA64-FPU32-LP64S-NEXT: __loongarch_lp64 1 +-// LA64-FPU32-LP64S-NOT: __loongarch_single_float +-// LA64-FPU32-LP64S-NEXT: __loongarch_soft_float 1 ++// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU32-LP64S %s ++// LA64-FPU32-LP64S-NOT: #define __loongarch_double_float ++// LA64-FPU32-LP64S: #define __loongarch_frlen 32 ++// LA64-FPU32-LP64S: #define __loongarch_grlen 64 ++// LA64-FPU32-LP64S-NOT: #define __loongarch_hard_float ++// LA64-FPU32-LP64S: #define __loongarch_lp64 1 ++// LA64-FPU32-LP64S-NOT: #define __loongarch_single_float ++// LA64-FPU32-LP64S: #define __loongarch_soft_float 1 + + // RUN: %clang --target=loongarch64 -mfpu=0 -mabi=lp64s -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU0-LP64S %s ++// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU0-LP64S %s + // RUN: %clang --target=loongarch64 -mfpu=none -mabi=lp64s -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU0-LP64S %s ++// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU0-LP64S %s + // RUN: %clang --target=loongarch64 -msoft-float -x c -E -dM %s -o - \ +-// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU0-LP64S %s +-// LA64-FPU0-LP64S-NOT: __loongarch_double_float +-// LA64-FPU0-LP64S: __loongarch_frlen 0 +-// LA64-FPU0-LP64S-NEXT: __loongarch_grlen 64 +-// LA64-FPU0-LP64S-NOT: __loongarch_hard_float +-// LA64-FPU0-LP64S-NEXT: __loongarch_lp64 1 +-// LA64-FPU0-LP64S-NOT: __loongarch_single_float +-// LA64-FPU0-LP64S-NEXT: __loongarch_soft_float 1 ++// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU0-LP64S %s ++// LA64-FPU0-LP64S-NOT: #define __loongarch_double_float ++// LA64-FPU0-LP64S: #define __loongarch_frlen 0 ++// LA64-FPU0-LP64S: #define __loongarch_grlen 64 ++// LA64-FPU0-LP64S-NOT: #define __loongarch_hard_float ++// LA64-FPU0-LP64S: #define __loongarch_lp64 1 ++// LA64-FPU0-LP64S-NOT: #define __loongarch_single_float ++// LA64-FPU0-LP64S: #define __loongarch_soft_float 1 ++ ++/// Check __loongarch_arch and __loongarch_tune. ++ ++// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - | \ ++// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=loongarch64 -DTUNE=loongarch64 %s ++// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -march=loongarch64 | \ ++// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=loongarch64 -DTUNE=loongarch64 %s ++// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -march=la464 | \ ++// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=la464 -DTUNE=la464 %s ++// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -mtune=loongarch64 | \ ++// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=loongarch64 -DTUNE=loongarch64 %s ++// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -mtune=la464 | \ ++// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=loongarch64 -DTUNE=la464 %s ++// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -march=loongarch64 -mtune=la464 | \ ++// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=loongarch64 -DTUNE=la464 %s ++// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -march=la464 -mtune=loongarch64 | \ ++// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=la464 -DTUNE=loongarch64 %s ++ ++// ARCH-TUNE: #define __loongarch_arch "[[ARCH]]" ++// ARCH-TUNE: #define __loongarch_tune "[[TUNE]]" +diff --git a/clang/test/Sema/patchable-function-entry-attr.cpp b/clang/test/Sema/patchable-function-entry-attr.cpp +index 3dd050498..9134c851d 100644 +--- a/clang/test/Sema/patchable-function-entry-attr.cpp ++++ b/clang/test/Sema/patchable-function-entry-attr.cpp +@@ -2,6 +2,8 @@ + // RUN: %clang_cc1 -triple aarch64_be -fsyntax-only -verify=silence %s + // RUN: %clang_cc1 -triple i386 -fsyntax-only -verify=silence %s + // RUN: %clang_cc1 -triple x86_64 -fsyntax-only -verify=silence %s ++// RUN: %clang_cc1 -triple loongarch32 -fsyntax-only -verify=silence %s ++// RUN: %clang_cc1 -triple loongarch64 -fsyntax-only -verify=silence %s + // RUN: %clang_cc1 -triple riscv32 -fsyntax-only -verify=silence %s + // RUN: %clang_cc1 -triple riscv64 -fsyntax-only -verify=silence %s + // RUN: %clang_cc1 -triple ppc64le -fsyntax-only -verify %s diff --git a/0002-LoongArch-fix-symbol-lookup-error.patch b/0002-LoongArch-fix-symbol-lookup-error.patch new file mode 100644 index 0000000..d04f88c --- /dev/null +++ b/0002-LoongArch-fix-symbol-lookup-error.patch @@ -0,0 +1,834 @@ +diff --git a/clang/lib/Basic/Targets/LoongArch.cpp b/clang/lib/Basic/Targets/LoongArch.cpp +index 96ef29620..b34ce4f4c 100644 +--- a/clang/lib/Basic/Targets/LoongArch.cpp ++++ b/clang/lib/Basic/Targets/LoongArch.cpp +@@ -14,8 +14,8 @@ + #include "clang/Basic/Diagnostic.h" + #include "clang/Basic/MacroBuilder.h" + #include "clang/Basic/TargetBuiltins.h" ++#include "llvm/Support/TargetParser.h" + #include "llvm/Support/raw_ostream.h" +-#include "llvm/TargetParser/LoongArchTargetParser.h" + + using namespace clang; + using namespace clang::targets; +@@ -188,15 +188,7 @@ void LoongArchTargetInfo::getTargetDefines(const LangOptions &Opts, + else + Builder.defineMacro("__loongarch_frlen", "0"); + +- // Define __loongarch_arch. +- StringRef ArchName = getCPU(); +- Builder.defineMacro("__loongarch_arch", Twine('"') + ArchName + Twine('"')); +- +- // Define __loongarch_tune. +- StringRef TuneCPU = getTargetOpts().TuneCPU; +- if (TuneCPU.empty()) +- TuneCPU = ArchName; +- Builder.defineMacro("__loongarch_tune", Twine('"') + TuneCPU + Twine('"')); ++ // TODO: define __loongarch_arch and __loongarch_tune. + + StringRef ABI = getABI(); + if (ABI == "lp64d" || ABI == "lp64f" || ABI == "lp64s") +@@ -268,12 +260,3 @@ bool LoongArchTargetInfo::handleTargetFeatures( + } + return true; + } +- +-bool LoongArchTargetInfo::isValidCPUName(StringRef Name) const { +- return llvm::LoongArch::isValidCPUName(Name); +-} +- +-void LoongArchTargetInfo::fillValidCPUList( +- SmallVectorImpl &Values) const { +- llvm::LoongArch::fillValidCPUList(Values); +-} +diff --git a/clang/lib/Basic/Targets/LoongArch.h b/clang/lib/Basic/Targets/LoongArch.h +index 46ce56b43..646c8d071 100644 +--- a/clang/lib/Basic/Targets/LoongArch.h ++++ b/clang/lib/Basic/Targets/LoongArch.h +@@ -24,7 +24,6 @@ namespace targets { + class LLVM_LIBRARY_VISIBILITY LoongArchTargetInfo : public TargetInfo { + protected: + std::string ABI; +- std::string CPU; + bool HasFeatureD; + bool HasFeatureF; + +@@ -41,15 +40,6 @@ public: + WIntType = UnsignedInt; + } + +- bool setCPU(const std::string &Name) override { +- if (!isValidCPUName(Name)) +- return false; +- CPU = Name; +- return true; +- } +- +- StringRef getCPU() const { return CPU; } +- + StringRef getABI() const override { return ABI; } + + void getTargetDefines(const LangOptions &Opts, +@@ -90,9 +80,6 @@ public: + const std::vector &FeaturesVec) const override; + + bool hasFeature(StringRef Feature) const override; +- +- bool isValidCPUName(StringRef Name) const override; +- void fillValidCPUList(SmallVectorImpl &Values) const override; + }; + + class LLVM_LIBRARY_VISIBILITY LoongArch32TargetInfo +diff --git a/clang/lib/Driver/ToolChains/Arch/LoongArch.cpp b/clang/lib/Driver/ToolChains/Arch/LoongArch.cpp +index f5d4018a4..4619b4214 100644 +--- a/clang/lib/Driver/ToolChains/Arch/LoongArch.cpp ++++ b/clang/lib/Driver/ToolChains/Arch/LoongArch.cpp +@@ -12,8 +12,7 @@ + #include "clang/Driver/Driver.h" + #include "clang/Driver/DriverDiagnostic.h" + #include "clang/Driver/Options.h" +-#include "llvm/TargetParser/Host.h" +-#include "llvm/TargetParser/LoongArchTargetParser.h" ++#include "llvm/Support/LoongArchTargetParser.h" + + using namespace clang::driver; + using namespace clang::driver::tools; +@@ -99,18 +98,53 @@ StringRef loongarch::getLoongArchABI(const Driver &D, const ArgList &Args, + } + + // Choose a default based on the triple. +- return IsLA32 ? "ilp32d" : "lp64d"; ++ // Honor the explicit ABI modifier suffix in triple's environment part if ++ // present, falling back to {ILP32,LP64}D otherwise. ++ switch (Triple.getEnvironment()) { ++ case llvm::Triple::GNUSF: ++ return IsLA32 ? "ilp32s" : "lp64s"; ++ case llvm::Triple::GNUF32: ++ return IsLA32 ? "ilp32f" : "lp64f"; ++ case llvm::Triple::GNUF64: ++ // This was originally permitted (and indeed the canonical way) to ++ // represent the {ILP32,LP64}D ABIs, but in Feb 2023 Loongson decided to ++ // drop the explicit suffix in favor of unmarked `-gnu` for the ++ // "general-purpose" ABIs, among other non-technical reasons. ++ // ++ // The spec change did not mention whether existing usages of "gnuf64" ++ // shall remain valid or not, so we are going to continue recognizing it ++ // for some time, until it is clear that everyone else has migrated away ++ // from it. ++ [[fallthrough]]; ++ case llvm::Triple::GNU: ++ default: ++ return IsLA32 ? "ilp32d" : "lp64d"; ++ } + } + + void loongarch::getLoongArchTargetFeatures(const Driver &D, + const llvm::Triple &Triple, + const ArgList &Args, + std::vector &Features) { +- std::string ArchName; +- if (const Arg *A = Args.getLastArg(options::OPT_march_EQ)) ++ StringRef ArchName; ++ llvm::LoongArch::ArchKind ArchKind = llvm::LoongArch::ArchKind::AK_INVALID; ++ if (const Arg *A = Args.getLastArg(options::OPT_march_EQ)) { ++ ArchKind = llvm::LoongArch::parseArch(A->getValue()); ++ if (ArchKind == llvm::LoongArch::ArchKind::AK_INVALID) { ++ D.Diag(clang::diag::err_drv_invalid_arch_name) << A->getAsString(Args); ++ return; ++ } + ArchName = A->getValue(); +- ArchName = postProcessTargetCPUString(ArchName, Triple); +- llvm::LoongArch::getArchFeatures(ArchName, Features); ++ } ++ ++ // TODO: handle -march=native and -mtune=xx. ++ ++ // Select a default arch name. ++ if (ArchName.empty() && Triple.getArch() == llvm::Triple::loongarch64) ++ ArchName = "loongarch64"; ++ ++ if (!ArchName.empty()) ++ llvm::LoongArch::getArchFeatures(ArchName, Features); + + // Select floating-point features determined by -mdouble-float, + // -msingle-float, -msoft-float and -mfpu. +@@ -149,25 +183,3 @@ void loongarch::getLoongArchTargetFeatures(const Driver &D, + AddTargetFeature(Args, Features, options::OPT_munaligned_access, + options::OPT_mno_unaligned_access, "ual"); + } +- +-std::string loongarch::postProcessTargetCPUString(const std::string &CPU, +- const llvm::Triple &Triple) { +- std::string CPUString = CPU; +- if (CPUString == "native") { +- CPUString = llvm::sys::getHostCPUName(); +- if (CPUString == "generic") +- CPUString = llvm::LoongArch::getDefaultArch(Triple.isLoongArch64()); +- } +- if (CPUString.empty()) +- CPUString = llvm::LoongArch::getDefaultArch(Triple.isLoongArch64()); +- return CPUString; +-} +- +-std::string loongarch::getLoongArchTargetCPU(const llvm::opt::ArgList &Args, +- const llvm::Triple &Triple) { +- std::string CPU; +- // If we have -march, use that. +- if (const Arg *A = Args.getLastArg(options::OPT_march_EQ)) +- CPU = A->getValue(); +- return postProcessTargetCPUString(CPU, Triple); +-} +diff --git a/clang/lib/Driver/ToolChains/Arch/LoongArch.h b/clang/lib/Driver/ToolChains/Arch/LoongArch.h +index d8280cd83..0084474e7 100644 +--- a/clang/lib/Driver/ToolChains/Arch/LoongArch.h ++++ b/clang/lib/Driver/ToolChains/Arch/LoongArch.h +@@ -23,12 +23,6 @@ void getLoongArchTargetFeatures(const Driver &D, const llvm::Triple &Triple, + + StringRef getLoongArchABI(const Driver &D, const llvm::opt::ArgList &Args, + const llvm::Triple &Triple); +- +-std::string postProcessTargetCPUString(const std::string &CPU, +- const llvm::Triple &Triple); +- +-std::string getLoongArchTargetCPU(const llvm::opt::ArgList &Args, +- const llvm::Triple &Triple); + } // end namespace loongarch + } // end namespace tools + } // end namespace driver +diff --git a/clang/lib/Driver/ToolChains/Clang.cpp b/clang/lib/Driver/ToolChains/Clang.cpp +index e5c3b1087..8e6f880be 100644 +--- a/clang/lib/Driver/ToolChains/Clang.cpp ++++ b/clang/lib/Driver/ToolChains/Clang.cpp +@@ -54,7 +54,6 @@ + #include "llvm/Support/Path.h" + #include "llvm/Support/Process.h" + #include "llvm/Support/YAMLParser.h" +-#include "llvm/TargetParser/LoongArchTargetParser.h" + #include + + using namespace clang::driver; +@@ -1834,20 +1833,10 @@ void Clang::AddAArch64TargetArgs(const ArgList &Args, + + void Clang::AddLoongArchTargetArgs(const ArgList &Args, + ArgStringList &CmdArgs) const { +- const llvm::Triple &Triple = getToolChain().getTriple(); +- + CmdArgs.push_back("-target-abi"); +- CmdArgs.push_back( +- loongarch::getLoongArchABI(getToolChain().getDriver(), Args, Triple) +- .data()); +- +- // Handle -mtune. +- if (const Arg *A = Args.getLastArg(options::OPT_mtune_EQ)) { +- std::string TuneCPU = A->getValue(); +- TuneCPU = loongarch::postProcessTargetCPUString(TuneCPU, Triple); +- CmdArgs.push_back("-tune-cpu"); +- CmdArgs.push_back(Args.MakeArgString(TuneCPU)); +- } ++ CmdArgs.push_back(loongarch::getLoongArchABI(getToolChain().getDriver(), Args, ++ getToolChain().getTriple()) ++ .data()); + } + + void Clang::AddMIPSTargetArgs(const ArgList &Args, +diff --git a/clang/lib/Driver/ToolChains/CommonArgs.cpp b/clang/lib/Driver/ToolChains/CommonArgs.cpp +index b462e2fe1..34640b3c4 100644 +--- a/clang/lib/Driver/ToolChains/CommonArgs.cpp ++++ b/clang/lib/Driver/ToolChains/CommonArgs.cpp +@@ -455,10 +455,6 @@ std::string tools::getCPUName(const Driver &D, const ArgList &Args, + case llvm::Triple::wasm32: + case llvm::Triple::wasm64: + return std::string(getWebAssemblyTargetCPU(Args)); +- +- case llvm::Triple::loongarch32: +- case llvm::Triple::loongarch64: +- return loongarch::getLoongArchTargetCPU(Args, T); + } + } + +diff --git a/clang/lib/Driver/ToolChains/Linux.cpp b/clang/lib/Driver/ToolChains/Linux.cpp +index c6fb290ff..ba4136902 100644 +--- a/clang/lib/Driver/ToolChains/Linux.cpp ++++ b/clang/lib/Driver/ToolChains/Linux.cpp +@@ -86,6 +86,39 @@ std::string Linux::getMultiarchTriple(const Driver &D, + case llvm::Triple::aarch64_be: + return "aarch64_be-linux-gnu"; + ++ case llvm::Triple::loongarch64: { ++ const char *Libc; ++ const char *FPFlavor; ++ ++ if (TargetTriple.isGNUEnvironment()) { ++ Libc = "gnu"; ++ } else if (TargetTriple.isMusl()) { ++ Libc = "musl"; ++ } else { ++ return TargetTriple.str(); ++ } ++ ++ switch (TargetEnvironment) { ++ default: ++ return TargetTriple.str(); ++ case llvm::Triple::GNUSF: ++ FPFlavor = "sf"; ++ break; ++ case llvm::Triple::GNUF32: ++ FPFlavor = "f32"; ++ break; ++ case llvm::Triple::GNU: ++ case llvm::Triple::GNUF64: ++ // This was going to be "f64" in an earlier Toolchain Conventions ++ // revision, but starting from Feb 2023 the F64 ABI variants are ++ // unmarked in their canonical forms. ++ FPFlavor = ""; ++ break; ++ } ++ ++ return (Twine("loongarch64-linux-") + Libc + FPFlavor).str(); ++ } ++ + case llvm::Triple::m68k: + return "m68k-linux-gnu"; + +diff --git a/clang/test/Driver/Inputs/debian_loong64_tree/usr/include/c++/13/backward/.keep b/clang/test/Driver/Inputs/debian_loong64_tree/usr/include/c++/13/backward/.keep +new file mode 100644 +index 000000000..e69de29bb +diff --git a/clang/test/Driver/Inputs/debian_loong64_tree/usr/include/loongarch64-linux-gnu/c++/.keep b/clang/test/Driver/Inputs/debian_loong64_tree/usr/include/loongarch64-linux-gnu/c++/.keep +new file mode 100644 +index 000000000..e69de29bb +diff --git a/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/gcc/loongarch64-linux-gnu/13/crtbegin.o b/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/gcc/loongarch64-linux-gnu/13/crtbegin.o +new file mode 100644 +index 000000000..e69de29bb +diff --git a/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/gcc/loongarch64-linux-gnu/13/crtend.o b/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/gcc/loongarch64-linux-gnu/13/crtend.o +new file mode 100644 +index 000000000..e69de29bb +diff --git a/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/gcc/loongarch64-linux-gnu/13/include/.keep b/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/gcc/loongarch64-linux-gnu/13/include/.keep +new file mode 100644 +index 000000000..e69de29bb +diff --git a/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/loongarch64-linux-gnu/crt1.o b/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/loongarch64-linux-gnu/crt1.o +new file mode 100644 +index 000000000..e69de29bb +diff --git a/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/loongarch64-linux-gnu/crti.o b/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/loongarch64-linux-gnu/crti.o +new file mode 100644 +index 000000000..e69de29bb +diff --git a/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/loongarch64-linux-gnu/crtn.o b/clang/test/Driver/Inputs/debian_loong64_tree/usr/lib/loongarch64-linux-gnu/crtn.o +new file mode 100644 +index 000000000..e69de29bb +diff --git a/clang/test/Driver/linux-header-search.cpp b/clang/test/Driver/linux-header-search.cpp +index 91e4f8825..e8e84f1e4 100644 +--- a/clang/test/Driver/linux-header-search.cpp ++++ b/clang/test/Driver/linux-header-search.cpp +@@ -244,6 +244,32 @@ + // CHECK-GENTOO-4-9-X-32: "-internal-externc-isystem" "[[SYSROOT]]/include" + // CHECK-GENTOO-4-9-X-32: "-internal-externc-isystem" "[[SYSROOT]]/usr/include" + // ++// Check header search on Debian loong64 ++// RUN: %clang -### %s -fsyntax-only 2>&1 \ ++// RUN: --target=loongarch64-unknown-linux-gnu -stdlib=libstdc++ \ ++// RUN: --sysroot=%S/Inputs/debian_loong64_tree \ ++// RUN: --gcc-toolchain="" \ ++// RUN: | FileCheck --check-prefix=CHECK-LOONG64-GNU %s ++// ++// Check that "-gnuf64" is seen as "-gnu" for loong64. ++// RUN: %clang -### %s -fsyntax-only 2>&1 \ ++// RUN: --target=loongarch64-unknown-linux-gnuf64 -stdlib=libstdc++ \ ++// RUN: --sysroot=%S/Inputs/debian_loong64_tree \ ++// RUN: --gcc-toolchain="" \ ++// RUN: | FileCheck --check-prefix=CHECK-LOONG64-GNU %s ++// CHECK-LOONG64-GNU: "-cc1" ++// CHECK-LOONG64-GNU: "-resource-dir" "[[RESOURCE_DIR:[^"]+]]" ++// CHECK-LOONG64-GNU: "-isysroot" "[[SYSROOT:[^"]+]]" ++// CHECK-LOONG64-GNU: "-internal-isystem" "[[SYSROOT]]/usr/lib/gcc/loongarch64-linux-gnu/13/../../../../include/c++/13" ++// CHECK-LOONG64-GNU: "-internal-isystem" "[[SYSROOT]]/usr/lib/gcc/loongarch64-linux-gnu/13/../../../../include/c++/13/loongarch64-linux-gnu" ++// CHECK-LOONG64-GNU: "-internal-isystem" "[[SYSROOT]]/usr/lib/gcc/loongarch64-linux-gnu/13/../../../../include/c++/13/backward" ++// CHECK-LOONG64-GNU: "-internal-isystem" "[[RESOURCE_DIR]]{{/|\\\\}}include" ++// CHECK-LOONG64-GNU: "-internal-isystem" "[[SYSROOT]]/usr/local/include" ++// CHECK-LOONG64-GNU: "-internal-isystem" "[[SYSROOT]]/usr/lib/gcc/loongarch64-linux-gnu/13/../../../../loongarch64-linux-gnu/include" ++// CHECK-LOONG64-GNU: "-internal-externc-isystem" "[[SYSROOT]]/usr/include/loongarch64-linux-gnu" ++// CHECK-LOONG64-GNU: "-internal-externc-isystem" "[[SYSROOT]]/include" ++// CHECK-LOONG64-GNU: "-internal-externc-isystem" "[[SYSROOT]]/usr/include" ++// + // Check header search on Debian 6 / MIPS64 + // RUN: %clang -### %s -fsyntax-only 2>&1 \ + // RUN: --target=mips64-unknown-linux-gnuabi64 -stdlib=libstdc++ \ +diff --git a/clang/test/Driver/linux-ld.c b/clang/test/Driver/linux-ld.c +index 10e6bee18..e937de950 100644 +--- a/clang/test/Driver/linux-ld.c ++++ b/clang/test/Driver/linux-ld.c +@@ -830,6 +830,30 @@ + // CHECK-ARM-HF: "-dynamic-linker" "{{.*}}/lib/ld-linux-armhf.so.3" + // + // RUN: %clang -### %s -no-pie 2>&1 \ ++// RUN: --target=loongarch64-linux-gnu \ ++// RUN: | FileCheck --check-prefix=CHECK-LOONGARCH-LP64D %s ++// RUN: %clang -### %s -no-pie 2>&1 \ ++// RUN: --target=loongarch64-linux-gnuf64 \ ++// RUN: | FileCheck --check-prefix=CHECK-LOONGARCH-LP64D %s ++// CHECK-LOONGARCH-LP64D: "{{.*}}ld{{(.exe)?}}" ++// CHECK-LOONGARCH-LP64D: "-m" "elf64loongarch" ++// CHECK-LOONGARCH-LP64D: "-dynamic-linker" "{{.*}}/lib64/ld-linux-loongarch-lp64d.so.1" ++// ++// RUN: %clang -### %s -no-pie 2>&1 \ ++// RUN: --target=loongarch64-linux-gnuf32 \ ++// RUN: | FileCheck --check-prefix=CHECK-LOONGARCH-LP64F %s ++// CHECK-LOONGARCH-LP64F: "{{.*}}ld{{(.exe)?}}" ++// CHECK-LOONGARCH-LP64F: "-m" "elf64loongarch" ++// CHECK-LOONGARCH-LP64F: "-dynamic-linker" "{{.*}}/lib64/ld-linux-loongarch-lp64f.so.1" ++// ++// RUN: %clang -### %s -no-pie 2>&1 \ ++// RUN: --target=loongarch64-linux-gnusf \ ++// RUN: | FileCheck --check-prefix=CHECK-LOONGARCH-LP64S %s ++// CHECK-LOONGARCH-LP64S: "{{.*}}ld{{(.exe)?}}" ++// CHECK-LOONGARCH-LP64S: "-m" "elf64loongarch" ++// CHECK-LOONGARCH-LP64S: "-dynamic-linker" "{{.*}}/lib64/ld-linux-loongarch-lp64s.so.1" ++// ++// RUN: %clang -### %s -no-pie 2>&1 \ + // RUN: --target=powerpc64-linux-gnu \ + // RUN: | FileCheck --check-prefix=CHECK-PPC64 %s + // CHECK-PPC64: "{{.*}}ld{{(.exe)?}}" +@@ -1388,6 +1412,29 @@ + // RUN: | FileCheck --check-prefix=CHECK-ANDROID-PTHREAD-LINK %s + // CHECK-ANDROID-PTHREAD-LINK-NOT: argument unused during compilation: '-pthread' + // ++// Check linker invocation on a Debian LoongArch sysroot. ++// RUN: %clang -### %s -no-pie 2>&1 \ ++// RUN: --target=loongarch64-linux-gnu -rtlib=platform \ ++// RUN: --gcc-toolchain="" \ ++// RUN: --sysroot=%S/Inputs/debian_loong64_tree \ ++// RUN: | FileCheck --check-prefix=CHECK-DEBIAN-ML-LOONG64 %s ++// ++// Check that "-gnuf64" is seen as "-gnu" for loong64. ++// RUN: %clang -### %s -no-pie 2>&1 \ ++// RUN: --target=loongarch64-linux-gnuf64 -rtlib=platform \ ++// RUN: --gcc-toolchain="" \ ++// RUN: --sysroot=%S/Inputs/debian_loong64_tree \ ++// RUN: | FileCheck --check-prefix=CHECK-DEBIAN-ML-LOONG64 %s ++// CHECK-DEBIAN-ML-LOONG64: "{{.*}}ld{{(.exe)?}}" "--sysroot=[[SYSROOT:[^"]+]]" ++// CHECK-DEBIAN-ML-LOONG64: "[[SYSROOT]]/usr/lib/loongarch64-linux-gnu/crt1.o" ++// CHECK-DEBIAN-ML-LOONG64: "[[SYSROOT]]/usr/lib/loongarch64-linux-gnu/crti.o" ++// CHECK-DEBIAN-ML-LOONG64: "[[SYSROOT]]/usr/lib/gcc/loongarch64-linux-gnu/13/crtbegin.o" ++// CHECK-DEBIAN-ML-LOONG64: "-L[[SYSROOT]]/usr/lib/gcc/loongarch64-linux-gnu/13" ++// CHECK-DEBIAN-ML-LOONG64: "-L[[SYSROOT]]/usr/lib/loongarch64-linux-gnu" ++// CHECK-DEBIAN-ML-LOONG64: "-L[[SYSROOT]]/usr/lib" ++// CHECK-DEBIAN-ML-LOONG64: "[[SYSROOT]]/usr/lib/gcc/loongarch64-linux-gnu/13/crtend.o" ++// CHECK-DEBIAN-ML-LOONG64: "[[SYSROOT]]/usr/lib/loongarch64-linux-gnu/crtn.o" ++// + // Check linker invocation on Debian 6 MIPS 32/64-bit. + // RUN: %clang -### %s -no-pie 2>&1 \ + // RUN: --target=mipsel-linux-gnu -rtlib=platform \ +diff --git a/clang/test/Driver/loongarch-abi.c b/clang/test/Driver/loongarch-abi.c +index 9359f25da..12a81d664 100644 +--- a/clang/test/Driver/loongarch-abi.c ++++ b/clang/test/Driver/loongarch-abi.c +@@ -16,6 +16,34 @@ + // RUN: %clang --target=loongarch64-unknown-elf %s -fsyntax-only -### -mabi=lp64d 2>&1 \ + // RUN: | FileCheck --check-prefix=LP64D %s + ++// RUN: %clang --target=loongarch32-linux-gnusf %s -fsyntax-only -### 2>&1 \ ++// RUN: | FileCheck --check-prefix=ILP32S %s ++// RUN: %clang --target=loongarch32-linux-gnuf32 %s -fsyntax-only -### 2>&1 \ ++// RUN: | FileCheck --check-prefix=ILP32F %s ++// RUN: %clang --target=loongarch32-linux-gnuf64 %s -fsyntax-only -### 2>&1 \ ++// RUN: | FileCheck --check-prefix=ILP32D %s ++// RUN: %clang --target=loongarch32-linux-gnu %s -fsyntax-only -### 2>&1 \ ++// RUN: | FileCheck --check-prefix=ILP32D %s ++ ++// RUN: %clang --target=loongarch64-linux-gnusf %s -fsyntax-only -### 2>&1 \ ++// RUN: | FileCheck --check-prefix=LP64S %s ++// RUN: %clang --target=loongarch64-linux-gnuf32 %s -fsyntax-only -### 2>&1 \ ++// RUN: | FileCheck --check-prefix=LP64F %s ++// RUN: %clang --target=loongarch64-linux-gnuf64 %s -fsyntax-only -### 2>&1 \ ++// RUN: | FileCheck --check-prefix=LP64D %s ++// RUN: %clang --target=loongarch64-linux-gnu %s -fsyntax-only -### 2>&1 \ ++// RUN: | FileCheck --check-prefix=LP64D %s ++ ++// Check that -mabi prevails in case of conflicts with the triple-implied ABI. ++// RUN: %clang --target=loongarch32-linux-gnuf64 %s -fsyntax-only -### -mabi=ilp32s 2>&1 \ ++// RUN: | FileCheck --check-prefix=ILP32S %s ++// RUN: %clang --target=loongarch64-linux-gnuf64 %s -fsyntax-only -### -mabi=lp64s 2>&1 \ ++// RUN: | FileCheck --check-prefix=LP64S %s ++// RUN: %clang --target=loongarch32-linux-gnu %s -fsyntax-only -### -mabi=ilp32s 2>&1 \ ++// RUN: | FileCheck --check-prefix=ILP32S %s ++// RUN: %clang --target=loongarch64-linux-gnu %s -fsyntax-only -### -mabi=lp64s 2>&1 \ ++// RUN: | FileCheck --check-prefix=LP64S %s ++ + // ILP32S: "-target-abi" "ilp32s" + // ILP32F: "-target-abi" "ilp32f" + // ILP32D: "-target-abi" "ilp32d" +diff --git a/clang/test/Driver/loongarch-march-error.c b/clang/test/Driver/loongarch-march-error.c +index 6bfaa18b0..f447de655 100644 +--- a/clang/test/Driver/loongarch-march-error.c ++++ b/clang/test/Driver/loongarch-march-error.c +@@ -1,7 +1,7 @@ + // RUN: not %clang --target=loongarch64 -march=loongarch -fsyntax-only %s 2>&1 | \ +-// RUN: FileCheck -DCPU=loongarch %s +-// RUN: not %clang --target=loongarch64 -march=LA464 -fsyntax-only %s 2>&1 | \ +-// RUN: FileCheck -DCPU=LA464 %s ++// RUN: FileCheck --check-prefix=LOONGARCH %s ++// LOONGARCH: error: invalid arch name '-march=loongarch' + +-// CHECK: error: unknown target CPU '[[CPU]]' +-// CHECK-NEXT: note: valid target CPU values are: {{.*}} ++// RUN: not %clang --target=loongarch64 -march=LA464 -fsyntax-only %s 2>&1 | \ ++// RUN: FileCheck --check-prefix=LA464-UPPER %s ++// LA464-UPPER: error: invalid arch name '-march=LA464' +diff --git a/clang/test/Driver/loongarch-march.c b/clang/test/Driver/loongarch-march.c +index 9214130cd..c3a5c9e8a 100644 +--- a/clang/test/Driver/loongarch-march.c ++++ b/clang/test/Driver/loongarch-march.c +@@ -7,20 +7,18 @@ + // RUN: %clang --target=loongarch64 -march=la464 -S -emit-llvm %s -o - | \ + // RUN: FileCheck %s --check-prefix=IR-LA464 + +-// CC1-LOONGARCH64: "-target-cpu" "loongarch64" + // CC1-LOONGARCH64-NOT: "-target-feature" + // CC1-LOONGARCH64: "-target-feature" "+64bit" "-target-feature" "+f" "-target-feature" "+d" "-target-feature" "+ual" + // CC1-LOONGARCH64-NOT: "-target-feature" + // CC1-LOONGARCH64: "-target-abi" "lp64d" + +-// CC1-LA464: "-target-cpu" "la464" + // CC1-LA464-NOT: "-target-feature" + // CC1-LA464: "-target-feature" "+64bit" "-target-feature" "+f" "-target-feature" "+d" "-target-feature" "+lsx" "-target-feature" "+lasx" "-target-feature" "+ual" + // CC1-LA464-NOT: "-target-feature" + // CC1-LA464: "-target-abi" "lp64d" + +-// IR-LOONGARCH64: attributes #[[#]] ={{.*}}"target-cpu"="loongarch64" {{.*}}"target-features"="+64bit,+d,+f,+ual" +-// IR-LA464: attributes #[[#]] ={{.*}}"target-cpu"="la464" {{.*}}"target-features"="+64bit,+d,+f,+lasx,+lsx,+ual" ++// IR-LOONGARCH64: attributes #[[#]] ={{.*}}"target-features"="+64bit,+d,+f,+ual" ++// IR-LA464: attributes #[[#]] ={{.*}}"target-features"="+64bit,+d,+f,+lasx,+lsx,+ual" + + int foo(void) { + return 3; +diff --git a/clang/test/Driver/loongarch-mtune.c b/clang/test/Driver/loongarch-mtune.c +deleted file mode 100644 +index 6f3f39e9b..000000000 +--- a/clang/test/Driver/loongarch-mtune.c ++++ /dev/null +@@ -1,34 +0,0 @@ +-// RUN: %clang --target=loongarch64 -mtune=loongarch64 -fsyntax-only %s -### 2>&1 | \ +-// RUN: FileCheck %s --check-prefix=CC1ARG -DCPU=loongarch64 +-// RUN: %clang --target=loongarch64 -mtune=loongarch64 -S -emit-llvm %s -o - | \ +-// RUN: FileCheck %s --check-prefix=IRATTR -DCPU=loongarch64 +- +-// RUN: %clang --target=loongarch64 -mtune=la464 -fsyntax-only %s -### 2>&1 | \ +-// RUN: FileCheck %s --check-prefix=CC1ARG -DCPU=la464 +-// RUN: %clang --target=loongarch64 -mtune=la464 -S -emit-llvm %s -o - | \ +-// RUN: FileCheck %s --check-prefix=IRATTR -DCPU=la464 +- +-// RUN: %clang --target=loongarch64 -mtune=invalidcpu -fsyntax-only %s -### 2>&1 | \ +-// RUN: FileCheck %s --check-prefix=CC1ARG -DCPU=invalidcpu +-// RUN: not %clang --target=loongarch64 -mtune=invalidcpu -S -emit-llvm %s -o /dev/null 2>&1 | \ +-// RUN: FileCheck %s --check-prefix=ERROR -DCPU=invalidcpu +- +-// RUN: %clang --target=loongarch64 -mtune=generic -fsyntax-only %s -### 2>&1 | \ +-// RUN: FileCheck %s --check-prefix=CC1ARG -DCPU=generic +-// RUN: not %clang --target=loongarch64 -mtune=generic -S -emit-llvm %s -o /dev/null 2>&1 | \ +-// RUN: FileCheck %s --check-prefix=ERROR -DCPU=generic +- +-// RUN: %clang --target=loongarch64 -mtune=generic-la64 -fsyntax-only %s -### 2>&1 | \ +-// RUN: FileCheck %s --check-prefix=CC1ARG -DCPU=generic-la64 +-// RUN: not %clang --target=loongarch64 -mtune=generic-la64 -S -emit-llvm %s -o /dev/null 2>&1 | \ +-// RUN: FileCheck %s --check-prefix=ERROR -DCPU=generic-la64 +- +-// CC1ARG: "-tune-cpu" "[[CPU]]" +-// IRATTR: "tune-cpu"="[[CPU]]" +- +-// ERROR: error: unknown target CPU '[[CPU]]' +-// ERROR-NEXT: note: valid target CPU values are: {{.*}} +- +-int foo(void) { +- return 3; +-} +diff --git a/clang/test/Preprocessor/init-loongarch.c b/clang/test/Preprocessor/init-loongarch.c +index 4ef42a921..686c96813 100644 +--- a/clang/test/Preprocessor/init-loongarch.c ++++ b/clang/test/Preprocessor/init-loongarch.c +@@ -3,16 +3,16 @@ + // RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple loongarch32-unknown-linux /dev/null \ + // RUN: | FileCheck --match-full-lines --check-prefixes=LA32,LA32-LINUX %s + // RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple loongarch32 \ +-// RUN: -fforce-enable-int128 /dev/null | FileCheck --match-full-lines \ +-// RUN: --check-prefixes=LA32,LA32-INT128 %s ++// RUN: -fforce-enable-int128 /dev/null | FileCheck --match-full-lines \ ++// RUN: --check-prefixes=LA32,LA32-INT128 %s + + // RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple loongarch64 /dev/null \ + // RUN: | FileCheck --match-full-lines --check-prefix=LA64 %s + // RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple loongarch64-unknown-linux /dev/null \ + // RUN: | FileCheck --match-full-lines --check-prefixes=LA64,LA64-LINUX %s + // RUN: %clang_cc1 -E -dM -ffreestanding -fgnuc-version=4.2.1 -triple loongarch64 \ +-// RUN: -fforce-enable-int128 /dev/null | FileCheck --match-full-lines \ +-// RUN: --check-prefixes=LA64,LA64-INT128 %s ++// RUN: -fforce-enable-int128 /dev/null | FileCheck --match-full-lines \ ++// RUN: --check-prefixes=LA64,LA64-INT128 %s + + //// Note that common macros are tested in init.c, such as __VERSION__. So they're not listed here. + +@@ -650,160 +650,141 @@ + // LA64-LINUX: #define unix 1 + + +-/// Check __loongarch_{double,single,hard,soft}_float, __loongarch_{gr,fr}len, __loongarch_lp64. ++/// Check various macros prefixed with "__loongarch_" in different cases. ++/// "__loongarch__"" is not listed here as it has been checked above. + + // RUN: %clang --target=loongarch32 -mfpu=64 -mabi=ilp32d -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU64-ILP32D %s ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU64-ILP32D %s + // RUN: %clang --target=loongarch32 -mdouble-float -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU64-ILP32D %s +-// LA32-FPU64-ILP32D: #define __loongarch_double_float 1 +-// LA32-FPU64-ILP32D: #define __loongarch_frlen 64 +-// LA32-FPU64-ILP32D: #define __loongarch_grlen 32 +-// LA32-FPU64-ILP32D: #define __loongarch_hard_float 1 +-// LA32-FPU64-ILP32D-NOT: #define __loongarch_lp64 +-// LA32-FPU64-ILP32D-NOT: #define __loongarch_single_float +-// LA32-FPU64-ILP32D-NOT: #define __loongarch_soft_float ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU64-ILP32D %s ++// LA32-FPU64-ILP32D: __loongarch_double_float 1 ++// LA32-FPU64-ILP32D-NEXT: __loongarch_frlen 64 ++// LA32-FPU64-ILP32D-NEXT: __loongarch_grlen 32 ++// LA32-FPU64-ILP32D-NEXT: __loongarch_hard_float 1 ++// LA32-FPU64-ILP32D-NOT: __loongarch_lp64 ++// LA32-FPU64-ILP32D-NOT: __loongarch_single_float ++// LA32-FPU64-ILP32D-NOT: __loongarch_soft_float + + // RUN: %clang --target=loongarch32 -mfpu=64 -mabi=ilp32f -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU64-ILP32F %s +-// LA32-FPU64-ILP32F-NOT: #define __loongarch_double_float +-// LA32-FPU64-ILP32F: #define __loongarch_frlen 64 +-// LA32-FPU64-ILP32F: #define __loongarch_grlen 32 +-// LA32-FPU64-ILP32F: #define __loongarch_hard_float 1 +-// LA32-FPU64-ILP32F-NOT: #define __loongarch_lp64 +-// LA32-FPU64-ILP32F: #define __loongarch_single_float 1 +-// LA32-FPU64-ILP32F-NOT: #define __loongarch_soft_float ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU64-ILP32F %s ++// LA32-FPU64-ILP32F-NOT: __loongarch_double_float ++// LA32-FPU64-ILP32F: __loongarch_frlen 64 ++// LA32-FPU64-ILP32F-NEXT: __loongarch_grlen 32 ++// LA32-FPU64-ILP32F-NEXT: __loongarch_hard_float 1 ++// LA32-FPU64-ILP32F-NOT: __loongarch_lp64 ++// LA32-FPU64-ILP32F-NEXT: __loongarch_single_float 1 ++// LA32-FPU64-ILP32F-NOT: __loongarch_soft_float + + // RUN: %clang --target=loongarch32 -mfpu=64 -mabi=ilp32s -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU64-ILP32S %s +-// LA32-FPU64-ILP32S-NOT: #define __loongarch_double_float +-// LA32-FPU64-ILP32S: #define __loongarch_frlen 64 +-// LA32-FPU64-ILP32S: #define __loongarch_grlen 32 +-// LA32-FPU64-ILP32S-NOT: #define __loongarch_hard_float +-// LA32-FPU64-ILP32S-NOT: #define __loongarch_lp64 +-// LA32-FPU64-ILP32S-NOT: #define __loongarch_single_float +-// LA32-FPU64-ILP32S: #define __loongarch_soft_float 1 ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU64-ILP32S %s ++// LA32-FPU64-ILP32S-NOT: __loongarch_double_float ++// LA32-FPU64-ILP32S: __loongarch_frlen 64 ++// LA32-FPU64-ILP32S-NEXT: __loongarch_grlen 32 ++// LA32-FPU64-ILP32S-NOT: __loongarch_hard_float ++// LA32-FPU64-ILP32S-NOT: __loongarch_lp64 ++// LA32-FPU64-ILP32S-NOT: __loongarch_single_float ++// LA32-FPU64-ILP32S-NEXT: __loongarch_soft_float 1 + + // RUN: %clang --target=loongarch32 -mfpu=32 -mabi=ilp32f -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU32-ILP32F %s ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU32-ILP32F %s + // RUN: %clang --target=loongarch32 -msingle-float -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU32-ILP32F %s +-// LA32-FPU32-ILP32F-NOT: #define __loongarch_double_float +-// LA32-FPU32-ILP32F: #define __loongarch_frlen 32 +-// LA32-FPU32-ILP32F: #define __loongarch_grlen 32 +-// LA32-FPU32-ILP32F: #define __loongarch_hard_float 1 +-// LA32-FPU32-ILP32F-NOT: #define __loongarch_lp64 +-// LA32-FPU32-ILP32F: #define __loongarch_single_float 1 +-// LA32-FPU32-ILP32F-NOT: #define __loongarch_soft_float ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU32-ILP32F %s ++// LA32-FPU32-ILP32F-NOT: __loongarch_double_float ++// LA32-FPU32-ILP32F: __loongarch_frlen 32 ++// LA32-FPU32-ILP32F-NEXT: __loongarch_grlen 32 ++// LA32-FPU32-ILP32F-NEXT: __loongarch_hard_float 1 ++// LA32-FPU32-ILP32F-NOT: __loongarch_lp64 ++// LA32-FPU32-ILP32F-NEXT: __loongarch_single_float 1 ++// LA32-FPU32-ILP32F-NOT: __loongarch_soft_float + + // RUN: %clang --target=loongarch32 -mfpu=32 -mabi=ilp32s -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU32-ILP32S %s +-// LA32-FPU32-ILP32S-NOT: #define __loongarch_double_float +-// LA32-FPU32-ILP32S: #define __loongarch_frlen 32 +-// LA32-FPU32-ILP32S: #define __loongarch_grlen 32 +-// LA32-FPU32-ILP32S-NOT: #define __loongarch_hard_float +-// LA32-FPU32-ILP32S-NOT: #define __loongarch_lp64 +-// LA32-FPU32-ILP32S-NOT: #define __loongarch_single_float +-// LA32-FPU32-ILP32S: #define __loongarch_soft_float 1 ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU32-ILP32S %s ++// LA32-FPU32-ILP32S-NOT: __loongarch_double_float ++// LA32-FPU32-ILP32S: __loongarch_frlen 32 ++// LA32-FPU32-ILP32S-NEXT: __loongarch_grlen 32 ++// LA32-FPU32-ILP32S-NOT: __loongarch_hard_float ++// LA32-FPU32-ILP32S-NOT: __loongarch_lp64 ++// LA32-FPU32-ILP32S-NOT: __loongarch_single_float ++// LA32-FPU32-ILP32S-NEXT: __loongarch_soft_float 1 + + // RUN: %clang --target=loongarch32 -mfpu=0 -mabi=ilp32s -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU0-ILP32S %s ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU0-ILP32S %s + // RUN: %clang --target=loongarch32 -mfpu=none -mabi=ilp32s -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU0-ILP32S %s ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU0-ILP32S %s + // RUN: %clang --target=loongarch32 -msoft-float -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA32-FPU0-ILP32S %s +-// LA32-FPU0-ILP32S-NOT: #define __loongarch_double_float +-// LA32-FPU0-ILP32S: #define __loongarch_frlen 0 +-// LA32-FPU0-ILP32S: #define __loongarch_grlen 32 +-// LA32-FPU0-ILP32S-NOT: #define __loongarch_hard_float +-// LA32-FPU0-ILP32S-NOT: #define __loongarch_lp64 +-// LA32-FPU0-ILP32S-NOT: #define __loongarch_single_float +-// LA32-FPU0-ILP32S: #define __loongarch_soft_float 1 ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA32-FPU0-ILP32S %s ++// LA32-FPU0-ILP32S-NOT: __loongarch_double_float ++// LA32-FPU0-ILP32S: __loongarch_frlen 0 ++// LA32-FPU0-ILP32S-NEXT: __loongarch_grlen 32 ++// LA32-FPU0-ILP32S-NOT: __loongarch_hard_float ++// LA32-FPU0-ILP32S-NOT: __loongarch_lp64 ++// LA32-FPU0-ILP32S-NOT: __loongarch_single_float ++// LA32-FPU0-ILP32S-NEXT: __loongarch_soft_float 1 + + // RUN: %clang --target=loongarch64 -mfpu=64 -mabi=lp64d -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU64-LP64D %s ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU64-LP64D %s + // RUN: %clang --target=loongarch64 -mdouble-float -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU64-LP64D %s +-// LA64-FPU64-LP64D: #define __loongarch_double_float 1 +-// LA64-FPU64-LP64D: #define __loongarch_frlen 64 +-// LA64-FPU64-LP64D: #define __loongarch_grlen 64 +-// LA64-FPU64-LP64D: #define __loongarch_hard_float 1 +-// LA64-FPU64-LP64D: #define __loongarch_lp64 1 +-// LA64-FPU64-LP64D-NOT: #define __loongarch_single_float +-// LA64-FPU64-LP64D-NOT: #define __loongarch_soft_float ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU64-LP64D %s ++// LA64-FPU64-LP64D: __loongarch_double_float 1 ++// LA64-FPU64-LP64D-NEXT: __loongarch_frlen 64 ++// LA64-FPU64-LP64D-NEXT: __loongarch_grlen 64 ++// LA64-FPU64-LP64D-NEXT: __loongarch_hard_float 1 ++// LA64-FPU64-LP64D-NEXT: __loongarch_lp64 1 ++// LA64-FPU64-LP64D-NOT: __loongarch_single_float ++// LA64-FPU64-LP64D-NOT: __loongarch_soft_float + + // RUN: %clang --target=loongarch64 -mfpu=64 -mabi=lp64f -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU64-LP64F %s +-// LA64-FPU64-LP64F-NOT: #define __loongarch_double_float +-// LA64-FPU64-LP64F: #define __loongarch_frlen 64 +-// LA64-FPU64-LP64F: #define __loongarch_grlen 64 +-// LA64-FPU64-LP64F: #define __loongarch_hard_float 1 +-// LA64-FPU64-LP64F: #define __loongarch_lp64 1 +-// LA64-FPU64-LP64F: #define __loongarch_single_float 1 +-// LA64-FPU64-LP64F-NOT: #define __loongarch_soft_float ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU64-LP64F %s ++// LA64-FPU64-LP64F-NOT: __loongarch_double_float ++// LA64-FPU64-LP64F: __loongarch_frlen 64 ++// LA64-FPU64-LP64F-NEXT: __loongarch_grlen 64 ++// LA64-FPU64-LP64F-NEXT: __loongarch_hard_float 1 ++// LA64-FPU64-LP64F-NEXT: __loongarch_lp64 1 ++// LA64-FPU64-LP64F-NEXT: __loongarch_single_float 1 ++// LA64-FPU64-LP64F-NOT: __loongarch_soft_float + + // RUN: %clang --target=loongarch64 -mfpu=64 -mabi=lp64s -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU64-LP64S %s +-// LA64-FPU64-LP64S-NOT: #define __loongarch_double_float +-// LA64-FPU64-LP64S: #define __loongarch_frlen 64 +-// LA64-FPU64-LP64S: #define __loongarch_grlen 64 +-// LA64-FPU64-LP64S-NOT: #define __loongarch_hard_float +-// LA64-FPU64-LP64S: #define __loongarch_lp64 1 +-// LA64-FPU64-LP64S-NOT: #define __loongarch_single_float +-// LA64-FPU64-LP64S: #define __loongarch_soft_float 1 ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU64-LP64S %s ++// LA64-FPU64-LP64S-NOT: __loongarch_double_float ++// LA64-FPU64-LP64S: __loongarch_frlen 64 ++// LA64-FPU64-LP64S-NEXT: __loongarch_grlen 64 ++// LA64-FPU64-LP64S-NOT: __loongarch_hard_float ++// LA64-FPU64-LP64S-NEXT: __loongarch_lp64 1 ++// LA64-FPU64-LP64S-NOT: __loongarch_single_float ++// LA64-FPU64-LP64S-NEXT: __loongarch_soft_float 1 + + // RUN: %clang --target=loongarch64 -mfpu=32 -mabi=lp64f -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU32-LP64F %s ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU32-LP64F %s + // RUN: %clang --target=loongarch64 -msingle-float -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU32-LP64F %s +-// LA64-FPU32-LP64F-NOT: #define __loongarch_double_float +-// LA64-FPU32-LP64F: #define __loongarch_frlen 32 +-// LA64-FPU32-LP64F: #define __loongarch_grlen 64 +-// LA64-FPU32-LP64F: #define __loongarch_hard_float 1 +-// LA64-FPU32-LP64F: #define __loongarch_lp64 1 +-// LA64-FPU32-LP64F: #define __loongarch_single_float 1 +-// LA64-FPU32-LP64F-NOT: #define __loongarch_soft_float ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU32-LP64F %s ++// LA64-FPU32-LP64F-NOT: __loongarch_double_float ++// LA64-FPU32-LP64F: __loongarch_frlen 32 ++// LA64-FPU32-LP64F-NEXT: __loongarch_grlen 64 ++// LA64-FPU32-LP64F-NEXT: __loongarch_hard_float 1 ++// LA64-FPU32-LP64F-NEXT: __loongarch_lp64 1 ++// LA64-FPU32-LP64F-NEXT: __loongarch_single_float 1 ++// LA64-FPU32-LP64F-NOT: __loongarch_soft_float + + // RUN: %clang --target=loongarch64 -mfpu=32 -mabi=lp64s -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU32-LP64S %s +-// LA64-FPU32-LP64S-NOT: #define __loongarch_double_float +-// LA64-FPU32-LP64S: #define __loongarch_frlen 32 +-// LA64-FPU32-LP64S: #define __loongarch_grlen 64 +-// LA64-FPU32-LP64S-NOT: #define __loongarch_hard_float +-// LA64-FPU32-LP64S: #define __loongarch_lp64 1 +-// LA64-FPU32-LP64S-NOT: #define __loongarch_single_float +-// LA64-FPU32-LP64S: #define __loongarch_soft_float 1 ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU32-LP64S %s ++// LA64-FPU32-LP64S-NOT: __loongarch_double_float ++// LA64-FPU32-LP64S: __loongarch_frlen 32 ++// LA64-FPU32-LP64S-NEXT: __loongarch_grlen 64 ++// LA64-FPU32-LP64S-NOT: __loongarch_hard_float ++// LA64-FPU32-LP64S-NEXT: __loongarch_lp64 1 ++// LA64-FPU32-LP64S-NOT: __loongarch_single_float ++// LA64-FPU32-LP64S-NEXT: __loongarch_soft_float 1 + + // RUN: %clang --target=loongarch64 -mfpu=0 -mabi=lp64s -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU0-LP64S %s ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU0-LP64S %s + // RUN: %clang --target=loongarch64 -mfpu=none -mabi=lp64s -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU0-LP64S %s ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU0-LP64S %s + // RUN: %clang --target=loongarch64 -msoft-float -x c -E -dM %s -o - \ +-// RUN: | FileCheck --match-full-lines --check-prefix=LA64-FPU0-LP64S %s +-// LA64-FPU0-LP64S-NOT: #define __loongarch_double_float +-// LA64-FPU0-LP64S: #define __loongarch_frlen 0 +-// LA64-FPU0-LP64S: #define __loongarch_grlen 64 +-// LA64-FPU0-LP64S-NOT: #define __loongarch_hard_float +-// LA64-FPU0-LP64S: #define __loongarch_lp64 1 +-// LA64-FPU0-LP64S-NOT: #define __loongarch_single_float +-// LA64-FPU0-LP64S: #define __loongarch_soft_float 1 +- +-/// Check __loongarch_arch and __loongarch_tune. +- +-// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - | \ +-// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=loongarch64 -DTUNE=loongarch64 %s +-// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -march=loongarch64 | \ +-// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=loongarch64 -DTUNE=loongarch64 %s +-// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -march=la464 | \ +-// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=la464 -DTUNE=la464 %s +-// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -mtune=loongarch64 | \ +-// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=loongarch64 -DTUNE=loongarch64 %s +-// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -mtune=la464 | \ +-// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=loongarch64 -DTUNE=la464 %s +-// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -march=loongarch64 -mtune=la464 | \ +-// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=loongarch64 -DTUNE=la464 %s +-// RUN: %clang --target=loongarch64 -x c -E -dM %s -o - -march=la464 -mtune=loongarch64 | \ +-// RUN: FileCheck --match-full-lines --check-prefix=ARCH-TUNE -DARCH=la464 -DTUNE=loongarch64 %s +- +-// ARCH-TUNE: #define __loongarch_arch "[[ARCH]]" +-// ARCH-TUNE: #define __loongarch_tune "[[TUNE]]" ++// RUN: | grep __loongarch_ | FileCheck --check-prefix=LA64-FPU0-LP64S %s ++// LA64-FPU0-LP64S-NOT: __loongarch_double_float ++// LA64-FPU0-LP64S: __loongarch_frlen 0 ++// LA64-FPU0-LP64S-NEXT: __loongarch_grlen 64 ++// LA64-FPU0-LP64S-NOT: __loongarch_hard_float ++// LA64-FPU0-LP64S-NEXT: __loongarch_lp64 1 ++// LA64-FPU0-LP64S-NOT: __loongarch_single_float ++// LA64-FPU0-LP64S-NEXT: __loongarch_soft_float 1 diff --git a/clang.spec b/clang.spec index 578900c..55d1b37 100644 --- a/clang.spec +++ b/clang.spec @@ -1,4 +1,4 @@ -%define anolis_release 1 +%define anolis_release 2 %global toolchain clang @@ -45,6 +45,8 @@ Patch8: D138472.diff Patch10: fix-ieee128-cross.diff # Add anolis support in driver Patch11: 1001-add-anolis-os-support-in-driver.patch +Patch12: 0001-backport-LoongArch-patches.patch +Patch13: 0002-LoongArch-fix-symbol-lookup-error.patch # Patches for clang-tools-extra # See https://reviews.llvm.org/D120301 @@ -467,6 +469,11 @@ LD_LIBRARY_PATH=%{buildroot}/%{_libdir} %{__ninja} check-all -C %{__cmake_buildd %{python3_sitelib}/clang/ %changelog +* Fri Aug 11 2023 Chen Li - 16.0.6-2 +- Backport LoongArch patches from llvmorg-17.0.0-rc2 +- Add the triple of loongarch64 for anolis os +- LoongArch: fix symbol lookup error when compiling on aarch and x86 + * Tue Aug 8 2023 Funda Wang - 16.0.6-1 - New version 16.0.6 -- Gitee