-
Notifications
You must be signed in to change notification settings - Fork 13.9k
[StackColoring] Change the StackColoring logic + enables it to handle spills #143800
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
base: main
Are you sure you want to change the base?
Conversation
…neInstructionElim
…+ deal with direct fallout
You can test this locally with the following command:git-clang-format --diff HEAD~1 HEAD --extensions cpp,h -- llvm/include/llvm/CodeGen/LiveStacks.h llvm/include/llvm/CodeGen/MachineFrameInfo.h llvm/include/llvm/CodeGen/MachineInstr.h llvm/lib/CodeGen/LiveStacks.cpp llvm/lib/CodeGen/MachineFrameInfo.cpp llvm/lib/CodeGen/MachineInstr.cpp llvm/lib/CodeGen/PrologEpilogInserter.cpp llvm/lib/CodeGen/StackColoring.cpp llvm/lib/CodeGen/StackSlotColoring.cpp llvm/lib/CodeGen/TargetPassConfig.cpp View the diff from clang-format here.diff --git a/llvm/include/llvm/CodeGen/LiveStacks.h b/llvm/include/llvm/CodeGen/LiveStacks.h
index 6b0b23bd7..e87f90c28 100644
--- a/llvm/include/llvm/CodeGen/LiveStacks.h
+++ b/llvm/include/llvm/CodeGen/LiveStacks.h
@@ -41,12 +41,12 @@ class LiveStacks {
VNInfo::Allocator VNInfoAllocator;
int StartIdx = -1;
- SmallVector<LiveInterval*> S2LI;
+ SmallVector<LiveInterval *> S2LI;
SmallVector<const TargetRegisterClass *> S2RC;
public:
- using iterator = SmallVector<LiveInterval*>::iterator;
- using const_iterator = SmallVector<LiveInterval*>::const_iterator;
+ using iterator = SmallVector<LiveInterval *>::iterator;
+ using const_iterator = SmallVector<LiveInterval *>::const_iterator;
const_iterator begin() const { return S2LI.begin(); }
const_iterator end() const { return S2LI.end(); }
diff --git a/llvm/include/llvm/CodeGen/MachineFrameInfo.h b/llvm/include/llvm/CodeGen/MachineFrameInfo.h
index 8041b2829..fdb2fbd13 100644
--- a/llvm/include/llvm/CodeGen/MachineFrameInfo.h
+++ b/llvm/include/llvm/CodeGen/MachineFrameInfo.h
@@ -123,7 +123,7 @@ public:
static constexpr int NoUnderlyingSlot = std::numeric_limits<int>::min();
static constexpr int IsUnderlyingSlot = std::numeric_limits<int>::min() + 1;
- private:
+private:
// Represent a single object allocated on the stack.
struct StackObject {
// The offset of this object from the stack pointer on entry to
@@ -542,7 +542,7 @@ public:
"Invalid Object Idx!");
assert(!isDeadObjectIndex(ObjectIdx) &&
"Getting frame offset for a dead object?");
- return Objects[ObjectIdx+NumFixedObjects].Offset;
+ return Objects[ObjectIdx + NumFixedObjects].Offset;
}
bool isObjectZExt(int ObjectIdx) const {
@@ -576,7 +576,7 @@ public:
"Invalid Object Idx!");
assert(!isDeadObjectIndex(ObjectIdx) &&
"Setting frame offset for a dead object?");
- Objects[ObjectIdx+NumFixedObjects].Offset = Offset;
+ Objects[ObjectIdx + NumFixedObjects].Offset = Offset;
}
SSPLayoutKind getObjectSSPLayout(int ObjectIdx) const {
diff --git a/llvm/lib/CodeGen/LiveStacks.cpp b/llvm/lib/CodeGen/LiveStacks.cpp
index 761c5a71f..ea158b2d9 100644
--- a/llvm/lib/CodeGen/LiveStacks.cpp
+++ b/llvm/lib/CodeGen/LiveStacks.cpp
@@ -56,7 +56,7 @@ LiveStacks::getOrCreateInterval(int Slot, const TargetRegisterClass *RC) {
assert(Slot >= 0 && "Spill slot indice must be >= 0");
if (StartIdx == -1)
StartIdx = Slot;
-
+
int Idx = Slot - StartIdx;
assert(Idx >= 0 && "Slot not in order ?");
if (Idx < (int)S2LI.size()) {
diff --git a/llvm/lib/CodeGen/MachineFrameInfo.cpp b/llvm/lib/CodeGen/MachineFrameInfo.cpp
index 5b9974962..4e65f8949 100644
--- a/llvm/lib/CodeGen/MachineFrameInfo.cpp
+++ b/llvm/lib/CodeGen/MachineFrameInfo.cpp
@@ -13,7 +13,6 @@
#include "llvm/CodeGen/MachineFrameInfo.h"
#include "llvm/ADT/BitVector.h"
-#include "llvm/IR/Instructions.h"
#include "llvm/CodeGen/MachineFunction.h"
#include "llvm/CodeGen/MachineRegisterInfo.h"
#include "llvm/CodeGen/TargetFrameLowering.h"
@@ -21,6 +20,7 @@
#include "llvm/CodeGen/TargetRegisterInfo.h"
#include "llvm/CodeGen/TargetSubtargetInfo.h"
#include "llvm/Config/llvm-config.h"
+#include "llvm/IR/Instructions.h"
#include "llvm/Support/Debug.h"
#include "llvm/Support/raw_ostream.h"
#include <cassert>
@@ -100,8 +100,7 @@ int MachineFrameInfo::CreateFixedObject(uint64_t Size, int64_t Offset,
return -++NumFixedObjects;
}
-int MachineFrameInfo::CreateFixedSpillStackObject(uint64_t Size,
- int64_t Offset,
+int MachineFrameInfo::CreateFixedSpillStackObject(uint64_t Size, int64_t Offset,
bool IsImmutable) {
Align Alignment =
commonAlignment(ForcedRealign ? Align(1) : StackAlignment, Offset);
diff --git a/llvm/lib/CodeGen/PrologEpilogInserter.cpp b/llvm/lib/CodeGen/PrologEpilogInserter.cpp
index d006e3984..7a44b3937 100644
--- a/llvm/lib/CodeGen/PrologEpilogInserter.cpp
+++ b/llvm/lib/CodeGen/PrologEpilogInserter.cpp
@@ -696,9 +696,9 @@ void PEIImpl::spillCalleeSavedRegs(MachineFunction &MF) {
static inline void UpdateOffset(MachineFrameInfo &MFI, int FrameIdx,
int64_t Offset) {
- LLVM_DEBUG(dbgs() << "alloc FI(" << FrameIdx << ") at SP[" << Offset
- << "]\n");
- MFI.setObjectOffset(FrameIdx, Offset); // Set the computed offset
+ LLVM_DEBUG(dbgs() << "alloc FI(" << FrameIdx << ") at SP[" << Offset
+ << "]\n");
+ MFI.setObjectOffset(FrameIdx, Offset); // Set the computed offset
}
/// AdjustStackOffset - Helper function used to adjust the stack frame offset.
|
I am willing to take a look, but for various reasons I won't be able to dig in for a couple of months (I am away from my work computers). Hope you can make progress without my eyeballs for now. Thanks. |
The cleanup commits look reasonable; please submit them separately. The IR representation of lifetimes has some pretty significant issues (see #45725 (comment) , #51838, #132085, #43674). Will this cause those issues to be exposed more frequently? |
Yes,
Here are my thoughts on the problems in general, I think there is 2 distinct issues: IR transformation moving accesses out of lifetime, causing UB: About the question, original question: |
Here is a patch set I have been working on to reduce stack usage.
It starts with a bunch if trivial NFC-like commits, that can be easily handled separately
Then a replacement of the StackColoring algorithm, with all the original analysis and assumption kept.
Finally changes to allow the new algo in StackColoring to operate on spill slots
I know that lifetime annotations are a mess, so I tried to not change any of the assumptions made by the old StackColoring.
here is some examples of the current stack coloring's shortcoming:
one of the int will be merged with the array, and thats it.
when all 4 ints could share the space with the array
The current StackColoring is not capable of re-using the same storage for all 3 of these arrays
Even if its the example given in the comments of StackColoring.
Both those issues are fixed by the Algorithm change
StackColoring had TODO's about this issue and handling spill slots at the same time as regular slots
This patch set adds 2 options used to do the testing.
-mllvm -new-stack-coloring, this swaps out the algorithm for stack-coloring.
-mllvm -merged-stack-coloring, this moves stack-coloring after regalloc instead of stack-slot-coloring
I have not yet updated tests because all of the work is behind options
and didn't added golden tests YET because the code has kept changing. But I obviously will add tests. before any merging.
Testing Done on this patch:
Benchmark results (mean):
Note: all benchmarks are done with release with assert build, on the llvm-test-suite
With max-candidates=unlimited, because it doesn't seem to have much impact on compile-time.
I suspect this is caused by some frequently accessed slot not being close to the sp,
leading to larger variants of the instruction being used. But I need to investigate
Note: The cleanup of the git history was only partial for now, its intended mostly help review.