From dfa332f927de3385f63acc807460e005f2fc1d41 Mon Sep 17 00:00:00 2001 From: Tim Northover Date: Tue, 17 Jan 2017 22:43:34 +0000 Subject: [PATCH] GlobalISel: add callseq instructions to record stack usage git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@292284 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Target/AArch64/AArch64CallLowering.cpp | 11 ++++++++++- test/CodeGen/AArch64/GlobalISel/call-translator.ll | 4 ++++ 2 files changed, 14 insertions(+), 1 deletion(-) diff --git a/lib/Target/AArch64/AArch64CallLowering.cpp b/lib/Target/AArch64/AArch64CallLowering.cpp index 7efee8bf8c2..4f5b2886b1a 100644 --- a/lib/Target/AArch64/AArch64CallLowering.cpp +++ b/lib/Target/AArch64/AArch64CallLowering.cpp @@ -97,7 +97,7 @@ struct OutgoingArgHandler : public CallLowering::ValueHandler { MachineInstrBuilder MIB, CCAssignFn *AssignFn, CCAssignFn *AssignFnVarArg) : ValueHandler(MIRBuilder, MRI, AssignFn), MIB(MIB), - AssignFnVarArg(AssignFnVarArg) {} + AssignFnVarArg(AssignFnVarArg), StackSize(0) {} unsigned getStackAddress(uint64_t Size, int64_t Offset, MachinePointerInfo &MPO) override { @@ -113,6 +113,7 @@ struct OutgoingArgHandler : public CallLowering::ValueHandler { MIRBuilder.buildGEP(AddrReg, SPReg, OffsetReg); MPO = MachinePointerInfo::getStack(MIRBuilder.getMF(), Offset); + StackSize = std::max(StackSize, Size + Offset); return AddrReg; } @@ -141,6 +142,7 @@ struct OutgoingArgHandler : public CallLowering::ValueHandler { MachineInstrBuilder MIB; CCAssignFn *AssignFnVarArg; + uint64_t StackSize; }; void AArch64CallLowering::splitToValueTypes( @@ -275,6 +277,8 @@ bool AArch64CallLowering::lowerCall(MachineIRBuilder &MIRBuilder, CCAssignFn *AssignFnVarArg = TLI.CCAssignFnForCall(F.getCallingConv(), /*IsVarArg=*/true); + auto CallSeqStart = MIRBuilder.buildInstr(AArch64::ADJCALLSTACKDOWN); + // Create a temporarily-floating call instruction so we can add the implicit // uses of arg registers. auto MIB = MIRBuilder.buildInstrNoInsert(Callee.isReg() ? AArch64::BLR @@ -329,5 +333,10 @@ bool AArch64CallLowering::lowerCall(MachineIRBuilder &MIRBuilder, MIRBuilder.buildSequence(OrigRet.Reg, SplitRegs, RegOffsets); } + CallSeqStart.addImm(Handler.StackSize); + MIRBuilder.buildInstr(AArch64::ADJCALLSTACKUP) + .addImm(Handler.StackSize) + .addImm(0); + return true; } diff --git a/test/CodeGen/AArch64/GlobalISel/call-translator.ll b/test/CodeGen/AArch64/GlobalISel/call-translator.ll index 7bedad38de1..f9c0fdb5bb2 100644 --- a/test/CodeGen/AArch64/GlobalISel/call-translator.ll +++ b/test/CodeGen/AArch64/GlobalISel/call-translator.ll @@ -1,7 +1,9 @@ ; RUN: llc -mtriple=aarch64-linux-gnu -O0 -stop-after=irtranslator -global-isel -verify-machineinstrs %s -o - 2>&1 | FileCheck %s ; CHECK-LABEL: name: test_trivial_call +; CHECK: ADJCALLSTACKDOWN 0, implicit-def %sp, implicit %sp ; CHECK: BL @trivial_callee, csr_aarch64_aapcs, implicit-def %lr +; CHECK: ADJCALLSTACKUP 0, 0, implicit-def %sp, implicit %sp declare void @trivial_callee() define void @test_trivial_call() { call void @trivial_callee() @@ -168,6 +170,7 @@ define void @test_stack_slots([8 x i64], i64 %lhs, i64 %rhs, i64* %addr) { ; CHECK: [[C42:%[0-9]+]](s64) = G_CONSTANT i64 42 ; CHECK: [[C12:%[0-9]+]](s64) = G_CONSTANT i64 12 ; CHECK: [[PTR:%[0-9]+]](p0) = G_CONSTANT i64 0 +; CHECK: ADJCALLSTACKDOWN 24, implicit-def %sp, implicit %sp ; CHECK: [[SP:%[0-9]+]](p0) = COPY %sp ; CHECK: [[C42_OFFS:%[0-9]+]](s64) = G_CONSTANT i64 0 ; CHECK: [[C42_LOC:%[0-9]+]](p0) = G_GEP [[SP]], [[C42_OFFS]](s64) @@ -181,6 +184,7 @@ define void @test_stack_slots([8 x i64], i64 %lhs, i64 %rhs, i64* %addr) { ; CHECK: [[PTR_LOC:%[0-9]+]](p0) = G_GEP [[SP]], [[PTR_OFFS]](s64) ; CHECK: G_STORE [[PTR]](p0), [[PTR_LOC]](p0) :: (store 8 into stack + 16, align 0) ; CHECK: BL @test_stack_slots +; CHECK: ADJCALLSTACKUP 24, 0, implicit-def %sp, implicit %sp define void @test_call_stack() { call void @test_stack_slots([8 x i64] undef, i64 42, i64 12, i64* null) ret void -- 2.40.0