///
static Value *DecomposeSimpleLinearExpr(Value *Val, unsigned &Scale,
int &Offset) {
- assert(Val->getType() == Type::getInt32Ty(Val->getContext()) &&
- "Unexpected allocation size type!");
+ assert(Val->getType()->isInteger(32) && "Unexpected allocation size type!");
if (ConstantInt *CI = dyn_cast<ConstantInt>(Val)) {
Offset = CI->getZExtValue();
Scale = 0;
return ConstantInt::get(Type::getInt32Ty(Val->getContext()), 0);
- } else if (BinaryOperator *I = dyn_cast<BinaryOperator>(Val)) {
+ }
+
+ if (BinaryOperator *I = dyn_cast<BinaryOperator>(Val)) {
if (ConstantInt *RHS = dyn_cast<ConstantInt>(I->getOperand(1))) {
if (I->getOpcode() == Instruction::Shl) {
// This is a value scaled by '1 << the shift amt'.
Scale = 1U << RHS->getZExtValue();
Offset = 0;
return I->getOperand(0);
- } else if (I->getOpcode() == Instruction::Mul) {
+ }
+
+ if (I->getOpcode() == Instruction::Mul) {
// This value is scaled by 'RHS'.
Scale = RHS->getZExtValue();
Offset = 0;
return I->getOperand(0);
- } else if (I->getOpcode() == Instruction::Add) {
+ }
+
+ if (I->getOpcode() == Instruction::Add) {
// We have X+C. Check to see if we really have (X*C2)+C1,
// where C1 is divisible by C2.
unsigned SubScale;
}
-/// CanEvaluateInDifferentType - Return true if we can take the specified value
-/// and return it as type Ty without inserting any new casts and without
-/// changing the computed value. This is used by code that tries to decide
-/// whether promoting or shrinking integer operations to wider or smaller types
-/// will allow us to eliminate a truncate or extend.
-///
-/// This is a truncation operation if Ty is smaller than V->getType(), or an
-/// extension operation if Ty is larger.
-///
-/// If CastOpc is a truncation, then Ty will be a type smaller than V. We
-/// should return true if trunc(V) can be computed by computing V in the smaller
-/// type. If V is an instruction, then trunc(inst(x,y)) can be computed as
-/// inst(trunc(x),trunc(y)), which only makes sense if x and y can be
-/// efficiently truncated.
-///
-/// If CastOpc is a sext or zext, we are asking if the low bits of the value can
-/// bit computed in a larger type, which is then and'd or sext_in_reg'd to get
-/// the final result.
-bool InstCombiner::CanEvaluateInDifferentType(Value *V, const Type *Ty,
- unsigned CastOpc,
- int &NumCastsRemoved){
- // We can always evaluate constants in another type.
- if (isa<Constant>(V))
- return true;
-
- Instruction *I = dyn_cast<Instruction>(V);
- if (!I) return false;
-
- const Type *OrigTy = V->getType();
-
- // If this is an extension or truncate, we can often eliminate it.
- if (isa<TruncInst>(I) || isa<ZExtInst>(I) || isa<SExtInst>(I)) {
- // If this is a cast from the destination type, we can trivially eliminate
- // it, and this will remove a cast overall.
- if (I->getOperand(0)->getType() == Ty) {
- // If the first operand is itself a cast, and is eliminable, do not count
- // this as an eliminable cast. We would prefer to eliminate those two
- // casts first.
- if (!isa<CastInst>(I->getOperand(0)) && I->hasOneUse())
- ++NumCastsRemoved;
- return true;
- }
- }
-
- // We can't extend or shrink something that has multiple uses: doing so would
- // require duplicating the instruction in general, which isn't profitable.
- if (!I->hasOneUse()) return false;
-
- unsigned Opc = I->getOpcode();
- switch (Opc) {
- case Instruction::Add:
- case Instruction::Sub:
- case Instruction::Mul:
- case Instruction::And:
- case Instruction::Or:
- case Instruction::Xor:
- // These operators can all arbitrarily be extended or truncated.
- return CanEvaluateInDifferentType(I->getOperand(0), Ty, CastOpc,
- NumCastsRemoved) &&
- CanEvaluateInDifferentType(I->getOperand(1), Ty, CastOpc,
- NumCastsRemoved);
-
- case Instruction::UDiv:
- case Instruction::URem: {
- // UDiv and URem can be truncated if all the truncated bits are zero.
- uint32_t OrigBitWidth = OrigTy->getScalarSizeInBits();
- uint32_t BitWidth = Ty->getScalarSizeInBits();
- if (BitWidth < OrigBitWidth) {
- APInt Mask = APInt::getHighBitsSet(OrigBitWidth, OrigBitWidth-BitWidth);
- if (MaskedValueIsZero(I->getOperand(0), Mask) &&
- MaskedValueIsZero(I->getOperand(1), Mask)) {
- return CanEvaluateInDifferentType(I->getOperand(0), Ty, CastOpc,
- NumCastsRemoved) &&
- CanEvaluateInDifferentType(I->getOperand(1), Ty, CastOpc,
- NumCastsRemoved);
- }
- }
- break;
- }
- case Instruction::Shl:
- // If we are truncating the result of this SHL, and if it's a shift of a
- // constant amount, we can always perform a SHL in a smaller type.
- if (ConstantInt *CI = dyn_cast<ConstantInt>(I->getOperand(1))) {
- uint32_t BitWidth = Ty->getScalarSizeInBits();
- if (BitWidth < OrigTy->getScalarSizeInBits() &&
- CI->getLimitedValue(BitWidth) < BitWidth)
- return CanEvaluateInDifferentType(I->getOperand(0), Ty, CastOpc,
- NumCastsRemoved);
- }
- break;
- case Instruction::LShr:
- // If this is a truncate of a logical shr, we can truncate it to a smaller
- // lshr iff we know that the bits we would otherwise be shifting in are
- // already zeros.
- if (ConstantInt *CI = dyn_cast<ConstantInt>(I->getOperand(1))) {
- uint32_t OrigBitWidth = OrigTy->getScalarSizeInBits();
- uint32_t BitWidth = Ty->getScalarSizeInBits();
- if (BitWidth < OrigBitWidth &&
- MaskedValueIsZero(I->getOperand(0),
- APInt::getHighBitsSet(OrigBitWidth, OrigBitWidth-BitWidth)) &&
- CI->getLimitedValue(BitWidth) < BitWidth) {
- return CanEvaluateInDifferentType(I->getOperand(0), Ty, CastOpc,
- NumCastsRemoved);
- }
- }
- break;
- case Instruction::ZExt:
- case Instruction::SExt:
- case Instruction::Trunc:
- // If this is the same kind of case as our original (e.g. zext+zext), we
- // can safely replace it. Note that replacing it does not reduce the number
- // of casts in the input.
- if (Opc == CastOpc)
- return true;
-
- // sext (zext ty1), ty2 -> zext ty2
- if (CastOpc == Instruction::SExt && Opc == Instruction::ZExt)
- return true;
- break;
- case Instruction::Select: {
- SelectInst *SI = cast<SelectInst>(I);
- return CanEvaluateInDifferentType(SI->getTrueValue(), Ty, CastOpc,
- NumCastsRemoved) &&
- CanEvaluateInDifferentType(SI->getFalseValue(), Ty, CastOpc,
- NumCastsRemoved);
- }
- case Instruction::PHI: {
- // We can change a phi if we can change all operands.
- PHINode *PN = cast<PHINode>(I);
- for (unsigned i = 0, e = PN->getNumIncomingValues(); i != e; ++i)
- if (!CanEvaluateInDifferentType(PN->getIncomingValue(i), Ty, CastOpc,
- NumCastsRemoved))
- return false;
- return true;
- }
- default:
- // TODO: Can handle more cases here.
- break;
- }
-
- return false;
-}
/// EvaluateInDifferentType - Given an expression that
-/// CanEvaluateInDifferentType returns true for, actually insert the code to
-/// evaluate the expression.
+/// CanEvaluateTruncated or CanEvaluateSExtd returns true for, actually
+/// insert the code to evaluate the expression.
Value *InstCombiner::EvaluateInDifferentType(Value *V, const Type *Ty,
bool isSigned) {
- if (Constant *C = dyn_cast<Constant>(V))
- return ConstantExpr::getIntegerCast(C, Ty, isSigned /*Sext or ZExt*/);
+ if (Constant *C = dyn_cast<Constant>(V)) {
+ C = ConstantExpr::getIntegerCast(C, Ty, isSigned /*Sext or ZExt*/);
+ // If we got a constantexpr back, try to simplify it with TD info.
+ if (ConstantExpr *CE = dyn_cast<ConstantExpr>(C))
+ C = ConstantFoldConstantExpression(CE, TD);
+ return C;
+ }
// Otherwise, it must be an instruction.
Instruction *I = cast<Instruction>(V);
return I->getOperand(0);
// Otherwise, must be the same type of cast, so just reinsert a new one.
- Res = CastInst::Create(cast<CastInst>(I)->getOpcode(), I->getOperand(0),Ty);
+ // This also handles the case of zext(trunc(x)) -> zext(x).
+ Res = CastInst::CreateIntegerCast(I->getOperand(0), Ty,
+ Opc == Instruction::SExt);
break;
case Instruction::Select: {
Value *True = EvaluateInDifferentType(I->getOperand(1), Ty, isSigned);
return 0;
}
-/// @brief Implement the transforms for cast of pointer (bitcast/ptrtoint)
-Instruction *InstCombiner::commonPointerCastTransforms(CastInst &CI) {
- Value *Src = CI.getOperand(0);
+/// CanEvaluateTruncated - Return true if we can evaluate the specified
+/// expression tree as type Ty instead of its larger type, and arrive with the
+/// same value. This is used by code that tries to eliminate truncates.
+///
+/// Ty will always be a type smaller than V. We should return true if trunc(V)
+/// can be computed by computing V in the smaller type. If V is an instruction,
+/// then trunc(inst(x,y)) can be computed as inst(trunc(x),trunc(y)), which only
+/// makes sense if x and y can be efficiently truncated.
+///
+/// This function works on both vectors and scalars.
+///
+static bool CanEvaluateTruncated(Value *V, const Type *Ty) {
+ // We can always evaluate constants in another type.
+ if (isa<Constant>(V))
+ return true;
- if (GetElementPtrInst *GEP = dyn_cast<GetElementPtrInst>(Src)) {
- // If casting the result of a getelementptr instruction with no offset, turn
- // this into a cast of the original pointer!
- if (GEP->hasAllZeroIndices()) {
- // Changing the cast operand is usually not a good idea but it is safe
- // here because the pointer operand is being replaced with another
- // pointer operand so the opcode doesn't need to change.
- Worklist.Add(GEP);
- CI.setOperand(0, GEP->getOperand(0));
- return &CI;
- }
-
- // If the GEP has a single use, and the base pointer is a bitcast, and the
- // 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.
- if (TD && GEP->hasOneUse() && isa<BitCastInst>(GEP->getOperand(0))) {
- if (GEP->hasAllConstantIndices()) {
- // We are guaranteed to get a constant from EmitGEPOffset.
- ConstantInt *OffsetV = cast<ConstantInt>(EmitGEPOffset(GEP));
- int64_t Offset = OffsetV->getSExtValue();
-
- // Get the base pointer input of the bitcast, and the type it points to.
- Value *OrigBase = cast<BitCastInst>(GEP->getOperand(0))->getOperand(0);
- const Type *GEPIdxTy =
- cast<PointerType>(OrigBase->getType())->getElementType();
- SmallVector<Value*, 8> NewIndices;
- if (FindElementAtOffset(GEPIdxTy, Offset, NewIndices)) {
- // 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.begin(), NewIndices.end()) :
- Builder->CreateGEP(OrigBase, NewIndices.begin(), NewIndices.end());
- 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);
-}
-
-/// commonIntCastTransforms - This function implements the common transforms
-/// for trunc, zext, and sext.
-Instruction *InstCombiner::commonIntCastTransforms(CastInst &CI) {
- if (Instruction *Result = commonCastTransforms(CI))
- return Result;
-
- Value *Src = CI.getOperand(0);
- const Type *SrcTy = Src->getType();
- const Type *DestTy = CI.getType();
- uint32_t SrcBitSize = SrcTy->getScalarSizeInBits();
- uint32_t DestBitSize = DestTy->getScalarSizeInBits();
-
- // See if we can simplify any instructions used by the LHS whose sole
- // purpose is to compute bits we don't care about.
- if (SimplifyDemandedInstructionBits(CI))
- return &CI;
-
- // If the source isn't an instruction or has more than one use then we
- // can't do anything more.
- Instruction *SrcI = dyn_cast<Instruction>(Src);
- if (!SrcI || !Src->hasOneUse())
- return 0;
-
- // Attempt to propagate the cast into the instruction for int->int casts.
- int NumCastsRemoved = 0;
- // Only do this if the dest type is a simple type, don't convert the
- // expression tree to something weird like i93 unless the source is also
- // strange.
- if ((isa<VectorType>(DestTy) ||
- ShouldChangeType(SrcI->getType(), DestTy)) &&
- CanEvaluateInDifferentType(SrcI, DestTy,
- CI.getOpcode(), NumCastsRemoved)) {
- // If this cast is a truncate, evaluting in a different type always
- // eliminates the cast, so it is always a win. If this is a zero-extension,
- // we need to do an AND to maintain the clear top-part of the computation,
- // so we require that the input have eliminated at least one cast. If this
- // is a sign extension, we insert two new casts (to do the extension) so we
- // require that two casts have been eliminated.
- bool DoXForm = false;
- bool JustReplace = false;
- switch (CI.getOpcode()) {
- default:
- // All the others use floating point so we shouldn't actually
- // get here because of the check above.
- llvm_unreachable("Unknown cast type");
- case Instruction::Trunc:
- DoXForm = true;
- break;
- case Instruction::ZExt: {
- DoXForm = NumCastsRemoved >= 1;
-
- if (!DoXForm && 0) {
- // If it's unnecessary to issue an AND to clear the high bits, it's
- // always profitable to do this xform.
- Value *TryRes = EvaluateInDifferentType(SrcI, DestTy, false);
- APInt Mask(APInt::getBitsSet(DestBitSize, SrcBitSize, DestBitSize));
- if (MaskedValueIsZero(TryRes, Mask))
- return ReplaceInstUsesWith(CI, TryRes);
-
- if (Instruction *TryI = dyn_cast<Instruction>(TryRes))
- if (TryI->use_empty())
- EraseInstFromFunction(*TryI);
- }
- break;
- }
- case Instruction::SExt: {
- DoXForm = NumCastsRemoved >= 2;
- if (!DoXForm && !isa<TruncInst>(SrcI) && 0) {
- // If we do not have to emit the truncate + sext pair, then it's always
- // profitable to do this xform.
- //
- // It's not safe to eliminate the trunc + sext pair if one of the
- // eliminated cast is a truncate. e.g.
- // t2 = trunc i32 t1 to i16
- // t3 = sext i16 t2 to i32
- // !=
- // i32 t1
- Value *TryRes = EvaluateInDifferentType(SrcI, DestTy, true);
- unsigned NumSignBits = ComputeNumSignBits(TryRes);
- if (NumSignBits > (DestBitSize - SrcBitSize))
- return ReplaceInstUsesWith(CI, TryRes);
-
- if (Instruction *TryI = dyn_cast<Instruction>(TryRes))
- if (TryI->use_empty())
- EraseInstFromFunction(*TryI);
- }
- break;
- }
- }
-
- if (DoXForm) {
- DEBUG(errs() << "ICE: EvaluateInDifferentType converting expression type"
- " to avoid cast: " << CI);
- Value *Res = EvaluateInDifferentType(SrcI, DestTy,
- CI.getOpcode() == Instruction::SExt);
- if (JustReplace)
- // Just replace this cast with the result.
- return ReplaceInstUsesWith(CI, Res);
-
- assert(Res->getType() == DestTy);
- switch (CI.getOpcode()) {
- default: llvm_unreachable("Unknown cast type!");
- case Instruction::Trunc:
- // Just replace this cast with the result.
- return ReplaceInstUsesWith(CI, Res);
- case Instruction::ZExt: {
- assert(SrcBitSize < DestBitSize && "Not a zext?");
-
- // If the high bits are already zero, just replace this cast with the
- // result.
- APInt Mask(APInt::getBitsSet(DestBitSize, SrcBitSize, DestBitSize));
- if (MaskedValueIsZero(Res, Mask))
- return ReplaceInstUsesWith(CI, Res);
-
- // We need to emit an AND to clear the high bits.
- Constant *C = ConstantInt::get(CI.getContext(),
- APInt::getLowBitsSet(DestBitSize, SrcBitSize));
- return BinaryOperator::CreateAnd(Res, C);
- }
- case Instruction::SExt: {
- // If the high bits are already filled with sign bit, just replace this
- // cast with the result.
- unsigned NumSignBits = ComputeNumSignBits(Res);
- if (NumSignBits > (DestBitSize - SrcBitSize))
- return ReplaceInstUsesWith(CI, Res);
-
- // We need to emit a cast to truncate, then a cast to sext.
- return new SExtInst(Builder->CreateTrunc(Res, Src->getType()), DestTy);
- }
- }
- }
- }
+ Instruction *I = dyn_cast<Instruction>(V);
+ if (!I) return false;
+
+ const Type *OrigTy = V->getType();
- Value *Op0 = SrcI->getNumOperands() > 0 ? SrcI->getOperand(0) : 0;
- Value *Op1 = SrcI->getNumOperands() > 1 ? SrcI->getOperand(1) : 0;
+ // If this is an extension from the dest type, we can eliminate it.
+ if ((isa<ZExtInst>(I) || isa<SExtInst>(I)) &&
+ I->getOperand(0)->getType() == Ty)
+ return true;
+
+ // We can't extend or shrink something that has multiple uses: doing so would
+ // require duplicating the instruction in general, which isn't profitable.
+ if (!I->hasOneUse()) return false;
- switch (SrcI->getOpcode()) {
+ unsigned Opc = I->getOpcode();
+ switch (Opc) {
case Instruction::Add:
+ case Instruction::Sub:
case Instruction::Mul:
case Instruction::And:
case Instruction::Or:
case Instruction::Xor:
- // If we are discarding information, rewrite.
- if (DestBitSize < SrcBitSize && DestBitSize != 1) {
- // Don't insert two casts unless at least one can be eliminated.
- if (!ValueRequiresCast(CI.getOpcode(), Op1, DestTy) ||
- !ValueRequiresCast(CI.getOpcode(), Op0, DestTy)) {
- Value *Op0c = Builder->CreateTrunc(Op0, DestTy, Op0->getName());
- Value *Op1c = Builder->CreateTrunc(Op1, DestTy, Op1->getName());
- return BinaryOperator::Create(
- cast<BinaryOperator>(SrcI)->getOpcode(), Op0c, Op1c);
+ // These operators can all arbitrarily be extended or truncated.
+ return CanEvaluateTruncated(I->getOperand(0), Ty) &&
+ CanEvaluateTruncated(I->getOperand(1), Ty);
+
+ case Instruction::UDiv:
+ case Instruction::URem: {
+ // UDiv and URem can be truncated if all the truncated bits are zero.
+ uint32_t OrigBitWidth = OrigTy->getScalarSizeInBits();
+ uint32_t BitWidth = Ty->getScalarSizeInBits();
+ if (BitWidth < OrigBitWidth) {
+ APInt Mask = APInt::getHighBitsSet(OrigBitWidth, OrigBitWidth-BitWidth);
+ if (MaskedValueIsZero(I->getOperand(0), Mask) &&
+ MaskedValueIsZero(I->getOperand(1), Mask)) {
+ return CanEvaluateTruncated(I->getOperand(0), Ty) &&
+ CanEvaluateTruncated(I->getOperand(1), Ty);
}
}
-
- // cast (xor bool X, true) to int --> xor (cast bool X to int), 1
- if (isa<ZExtInst>(CI) && SrcBitSize == 1 &&
- SrcI->getOpcode() == Instruction::Xor &&
- Op1 == ConstantInt::getTrue(CI.getContext()) &&
- (!Op0->hasOneUse() || !isa<CmpInst>(Op0))) {
- Value *New = Builder->CreateZExt(Op0, DestTy, Op0->getName());
- return BinaryOperator::CreateXor(New,
- ConstantInt::get(CI.getType(), 1));
+ break;
+ }
+ case Instruction::Shl:
+ // If we are truncating the result of this SHL, and if it's a shift of a
+ // constant amount, we can always perform a SHL in a smaller type.
+ if (ConstantInt *CI = dyn_cast<ConstantInt>(I->getOperand(1))) {
+ uint32_t BitWidth = Ty->getScalarSizeInBits();
+ if (CI->getLimitedValue(BitWidth) < BitWidth)
+ return CanEvaluateTruncated(I->getOperand(0), Ty);
}
break;
-
- case Instruction::Shl: {
- // Canonicalize trunc inside shl, if we can.
- ConstantInt *CI = dyn_cast<ConstantInt>(Op1);
- if (CI && DestBitSize < SrcBitSize &&
- CI->getLimitedValue(DestBitSize) < DestBitSize) {
- Value *Op0c = Builder->CreateTrunc(Op0, DestTy, Op0->getName());
- Value *Op1c = Builder->CreateTrunc(Op1, DestTy, Op1->getName());
- return BinaryOperator::CreateShl(Op0c, Op1c);
+ case Instruction::LShr:
+ // If this is a truncate of a logical shr, we can truncate it to a smaller
+ // lshr iff we know that the bits we would otherwise be shifting in are
+ // already zeros.
+ if (ConstantInt *CI = dyn_cast<ConstantInt>(I->getOperand(1))) {
+ uint32_t OrigBitWidth = OrigTy->getScalarSizeInBits();
+ uint32_t BitWidth = Ty->getScalarSizeInBits();
+ if (MaskedValueIsZero(I->getOperand(0),
+ APInt::getHighBitsSet(OrigBitWidth, OrigBitWidth-BitWidth)) &&
+ CI->getLimitedValue(BitWidth) < BitWidth) {
+ return CanEvaluateTruncated(I->getOperand(0), Ty);
+ }
}
break;
+ case Instruction::Trunc:
+ // trunc(trunc(x)) -> trunc(x)
+ return true;
+ case Instruction::Select: {
+ SelectInst *SI = cast<SelectInst>(I);
+ return CanEvaluateTruncated(SI->getTrueValue(), Ty) &&
+ CanEvaluateTruncated(SI->getFalseValue(), Ty);
}
+ case Instruction::PHI: {
+ // We can change a phi if we can change all operands. Note that we never
+ // get into trouble with cyclic PHIs here because we only consider
+ // instructions with a single use.
+ PHINode *PN = cast<PHINode>(I);
+ for (unsigned i = 0, e = PN->getNumIncomingValues(); i != e; ++i)
+ if (!CanEvaluateTruncated(PN->getIncomingValue(i), Ty))
+ return false;
+ return true;
}
- return 0;
+ default:
+ // TODO: Can handle more cases here.
+ break;
+ }
+
+ return false;
}
-
Instruction *InstCombiner::visitTrunc(TruncInst &CI) {
- if (Instruction *Result = commonIntCastTransforms(CI))
+ if (Instruction *Result = commonCastTransforms(CI))
return Result;
+ // See if we can simplify any instructions used by the input whose sole
+ // purpose is to compute bits we don't care about.
+ if (SimplifyDemandedInstructionBits(CI))
+ return &CI;
+
Value *Src = CI.getOperand(0);
- const Type *Ty = CI.getType();
- uint32_t DestBitWidth = Ty->getScalarSizeInBits();
- uint32_t SrcBitWidth = Src->getType()->getScalarSizeInBits();
+ const Type *DestTy = CI.getType(), *SrcTy = Src->getType();
+
+ // Attempt to truncate the entire input expression tree to the destination
+ // type. Only do this if the dest type is a simple type, don't convert the
+ // expression tree to something weird like i93 unless the source is also
+ // strange.
+ if ((isa<VectorType>(DestTy) || ShouldChangeType(SrcTy, DestTy)) &&
+ CanEvaluateTruncated(Src, DestTy)) {
+
+ // If this cast is a truncate, evaluting in a different type always
+ // eliminates the cast, so it is always a win.
+ DEBUG(dbgs() << "ICE: EvaluateInDifferentType converting expression type"
+ " to avoid cast: " << CI);
+ Value *Res = EvaluateInDifferentType(Src, DestTy, false);
+ assert(Res->getType() == DestTy);
+ return ReplaceInstUsesWith(CI, Res);
+ }
- // Canonicalize trunc x to i1 -> (icmp ne (and x, 1), 0)
- if (DestBitWidth == 1) {
+ // Canonicalize trunc x to i1 -> (icmp ne (and x, 1), 0), likewise for vector.
+ if (DestTy->getScalarSizeInBits() == 1) {
Constant *One = ConstantInt::get(Src->getType(), 1);
Src = Builder->CreateAnd(Src, One, "tmp");
Value *Zero = Constant::getNullValue(Src->getType());
return new ICmpInst(ICmpInst::ICMP_NE, Src, Zero);
}
- // Optimize trunc(lshr(), c) to pull the shift through the truncate.
- ConstantInt *ShAmtV = 0;
- Value *ShiftOp = 0;
- if (Src->hasOneUse() &&
- match(Src, m_LShr(m_Value(ShiftOp), m_ConstantInt(ShAmtV)))) {
- uint32_t ShAmt = ShAmtV->getLimitedValue(SrcBitWidth);
-
- // Get a mask for the bits shifting in.
- APInt Mask(APInt::getLowBitsSet(SrcBitWidth, ShAmt).shl(DestBitWidth));
- if (MaskedValueIsZero(ShiftOp, Mask)) {
- if (ShAmt >= DestBitWidth) // All zeros.
- return ReplaceInstUsesWith(CI, Constant::getNullValue(Ty));
-
- // Okay, we can shrink this. Truncate the input, then return a new
- // shift.
- Value *V1 = Builder->CreateTrunc(ShiftOp, Ty, ShiftOp->getName());
- Value *V2 = ConstantExpr::getTrunc(ShAmtV, Ty);
- return BinaryOperator::CreateLShr(V1, V2);
- }
- }
-
return 0;
}
return 0;
}
+/// CanEvaluateZExtd - Determine if the specified value can be computed in the
+/// specified wider type and produce the same low bits. If not, return false.
+///
+/// If this function returns true, it can also return a non-zero number of bits
+/// (in BitsToClear) which indicates that the value it computes is correct for
+/// the zero extend, but that the additional BitsToClear bits need to be zero'd
+/// out. For example, to promote something like:
+///
+/// %B = trunc i64 %A to i32
+/// %C = lshr i32 %B, 8
+/// %E = zext i32 %C to i64
+///
+/// CanEvaluateZExtd for the 'lshr' will return true, and BitsToClear will be
+/// set to 8 to indicate that the promoted value needs to have bits 24-31
+/// cleared in addition to bits 32-63. Since an 'and' will be generated to
+/// clear the top bits anyway, doing this has no extra cost.
+///
+/// This function works on both vectors and scalars.
+static bool CanEvaluateZExtd(Value *V, const Type *Ty, unsigned &BitsToClear) {
+ BitsToClear = 0;
+ if (isa<Constant>(V))
+ return true;
+
+ Instruction *I = dyn_cast<Instruction>(V);
+ if (!I) return false;
+
+ // If the input is a truncate from the destination type, we can trivially
+ // eliminate it.
+ if (isa<TruncInst>(I) && I->getOperand(0)->getType() == Ty)
+ return true;
+
+ // We can't extend or shrink something that has multiple uses: doing so would
+ // require duplicating the instruction in general, which isn't profitable.
+ if (!I->hasOneUse()) return false;
+
+ unsigned Opc = I->getOpcode(), Tmp;
+ switch (Opc) {
+ case Instruction::ZExt: // zext(zext(x)) -> zext(x).
+ case Instruction::SExt: // zext(sext(x)) -> sext(x).
+ case Instruction::Trunc: // zext(trunc(x)) -> trunc(x) or zext(x)
+ return true;
+ case Instruction::And:
+ case Instruction::Or:
+ case Instruction::Xor:
+ case Instruction::Add:
+ case Instruction::Sub:
+ case Instruction::Mul:
+ case Instruction::Shl:
+ if (!CanEvaluateZExtd(I->getOperand(0), Ty, BitsToClear) ||
+ !CanEvaluateZExtd(I->getOperand(1), Ty, Tmp))
+ return false;
+ // These can all be promoted if neither operand has 'bits to clear'.
+ if (BitsToClear == 0 && Tmp == 0)
+ return true;
+
+ return false;
+
+ case Instruction::LShr:
+ // We can promote lshr(x, cst) if we can promote x. This requires the
+ // ultimate 'and' to clear out the high zero bits we're clearing out though.
+ if (ConstantInt *Amt = dyn_cast<ConstantInt>(I->getOperand(1))) {
+ if (!CanEvaluateZExtd(I->getOperand(0), Ty, BitsToClear))
+ return false;
+ BitsToClear += Amt->getZExtValue();
+ if (BitsToClear > V->getType()->getScalarSizeInBits())
+ BitsToClear = V->getType()->getScalarSizeInBits();
+ return true;
+ }
+ // Cannot promote variable LSHR.
+ return false;
+ case Instruction::Select:
+ if (!CanEvaluateZExtd(I->getOperand(1), Ty, Tmp) ||
+ !CanEvaluateZExtd(I->getOperand(2), Ty, BitsToClear) ||
+ Tmp != BitsToClear)
+ return false;
+ return true;
+
+ case Instruction::PHI: {
+ // We can change a phi if we can change all operands. Note that we never
+ // get into trouble with cyclic PHIs here because we only consider
+ // instructions with a single use.
+ PHINode *PN = cast<PHINode>(I);
+ if (!CanEvaluateZExtd(PN->getIncomingValue(0), Ty, BitsToClear))
+ return false;
+ for (unsigned i = 1, e = PN->getNumIncomingValues(); i != e; ++i)
+ if (!CanEvaluateZExtd(PN->getIncomingValue(i), Ty, Tmp) ||
+ Tmp != BitsToClear)
+ return false;
+ return true;
+ }
+ default:
+ // TODO: Can handle more cases here.
+ return false;
+ }
+}
+
Instruction *InstCombiner::visitZExt(ZExtInst &CI) {
+ // If this zero extend is only used by a truncate, let the truncate by
+ // eliminated before we try to optimize this zext.
+ if (CI.hasOneUse() && isa<TruncInst>(CI.use_back()))
+ return 0;
+
// If one of the common conversion will work, do it.
- if (Instruction *Result = commonIntCastTransforms(CI))
+ if (Instruction *Result = commonCastTransforms(CI))
return Result;
+ // See if we can simplify any instructions used by the input whose sole
+ // purpose is to compute bits we don't care about.
+ if (SimplifyDemandedInstructionBits(CI))
+ return &CI;
+
Value *Src = CI.getOperand(0);
+ const Type *SrcTy = Src->getType(), *DestTy = CI.getType();
+
+ // Attempt to extend the entire input expression tree to the destination
+ // type. Only do this if the dest type is a simple type, don't convert the
+ // expression tree to something weird like i93 unless the source is also
+ // strange.
+ unsigned BitsToClear;
+ if ((isa<VectorType>(DestTy) || ShouldChangeType(SrcTy, DestTy)) &&
+ CanEvaluateZExtd(Src, DestTy, BitsToClear)) {
+ assert(BitsToClear < SrcTy->getScalarSizeInBits() &&
+ "Unreasonable BitsToClear");
+
+ // Okay, we can transform this! Insert the new expression now.
+ DEBUG(dbgs() << "ICE: EvaluateInDifferentType converting expression type"
+ " to avoid zero extend: " << CI);
+ Value *Res = EvaluateInDifferentType(Src, DestTy, false);
+ assert(Res->getType() == DestTy);
+
+ uint32_t SrcBitsKept = SrcTy->getScalarSizeInBits()-BitsToClear;
+ uint32_t DestBitSize = DestTy->getScalarSizeInBits();
+
+ // If the high bits are already filled with zeros, just replace this
+ // cast with the result.
+ if (MaskedValueIsZero(Res, APInt::getHighBitsSet(DestBitSize,
+ DestBitSize-SrcBitsKept)))
+ return ReplaceInstUsesWith(CI, Res);
+
+ // We need to emit an AND to clear the high bits.
+ Constant *C = ConstantInt::get(Res->getType(),
+ APInt::getLowBitsSet(DestBitSize, SrcBitsKept));
+ return BinaryOperator::CreateAnd(Res, C);
+ }
// If this is a TRUNC followed by a ZEXT then we are dealing with integral
// types and if the sizes are just right we can convert this into a logical
// 'and' which will be much cheaper than the pair of casts.
if (TruncInst *CSrc = dyn_cast<TruncInst>(Src)) { // A->B->C cast
+ // TODO: Subsume this into EvaluateInDifferentType.
+
// Get the sizes of the types involved. We know that the intermediate type
// will be smaller than A or C, but don't know the relation between A and C.
Value *A = CSrc->getOperand(0);
APInt AndValue(APInt::getLowBitsSet(DstSize, MidSize));
return BinaryOperator::CreateAnd(Trunc,
ConstantInt::get(Trunc->getType(),
- AndValue));
+ AndValue));
}
}
}
}
+ // zext (xor i1 X, true) to i32 --> xor (zext i1 X to i32), 1
+ Value *X;
+ if (SrcI && SrcI->hasOneUse() && SrcI->getType()->isInteger(1) &&
+ match(SrcI, m_Not(m_Value(X))) &&
+ (!X->hasOneUse() || !isa<CmpInst>(X))) {
+ Value *New = Builder->CreateZExt(X, CI.getType());
+ return BinaryOperator::CreateXor(New, ConstantInt::get(CI.getType(), 1));
+ }
+
return 0;
}
+/// CanEvaluateSExtd - Return true if we can take the specified value
+/// and return it as type Ty without inserting any new casts and without
+/// changing the value of the common low bits. This is used by code that tries
+/// to promote integer operations to a wider types will allow us to eliminate
+/// the extension.
+///
+/// This function works on both vectors and scalars.
+///
+static bool CanEvaluateSExtd(Value *V, const Type *Ty) {
+ assert(V->getType()->getScalarSizeInBits() < Ty->getScalarSizeInBits() &&
+ "Can't sign extend type to a smaller type");
+ // If this is a constant, it can be trivially promoted.
+ if (isa<Constant>(V))
+ return true;
+
+ Instruction *I = dyn_cast<Instruction>(V);
+ if (!I) return false;
+
+ // If this is a truncate from the dest type, we can trivially eliminate it.
+ if (isa<TruncInst>(I) && I->getOperand(0)->getType() == Ty)
+ return true;
+
+ // We can't extend or shrink something that has multiple uses: doing so would
+ // require duplicating the instruction in general, which isn't profitable.
+ if (!I->hasOneUse()) return false;
+
+ switch (I->getOpcode()) {
+ case Instruction::SExt: // sext(sext(x)) -> sext(x)
+ case Instruction::ZExt: // sext(zext(x)) -> zext(x)
+ case Instruction::Trunc: // sext(trunc(x)) -> trunc(x) or sext(x)
+ return true;
+ case Instruction::And:
+ case Instruction::Or:
+ case Instruction::Xor:
+ case Instruction::Add:
+ case Instruction::Sub:
+ case Instruction::Mul:
+ // These operators can all arbitrarily be extended if their inputs can.
+ return CanEvaluateSExtd(I->getOperand(0), Ty) &&
+ CanEvaluateSExtd(I->getOperand(1), Ty);
+
+ //case Instruction::Shl: TODO
+ //case Instruction::LShr: TODO
+
+ case Instruction::Select:
+ return CanEvaluateSExtd(I->getOperand(1), Ty) &&
+ CanEvaluateSExtd(I->getOperand(2), Ty);
+
+ case Instruction::PHI: {
+ // We can change a phi if we can change all operands. Note that we never
+ // get into trouble with cyclic PHIs here because we only consider
+ // instructions with a single use.
+ PHINode *PN = cast<PHINode>(I);
+ for (unsigned i = 0, e = PN->getNumIncomingValues(); i != e; ++i)
+ if (!CanEvaluateSExtd(PN->getIncomingValue(i), Ty)) return false;
+ return true;
+ }
+ default:
+ // TODO: Can handle more cases here.
+ break;
+ }
+
+ return false;
+}
+
Instruction *InstCombiner::visitSExt(SExtInst &CI) {
- if (Instruction *I = commonIntCastTransforms(CI))
+ // If this sign extend is only used by a truncate, let the truncate by
+ // eliminated before we try to optimize this zext.
+ if (CI.hasOneUse() && isa<TruncInst>(CI.use_back()))
+ return 0;
+
+ if (Instruction *I = commonCastTransforms(CI))
return I;
- Value *Src = CI.getOperand(0);
+ // See if we can simplify any instructions used by the input whose sole
+ // purpose is to compute bits we don't care about.
+ if (SimplifyDemandedInstructionBits(CI))
+ return &CI;
+ Value *Src = CI.getOperand(0);
+ const Type *SrcTy = Src->getType(), *DestTy = CI.getType();
+
// Canonicalize sign-extend from i1 to a select.
- if (Src->getType() == Type::getInt1Ty(CI.getContext()))
+ if (Src->getType()->isInteger(1))
return SelectInst::Create(Src,
Constant::getAllOnesValue(CI.getType()),
Constant::getNullValue(CI.getType()));
-
- // See if the value being truncated is already sign extended. If so, just
- // eliminate the trunc/sext pair.
- if (Operator::getOpcode(Src) == Instruction::Trunc) {
- Value *Op = cast<User>(Src)->getOperand(0);
- unsigned OpBits = Op->getType()->getScalarSizeInBits();
- unsigned MidBits = Src->getType()->getScalarSizeInBits();
- unsigned DestBits = CI.getType()->getScalarSizeInBits();
- unsigned NumSignBits = ComputeNumSignBits(Op);
-
- if (OpBits == DestBits) {
- // Op is i32, Mid is i8, and Dest is i32. If Op has more than 24 sign
- // bits, it is already ready.
- if (NumSignBits > DestBits-MidBits)
- return ReplaceInstUsesWith(CI, Op);
- } else if (OpBits < DestBits) {
- // Op is i32, Mid is i8, and Dest is i64. If Op has more than 24 sign
- // bits, just sext from i32.
- if (NumSignBits > OpBits-MidBits)
- return new SExtInst(Op, CI.getType(), "tmp");
- } else {
- // Op is i64, Mid is i8, and Dest is i32. If Op has more than 56 sign
- // bits, just truncate to i32.
- if (NumSignBits > OpBits-MidBits)
- return new TruncInst(Op, CI.getType(), "tmp");
- }
+
+ // Attempt to extend the entire input expression tree to the destination
+ // type. Only do this if the dest type is a simple type, don't convert the
+ // expression tree to something weird like i93 unless the source is also
+ // strange.
+ if ((isa<VectorType>(DestTy) || ShouldChangeType(SrcTy, DestTy)) &&
+ CanEvaluateSExtd(Src, DestTy)) {
+ // Okay, we can transform this! Insert the new expression now.
+ DEBUG(dbgs() << "ICE: EvaluateInDifferentType converting expression type"
+ " to avoid sign extend: " << CI);
+ Value *Res = EvaluateInDifferentType(Src, DestTy, true);
+ assert(Res->getType() == DestTy);
+
+ uint32_t SrcBitSize = SrcTy->getScalarSizeInBits();
+ uint32_t DestBitSize = DestTy->getScalarSizeInBits();
+
+ // If the high bits are already filled with sign bit, just replace this
+ // cast with the result.
+ if (ComputeNumSignBits(Res) > DestBitSize - SrcBitSize)
+ return ReplaceInstUsesWith(CI, Res);
+
+ // We need to emit a shl + ashr to do the sign extend.
+ Value *ShAmt = ConstantInt::get(DestTy, DestBitSize-SrcBitSize);
+ return BinaryOperator::CreateAShr(Builder->CreateShl(Res, ShAmt, "sext"),
+ ShAmt);
}
// If the input is a shl/ashr pair of a same constant, then this is a sign
// %a = shl i32 %i, 30
// %d = ashr i32 %a, 30
Value *A = 0;
+ // TODO: Eventually this could be subsumed by EvaluateInDifferentType.
ConstantInt *BA = 0, *CA = 0;
- if (match(Src, m_AShr(m_Shl(m_Value(A), m_ConstantInt(BA)),
+ if (match(Src, m_AShr(m_Shl(m_Trunc(m_Value(A)), m_ConstantInt(BA)),
m_ConstantInt(CA))) &&
- BA == CA && isa<TruncInst>(A)) {
- Value *I = cast<TruncInst>(A)->getOperand(0);
- if (I->getType() == CI.getType()) {
- unsigned MidSize = Src->getType()->getScalarSizeInBits();
- unsigned SrcDstSize = CI.getType()->getScalarSizeInBits();
- unsigned ShAmt = CA->getZExtValue()+SrcDstSize-MidSize;
- Constant *ShAmtV = ConstantInt::get(CI.getType(), ShAmt);
- I = Builder->CreateShl(I, ShAmtV, CI.getName());
- return BinaryOperator::CreateAShr(I, ShAmtV);
- }
+ BA == CA && A->getType() == CI.getType()) {
+ unsigned MidSize = Src->getType()->getScalarSizeInBits();
+ unsigned SrcDstSize = CI.getType()->getScalarSizeInBits();
+ unsigned ShAmt = CA->getZExtValue()+SrcDstSize-MidSize;
+ Constant *ShAmtV = ConstantInt::get(CI.getType(), ShAmt);
+ A = Builder->CreateShl(A, ShAmtV, CI.getName());
+ return BinaryOperator::CreateAShr(A, ShAmtV);
}
return 0;
return commonCastTransforms(CI);
}
-Instruction *InstCombiner::visitPtrToInt(PtrToIntInst &CI) {
- // If the destination integer type is smaller than the intptr_t type for
- // this target, do a ptrtoint to intptr_t then do a trunc. This allows the
- // trunc to be exposed to other transforms. Don't do this for extending
- // ptrtoint's, because we don't know if the target sign or zero extends its
- // pointers.
- if (TD &&
- CI.getType()->getScalarSizeInBits() < TD->getPointerSizeInBits()) {
- Value *P = Builder->CreatePtrToInt(CI.getOperand(0),
- TD->getIntPtrType(CI.getContext()),
- "tmp");
- return new TruncInst(P, CI.getType());
- }
-
- return commonPointerCastTransforms(CI);
-}
-
-
Instruction *InstCombiner::visitIntToPtr(IntToPtrInst &CI) {
// If the source integer type is larger than the intptr_t type for
// this target, do a trunc to the intptr_t type, then inttoptr of it. This
return 0;
}
+/// @brief Implement the transforms for cast of pointer (bitcast/ptrtoint)
+Instruction *InstCombiner::commonPointerCastTransforms(CastInst &CI) {
+ Value *Src = CI.getOperand(0);
+
+ if (GetElementPtrInst *GEP = dyn_cast<GetElementPtrInst>(Src)) {
+ // If casting the result of a getelementptr instruction with no offset, turn
+ // this into a cast of the original pointer!
+ if (GEP->hasAllZeroIndices()) {
+ // Changing the cast operand is usually not a good idea but it is safe
+ // here because the pointer operand is being replaced with another
+ // pointer operand so the opcode doesn't need to change.
+ Worklist.Add(GEP);
+ CI.setOperand(0, GEP->getOperand(0));
+ return &CI;
+ }
+
+ // If the GEP has a single use, and the base pointer is a bitcast, and the
+ // 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.
+ if (TD && GEP->hasOneUse() && isa<BitCastInst>(GEP->getOperand(0)) &&
+ GEP->hasAllConstantIndices()) {
+ // We are guaranteed to get a constant from EmitGEPOffset.
+ ConstantInt *OffsetV = cast<ConstantInt>(EmitGEPOffset(GEP));
+ int64_t Offset = OffsetV->getSExtValue();
+
+ // Get the base pointer input of the bitcast, and the type it points to.
+ Value *OrigBase = cast<BitCastInst>(GEP->getOperand(0))->getOperand(0);
+ const Type *GEPIdxTy =
+ cast<PointerType>(OrigBase->getType())->getElementType();
+ SmallVector<Value*, 8> NewIndices;
+ if (FindElementAtOffset(GEPIdxTy, Offset, NewIndices)) {
+ // 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.begin(), NewIndices.end()) :
+ Builder->CreateGEP(OrigBase, NewIndices.begin(), NewIndices.end());
+ 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);
+}
+
+Instruction *InstCombiner::visitPtrToInt(PtrToIntInst &CI) {
+ // If the destination integer type is smaller than the intptr_t type for
+ // this target, do a ptrtoint to intptr_t then do a trunc. This allows the
+ // trunc to be exposed to other transforms. Don't do this for extending
+ // ptrtoint's, because we don't know if the target sign or zero extends its
+ // pointers.
+ if (TD &&
+ CI.getType()->getScalarSizeInBits() < TD->getPointerSizeInBits()) {
+ Value *P = Builder->CreatePtrToInt(CI.getOperand(0),
+ TD->getIntPtrType(CI.getContext()),
+ "tmp");
+ return new TruncInst(P, CI.getType());
+ }
+
+ return commonPointerCastTransforms(CI);
+}
+
Instruction *InstCombiner::visitBitCast(BitCastInst &CI) {
// If the operands are integer typed then apply the integer transforms,
// otherwise just apply the common ones.
const Type *SrcTy = Src->getType();
const Type *DestTy = CI.getType();
- if (isa<PointerType>(SrcTy)) {
- if (Instruction *I = commonPointerCastTransforms(CI))
- return I;
- } else {
- if (Instruction *Result = commonCastTransforms(CI))
- return Result;
- }
-
-
// Get rid of casts from one type to the same type. These are useless and can
// be replaced by the operand.
if (DestTy == Src->getType())
if (SrcElTy == DstElTy) {
SmallVector<Value*, 8> Idxs(NumZeros+1, ZeroUInt);
return GetElementPtrInst::CreateInBounds(Src, Idxs.begin(), Idxs.end(),"",
- ((Instruction*) NULL));
+ ((Instruction*)NULL));
}
}
if (const VectorType *DestVTy = dyn_cast<VectorType>(DestTy)) {
- if (DestVTy->getNumElements() == 1) {
- if (!isa<VectorType>(SrcTy)) {
- Value *Elem = Builder->CreateBitCast(Src, DestVTy->getElementType());
- return InsertElementInst::Create(UndefValue::get(DestTy), Elem,
+ if (DestVTy->getNumElements() == 1 && !isa<VectorType>(SrcTy)) {
+ Value *Elem = Builder->CreateBitCast(Src, DestVTy->getElementType());
+ return InsertElementInst::Create(UndefValue::get(DestTy), Elem,
Constant::getNullValue(Type::getInt32Ty(CI.getContext())));
- }
// FIXME: Canonicalize bitcast(insertelement) -> insertelement(bitcast)
}
}
if (const VectorType *SrcVTy = dyn_cast<VectorType>(SrcTy)) {
- if (SrcVTy->getNumElements() == 1) {
- if (!isa<VectorType>(DestTy)) {
- Value *Elem =
- Builder->CreateExtractElement(Src,
- Constant::getNullValue(Type::getInt32Ty(CI.getContext())));
- return CastInst::Create(Instruction::BitCast, Elem, DestTy);
- }
+ if (SrcVTy->getNumElements() == 1 && !isa<VectorType>(DestTy)) {
+ Value *Elem =
+ Builder->CreateExtractElement(Src,
+ Constant::getNullValue(Type::getInt32Ty(CI.getContext())));
+ return CastInst::Create(Instruction::BitCast, Elem, DestTy);
}
}
if (ShuffleVectorInst *SVI = dyn_cast<ShuffleVectorInst>(Src)) {
- if (SVI->hasOneUse()) {
- // Okay, we have (bitconvert (shuffle ..)). Check to see if this is
- // a bitconvert to a vector with the same # elts.
- if (isa<VectorType>(DestTy) &&
- cast<VectorType>(DestTy)->getNumElements() ==
- SVI->getType()->getNumElements() &&
- SVI->getType()->getNumElements() ==
- cast<VectorType>(SVI->getOperand(0)->getType())->getNumElements()) {
- CastInst *Tmp;
- // If either of the operands is a cast from CI.getType(), then
- // evaluating the shuffle in the casted destination's type will allow
- // us to eliminate at least one cast.
- if (((Tmp = dyn_cast<CastInst>(SVI->getOperand(0))) &&
- Tmp->getOperand(0)->getType() == DestTy) ||
- ((Tmp = dyn_cast<CastInst>(SVI->getOperand(1))) &&
- Tmp->getOperand(0)->getType() == DestTy)) {
- Value *LHS = Builder->CreateBitCast(SVI->getOperand(0), DestTy);
- Value *RHS = Builder->CreateBitCast(SVI->getOperand(1), DestTy);
- // Return a new shuffle vector. Use the same element ID's, as we
- // know the vector types match #elts.
- return new ShuffleVectorInst(LHS, RHS, SVI->getOperand(2));
- }
+ // Okay, we have (bitcast (shuffle ..)). Check to see if this is
+ // a bitconvert to a vector with the same # elts.
+ if (SVI->hasOneUse() && isa<VectorType>(DestTy) &&
+ cast<VectorType>(DestTy)->getNumElements() ==
+ SVI->getType()->getNumElements() &&
+ SVI->getType()->getNumElements() ==
+ cast<VectorType>(SVI->getOperand(0)->getType())->getNumElements()) {
+ BitCastInst *Tmp;
+ // If either of the operands is a cast from CI.getType(), then
+ // evaluating the shuffle in the casted destination's type will allow
+ // us to eliminate at least one cast.
+ if (((Tmp = dyn_cast<BitCastInst>(SVI->getOperand(0))) &&
+ Tmp->getOperand(0)->getType() == DestTy) ||
+ ((Tmp = dyn_cast<BitCastInst>(SVI->getOperand(1))) &&
+ Tmp->getOperand(0)->getType() == DestTy)) {
+ Value *LHS = Builder->CreateBitCast(SVI->getOperand(0), DestTy);
+ Value *RHS = Builder->CreateBitCast(SVI->getOperand(1), DestTy);
+ // Return a new shuffle vector. Use the same element ID's, as we
+ // know the vector types match #elts.
+ return new ShuffleVectorInst(LHS, RHS, SVI->getOperand(2));
}
}
}
- return 0;
+
+ if (isa<PointerType>(SrcTy))
+ return commonPointerCastTransforms(CI);
+ return commonCastTransforms(CI);
}