https://github.com/arsenm created https://github.com/llvm/llvm-project/pull/142617
These Module level triple checks implemented in the Subtarget are kind of a pain and we should probably get rid of all of them in across all targets, and stick to a consistent set of names. >From cf2ad5a269d2320885e3c986b317e7c136ccda63 Mon Sep 17 00:00:00 2001 From: Matt Arsenault <matthew.arsena...@amd.com> Date: Tue, 3 Jun 2025 03:55:53 +0200 Subject: [PATCH] ARM: Start moving runtime libcall configuration out of TargetLowering These Module level triple checks implemented in the Subtarget are kind of a pain and we should probably get rid of all of them in across all targets, and stick to a consistent set of names. --- llvm/include/llvm/TargetParser/Triple.h | 28 +++++++++++++ llvm/lib/IR/RuntimeLibcalls.cpp | 53 +++++++++++++++++++++++++ llvm/lib/Target/ARM/ARMISelLowering.cpp | 44 -------------------- llvm/lib/Target/ARM/ARMSubtarget.h | 30 +++----------- 4 files changed, 86 insertions(+), 69 deletions(-) diff --git a/llvm/include/llvm/TargetParser/Triple.h b/llvm/include/llvm/TargetParser/Triple.h index 7fd5278f1ed53..351da0d6598c2 100644 --- a/llvm/include/llvm/TargetParser/Triple.h +++ b/llvm/include/llvm/TargetParser/Triple.h @@ -917,6 +917,34 @@ class Triple { isOSBinFormatELF(); } + // ARM EABI is the bare-metal EABI described in ARM ABI documents and + // can be accessed via -target arm-none-eabi. This is NOT GNUEABI. + // FIXME: Add a flag for bare-metal for that target and set Triple::EABI + // even for GNUEABI, so we can make a distinction here and still conform to + // the EABI on GNU (and Android) mode. This requires change in Clang, too. + // FIXME: The Darwin exception is temporary, while we move users to + // "*-*-*-macho" triples as quickly as possible. + bool isTargetAEABI() const { + return (getEnvironment() == Triple::EABI || + getEnvironment() == Triple::EABIHF) && + !isOSDarwin() && !isOSWindows(); + } + + bool isTargetGNUAEABI() const { + return (getEnvironment() == Triple::GNUEABI || + getEnvironment() == Triple::GNUEABIT64 || + getEnvironment() == Triple::GNUEABIHF || + getEnvironment() == Triple::GNUEABIHFT64) && + !isOSDarwin() && !isOSWindows(); + } + + bool isTargetMuslAEABI() const { + return (getEnvironment() == Triple::MuslEABI || + getEnvironment() == Triple::MuslEABIHF || + getEnvironment() == Triple::OpenHOS) && + !isOSDarwin() && !isOSWindows(); + } + /// Tests whether the target is T32. bool isArmT32() const { switch (getSubArch()) { diff --git a/llvm/lib/IR/RuntimeLibcalls.cpp b/llvm/lib/IR/RuntimeLibcalls.cpp index db0373055160c..30290e97f64d3 100644 --- a/llvm/lib/IR/RuntimeLibcalls.cpp +++ b/llvm/lib/IR/RuntimeLibcalls.cpp @@ -11,6 +11,56 @@ using namespace llvm; using namespace RTLIB; +static void setARMLibcallNames(RuntimeLibcallsInfo &Info, const Triple &TT) { + // Register based DivRem for AEABI (RTABI 4.2) + if (TT.isTargetAEABI() || TT.isAndroid() || TT.isTargetGNUAEABI() || + TT.isTargetMuslAEABI() || TT.isOSWindows()) { + if (TT.isOSWindows()) { + const struct { + const RTLIB::Libcall Op; + const char *const Name; + const CallingConv::ID CC; + } LibraryCalls[] = { + {RTLIB::SDIVREM_I8, "__rt_sdiv", CallingConv::ARM_AAPCS}, + {RTLIB::SDIVREM_I16, "__rt_sdiv", CallingConv::ARM_AAPCS}, + {RTLIB::SDIVREM_I32, "__rt_sdiv", CallingConv::ARM_AAPCS}, + {RTLIB::SDIVREM_I64, "__rt_sdiv64", CallingConv::ARM_AAPCS}, + + {RTLIB::UDIVREM_I8, "__rt_udiv", CallingConv::ARM_AAPCS}, + {RTLIB::UDIVREM_I16, "__rt_udiv", CallingConv::ARM_AAPCS}, + {RTLIB::UDIVREM_I32, "__rt_udiv", CallingConv::ARM_AAPCS}, + {RTLIB::UDIVREM_I64, "__rt_udiv64", CallingConv::ARM_AAPCS}, + }; + + for (const auto &LC : LibraryCalls) { + Info.setLibcallName(LC.Op, LC.Name); + Info.setLibcallCallingConv(LC.Op, LC.CC); + } + } else { + const struct { + const RTLIB::Libcall Op; + const char *const Name; + const CallingConv::ID CC; + } LibraryCalls[] = { + {RTLIB::SDIVREM_I8, "__aeabi_idivmod", CallingConv::ARM_AAPCS}, + {RTLIB::SDIVREM_I16, "__aeabi_idivmod", CallingConv::ARM_AAPCS}, + {RTLIB::SDIVREM_I32, "__aeabi_idivmod", CallingConv::ARM_AAPCS}, + {RTLIB::SDIVREM_I64, "__aeabi_ldivmod", CallingConv::ARM_AAPCS}, + + {RTLIB::UDIVREM_I8, "__aeabi_uidivmod", CallingConv::ARM_AAPCS}, + {RTLIB::UDIVREM_I16, "__aeabi_uidivmod", CallingConv::ARM_AAPCS}, + {RTLIB::UDIVREM_I32, "__aeabi_uidivmod", CallingConv::ARM_AAPCS}, + {RTLIB::UDIVREM_I64, "__aeabi_uldivmod", CallingConv::ARM_AAPCS}, + }; + + for (const auto &LC : LibraryCalls) { + Info.setLibcallName(LC.Op, LC.Name); + Info.setLibcallCallingConv(LC.Op, LC.CC); + } + } + } +} + /// Set default libcall names. If a target wants to opt-out of a libcall it /// should be placed here. void RuntimeLibcallsInfo::initLibcalls(const Triple &TT) { @@ -249,6 +299,9 @@ void RuntimeLibcallsInfo::initLibcalls(const Triple &TT) { } } + if (TT.getArch() == Triple::ArchType::arm) + setARMLibcallNames(*this, TT); + if (TT.getArch() == Triple::ArchType::avr) { // Division rtlib functions (not supported), use divmod functions instead setLibcallName(RTLIB::SDIV_I8, nullptr); diff --git a/llvm/lib/Target/ARM/ARMISelLowering.cpp b/llvm/lib/Target/ARM/ARMISelLowering.cpp index d156851d7e214..4b01d6fe6edb7 100644 --- a/llvm/lib/Target/ARM/ARMISelLowering.cpp +++ b/llvm/lib/Target/ARM/ARMISelLowering.cpp @@ -1274,50 +1274,6 @@ ARMTargetLowering::ARMTargetLowering(const TargetMachine &TM, setOperationAction(ISD::UREM, MVT::i64, Custom); HasStandaloneRem = false; - if (Subtarget->isTargetWindows()) { - const struct { - const RTLIB::Libcall Op; - const char * const Name; - const CallingConv::ID CC; - } LibraryCalls[] = { - { RTLIB::SDIVREM_I8, "__rt_sdiv", CallingConv::ARM_AAPCS }, - { RTLIB::SDIVREM_I16, "__rt_sdiv", CallingConv::ARM_AAPCS }, - { RTLIB::SDIVREM_I32, "__rt_sdiv", CallingConv::ARM_AAPCS }, - { RTLIB::SDIVREM_I64, "__rt_sdiv64", CallingConv::ARM_AAPCS }, - - { RTLIB::UDIVREM_I8, "__rt_udiv", CallingConv::ARM_AAPCS }, - { RTLIB::UDIVREM_I16, "__rt_udiv", CallingConv::ARM_AAPCS }, - { RTLIB::UDIVREM_I32, "__rt_udiv", CallingConv::ARM_AAPCS }, - { RTLIB::UDIVREM_I64, "__rt_udiv64", CallingConv::ARM_AAPCS }, - }; - - for (const auto &LC : LibraryCalls) { - setLibcallName(LC.Op, LC.Name); - setLibcallCallingConv(LC.Op, LC.CC); - } - } else { - const struct { - const RTLIB::Libcall Op; - const char * const Name; - const CallingConv::ID CC; - } LibraryCalls[] = { - { RTLIB::SDIVREM_I8, "__aeabi_idivmod", CallingConv::ARM_AAPCS }, - { RTLIB::SDIVREM_I16, "__aeabi_idivmod", CallingConv::ARM_AAPCS }, - { RTLIB::SDIVREM_I32, "__aeabi_idivmod", CallingConv::ARM_AAPCS }, - { RTLIB::SDIVREM_I64, "__aeabi_ldivmod", CallingConv::ARM_AAPCS }, - - { RTLIB::UDIVREM_I8, "__aeabi_uidivmod", CallingConv::ARM_AAPCS }, - { RTLIB::UDIVREM_I16, "__aeabi_uidivmod", CallingConv::ARM_AAPCS }, - { RTLIB::UDIVREM_I32, "__aeabi_uidivmod", CallingConv::ARM_AAPCS }, - { RTLIB::UDIVREM_I64, "__aeabi_uldivmod", CallingConv::ARM_AAPCS }, - }; - - for (const auto &LC : LibraryCalls) { - setLibcallName(LC.Op, LC.Name); - setLibcallCallingConv(LC.Op, LC.CC); - } - } - setOperationAction(ISD::SDIVREM, MVT::i32, Custom); setOperationAction(ISD::UDIVREM, MVT::i32, Custom); setOperationAction(ISD::SDIVREM, MVT::i64, Custom); diff --git a/llvm/lib/Target/ARM/ARMSubtarget.h b/llvm/lib/Target/ARM/ARMSubtarget.h index 7329d3f2055f0..890a22f574a6b 100644 --- a/llvm/lib/Target/ARM/ARMSubtarget.h +++ b/llvm/lib/Target/ARM/ARMSubtarget.h @@ -348,31 +348,11 @@ class ARMSubtarget : public ARMGenSubtargetInfo { bool isTargetELF() const { return TargetTriple.isOSBinFormatELF(); } bool isTargetMachO() const { return TargetTriple.isOSBinFormatMachO(); } - // ARM EABI is the bare-metal EABI described in ARM ABI documents and - // can be accessed via -target arm-none-eabi. This is NOT GNUEABI. - // FIXME: Add a flag for bare-metal for that target and set Triple::EABI - // even for GNUEABI, so we can make a distinction here and still conform to - // the EABI on GNU (and Android) mode. This requires change in Clang, too. - // FIXME: The Darwin exception is temporary, while we move users to - // "*-*-*-macho" triples as quickly as possible. - bool isTargetAEABI() const { - return (TargetTriple.getEnvironment() == Triple::EABI || - TargetTriple.getEnvironment() == Triple::EABIHF) && - !isTargetDarwin() && !isTargetWindows(); - } - bool isTargetGNUAEABI() const { - return (TargetTriple.getEnvironment() == Triple::GNUEABI || - TargetTriple.getEnvironment() == Triple::GNUEABIT64 || - TargetTriple.getEnvironment() == Triple::GNUEABIHF || - TargetTriple.getEnvironment() == Triple::GNUEABIHFT64) && - !isTargetDarwin() && !isTargetWindows(); - } - bool isTargetMuslAEABI() const { - return (TargetTriple.getEnvironment() == Triple::MuslEABI || - TargetTriple.getEnvironment() == Triple::MuslEABIHF || - TargetTriple.getEnvironment() == Triple::OpenHOS) && - !isTargetDarwin() && !isTargetWindows(); - } + bool isTargetAEABI() const { return TargetTriple.isTargetAEABI(); } + + bool isTargetGNUAEABI() const { return TargetTriple.isTargetGNUAEABI(); } + + bool isTargetMuslAEABI() const { return TargetTriple.isTargetMuslAEABI(); } // ARM Targets that support EHABI exception handling standard // Darwin uses SjLj. Other targets might need more checks. _______________________________________________ llvm-branch-commits mailing list llvm-branch-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits