summaryrefslogtreecommitdiffstats
path: root/llvm/lib/CodeGen/SimpleRegisterCoalescing.cpp
diff options
context:
space:
mode:
authorJakob Stoklund Olesen <stoklund@2pi.dk>2011-05-17 16:38:37 +0000
committerJakob Stoklund Olesen <stoklund@2pi.dk>2011-05-17 16:38:37 +0000
commit52375e6a01a0dd8a8c1fbc197316ec5868edc14c (patch)
tree5e6f1540564dd4caf68d682ad50049517230ba7e /llvm/lib/CodeGen/SimpleRegisterCoalescing.cpp
parent314d07b51c6300a2095a0b0ac1d222d3bf3d9e2a (diff)
downloadbcm5719-llvm-52375e6a01a0dd8a8c1fbc197316ec5868edc14c.tar.gz
bcm5719-llvm-52375e6a01a0dd8a8c1fbc197316ec5868edc14c.zip
Tweak cross-class coalescing to be more aggressive when the target class is small.
The greedy register allocator has live range splitting and register class inflation, so it can actually fully undo this join, including restoring the original register classes. We still don't want to do this for long live ranges, mostly because of the high register pressure of there are many constrained live ranges overlapping. llvm-svn: 131466
Diffstat (limited to 'llvm/lib/CodeGen/SimpleRegisterCoalescing.cpp')
-rw-r--r--llvm/lib/CodeGen/SimpleRegisterCoalescing.cpp12
1 files changed, 9 insertions, 3 deletions
diff --git a/llvm/lib/CodeGen/SimpleRegisterCoalescing.cpp b/llvm/lib/CodeGen/SimpleRegisterCoalescing.cpp
index cebf4c9f4a5..1a2151fecf2 100644
--- a/llvm/lib/CodeGen/SimpleRegisterCoalescing.cpp
+++ b/llvm/lib/CodeGen/SimpleRegisterCoalescing.cpp
@@ -987,8 +987,14 @@ SimpleRegisterCoalescing::isWinToJoinCrossClass(unsigned SrcReg,
LiveInterval &DstInt = li_->getInterval(DstReg);
unsigned SrcSize = li_->getApproximateInstructionCount(SrcInt);
unsigned DstSize = li_->getApproximateInstructionCount(DstInt);
- if (SrcSize <= NewRCCount && DstSize <= NewRCCount)
+
+ // Coalesce aggressively if the intervals are small compared to the number of
+ // registers in the new class. The number 4 is fairly arbitrary, chosen to be
+ // less aggressive than the 8 used for the whole function size.
+ const unsigned ThresSize = 4 * NewRCCount;
+ if (SrcSize <= ThresSize && DstSize <= ThresSize)
return true;
+
// Estimate *register use density*. If it doubles or more, abort.
unsigned SrcUses = std::distance(mri_->use_nodbg_begin(SrcReg),
mri_->use_nodbg_end());
@@ -996,12 +1002,12 @@ SimpleRegisterCoalescing::isWinToJoinCrossClass(unsigned SrcReg,
mri_->use_nodbg_end());
unsigned NewUses = SrcUses + DstUses;
unsigned NewSize = SrcSize + DstSize;
- if (SrcRC != NewRC && SrcSize > NewRCCount) {
+ if (SrcRC != NewRC && SrcSize > ThresSize) {
unsigned SrcRCCount = allocatableRCRegs_[SrcRC].count();
if (NewUses*SrcSize*SrcRCCount > 2*SrcUses*NewSize*NewRCCount)
return false;
}
- if (DstRC != NewRC && DstSize > NewRCCount) {
+ if (DstRC != NewRC && DstSize > ThresSize) {
unsigned DstRCCount = allocatableRCRegs_[DstRC].count();
if (NewUses*DstSize*DstRCCount > 2*DstUses*NewSize*NewRCCount)
return false;
OpenPOWER on IntegriCloud