* Remove dead code from ExprTypeConvert.cpp
   - I->use_empty() can never be true because of the IHolder's
* Fix bug: test/Regression/Transforms/LevelRaise/2002-07-16-SourceAndDestCrash.ll
   - Add a new NewCasts member to VMC to keep track of casts that have been
     created and to ensure there is always a reference to the cast.
   - Extend ValueHandle a bit so it can be used in an STL container
   - Make sure we destroy the ValueMapCache before verifying the function
     in LevelRaise.cpp


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@2936 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/Transforms/ExprTypeConvert.cpp b/lib/Transforms/ExprTypeConvert.cpp
index d7caa2e..2277676 100644
--- a/lib/Transforms/ExprTypeConvert.cpp
+++ b/lib/Transforms/ExprTypeConvert.cpp
@@ -377,7 +377,9 @@
 
   switch (I->getOpcode()) {
   case Instruction::Cast:
+    assert(VMC.NewCasts.count(ValueHandle(VMC, I)) == 0);
     Res = new CastInst(I->getOperand(0), Ty, Name);
+    VMC.NewCasts.insert(ValueHandle(VMC, Res));
     break;
     
   case Instruction::Add:
@@ -540,14 +542,6 @@
   DEBUG(cerr << "ExpIn: " << (void*)I << " " << I
              << "ExpOut: " << (void*)Res << " " << Res);
 
-  if (I->use_empty()) {
-    DEBUG(cerr << "EXPR DELETING: " << (void*)I << " " << I);
-    BIL.remove(I);
-    VMC.OperandsMapped.erase(I);
-    VMC.ExprMap.erase(I);
-    delete I;
-  }
-
   return Res;
 }
 
@@ -906,7 +900,8 @@
   BasicBlock *BB = I->getParent();
   assert(BB != 0 && "Instruction not embedded in basic block!");
   BasicBlock::InstListType &BIL = BB->getInstList();
-  std::string Name = I->getName();  if (!Name.empty()) I->setName("");
+  std::string Name = I->getName();
+  I->setName("");
   Instruction *Res;     // Result of conversion
 
   //cerr << endl << endl << "Type:\t" << Ty << "\nInst: " << I << "BB Before: " << BB << endl;
@@ -920,8 +915,18 @@
 
   switch (I->getOpcode()) {
   case Instruction::Cast:
-    assert(I->getOperand(0) == OldVal);
-    Res = new CastInst(NewVal, I->getType(), Name);
+    if (VMC.NewCasts.count(ValueHandle(VMC, I))) {
+      // This cast has already had it's value converted, causing a new cast to
+      // be created.  We don't want to create YET ANOTHER cast instruction
+      // representing the original one, so just modify the operand of this cast
+      // instruction, which we know is newly created.
+      I->setOperand(0, NewVal);
+      I->setName(Name);  // give I its name back
+      return;
+
+    } else {
+      Res = new CastInst(NewVal, I->getType(), Name);
+    }
     break;
 
   case Instruction::Add:
@@ -1154,21 +1159,9 @@
         Use->replaceUsesOfWith(I, Res);
     }
 
-    if (I->use_empty()) {
-      // Now we just need to remove the old instruction so we don't get infinite
-      // loops.  Note that we cannot use DCE because DCE won't remove a store
-      // instruction, for example.
-      //
-      DEBUG(cerr << "DELETING: " << (void*)I << " " << I);
-      BIL.remove(I);
-      VMC.OperandsMapped.erase(I);
-      VMC.ExprMap.erase(I);
-      delete I;
-    } else {
-      for (Value::use_iterator UI = I->use_begin(), UE = I->use_end();
-           UI != UE; ++UI)
-        assert(isa<ValueHandle>((Value*)*UI) &&"Uses of Instruction remain!!!");
-    }
+    for (Value::use_iterator UI = I->use_begin(), UE = I->use_end();
+         UI != UE; ++UI)
+      assert(isa<ValueHandle>((Value*)*UI) &&"Uses of Instruction remain!!!");
   }
 }
 
@@ -1179,6 +1172,12 @@
   Operands.push_back(Use(V, this));
 }
 
+ValueHandle::ValueHandle(const ValueHandle &VH)
+  : Instruction(Type::VoidTy, UserOp1, ""), Cache(VH.Cache) {
+  //DEBUG(cerr << "VH AQUIRING: " << (void*)V << " " << V);
+  Operands.push_back(Use((Value*)VH.getOperand(0), this));
+}
+
 static void RecursiveDelete(ValueMapCache &Cache, Instruction *I) {
   if (!I || !I->use_empty()) return;
 
diff --git a/lib/Transforms/LevelRaise.cpp b/lib/Transforms/LevelRaise.cpp
index 94aebcb..7e27c5f 100644
--- a/lib/Transforms/LevelRaise.cpp
+++ b/lib/Transforms/LevelRaise.cpp
@@ -225,17 +225,20 @@
         PRINT_PEEPHOLE3("CAST-SRC-EXPR-CONV:in ", Src, CI, BB->getParent());
           
         DEBUG(cerr << "\nCONVERTING SRC EXPR TYPE:\n");
-        ValueMapCache ValueMap;
-        Value *E = ConvertExpressionToType(Src, DestTy, ValueMap);
-        if (Constant *CPV = dyn_cast<Constant>(E))
-          CI->replaceAllUsesWith(CPV);
+        { // ValueMap must be destroyed before function verified!
+          ValueMapCache ValueMap;
+          Value *E = ConvertExpressionToType(Src, DestTy, ValueMap);
 
-        BI = BB->begin();  // Rescan basic block.  BI might be invalidated.
-        PRINT_PEEPHOLE1("CAST-SRC-EXPR-CONV:out", E);
-        DEBUG(cerr << "DONE CONVERTING SRC EXPR TYPE: \n" << BB->getParent());
+          if (Constant *CPV = dyn_cast<Constant>(E))
+            CI->replaceAllUsesWith(CPV);
+          
+          PRINT_PEEPHOLE1("CAST-SRC-EXPR-CONV:out", E);
+          DEBUG(cerr << "DONE CONVERTING SRC EXPR TYPE: \n" << BB->getParent());
+        }
 
         DEBUG(assert(verifyFunction(*BB->getParent()) == false &&
                      "Function broken!"));
+        BI = BB->begin();  // Rescan basic block.  BI might be invalidated.
         ++NumExprTreesConv;
         return true;
       }
@@ -249,15 +252,17 @@
         PRINT_PEEPHOLE3("CAST-DEST-EXPR-CONV:in ", Src, CI, BB->getParent());
 
         DEBUG(cerr << "\nCONVERTING EXPR TYPE:\n");
-        ValueMapCache ValueMap;
-        ConvertValueToNewType(CI, Src, ValueMap);  // This will delete CI!
+        { // ValueMap must be destroyed before function verified!
+          ValueMapCache ValueMap;
+          ConvertValueToNewType(CI, Src, ValueMap);  // This will delete CI!
+        }
 
-        BI = BB->begin();  // Rescan basic block.  BI might be invalidated.
         PRINT_PEEPHOLE1("CAST-DEST-EXPR-CONV:out", Src);
         DEBUG(cerr << "DONE CONVERTING EXPR TYPE: \n\n" << BB->getParent());
 
         DEBUG(assert(verifyFunction(*BB->getParent()) == false &&
                      "Function broken!"));
+        BI = BB->begin();  // Rescan basic block.  BI might be invalidated.
         ++NumExprTreesConv;
         return true;
       }
diff --git a/lib/Transforms/TransformInternals.h b/lib/Transforms/TransformInternals.h
index 6680d02..7a2dbf1 100644
--- a/lib/Transforms/TransformInternals.h
+++ b/lib/Transforms/TransformInternals.h
@@ -9,7 +9,6 @@
 #define TRANSFORM_INTERNALS_H
 
 #include "llvm/BasicBlock.h"
-#include "llvm/Instruction.h"
 #include "llvm/Target/TargetData.h"
 #include "llvm/DerivedTypes.h"
 #include "llvm/Constants.h"
@@ -53,9 +52,43 @@
                              BasicBlock::iterator *BI = 0);
 
 
+//===----------------------------------------------------------------------===//
+//  ValueHandle Class - Smart pointer that occupies a slot on the users USE list
+//  that prevents it from being destroyed.  This "looks" like an Instruction
+//  with Opcode UserOp1.
+// 
+class ValueMapCache;
+class ValueHandle : public Instruction {
+  ValueMapCache &Cache;
+public:
+  ValueHandle(ValueMapCache &VMC, Value *V);
+  ValueHandle(const ValueHandle &);
+  ~ValueHandle();
+
+  virtual Instruction *clone() const { abort(); return 0; }
+
+  virtual const char *getOpcodeName() const {
+    return "ValueHandle";
+  }
+
+  inline bool operator<(const ValueHandle &VH) const {
+    return getOperand(0) < VH.getOperand(0);
+  }
+
+  // Methods for support type inquiry through isa, cast, and dyn_cast:
+  static inline bool classof(const ValueHandle *) { return true; }
+  static inline bool classof(const Instruction *I) {
+    return (I->getOpcode() == Instruction::UserOp1);
+  }
+  static inline bool classof(const Value *V) {
+    return isa<Instruction>(V) && classof(cast<Instruction>(V));
+  }
+};
+
+
 // ------------- Expression Conversion ---------------------
 
-typedef std::map<const Value*, const Type*>         ValueTypeCache;
+typedef std::map<const Value*, const Type*> ValueTypeCache;
 
 struct ValueMapCache {
   // Operands mapped - Contains an entry if the first value (the user) has had
@@ -68,6 +101,14 @@
   //
   std::map<const Value *, Value *> ExprMap;
   typedef std::map<const Value *, Value *> ExprMapTy;
+
+  // Cast Map - Cast instructions can have their source and destination values
+  // changed independantly for each part.  Because of this, our old naive
+  // implementation would create a TWO new cast instructions, which would cause
+  // all kinds of problems.  Here we keep track of the newly allocated casts, so
+  // that we only create one for a particular instruction.
+  //
+  std::set<ValueHandle> NewCasts;
 };
 
 
@@ -81,34 +122,6 @@
 void ConvertValueToNewType(Value *V, Value *NewVal, ValueMapCache &VMC);
 
 
-//===----------------------------------------------------------------------===//
-//  ValueHandle Class - Smart pointer that occupies a slot on the users USE list
-//  that prevents it from being destroyed.  This "looks" like an Instruction
-//  with Opcode UserOp1.
-// 
-class ValueHandle : public Instruction {
-  ValueHandle(const ValueHandle &); // DO NOT IMPLEMENT
-  ValueMapCache &Cache;
-public:
-  ValueHandle(ValueMapCache &VMC, Value *V);
-  ~ValueHandle();
-
-  virtual Instruction *clone() const { abort(); return 0; }
-
-  virtual const char *getOpcodeName() const {
-    return "ValueHandle";
-  }
-
-  // Methods for support type inquiry through isa, cast, and dyn_cast:
-  static inline bool classof(const ValueHandle *) { return true; }
-  static inline bool classof(const Instruction *I) {
-    return (I->getOpcode() == Instruction::UserOp1);
-  }
-  static inline bool classof(const Value *V) {
-    return isa<Instruction>(V) && classof(cast<Instruction>(V));
-  }
-};
-
 // getStructOffsetType - Return a vector of offsets that are to be used to index
 // into the specified struct type to get as close as possible to index as we
 // can.  Note that it is possible that we cannot get exactly to Offset, in which