diff options
Diffstat (limited to 'llvm/lib/Target')
-rw-r--r-- | llvm/lib/Target/AArch64/AArch64FrameLowering.cpp | 9 | ||||
-rw-r--r-- | llvm/lib/Target/AArch64/AArch64MachineFunctionInfo.h | 52 | ||||
-rw-r--r-- | llvm/lib/Target/ARM/ARMFrameLowering.cpp | 6 | ||||
-rw-r--r-- | llvm/lib/Target/ARM/ARMFrameLowering.h | 2 |
4 files changed, 65 insertions, 4 deletions
diff --git a/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp b/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp index 68e1e6a3022..042d8fdcc51 100644 --- a/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp +++ b/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp @@ -1588,7 +1588,8 @@ static StackOffset getFPOffset(const MachineFunction &MF, int ObjectOffset) { bool IsWin64 = Subtarget.isCallingConvWin64(MF.getFunction().getCallingConv()); unsigned FixedObject = IsWin64 ? alignTo(AFI->getVarArgsGPRSize(), 16) : 0; - unsigned FPAdjust = isTargetDarwin(MF) ? 16 : AFI->getCalleeSavedStackSize(); + unsigned FPAdjust = isTargetDarwin(MF) + ? 16 : AFI->getCalleeSavedStackSize(MF.getFrameInfo()); return {ObjectOffset + FixedObject + FPAdjust, MVT::i8}; } @@ -1630,7 +1631,7 @@ StackOffset AArch64FrameLowering::resolveFrameOffsetReference( int FPOffset = getFPOffset(MF, ObjectOffset).getBytes(); int Offset = getStackOffset(MF, ObjectOffset).getBytes(); bool isCSR = - !isFixed && ObjectOffset >= -((int)AFI->getCalleeSavedStackSize()); + !isFixed && ObjectOffset >= -((int)AFI->getCalleeSavedStackSize(MFI)); const StackOffset &SVEStackSize = getSVEStackSize(MF); @@ -2304,6 +2305,10 @@ void AArch64FrameLowering::determineCalleeSaves(MachineFunction &MF, << EstimatedStackSize + AlignedCSStackSize << " bytes.\n"); + assert((!MFI.isCalleeSavedInfoValid() || + AFI->getCalleeSavedStackSize() == AlignedCSStackSize) && + "Should not invalidate callee saved info"); + // Round up to register pair alignment to avoid additional SP adjustment // instructions. AFI->setCalleeSavedStackSize(AlignedCSStackSize); diff --git a/llvm/lib/Target/AArch64/AArch64MachineFunctionInfo.h b/llvm/lib/Target/AArch64/AArch64MachineFunctionInfo.h index 0009fb7b552..32661860934 100644 --- a/llvm/lib/Target/AArch64/AArch64MachineFunctionInfo.h +++ b/llvm/lib/Target/AArch64/AArch64MachineFunctionInfo.h @@ -55,6 +55,7 @@ class AArch64FunctionInfo final : public MachineFunctionInfo { /// Amount of stack frame size used for saving callee-saved registers. unsigned CalleeSavedStackSize; + bool HasCalleeSavedStackSize = false; /// Number of TLS accesses using the special (combinable) /// _TLS_MODULE_BASE_ symbol. @@ -167,8 +168,55 @@ public: void setLocalStackSize(unsigned Size) { LocalStackSize = Size; } unsigned getLocalStackSize() const { return LocalStackSize; } - void setCalleeSavedStackSize(unsigned Size) { CalleeSavedStackSize = Size; } - unsigned getCalleeSavedStackSize() const { return CalleeSavedStackSize; } + void setCalleeSavedStackSize(unsigned Size) { + CalleeSavedStackSize = Size; + HasCalleeSavedStackSize = true; + } + + // When CalleeSavedStackSize has not been set (for example when + // some MachineIR pass is run in isolation), then recalculate + // the CalleeSavedStackSize directly from the CalleeSavedInfo. + // Note: This information can only be recalculated after PEI + // has assigned offsets to the callee save objects. + unsigned getCalleeSavedStackSize(const MachineFrameInfo &MFI) const { + bool ValidateCalleeSavedStackSize = false; + +#ifndef NDEBUG + // Make sure the calculated size derived from the CalleeSavedInfo + // equals the cached size that was calculated elsewhere (e.g. in + // determineCalleeSaves). + ValidateCalleeSavedStackSize = HasCalleeSavedStackSize; +#endif + + if (!HasCalleeSavedStackSize || ValidateCalleeSavedStackSize) { + assert(MFI.isCalleeSavedInfoValid() && "CalleeSavedInfo not calculated"); + if (MFI.getCalleeSavedInfo().empty()) + return 0; + + int64_t MinOffset = std::numeric_limits<int64_t>::max(); + int64_t MaxOffset = std::numeric_limits<int64_t>::min(); + for (const auto &Info : MFI.getCalleeSavedInfo()) { + int FrameIdx = Info.getFrameIdx(); + int64_t Offset = MFI.getObjectOffset(FrameIdx); + int64_t ObjSize = MFI.getObjectSize(FrameIdx); + MinOffset = std::min<int64_t>(Offset, MinOffset); + MaxOffset = std::max<int64_t>(Offset + ObjSize, MaxOffset); + } + + unsigned Size = alignTo(MaxOffset - MinOffset, 16); + assert((!HasCalleeSavedStackSize || getCalleeSavedStackSize() == Size) && + "Invalid size calculated for callee saves"); + return Size; + } + + return getCalleeSavedStackSize(); + } + + unsigned getCalleeSavedStackSize() const { + assert(HasCalleeSavedStackSize && + "CalleeSavedStackSize has not been calculated"); + return CalleeSavedStackSize; + } void incNumLocalDynamicTLSAccesses() { ++NumLocalDynamicTLSAccesses; } unsigned getNumLocalDynamicTLSAccesses() const { diff --git a/llvm/lib/Target/ARM/ARMFrameLowering.cpp b/llvm/lib/Target/ARM/ARMFrameLowering.cpp index 01ae93086dc..5428bd6c94b 100644 --- a/llvm/lib/Target/ARM/ARMFrameLowering.cpp +++ b/llvm/lib/Target/ARM/ARMFrameLowering.cpp @@ -2128,10 +2128,16 @@ void ARMFrameLowering::determineCalleeSaves(MachineFunction &MF, AFI->setLRIsSpilledForFarJump(true); } AFI->setLRIsSpilled(SavedRegs.test(ARM::LR)); +} + +void ARMFrameLowering::getCalleeSaves(const MachineFunction &MF, + BitVector &SavedRegs) const { + TargetFrameLowering::getCalleeSaves(MF, SavedRegs); // If we have the "returned" parameter attribute which guarantees that we // return the value which was passed in r0 unmodified (e.g. C++ 'structors), // record that fact for IPRA. + const ARMFunctionInfo *AFI = MF.getInfo<ARMFunctionInfo>(); if (AFI->getPreservesR0()) SavedRegs.set(ARM::R0); } diff --git a/llvm/lib/Target/ARM/ARMFrameLowering.h b/llvm/lib/Target/ARM/ARMFrameLowering.h index 6d8aee59794..0462b01af70 100644 --- a/llvm/lib/Target/ARM/ARMFrameLowering.h +++ b/llvm/lib/Target/ARM/ARMFrameLowering.h @@ -53,6 +53,8 @@ public: int ResolveFrameIndexReference(const MachineFunction &MF, int FI, unsigned &FrameReg, int SPAdj) const; + void getCalleeSaves(const MachineFunction &MF, + BitVector &SavedRegs) const override; void determineCalleeSaves(MachineFunction &MF, BitVector &SavedRegs, RegScavenger *RS) const override; |