Fix PR1329.
[oota-llvm.git] / include / llvm / InstrTypes.h
index 22b52c5f73663799c76afba4e1734423e84b83d5..5439337224a613bc0a9a7eed8c1d76031e6dd7f3 100644 (file)
@@ -29,19 +29,14 @@ namespace llvm {
 ///
 class TerminatorInst : public Instruction {
 protected:
-  TerminatorInst(Instruction::TermOps iType, Use *Ops, unsigned NumOps,
-                 Instruction *InsertBefore = 0);
   TerminatorInst(const Type *Ty, Instruction::TermOps iType,
-                  Use *Ops, unsigned NumOps,
-                 const std::string &Name = "", Instruction *InsertBefore = 0)
-    : Instruction(Ty, iType, Ops, NumOps, Name, InsertBefore) {}
+                 Use *Ops, unsigned NumOps,
+                 Instruction *InsertBefore = 0)
+    : Instruction(Ty, iType, Ops, NumOps, InsertBefore) {}
 
-  TerminatorInst(Instruction::TermOps iType, Use *Ops, unsigned NumOps,
-                 BasicBlock *InsertAtEnd);
   TerminatorInst(const Type *Ty, Instruction::TermOps iType,
-                  Use *Ops, unsigned NumOps,
-                 const std::string &Name, BasicBlock *InsertAtEnd)
-    : Instruction(Ty, iType, Ops, NumOps, Name, InsertAtEnd) {}
+                 Use *Ops, unsigned NumOps, BasicBlock *InsertAtEnd)
+    : Instruction(Ty, iType, Ops, NumOps, InsertAtEnd) {}
 
   // Out of line virtual method, so the vtable, etc has a home.
   ~TerminatorInst();
@@ -90,13 +85,11 @@ public:
 class UnaryInstruction : public Instruction {
   Use Op;
 protected:
-  UnaryInstruction(const Type *Ty, unsigned iType, Value *V,
-                   const std::string &Name = "", Instruction *IB = 0)
-    : Instruction(Ty, iType, &Op, 1, Name, IB), Op(V, this) {
+  UnaryInstruction(const Type *Ty, unsigned iType, Value *V, Instruction *IB =0)
+    : Instruction(Ty, iType, &Op, 1, IB), Op(V, this) {
   }
-  UnaryInstruction(const Type *Ty, unsigned iType, Value *V,
-                   const std::string &Name, BasicBlock *IAE)
-    : Instruction(Ty, iType, &Op, 1, Name, IAE), Op(V, this) {
+  UnaryInstruction(const Type *Ty, unsigned iType, Value *V, BasicBlock *IAE)
+    : Instruction(Ty, iType, &Op, 1, IAE), Op(V, this) {
   }
 public:
   // Out of line virtual method, so the vtable, etc has a home.
@@ -123,20 +116,9 @@ class BinaryOperator : public Instruction {
 protected:
   void init(BinaryOps iType);
   BinaryOperator(BinaryOps iType, Value *S1, Value *S2, const Type *Ty,
-                 const std::string &Name, Instruction *InsertBefore)
-    : Instruction(Ty, iType, Ops, 2, Name, InsertBefore) {
-      Ops[0].init(S1, this);
-      Ops[1].init(S2, this);
-    init(iType);
-  }
+                 const std::string &Name, Instruction *InsertBefore);
   BinaryOperator(BinaryOps iType, Value *S1, Value *S2, const Type *Ty,
-                 const std::string &Name, BasicBlock *InsertAtEnd)
-    : Instruction(Ty, iType, Ops, 2, Name, InsertAtEnd) {
-    Ops[0].init(S1, this);
-    Ops[1].init(S2, this);
-    init(iType);
-  }
-
+                 const std::string &Name, BasicBlock *InsertAtEnd);
 public:
 
   /// Transparently provide more efficient getOperand methods.
@@ -263,13 +245,15 @@ class CastInst : public UnaryInstruction {
 protected:
   /// @brief Constructor with insert-before-instruction semantics for subclasses
   CastInst(const Type *Ty, unsigned iType, Value *S, 
-      const std::string &Name = "", Instruction *InsertBefore = 0)
-    : UnaryInstruction(Ty, iType, S, Name, InsertBefore) {
+           const std::string &Name = "", Instruction *InsertBefore = 0)
+    : UnaryInstruction(Ty, iType, S, InsertBefore) {
+    setName(Name);
   }
   /// @brief Constructor with insert-at-end-of-block semantics for subclasses
   CastInst(const Type *Ty, unsigned iType, Value *S, 
-      const std::string &Name, BasicBlock *InsertAtEnd)
-    : UnaryInstruction(Ty, iType, S, Name, InsertAtEnd) {
+           const std::string &Name, BasicBlock *InsertAtEnd)
+    : UnaryInstruction(Ty, iType, S, InsertAtEnd) {
+    setName(Name);
   }
 public:
   /// Provides a way to construct any of the CastInst subclasses using an 
@@ -427,7 +411,7 @@ public:
   /// involving Integer and Pointer types. They are no-op casts if the integer
   /// is the same size as the pointer. However, pointer size varies with 
   /// platform. Generally, the result of TargetData::getIntPtrType() should be
-  /// passed in. If that's not available, use Type::ULongTy, which will make
+  /// passed in. If that's not available, use Type::Int64Ty, which will make
   /// the isNoopCast call conservative.
   /// @brief Determine if this cast is a no-op cast. 
   bool isNoopCast(
@@ -454,6 +438,17 @@ public:
     return Instruction::CastOps(Instruction::getOpcode()); 
   }
 
+  /// @brief Return the source type, as a convenience
+  const Type* getSrcTy() const { return getOperand(0)->getType(); }
+  /// @brief Return the destination type, as a convenience
+  const Type* getDestTy() const { return getType(); }
+
+  /// This method can be used to determine if a cast from S to DstTy using
+  /// Opcode op is valid or not. 
+  /// @returns true iff the proposed cast is valid.
+  /// @brief Determine if a cast is valid without creating one.
+  static bool castIsValid(Instruction::CastOps op, Value *S, const Type *DstTy);
+
   /// @brief Methods for support type inquiry through isa, cast, and dyn_cast:
   static inline bool classof(const CastInst *) { return true; }
   static inline bool classof(const Instruction *I) {