diff options
| author | Chris Lattner <sabre@nondot.org> | 2006-04-12 18:09:35 +0000 |
|---|---|---|
| committer | Chris Lattner <sabre@nondot.org> | 2006-04-12 18:09:35 +0000 |
| commit | b19a5c661b750f96967c10b1a1764312d417fb2d (patch) | |
| tree | 8085a40bafc7347cc14cb80ec1c76ebd8e187ff8 /llvm/lib/Transforms | |
| parent | bd4a2032084e2056814aa7e0ee824ec983b92a57 (diff) | |
| download | bcm5719-llvm-b19a5c661b750f96967c10b1a1764312d417fb2d.tar.gz bcm5719-llvm-b19a5c661b750f96967c10b1a1764312d417fb2d.zip | |
Turn casts into getelementptr's when possible. This enables SROA to be more
aggressive in some cases where LLVMGCC 4 is inserting casts for no reason.
This implements InstCombine/cast.ll:test27/28.
llvm-svn: 27620
Diffstat (limited to 'llvm/lib/Transforms')
| -rw-r--r-- | llvm/lib/Transforms/Scalar/InstructionCombining.cpp | 23 |
1 files changed, 23 insertions, 0 deletions
diff --git a/llvm/lib/Transforms/Scalar/InstructionCombining.cpp b/llvm/lib/Transforms/Scalar/InstructionCombining.cpp index f79a48e3bda..f9b01c7a30d 100644 --- a/llvm/lib/Transforms/Scalar/InstructionCombining.cpp +++ b/llvm/lib/Transforms/Scalar/InstructionCombining.cpp @@ -4813,7 +4813,30 @@ Instruction *InstCombiner::visitCastInst(CastInst &CI) { if (isa<PHINode>(Src)) if (Instruction *NV = FoldOpIntoPhi(CI)) return NV; + + // If the source and destination are pointers, and this cast is equivalent to + // a getelementptr X, 0, 0, 0... turn it into the appropriate getelementptr. + // This can enhance SROA and other transforms that want type-safe pointers. + if (const PointerType *DstPTy = dyn_cast<PointerType>(CI.getType())) + if (const PointerType *SrcPTy = dyn_cast<PointerType>(Src->getType())) { + const Type *DstTy = DstPTy->getElementType(); + const Type *SrcTy = SrcPTy->getElementType(); + + Constant *ZeroUInt = Constant::getNullValue(Type::UIntTy); + unsigned NumZeros = 0; + while (SrcTy != DstTy && + isa<CompositeType>(SrcTy) && !isa<PointerType>(SrcTy)) { + SrcTy = cast<CompositeType>(SrcTy)->getTypeAtIndex(ZeroUInt); + ++NumZeros; + } + // If we found a path from the src to dest, create the getelementptr now. + if (SrcTy == DstTy) { + std::vector<Value*> Idxs(NumZeros+1, ZeroUInt); + return new GetElementPtrInst(Src, Idxs); + } + } + // If the source value is an instruction with only this use, we can attempt to // propagate the cast into the instruction. Also, only handle integral types // for now. |

