diff options
| author | Chen Zheng <czhengsz@cn.ibm.com> | 2021-07-01 09:41:03 +0000 |
|---|---|---|
| committer | Chen Zheng <czhengsz@cn.ibm.com> | 2021-08-27 01:58:41 +0000 |
| commit | 324bd467a217d89b5ab84a8ed66c0d3dc431782a (patch) | |
| tree | e31354a71677c93b5dcd7bbb0197e0aeed282e2d | |
| parent | 088cc63640f4593a0af1fc81859853d5ee0d00ef (diff) | |
| download | llvm-324bd467a217d89b5ab84a8ed66c0d3dc431782a.zip llvm-324bd467a217d89b5ab84a8ed66c0d3dc431782a.tar.gz llvm-324bd467a217d89b5ab84a8ed66c0d3dc431782a.tar.bz2 | |
[PowerPC][ELF] make sure local variable space does not overlap with parameter save area
Reviewed By: jsji
Differential Revision: https://reviews.llvm.org/D105271
| -rw-r--r-- | llvm/lib/Target/PowerPC/PPCISelLowering.cpp | 26 | ||||
| -rw-r--r-- | llvm/test/CodeGen/PowerPC/byval.ll | 11 |
2 files changed, 22 insertions, 15 deletions
diff --git a/llvm/lib/Target/PowerPC/PPCISelLowering.cpp b/llvm/lib/Target/PowerPC/PPCISelLowering.cpp index 6d38b39f..838ac93 100644 --- a/llvm/lib/Target/PowerPC/PPCISelLowering.cpp +++ b/llvm/lib/Target/PowerPC/PPCISelLowering.cpp @@ -3878,7 +3878,8 @@ static Align CalculateStackSlotAlignment(EVT ArgVT, EVT OrigVT, /// stack slot (instead of being passed in registers). ArgOffset, /// AvailableFPRs, and AvailableVRs must hold the current argument /// position, and will be updated to account for this argument. -static bool CalculateStackSlotUsed(EVT ArgVT, EVT OrigVT, ISD::ArgFlagsTy Flags, +static bool CalculateStackSlotUsed(const PPCSubtarget &Subtarget, EVT ArgVT, + EVT OrigVT, ISD::ArgFlagsTy Flags, unsigned PtrByteSize, unsigned LinkageSize, unsigned ParamAreaSize, unsigned &ArgOffset, unsigned &AvailableFPRs, @@ -3919,7 +3920,13 @@ static bool CalculateStackSlotUsed(EVT ArgVT, EVT OrigVT, ISD::ArgFlagsTy Flags, --AvailableVRs; return false; } - } + } else if (Subtarget.isPPC64() && Subtarget.isELFv2ABI() && + Flags.getByValSize() >= 8) + // For 64-bit ELF v2, passing by value object whose size is no less than 8 + // bytes will be copied to parameter save area. This is for compatibility + // for other compiler which requires byval parameters to be stored in + // caller's parameter save area. + return true; return UseMemory; } @@ -4262,7 +4269,7 @@ SDValue PPCTargetLowering::LowerFormalArguments_64SVR4( if (Ins[i].Flags.isNest()) continue; - if (CalculateStackSlotUsed(Ins[i].VT, Ins[i].ArgVT, Ins[i].Flags, + if (CalculateStackSlotUsed(Subtarget, Ins[i].VT, Ins[i].ArgVT, Ins[i].Flags, PtrByteSize, LinkageSize, ParamAreaSize, NumBytes, AvailableFPRs, AvailableVRs)) HasParameterArea = true; @@ -4723,9 +4730,9 @@ needStackSlotPassParameters(const PPCSubtarget &Subtarget, for (const ISD::OutputArg& Param : Outs) { if (Param.Flags.isNest()) continue; - if (CalculateStackSlotUsed(Param.VT, Param.ArgVT, Param.Flags, PtrByteSize, - LinkageSize, ParamAreaSize, NumBytes, - AvailableFPRs, AvailableVRs)) + if (CalculateStackSlotUsed(Subtarget, Param.VT, Param.ArgVT, Param.Flags, + PtrByteSize, LinkageSize, ParamAreaSize, + NumBytes, AvailableFPRs, AvailableVRs)) return true; } return false; @@ -5961,9 +5968,10 @@ SDValue PPCTargetLowering::LowerCall_64SVR4( unsigned NumBytesTmp = NumBytes; for (unsigned i = 0; i != NumOps; ++i) { if (Outs[i].Flags.isNest()) continue; - if (CalculateStackSlotUsed(Outs[i].VT, Outs[i].ArgVT, Outs[i].Flags, - PtrByteSize, LinkageSize, ParamAreaSize, - NumBytesTmp, AvailableFPRs, AvailableVRs)) + if (CalculateStackSlotUsed(Subtarget, Outs[i].VT, Outs[i].ArgVT, + Outs[i].Flags, PtrByteSize, LinkageSize, + ParamAreaSize, NumBytesTmp, AvailableFPRs, + AvailableVRs)) HasParameterArea = true; } } diff --git a/llvm/test/CodeGen/PowerPC/byval.ll b/llvm/test/CodeGen/PowerPC/byval.ll index c67cc10..e6ad0f4 100644 --- a/llvm/test/CodeGen/PowerPC/byval.ll +++ b/llvm/test/CodeGen/PowerPC/byval.ll @@ -1,4 +1,3 @@ -; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py ; RUN: llc -verify-machineinstrs < %s | FileCheck %s target datalayout = "e-m:e-i64:64-n32:64-S128-v256:256:256-v512:512:512" @@ -9,15 +8,15 @@ target triple = "powerpc64le-unknown-linux-gnu" declare dso_local i32 @foo1(%struct* byval(%struct) %var) declare dso_local void @foo(%struct* %var) -; FIXME: for the byval parameter %x, now the memory for local variable and -; for parameter save area are overlap. +; for the byval parameter %x, make sure the memory for local variable and +; for parameter save area are not overlap. ; For the below case, -; the local variable space is r1 + 40 ~ r1 + 76 +; the local variable space is r1 + 104 ~ r1 + 140 ; the parameter save area is r1 + 32 ~ r1 + 68 define dso_local i32 @bar() { ; CHECK-LABEL: bar: -; CHECK: addi 30, 1, 40 +; CHECK: addi 30, 1, 104 ; CHECK: li 3, 16 ; CHECK: lxvd2x 0, 30, 3 ; CHECK: li 3, 48 @@ -25,7 +24,7 @@ define dso_local i32 @bar() { ; CHECK: li 3, 32 ; CHECK: lxvd2x 0, 0, 30 ; CHECK: stxvd2x 0, 1, 3 -; CHECK: lwz 3, 72(1) +; CHECK: lwz 3, 136(1) ; CHECK: stw 3, 64(1) entry: %x = alloca %struct, align 4 |
