Skip to content

[StackColoring] Delete dead stack slots #75351

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Dec 15, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 18 additions & 2 deletions llvm/lib/CodeGen/StackColoring.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -900,6 +900,15 @@ void StackColoring::remapInstructions(DenseMap<int, int> &SlotRemap) {
unsigned FixedMemOp = 0;
unsigned FixedDbg = 0;

// Remove debug information for deleted slots.
erase_if(MF->getVariableDbgInfo(), [&](auto &VI) {
if (!VI.inStackSlot())
return false;
int Slot = VI.getStackSlot();
return Slot >= 0 && Intervals[Slot]->empty() &&
InterestingSlots.test(Slot) && !ConservativeSlots.test(Slot);
});

// Remap debug information that refers to stack slots.
for (auto &VI : MF->getVariableDbgInfo()) {
if (!VI.Var || !VI.inStackSlot())
Expand Down Expand Up @@ -1250,8 +1259,15 @@ bool StackColoring::runOnMachineFunction(MachineFunction &Func) {

// Do not bother looking at empty intervals.
for (unsigned I = 0; I < NumSlots; ++I) {
if (Intervals[SortedSlots[I]]->empty())
int Slot = SortedSlots[I];
if (Intervals[Slot]->empty()) {
if (InterestingSlots.test(Slot) && !ConservativeSlots.test(Slot)) {
RemovedSlots += 1;
ReducedSize += MFI->getObjectSize(Slot);
MFI->RemoveStackObject(Slot);
}
SortedSlots[I] = -1;
}
}

// This is a simple greedy algorithm for merging allocas. First, sort the
Expand Down Expand Up @@ -1339,7 +1355,7 @@ bool StackColoring::runOnMachineFunction(MachineFunction &Func) {

// Scan the entire function and update all machine operands that use frame
// indices to use the remapped frame index.
if (!SlotRemap.empty()) {
if (RemovedSlots > 0) {
expungeSlotMap(SlotRemap, NumSlots);
remapInstructions(SlotRemap);
}
Expand Down
1 change: 0 additions & 1 deletion llvm/test/CodeGen/PowerPC/aix32-cc-abi-vaarg.ll
Original file line number Diff line number Diff line change
Expand Up @@ -347,7 +347,6 @@ entry:

; 32BIT-LABEL: stack:
; 32BIT-DAG: - { id: 0, name: arg1, type: default, offset: 0, size: 4, alignment: 4,
; 32BIT-DAG: - { id: 1, name: arg2, type: default, offset: 0, size: 4, alignment: 4,
; 32BIT-DAG: - { id: 2, name: '', type: default, offset: 0, size: 8, alignment: 8,
; 32BIT-DAG: - { id: 3, name: '', type: default, offset: 0, size: 8, alignment: 8,

Expand Down
8 changes: 2 additions & 6 deletions llvm/test/CodeGen/PowerPC/aix64-cc-abi-vaarg.ll
Original file line number Diff line number Diff line change
Expand Up @@ -138,9 +138,7 @@
; 64BIT-LABEL: fixedStack:
; 64BIT-DAG: - { id: 0, type: default, offset: 112, size: 8, alignment: 16, stack-id: default,

; 64BIT-LABEL: stack:
; 64BIT-DAG: - { id: 0, name: arg1, type: default, offset: 0, size: 8, alignment: 8,
; 64BIT-DAG: - { id: 1, name: arg2, type: default, offset: 0, size: 8, alignment: 8,
; 64BIT-LABEL: stack: []

; 64BIT-LABEL: body: |
; 64BIT-DAG: liveins: $x3, $x4, $x5, $x6, $x7, $x8, $x9, $x10
Expand Down Expand Up @@ -305,9 +303,7 @@
; 64BIT-LABEL: fixedStack:
; 64BIT-DAG: - { id: 0, type: default, offset: 152, size: 8

; 64BIT-LABEL: stack:
; 64BIT-DAG: - { id: 0, name: arg1, type: default, offset: 0, size: 8
; 64BIT-DAG: - { id: 1, name: arg2, type: default, offset: 0, size: 8
; 64BIT-LABEL: stack: []

; 64BIT-LABEL: body: |
; 64BIT-DAG: liveins: $f1, $f2, $f3, $f4, $f5, $f6, $f7, $f8, $f9, $f10, $f11, $f12, $f13
Expand Down
25 changes: 25 additions & 0 deletions llvm/test/CodeGen/RISCV/dead-stack-slot.ll
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
; RUN: llc -mtriple=riscv32 -verify-machineinstrs < %s \
; RUN: | FileCheck %s
; RUN: llc -mtriple=riscv64 -verify-machineinstrs < %s \
; RUN: | FileCheck %s

; Remove the lifetime-marked alloca, but not the unmarked one.
define signext i32 @f1() nounwind {
; CHECK-LABEL: f1:
; CHECK: # %bb.0:
; CHECK-NEXT: addi sp, sp, -32
; CHECK-NEXT: li a0, 0
; CHECK-NEXT: addi sp, sp, 32
; CHECK-NEXT: ret
%1 = alloca [32 x i8], align 4
%2 = alloca [32 x i8], align 4
%3 = getelementptr inbounds [32 x i8], ptr %1, i64 0, i64 0
call void @llvm.lifetime.start.p0(i64 32, ptr nonnull %3)
call void @llvm.lifetime.end.p0(i64 32, ptr nonnull %3)
ret i32 0
}

declare void @llvm.lifetime.start.p0(i64 immarg, ptr nocapture)
declare void @llvm.lifetime.end.p0(i64 immarg, ptr nocapture)

2 changes: 1 addition & 1 deletion llvm/test/CodeGen/X86/StackColoring-tbaa.mir
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ body: |
; CHECK: [[LEA64r:%[0-9]+]]:gr64 = nuw LEA64r %stack.1.agg, 1, $noreg, 24, $noreg
; CHECK-NEXT: CMP8mi %stack.1.agg, 1, $noreg, 47, $noreg, 0, implicit-def $eflags :: (dereferenceable load (s8) from %ir.a22, !tbaa !2)
; CHECK-NEXT: [[CMOV64rm:%[0-9]+]]:gr64 = CMOV64rm [[LEA64r]], %stack.1.agg, 1, $noreg, 24, $noreg, 8, implicit $eflags :: (dereferenceable load (s64) from %ir.a2)
; CHECK-NEXT: [[MOV8rm:%[0-9]+]]:gr8 = MOV8rm killed [[CMOV64rm]], 1, $noreg, 16, $noreg :: (load (s8) from %ir.add.ptr.i, !tbaa !2)
; CHECK-NEXT: [[MOV8rm:%[0-9]+]]:gr8 = MOV8rm killed [[CMOV64rm]], 1, $noreg, 16, $noreg :: (load (s8) from %ir.add.ptr.i)
; CHECK-NEXT: $al = COPY [[MOV8rm]]
; CHECK-NEXT: RET 0, $al
LIFETIME_START %stack.0.padding
Expand Down
24 changes: 2 additions & 22 deletions llvm/test/DebugInfo/COFF/lexicalblock.ll
Original file line number Diff line number Diff line change
Expand Up @@ -63,32 +63,12 @@
; CHECK: LocalSym {
; CHECK: VarName: localA
; CHECK: }
; CHECK: LocalSym {
; CHECK: VarName: localB
; CHECK: }
; CHECK: BlockSym {
; CHECK: Kind: S_BLOCK32 {{.*}}
; CHECK: BlockName:
; CHECK: }
; CHECK: ScopeEndSym {
; CHECK: Kind: S_END {{.*}}
; CHECK: }
; CHECK: BlockSym {
; CHECK: Kind: S_BLOCK32 {{.*}}
; CHECK: BlockName:
; CHECK: }
; CHECK: ScopeEndSym {
; CHECK: Kind: S_END {{.*}}
; CHECK: }
; CHECK: BlockSym {
; CHECK: Kind: S_BLOCK32 {{.*}}
; CHECK: BlockName:
; CHECK: }
; CHECK: ScopeEndSym {
; CHECK: }
; CHECK: BlockSym {
; CHECK: Kind: S_BLOCK32 {{.*}}
; CHECK: BlockName:
; CHECK: LocalSym {
; CHECK: VarName: localB
; CHECK: }
; CHECK: ScopeEndSym {
; CHECK: Kind: S_END {{.*}}
Expand Down