[llvm] 8a7e2fb - [SystemZ] [z/OS] Add SystemZCallingConventionRegisters class

Kai Nacke via llvm-commits llvm-commits at lists.llvm.org
Fri May 14 13:52:06 PDT 2021


Author: Neumann Hon
Date: 2021-05-14T16:51:26-04:00
New Revision: 8a7e2fb5f2070523868f5a46ee43fcc3a9aa6b1e

URL: https://github.com/llvm/llvm-project/commit/8a7e2fb5f2070523868f5a46ee43fcc3a9aa6b1e
DIFF: https://github.com/llvm/llvm-project/commit/8a7e2fb5f2070523868f5a46ee43fcc3a9aa6b1e.diff

LOG: [SystemZ] [z/OS] Add SystemZCallingConventionRegisters class

This patch adds the abstract class SystemZCallingConventionRegisters
which is a SystemZ-specific class detailing special registers used
by calling conventions on the target. SystemZELFRegisters and
SystemZXPLINK64Registers implement this class for ELF and XPLINK64
respectively.

Reviewed By: uweigand

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

Added: 
    

Modified: 
    llvm/lib/Target/SystemZ/SystemZInstrInfo.cpp
    llvm/lib/Target/SystemZ/SystemZRegisterInfo.cpp
    llvm/lib/Target/SystemZ/SystemZRegisterInfo.h
    llvm/lib/Target/SystemZ/SystemZSubtarget.cpp
    llvm/lib/Target/SystemZ/SystemZSubtarget.h

Removed: 
    


################################################################################
diff  --git a/llvm/lib/Target/SystemZ/SystemZInstrInfo.cpp b/llvm/lib/Target/SystemZ/SystemZInstrInfo.cpp
index 5d3a8f28ea90c..b9f64198f4e50 100644
--- a/llvm/lib/Target/SystemZ/SystemZInstrInfo.cpp
+++ b/llvm/lib/Target/SystemZ/SystemZInstrInfo.cpp
@@ -56,9 +56,9 @@ static uint64_t allOnes(unsigned int Count) {
 void SystemZInstrInfo::anchor() {}
 
 SystemZInstrInfo::SystemZInstrInfo(SystemZSubtarget &sti)
-  : SystemZGenInstrInfo(SystemZ::ADJCALLSTACKDOWN, SystemZ::ADJCALLSTACKUP),
-    RI(), STI(sti) {
-}
+    : SystemZGenInstrInfo(SystemZ::ADJCALLSTACKDOWN, SystemZ::ADJCALLSTACKUP),
+      RI(sti.getSpecialRegisters()->getReturnFunctionAddressRegister()),
+      STI(sti) {}
 
 // MI is a 128-bit load or store.  Split it into two 64-bit loads or stores,
 // each having the opcode given by NewOpcode.

diff  --git a/llvm/lib/Target/SystemZ/SystemZRegisterInfo.cpp b/llvm/lib/Target/SystemZ/SystemZRegisterInfo.cpp
index da91316db7946..0062e39602f56 100644
--- a/llvm/lib/Target/SystemZ/SystemZRegisterInfo.cpp
+++ b/llvm/lib/Target/SystemZ/SystemZRegisterInfo.cpp
@@ -22,9 +22,6 @@ using namespace llvm;
 #define GET_REGINFO_TARGET_DESC
 #include "SystemZGenRegisterInfo.inc"
 
-SystemZRegisterInfo::SystemZRegisterInfo()
-    : SystemZGenRegisterInfo(SystemZ::R14D) {}
-
 // Given that MO is a GRX32 operand, return either GR32 or GRH32 if MO
 // somehow belongs in it. Otherwise, return GRX32.
 static const TargetRegisterClass *getRC32(MachineOperand &MO,
@@ -192,7 +189,12 @@ bool SystemZRegisterInfo::getRegAllocationHints(
 }
 
 const MCPhysReg *
-SystemZRegisterInfo::getCalleeSavedRegs(const MachineFunction *MF) const {
+SystemZXPLINK64Registers::getCalleeSavedRegs(const MachineFunction *MF) const {
+  return CSR_SystemZ_XPLINK64_SaveList;
+}
+
+const MCPhysReg *
+SystemZELFRegisters::getCalleeSavedRegs(const MachineFunction *MF) const {
   const SystemZSubtarget &Subtarget = MF->getSubtarget<SystemZSubtarget>();
   if (MF->getFunction().getCallingConv() == CallingConv::GHC)
     return CSR_SystemZ_NoRegs_SaveList;
@@ -207,7 +209,13 @@ SystemZRegisterInfo::getCalleeSavedRegs(const MachineFunction *MF) const {
 }
 
 const uint32_t *
-SystemZRegisterInfo::getCallPreservedMask(const MachineFunction &MF,
+SystemZXPLINK64Registers::getCallPreservedMask(const MachineFunction &MF,
+                                               CallingConv::ID CC) const {
+  return CSR_SystemZ_XPLINK64_RegMask;
+}
+
+const uint32_t *
+SystemZELFRegisters::getCallPreservedMask(const MachineFunction &MF,
                                           CallingConv::ID CC) const {
   const SystemZSubtarget &Subtarget = MF.getSubtarget<SystemZSubtarget>();
   if (CC == CallingConv::GHC)
@@ -222,24 +230,43 @@ SystemZRegisterInfo::getCallPreservedMask(const MachineFunction &MF,
   return CSR_SystemZ_ELF_RegMask;
 }
 
+SystemZRegisterInfo::SystemZRegisterInfo(unsigned int RA)
+    : SystemZGenRegisterInfo(RA) {}
+
+const MCPhysReg *
+SystemZRegisterInfo::getCalleeSavedRegs(const MachineFunction *MF) const {
+
+  const SystemZSubtarget *Subtarget = &MF->getSubtarget<SystemZSubtarget>();
+  SystemZCallingConventionRegisters *Regs = Subtarget->getSpecialRegisters();
+
+  return Regs->getCalleeSavedRegs(MF);
+}
+
+const uint32_t *
+SystemZRegisterInfo::getCallPreservedMask(const MachineFunction &MF,
+                                          CallingConv::ID CC) const {
+
+  const SystemZSubtarget *Subtarget = &MF.getSubtarget<SystemZSubtarget>();
+  SystemZCallingConventionRegisters *Regs = Subtarget->getSpecialRegisters();
+  return Regs->getCallPreservedMask(MF, CC);
+}
+
 BitVector
 SystemZRegisterInfo::getReservedRegs(const MachineFunction &MF) const {
   BitVector Reserved(getNumRegs());
   const SystemZFrameLowering *TFI = getFrameLowering(MF);
-
-  if (TFI->hasFP(MF)) {
-    // R11D is the frame pointer.  Reserve all aliases.
-    Reserved.set(SystemZ::R11D);
-    Reserved.set(SystemZ::R11L);
-    Reserved.set(SystemZ::R11H);
-    Reserved.set(SystemZ::R10Q);
-  }
-
-  // R15D is the stack pointer.  Reserve all aliases.
-  Reserved.set(SystemZ::R15D);
-  Reserved.set(SystemZ::R15L);
-  Reserved.set(SystemZ::R15H);
-  Reserved.set(SystemZ::R14Q);
+  const SystemZSubtarget *Subtarget = &MF.getSubtarget<SystemZSubtarget>();
+  SystemZCallingConventionRegisters *Regs = Subtarget->getSpecialRegisters();
+  if (TFI->hasFP(MF))
+    // The frame pointer. Reserve all aliases.
+    for (MCRegAliasIterator AI(Regs->getFramePointerRegister(), this, true);
+         AI.isValid(); ++AI)
+      Reserved.set(*AI);
+
+  // Reserve all aliases for the stack pointer.
+  for (MCRegAliasIterator AI(Regs->getStackPointerRegister(), this, true);
+       AI.isValid(); ++AI)
+    Reserved.set(*AI);
 
   // A0 and A1 hold the thread pointer.
   Reserved.set(SystemZ::A0);
@@ -420,7 +447,11 @@ bool SystemZRegisterInfo::shouldCoalesce(MachineInstr *MI,
 Register
 SystemZRegisterInfo::getFrameRegister(const MachineFunction &MF) const {
   const SystemZFrameLowering *TFI = getFrameLowering(MF);
-  return TFI->hasFP(MF) ? SystemZ::R11D : SystemZ::R15D;
+  const SystemZSubtarget *Subtarget = &MF.getSubtarget<SystemZSubtarget>();
+  SystemZCallingConventionRegisters *Regs = Subtarget->getSpecialRegisters();
+
+  return TFI->hasFP(MF) ? Regs->getFramePointerRegister()
+                        : Regs->getStackPointerRegister();
 }
 
 const TargetRegisterClass *

diff  --git a/llvm/lib/Target/SystemZ/SystemZRegisterInfo.h b/llvm/lib/Target/SystemZ/SystemZRegisterInfo.h
index 9f2cca0c83f60..122504d4b44b3 100644
--- a/llvm/lib/Target/SystemZ/SystemZRegisterInfo.h
+++ b/llvm/lib/Target/SystemZ/SystemZRegisterInfo.h
@@ -39,9 +39,84 @@ inline bool isHighReg(unsigned int Reg) {
 }
 } // end namespace SystemZ
 
+/// A SystemZ-specific class detailing special use registers
+/// particular for calling conventions.
+/// It is abstract, all calling conventions must override and
+/// define the pure virtual member function defined in this class.
+class SystemZCallingConventionRegisters {
+public:
+  /// \returns the register that keeps the
+  /// return function address.
+  virtual int getReturnFunctionAddressRegister() = 0;
+
+  /// \returns the register that keeps the
+  /// stack pointer address.
+  virtual int getStackPointerRegister() = 0;
+
+  /// \returns the register that keeps the
+  /// frame pointer address.
+  virtual int getFramePointerRegister() = 0;
+
+  /// \returns an array of all the callee saved registers.
+  virtual const MCPhysReg *
+  getCalleeSavedRegs(const MachineFunction *MF) const = 0;
+
+  /// \returns the mask of all the call preserved registers.
+  virtual const uint32_t *getCallPreservedMask(const MachineFunction &MF,
+                                               CallingConv::ID CC) const = 0;
+
+  /// Destroys the object. Bogus destructor allowing derived classes
+  /// to override it.
+  virtual ~SystemZCallingConventionRegisters(){};
+};
+
+/// XPLINK64 calling convention specific use registers
+/// Particular to z/OS when in 64 bit mode
+class SystemZXPLINK64Registers : public SystemZCallingConventionRegisters {
+public:
+  int getReturnFunctionAddressRegister() override final {
+    return SystemZ::R7D;
+  };
+
+  int getStackPointerRegister() override final { return SystemZ::R4D; };
+
+  int getFramePointerRegister() override final { return SystemZ::R8D; };
+
+  const MCPhysReg *
+  getCalleeSavedRegs(const MachineFunction *MF) const override final;
+
+  const uint32_t *getCallPreservedMask(const MachineFunction &MF,
+                                       CallingConv::ID CC) const override final;
+
+  /// Destroys the object. Bogus destructor overriding base class destructor
+  ~SystemZXPLINK64Registers(){};
+};
+
+/// ELF calling convention specific use registers
+/// Particular when on zLinux in 64 bit mode
+class SystemZELFRegisters : public SystemZCallingConventionRegisters {
+public:
+  int getReturnFunctionAddressRegister() override final {
+    return SystemZ::R14D;
+  };
+
+  int getStackPointerRegister() override final { return SystemZ::R15D; };
+
+  int getFramePointerRegister() override final { return SystemZ::R11D; };
+
+  const MCPhysReg *
+  getCalleeSavedRegs(const MachineFunction *MF) const override final;
+
+  const uint32_t *getCallPreservedMask(const MachineFunction &MF,
+                                       CallingConv::ID CC) const override final;
+
+  /// Destroys the object. Bogus destructor overriding base class destructor
+  ~SystemZELFRegisters(){};
+};
+
 struct SystemZRegisterInfo : public SystemZGenRegisterInfo {
 public:
-  SystemZRegisterInfo();
+  SystemZRegisterInfo(unsigned int RA);
 
   /// getPointerRegClass - Return the register class to use to hold pointers.
   /// This is currently only used by LOAD_STACK_GUARD, which requires a non-%r0

diff  --git a/llvm/lib/Target/SystemZ/SystemZSubtarget.cpp b/llvm/lib/Target/SystemZ/SystemZSubtarget.cpp
index d24e264b03a5f..0b344c1fe9c62 100644
--- a/llvm/lib/Target/SystemZ/SystemZSubtarget.cpp
+++ b/llvm/lib/Target/SystemZ/SystemZSubtarget.cpp
@@ -50,6 +50,18 @@ SystemZSubtarget::initializeSubtargetDependencies(StringRef CPU, StringRef FS) {
   return *this;
 }
 
+SystemZCallingConventionRegisters *
+SystemZSubtarget::initializeSpecialRegisters() {
+  if (isTargetXPLINK64())
+    return new SystemZXPLINK64Registers;
+  else if (isTargetELF())
+    return new SystemZELFRegisters;
+  else {
+    llvm_unreachable("Invalid Calling Convention. Cannot initialize Special "
+                     "Call Registers!");
+  }
+}
+
 SystemZSubtarget::SystemZSubtarget(const Triple &TT, const std::string &CPU,
                                    const std::string &FS,
                                    const TargetMachine &TM)
@@ -61,20 +73,21 @@ SystemZSubtarget::SystemZSubtarget(const Triple &TT, const std::string &CPU,
       HasInterlockedAccess1(false), HasMiscellaneousExtensions(false),
       HasExecutionHint(false), HasLoadAndTrap(false),
       HasTransactionalExecution(false), HasProcessorAssist(false),
-      HasDFPZonedConversion(false), HasEnhancedDAT2(false),
-      HasVector(false), HasLoadStoreOnCond2(false),
-      HasLoadAndZeroRightmostByte(false), HasMessageSecurityAssist5(false),
-      HasDFPPackedConversion(false),
+      HasDFPZonedConversion(false), HasEnhancedDAT2(false), HasVector(false),
+      HasLoadStoreOnCond2(false), HasLoadAndZeroRightmostByte(false),
+      HasMessageSecurityAssist5(false), HasDFPPackedConversion(false),
       HasMiscellaneousExtensions2(false), HasGuardedStorage(false),
       HasMessageSecurityAssist7(false), HasMessageSecurityAssist8(false),
       HasVectorEnhancements1(false), HasVectorPackedDecimal(false),
-      HasInsertReferenceBitsMultiple(false),
-      HasMiscellaneousExtensions3(false), HasMessageSecurityAssist9(false),
-      HasVectorEnhancements2(false), HasVectorPackedDecimalEnhancement(false),
-      HasEnhancedSort(false), HasDeflateConversion(false), HasSoftFloat(false),
-      TargetTriple(TT), InstrInfo(initializeSubtargetDependencies(CPU, FS)),
-      TLInfo(TM, *this), TSInfo(), FrameLowering() {}
-
+      HasInsertReferenceBitsMultiple(false), HasMiscellaneousExtensions3(false),
+      HasMessageSecurityAssist9(false), HasVectorEnhancements2(false),
+      HasVectorPackedDecimalEnhancement(false), HasEnhancedSort(false),
+      HasDeflateConversion(false), HasSoftFloat(false), TargetTriple(TT),
+      SpecialRegisters(initializeSpecialRegisters()),
+      InstrInfo(initializeSubtargetDependencies(CPU, FS)), TLInfo(TM, *this),
+      TSInfo(), FrameLowering() {}
+
+SystemZSubtarget::~SystemZSubtarget() { delete getSpecialRegisters(); }
 
 bool SystemZSubtarget::enableSubRegLiveness() const {
   return UseSubRegLiveness;

diff  --git a/llvm/lib/Target/SystemZ/SystemZSubtarget.h b/llvm/lib/Target/SystemZ/SystemZSubtarget.h
index 87cb701824324..2fc7d30ec0cea 100644
--- a/llvm/lib/Target/SystemZ/SystemZSubtarget.h
+++ b/llvm/lib/Target/SystemZ/SystemZSubtarget.h
@@ -72,6 +72,7 @@ class SystemZSubtarget : public SystemZGenSubtargetInfo {
 
 private:
   Triple TargetTriple;
+  SystemZCallingConventionRegisters *SpecialRegisters;
   SystemZInstrInfo InstrInfo;
   SystemZTargetLowering TLInfo;
   SystemZSelectionDAGInfo TSInfo;
@@ -79,10 +80,19 @@ class SystemZSubtarget : public SystemZGenSubtargetInfo {
 
   SystemZSubtarget &initializeSubtargetDependencies(StringRef CPU,
                                                     StringRef FS);
+  SystemZCallingConventionRegisters *initializeSpecialRegisters(void);
+
 public:
   SystemZSubtarget(const Triple &TT, const std::string &CPU,
                    const std::string &FS, const TargetMachine &TM);
 
+  ~SystemZSubtarget();
+
+  SystemZCallingConventionRegisters *getSpecialRegisters() const {
+    assert(SpecialRegisters && "Unsupported SystemZ calling convention");
+    return SpecialRegisters;
+  }
+
   const TargetFrameLowering *getFrameLowering() const override {
     return &FrameLowering;
   }


        


More information about the llvm-commits mailing list