mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-02-21 21:29:41 +00:00
SimplifyCFG: Omit range checks for switch lookup tables when default is unreachable
They would get optimized away later, but we might as well not emit them. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@223051 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
b2fd944378
commit
07c6024f48
@ -4134,19 +4134,20 @@ static bool SwitchToLookupTable(SwitchInst *SI,
|
||||
"It is impossible for a switch to have more entries than the max "
|
||||
"representable value of its input integer type's size.");
|
||||
|
||||
// If we have a fully covered lookup table, unconditionally branch to the
|
||||
// lookup table BB. Otherwise, check if the condition value is within the case
|
||||
// range. If it is so, branch to the new BB. Otherwise branch to SI's default
|
||||
// destination.
|
||||
// If the default destination is unreachable, or if the lookup table covers
|
||||
// all values of the conditional variable, branch directly to the lookup table
|
||||
// BB. Otherwise, check that the condition is within the case range.
|
||||
const bool DefaultIsReachable =
|
||||
!isa<UnreachableInst>(SI->getDefaultDest()->getFirstNonPHIOrDbg());
|
||||
const bool GeneratingCoveredLookupTable = (MaxTableSize == TableSize);
|
||||
BranchInst *RangeCheckBranch = nullptr;
|
||||
|
||||
const bool GeneratingCoveredLookupTable = MaxTableSize == TableSize;
|
||||
if (GeneratingCoveredLookupTable) {
|
||||
if (!DefaultIsReachable || GeneratingCoveredLookupTable) {
|
||||
Builder.CreateBr(LookupBB);
|
||||
// We cached PHINodes in PHIs, to avoid accessing deleted PHINodes later,
|
||||
// do not delete PHINodes here.
|
||||
SI->getDefaultDest()->removePredecessor(SI->getParent(),
|
||||
true/*DontDeleteUselessPHIs*/);
|
||||
true /*DontDeleteUselessPHIs*/);
|
||||
} else {
|
||||
Value *Cmp = Builder.CreateICmpULT(TableIndex, ConstantInt::get(
|
||||
MinCaseVal->getType(), TableSize));
|
||||
|
@ -781,6 +781,35 @@ return:
|
||||
; CHECK: getelementptr inbounds [9 x i32]* @switch.table6, i32 0, i32 %switch.tableidx
|
||||
}
|
||||
|
||||
define i32 @unreachable_default(i32 %x) {
|
||||
entry:
|
||||
switch i32 %x, label %default [
|
||||
i32 0, label %bb0
|
||||
i32 1, label %bb1
|
||||
i32 2, label %bb2
|
||||
i32 3, label %bb3
|
||||
]
|
||||
|
||||
bb0: br label %return
|
||||
bb1: br label %return
|
||||
bb2: br label %return
|
||||
bb3: br label %return
|
||||
default: unreachable
|
||||
|
||||
return:
|
||||
%retval = phi i32 [ 42, %bb0 ], [ 52, %bb1 ], [ 1, %bb2 ], [ 2, %bb3 ]
|
||||
ret i32 %retval
|
||||
|
||||
; CHECK-LABEL: @unreachable_default(
|
||||
; CHECK: entry:
|
||||
; CHECK-NEXT: %switch.tableidx = sub i32 %x, 0
|
||||
; CHECK-NOT: icmp
|
||||
; CHECK-NOT: br 1i
|
||||
; CHECK-NEXT: %switch.gep = getelementptr inbounds [4 x i32]* @switch.table7, i32 0, i32 %switch.tableidx
|
||||
; CHECK-NEXT: %switch.load = load i32* %switch.gep
|
||||
; CHECK-NEXT: ret i32 %switch.load
|
||||
}
|
||||
|
||||
; Don't create a table with illegal type
|
||||
define i96 @illegaltype(i32 %c) {
|
||||
entry:
|
||||
|
Loading…
x
Reference in New Issue
Block a user