summaryrefslogtreecommitdiffstats
path: root/llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp
diff options
context:
space:
mode:
authorDavid Blaikie <dblaikie@gmail.com>2015-03-24 21:50:35 +0000
committerDavid Blaikie <dblaikie@gmail.com>2015-03-24 21:50:35 +0000
commit1a6bb9fcf6ea8e917b7fdcb9cf6ff76b79ec6985 (patch)
tree44287548425d0f50a231cadabdfdffe5554c2c71 /llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp
parent8b4817b5f7b710d98cdb8cc4a85da0450a8786de (diff)
downloadbcm5719-llvm-1a6bb9fcf6ea8e917b7fdcb9cf6ff76b79ec6985.tar.gz
bcm5719-llvm-1a6bb9fcf6ea8e917b7fdcb9cf6ff76b79ec6985.zip
Revert "Remove an InstCombine that seems to have become redundant."
Assertion fires in compiler-rt. Guess it does fire.. This reverts commit r233116. llvm-svn: 233121
Diffstat (limited to 'llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp')
-rw-r--r--llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp41
1 files changed, 28 insertions, 13 deletions
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp
index 94883cab12a..0625d8deca0 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp
@@ -1455,20 +1455,35 @@ Instruction *InstCombiner::commonPointerCastTransforms(CastInst &CI) {
// GEP computes a constant offset, see if we can convert these three
// instructions into fewer. This typically happens with unions and other
// non-type-safe code.
- // Looks like this never actually fires due to bitcast+gep folding happening
- // in InstCombiner::visitGetElementPtrInst where the bitcast operand to a
- // gep is folded into the gep if possible, before we consider whether that
- // gep is used in a bitcast as well.
- // Let's assert that this wouldn't fire just to be sure.
-#ifndef NDEBUG
- APInt Offset(DL.getPointerSizeInBits(GEP->getPointerAddressSpace()), 0);
+ unsigned AS = GEP->getPointerAddressSpace();
+ unsigned OffsetBits = DL.getPointerSizeInBits(AS);
+ APInt Offset(OffsetBits, 0);
BitCastInst *BCI = dyn_cast<BitCastInst>(GEP->getOperand(0));
- SmallVector<Value *, 8> NewIndices;
- assert(!BCI || !GEP->hasOneUse() ||
- !GEP->accumulateConstantOffset(DL, Offset) ||
- !FindElementAtOffset(BCI->getOperand(0)->getType(),
- Offset.getSExtValue(), NewIndices));
-#endif
+ if (GEP->hasOneUse() && BCI && GEP->accumulateConstantOffset(DL, Offset)) {
+ // FIXME: This is insufficiently tested - just a no-crash test
+ // (test/Transforms/InstCombine/2007-05-14-Crash.ll)
+ //
+ // Get the base pointer input of the bitcast, and the type it points to.
+ Value *OrigBase = BCI->getOperand(0);
+ SmallVector<Value*, 8> NewIndices;
+ if (FindElementAtOffset(OrigBase->getType(), Offset.getSExtValue(),
+ NewIndices)) {
+ // FIXME: This codepath is completely untested - could be unreachable
+ // for all I know.
+ // If we were able to index down into an element, create the GEP
+ // and bitcast the result. This eliminates one bitcast, potentially
+ // two.
+ Value *NGEP = cast<GEPOperator>(GEP)->isInBounds() ?
+ Builder->CreateInBoundsGEP(OrigBase, NewIndices) :
+ Builder->CreateGEP(OrigBase, NewIndices);
+ NGEP->takeName(GEP);
+
+ if (isa<BitCastInst>(CI))
+ return new BitCastInst(NGEP, CI.getType());
+ assert(isa<PtrToIntInst>(CI));
+ return new PtrToIntInst(NGEP, CI.getType());
+ }
+ }
}
return commonCastTransforms(CI);
OpenPOWER on IntegriCloud