summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorOwen Anderson <resistor@mac.com>2010-09-20 20:39:59 +0000
committerOwen Anderson <resistor@mac.com>2010-09-20 20:39:59 +0000
commit4a9f150926d593b30354db76d8d061fe4c9d124d (patch)
treef6470be3ce76c543587a91e9a1de1ce2d1018255
parent1dc335a79f5e899aacc6710dfe08ef20abb6a6c0 (diff)
downloadllvm-4a9f150926d593b30354db76d8d061fe4c9d124d.tar.gz
llvm-4a9f150926d593b30354db76d8d061fe4c9d124d.tar.bz2
llvm-4a9f150926d593b30354db76d8d061fe4c9d124d.tar.xz
When TCO is turned on, it is possible to end up with aliasing FrameIndex's. Therefore,
CombinerAA cannot assume that different FrameIndex's never alias, but can instead use MachineFrameInfo to get the actual offsets of these slots and check for actual aliasing. This fixes CodeGen/X86/2010-02-19-TailCallRetAddrBug.ll and CodeGen/X86/tailcallstack64.ll when CombinerAA is enabled, modulo a different register allocation sequence. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@114348 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--lib/CodeGen/SelectionDAG/DAGCombiner.cpp15
-rw-r--r--test/CodeGen/X86/2010-09-17-SideEffectsInChain.ll8
2 files changed, 17 insertions, 6 deletions
diff --git a/lib/CodeGen/SelectionDAG/DAGCombiner.cpp b/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
index c9c4d91e97..91e370b271 100644
--- a/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
+++ b/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
@@ -7030,8 +7030,19 @@ bool DAGCombiner::isAlias(SDValue Ptr1, int64_t Size1,
if (Base1 == Base2 || (GV1 && (GV1 == GV2)) || (CV1 && (CV1 == CV2)))
return !((Offset1 + Size1) <= Offset2 || (Offset2 + Size2) <= Offset1);
- // If we know what the bases are, and they aren't identical, then we know they
- // cannot alias.
+ // It is possible for different frame indices to alias each other, mostly
+ // when tail call optimization reuses return address slots for arguments.
+ // To catch this case, look up the actual index of frame indices to compute
+ // the real alias relationship.
+ if (isFrameIndex1 && isFrameIndex2) {
+ MachineFrameInfo *MFI = DAG.getMachineFunction().getFrameInfo();
+ Offset1 += MFI->getObjectOffset(cast<FrameIndexSDNode>(Base1)->getIndex());
+ Offset2 += MFI->getObjectOffset(cast<FrameIndexSDNode>(Base2)->getIndex());
+ return !((Offset1 + Size1) <= Offset2 || (Offset2 + Size2) <= Offset1);
+ }
+
+ // Otherwise, if we know what the bases are, and they aren't identical, then
+ // we know they cannot alias.
if ((isFrameIndex1 || CV1 || GV1) && (isFrameIndex2 || CV2 || GV2))
return false;
diff --git a/test/CodeGen/X86/2010-09-17-SideEffectsInChain.ll b/test/CodeGen/X86/2010-09-17-SideEffectsInChain.ll
index 35434ffafa..8fe0309421 100644
--- a/test/CodeGen/X86/2010-09-17-SideEffectsInChain.ll
+++ b/test/CodeGen/X86/2010-09-17-SideEffectsInChain.ll
@@ -19,8 +19,8 @@ entry:
}
; CHECK: movq ___stack_chk_guard@GOTPCREL(%rip), %rax
-; CHECK: movb (%rsp), %dl
-; CHECK-NEXT: movb 30(%rsp), %sil
-; CHECK: movb %dl, (%rsp)
-; CHECK-NEXT: movb %sil, 30(%rsp)
+; CHECK: movb 30(%rsp), %dl
+; CHECK: movb (%rsp), %sil
+; CHECK: movb %sil, (%rsp)
+; CHECK: movb %dl, 30(%rsp)
; CHECK: callq ___stack_chk_fail