Simplify ComputeMultiple so that it doesn't depend on TargetData.

llvm-svn: 89175
This commit is contained in:
Dan Gohman 2009-11-18 00:58:27 +00:00
parent 24f55430c8
commit 6a976bbcb7
3 changed files with 13 additions and 27 deletions

View File

@ -68,8 +68,8 @@ namespace llvm {
/// Multiple. If unsuccessful, it returns false. Also, if V can be /// Multiple. If unsuccessful, it returns false. Also, if V can be
/// simplified to an integer, then the simplified V is returned in Val. Look /// simplified to an integer, then the simplified V is returned in Val. Look
/// through sext only if LookThroughSExt=true. /// through sext only if LookThroughSExt=true.
bool ComputeMultiple(Value *V, unsigned Base, Value *&Multiple, APInt &Val, bool ComputeMultiple(Value *V, unsigned Base, Value *&Multiple,
bool LookThroughSExt = false, const TargetData *TD = 0, bool LookThroughSExt = false,
unsigned Depth = 0); unsigned Depth = 0);
/// CannotBeNegativeZero - Return true if we can prove that the specified FP /// CannotBeNegativeZero - Return true if we can prove that the specified FP

View File

@ -105,9 +105,8 @@ static Value *computeArraySize(const CallInst *CI, const TargetData *TD,
// return the multiple. Otherwise, return NULL. // return the multiple. Otherwise, return NULL.
Value *MallocArg = CI->getOperand(1); Value *MallocArg = CI->getOperand(1);
Value *Multiple = NULL; Value *Multiple = NULL;
APInt Val(TD->getTypeSizeInBits(MallocArg->getType()->getScalarType()), 0);
if (ComputeMultiple(MallocArg, ElementSize, Multiple, if (ComputeMultiple(MallocArg, ElementSize, Multiple,
Val, LookThroughSExt, TD)) LookThroughSExt))
return Multiple; return Multiple;
return NULL; return NULL;

View File

@ -791,24 +791,19 @@ unsigned llvm::ComputeNumSignBits(Value *V, const TargetData *TD,
/// ComputeMultiple - This function computes the integer multiple of Base that /// ComputeMultiple - This function computes the integer multiple of Base that
/// equals V. If successful, it returns true and returns the multiple in /// equals V. If successful, it returns true and returns the multiple in
/// Multiple. If unsuccessful, it returns false. Also, if V can be /// Multiple. If unsuccessful, it returns false. It looks
/// simplified to an integer, then the simplified V is returned in Val. It looks
/// through SExt instructions only if LookThroughSExt is true. /// through SExt instructions only if LookThroughSExt is true.
bool llvm::ComputeMultiple(Value *V, unsigned Base, Value *&Multiple, bool llvm::ComputeMultiple(Value *V, unsigned Base, Value *&Multiple,
APInt &Val, bool LookThroughSExt, bool LookThroughSExt, unsigned Depth) {
const TargetData *TD, unsigned Depth) {
const unsigned MaxDepth = 6; const unsigned MaxDepth = 6;
assert(TD && V && "No Value?"); assert(V && "No Value?");
assert(Depth <= MaxDepth && "Limit Search Depth"); assert(Depth <= MaxDepth && "Limit Search Depth");
assert(V->getType()->isInteger() && "Not integer or pointer type!"); assert(V->getType()->isInteger() && "Not integer or pointer type!");
const Type *T = V->getType(); const Type *T = V->getType();
unsigned TSize = TD->getTypeSizeInBits(T->getScalarType());
ConstantInt *CI = NULL; ConstantInt *CI = dyn_cast<ConstantInt>(V);
if ((CI = dyn_cast<ConstantInt>(V)))
Val = CI->getValue();
if (Base == 0) if (Base == 0)
return false; return false;
@ -843,8 +838,8 @@ bool llvm::ComputeMultiple(Value *V, unsigned Base, Value *&Multiple,
// otherwise fall through to ZExt // otherwise fall through to ZExt
} }
case Instruction::ZExt: { case Instruction::ZExt: {
return ComputeMultiple(I->getOperand(0), Base, Multiple, Val, return ComputeMultiple(I->getOperand(0), Base, Multiple,
LookThroughSExt, TD, Depth+1); LookThroughSExt, Depth+1);
} }
case Instruction::Shl: case Instruction::Shl:
case Instruction::Mul: { case Instruction::Mul: {
@ -863,17 +858,15 @@ bool llvm::ComputeMultiple(Value *V, unsigned Base, Value *&Multiple,
Value *Mul0 = NULL; Value *Mul0 = NULL;
Value *Mul1 = NULL; Value *Mul1 = NULL;
APInt Val0(TSize, 0), Val1(TSize, 0); bool M0 = ComputeMultiple(Op0, Base, Mul0,
bool M0 = ComputeMultiple(Op0, Base, Mul0, Val0, LookThroughSExt, Depth+1);
LookThroughSExt, TD, Depth+1); bool M1 = ComputeMultiple(Op1, Base, Mul1,
bool M1 = ComputeMultiple(Op1, Base, Mul1, Val1, LookThroughSExt, Depth+1);
LookThroughSExt, TD, Depth+1);
if (M0) { if (M0) {
if (isa<Constant>(Op1) && isa<Constant>(Mul0)) { if (isa<Constant>(Op1) && isa<Constant>(Mul0)) {
// V == Base * (Mul0 * Op1), so return (Mul0 * Op1) // V == Base * (Mul0 * Op1), so return (Mul0 * Op1)
Multiple = ConstantExpr::getMul(cast<Constant>(Mul0), Multiple = ConstantExpr::getMul(cast<Constant>(Mul0),
Val1.getBoolValue() ? ConstantInt::get(V->getContext(), Val1):
cast<Constant>(Op1)); cast<Constant>(Op1));
return true; return true;
} }
@ -890,7 +883,6 @@ bool llvm::ComputeMultiple(Value *V, unsigned Base, Value *&Multiple,
if (isa<Constant>(Op0) && isa<Constant>(Mul1)) { if (isa<Constant>(Op0) && isa<Constant>(Mul1)) {
// V == Base * (Mul1 * Op0), so return (Mul1 * Op0) // V == Base * (Mul1 * Op0), so return (Mul1 * Op0)
Multiple = ConstantExpr::getMul(cast<Constant>(Mul1), Multiple = ConstantExpr::getMul(cast<Constant>(Mul1),
Val0.getBoolValue() ? ConstantInt::get(V->getContext(), Val0):
cast<Constant>(Op0)); cast<Constant>(Op0));
return true; return true;
} }
@ -902,11 +894,6 @@ bool llvm::ComputeMultiple(Value *V, unsigned Base, Value *&Multiple,
return true; return true;
} }
} }
if (Val0.getBoolValue() && Val1.getBoolValue())
// Op1*Op2 was simplified, try computing multiple again.
return ComputeMultiple(ConstantInt::get(V->getContext(), Val0 * Val1),
Base, Multiple, Val, LookThroughSExt, TD, Depth+1);
} }
} }