aboutsummaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
authorChris Lattner <sabre@nondot.org>2002-07-31 22:31:34 +0000
committerChris Lattner <sabre@nondot.org>2002-07-31 22:31:34 +0000
commit280b09b1783f11fe235cc0c0c1d0d39f2b3af3c5 (patch)
tree948f207ba40fccf48ff4fb216381c265c91b615e /lib
parent1917e95cf0f5e72b228adea1647165bb904574ef (diff)
downloadexternal_llvm-280b09b1783f11fe235cc0c0c1d0d39f2b3af3c5.zip
external_llvm-280b09b1783f11fe235cc0c0c1d0d39f2b3af3c5.tar.gz
external_llvm-280b09b1783f11fe235cc0c0c1d0d39f2b3af3c5.tar.bz2
Implement the other half of a feature advertised by OperandConvertableToType.
This fixes bug: test/Regression/Transforms/LevelRaise/2002-07-31-AssertionFailure.ll git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@3193 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib')
-rw-r--r--lib/Transforms/ExprTypeConvert.cpp45
1 files changed, 39 insertions, 6 deletions
diff --git a/lib/Transforms/ExprTypeConvert.cpp b/lib/Transforms/ExprTypeConvert.cpp
index 2277676..98bc942 100644
--- a/lib/Transforms/ExprTypeConvert.cpp
+++ b/lib/Transforms/ExprTypeConvert.cpp
@@ -159,8 +159,6 @@ static Instruction *ConvertMallocToType(MallocInst *MI, const Type *Ty,
// ExpressionConvertableToType - Return true if it is possible
bool ExpressionConvertableToType(Value *V, const Type *Ty,
ValueTypeCache &CTMap) {
- if (V->getType() == Ty) return true; // Expression already correct type!
-
// Expression type must be holdable in a register.
if (!Ty->isFirstClassType())
return false;
@@ -169,6 +167,7 @@ bool ExpressionConvertableToType(Value *V, const Type *Ty,
if (CTMI != CTMap.end()) return CTMI->second == Ty;
CTMap[V] = Ty;
+ if (V->getType() == Ty) return true; // Expression already correct type!
Instruction *I = dyn_cast<Instruction>(V);
if (I == 0) {
@@ -341,6 +340,8 @@ Value *ConvertExpressionToType(Value *V, const Type *Ty, ValueMapCache &VMC) {
ValueMapCache::ExprMapTy::iterator VMCI = VMC.ExprMap.find(V);
if (VMCI != VMC.ExprMap.end()) {
+ const Value *GV = VMCI->second;
+ const Type *GTy = VMCI->second->getType();
assert(VMCI->second->getType() == Ty);
if (Instruction *I = dyn_cast<Instruction>(V))
@@ -996,10 +997,42 @@ static void ConvertOperandToType(User *U, Value *OldVal, Value *NewVal,
case Instruction::Store: {
if (I->getOperand(0) == OldVal) { // Replace the source value
- const PointerType *NewPT = PointerType::get(NewTy);
- Res = new StoreInst(NewVal, Constant::getNullValue(NewPT));
- VMC.ExprMap[I] = Res;
- Res->setOperand(1, ConvertExpressionToType(I->getOperand(1), NewPT, VMC));
+ // Check to see if operand #1 has already been converted...
+ ValueMapCache::ExprMapTy::iterator VMCI =
+ VMC.ExprMap.find(I->getOperand(1));
+ if (VMCI != VMC.ExprMap.end()) {
+ // Comments describing this stuff are in the OperandConvertableToType
+ // switch statement for Store...
+ //
+ const Type *ElTy =
+ cast<PointerType>(VMCI->second->getType())->getElementType();
+ if (ElTy == NewTy) {
+ // If it happens to be converted to exactly the right type, use it
+ // directly...
+ Res = new StoreInst(NewVal, VMCI->second);
+ } else {
+ // We check that this is a struct in the initial scan...
+ const StructType *SElTy = cast<StructType>(ElTy);
+
+ unsigned Offset = 0;
+ std::vector<Value*> Indices;
+ Indices.push_back(ConstantUInt::get(Type::UIntTy, 0));
+ const Type *Ty = getStructOffsetType(ElTy, Offset, Indices, false);
+ assert(Offset == 0 && "Offset changed!");
+ assert(NewTy == Ty && "Did not convert to correct type!");
+
+ Res = new StoreInst(NewVal, VMCI->second, Indices);
+ }
+
+ VMC.ExprMap[I] = Res;
+ } else {
+ // Otherwise, we haven't converted Operand #1 over yet...
+ const PointerType *NewPT = PointerType::get(NewTy);
+ Res = new StoreInst(NewVal, Constant::getNullValue(NewPT));
+ VMC.ExprMap[I] = Res;
+ Res->setOperand(1, ConvertExpressionToType(I->getOperand(1),
+ NewPT, VMC));
+ }
} else { // Replace the source pointer
const Type *ValTy = cast<PointerType>(NewTy)->getElementType();
std::vector<Value*> Indices;