Replace CanBeDuplicated() with a M_NOT_DUPLICABLE bit.
[oota-llvm.git] / include / llvm / Target / TargetInstrInfo.h
index 71a6dcdeb305775bd018787a44acaa64b340e03e..2a1843f8df7c23bc5982af3c74bd73cda66f8fe2 100644 (file)
@@ -74,14 +74,21 @@ const unsigned M_USES_CUSTOM_DAG_SCHED_INSERTION = 1 << 10;
 // operands in addition to the minimum number operands specified.
 const unsigned M_VARIABLE_OPS = 1 << 11;
 
-// M_PREDICATED - Set if this instruction has a predicate that controls its
-// execution.
-const unsigned M_PREDICATED = 1 << 12;
+// M_PREDICABLE - Set if this instruction has a predicate operand that
+// controls execution. It may be set to 'always'.
+const unsigned M_PREDICABLE = 1 << 12;
 
 // M_REMATERIALIZIBLE - Set if this instruction can be trivally re-materialized
 // at any time, e.g. constant generation, load from constant pool.
 const unsigned M_REMATERIALIZIBLE = 1 << 13;
 
+// M_CLOBBERS_PRED - Set if this instruction may clobbers the condition code
+// register and / or registers that are used to predicate instructions.
+const unsigned M_CLOBBERS_PRED = 1 << 14;
+
+// M_NOT_DUPLICABLE - Set if this instruction cannot be safely duplicated.
+// (e.g. instructions with unique labels attached).
+const unsigned M_NOT_DUPLICABLE = 1 << 15;
 
 // Machine operand flags
 // M_LOOK_UP_PTR_REG_CLASS - Set if this operand is a pointer value and it
@@ -208,16 +215,10 @@ public:
     return get(Opcode).Flags & M_RET_FLAG;
   }
 
-  bool isPredicated(MachineOpCode Opcode) const {
-    return get(Opcode).Flags & M_PREDICATED;
-  }
-  bool isReMaterializable(MachineOpCode Opcode) const {
-    return get(Opcode).Flags & M_REMATERIALIZIBLE;
-  }
   bool isCommutableInstr(MachineOpCode Opcode) const {
     return get(Opcode).Flags & M_COMMUTABLE;
   }
-  bool isTerminatorInstr(unsigned Opcode) const {
+  bool isTerminatorInstr(MachineOpCode Opcode) const {
     return get(Opcode).Flags & M_TERMINATOR_FLAG;
   }
   
@@ -244,14 +245,14 @@ public:
   
   /// hasDelaySlot - Returns true if the specified instruction has a delay slot
   /// which must be filled by the code generator.
-  bool hasDelaySlot(unsigned Opcode) const {
+  bool hasDelaySlot(MachineOpCode Opcode) const {
     return get(Opcode).Flags & M_DELAY_SLOT_FLAG;
   }
   
   /// usesCustomDAGSchedInsertionHook - Return true if this instruction requires
   /// custom insertion support when the DAG scheduler is inserting it into a
   /// machine basic block.
-  bool usesCustomDAGSchedInsertionHook(unsigned Opcode) const {
+  bool usesCustomDAGSchedInsertionHook(MachineOpCode Opcode) const {
     return get(Opcode).Flags & M_USES_CUSTOM_DAG_SCHED_INSERTION;
   }
 
@@ -259,6 +260,22 @@ public:
     return get(Opcode).Flags & M_VARIABLE_OPS;
   }
 
+  bool isPredicable(MachineOpCode Opcode) const {
+    return get(Opcode).Flags & M_PREDICABLE;
+  }
+
+  bool isReMaterializable(MachineOpCode Opcode) const {
+    return get(Opcode).Flags & M_REMATERIALIZIBLE;
+  }
+
+  bool clobbersPredicate(MachineOpCode Opcode) const {
+    return get(Opcode).Flags & M_CLOBBERS_PRED;
+  }
+
+  bool isNotDuplicable(MachineOpCode Opcode) const {
+    return get(Opcode).Flags & M_NOT_DUPLICABLE;
+  }
+
   /// getOperandConstraint - Returns the value of the specific constraint if
   /// it is set. Returns -1 if it is not set.
   int getOperandConstraint(MachineOpCode Opcode, unsigned OpNum,
@@ -292,6 +309,16 @@ public:
     return 0;
   }
 
+  /// isOtherReMaterializableLoad - If the specified machine instruction is a
+  /// direct load that is trivially rematerializable, not counting loads from
+  /// stack slots, return true. If not, return false.  This predicate must
+  /// return false if the instruction has any side effects other than
+  /// producing the value from the load, or if it requres any address
+  /// registers that are not always available.
+  virtual bool isOtherReMaterializableLoad(MachineInstr *MI) const {
+    return false;
+  }
+
   /// convertToThreeAddress - This method must be implemented by targets that
   /// set the M_CONVERTIBLE_TO_3_ADDR flag.  When this flag is set, the target
   /// may be able to convert a two-address instruction into one or moretrue
@@ -329,10 +356,16 @@ public:
   ///    just return false, leaving TBB/FBB null.
   /// 2. If this block ends with only an unconditional branch, it sets TBB to be
   ///    the destination block.
-  /// 3. If this block ends with an conditional branch, it returns the 'true'
-  ///    destination in TBB, the 'false' destination in FBB, and a list of
-  ///    operands that evaluate the condition.  These operands can be passed to
-  ///    other TargetInstrInfo methods to create new branches.
+  /// 3. If this block ends with an conditional branch and it falls through to
+  ///    an successor block, it sets TBB to be the branch destination block and a
+  ///    list of operands that evaluate the condition. These
+  ///    operands can be passed to other TargetInstrInfo methods to create new
+  ///    branches.
+  /// 4. If this block ends with an conditional branch and an unconditional
+  ///    block, it returns the 'true' destination in TBB, the 'false' destination
+  ///    in FBB, and a list of operands that evaluate the condition. These
+  ///    operands can be passed to other TargetInstrInfo methods to create new
+  ///    branches.
   ///
   /// Note that RemoveBranch and InsertBranch must be implemented to support
   /// cases where this method returns success.
@@ -344,20 +377,24 @@ public:
   }
   
   /// RemoveBranch - Remove the branching code at the end of the specific MBB.
-  /// this is only invoked in cases where AnalyzeBranch returns success.
-  virtual void RemoveBranch(MachineBasicBlock &MBB) const {
+  /// this is only invoked in cases where AnalyzeBranch returns success. It
+  /// returns the number of instructions that were removed.
+  virtual unsigned RemoveBranch(MachineBasicBlock &MBB) const {
     assert(0 && "Target didn't implement TargetInstrInfo::RemoveBranch!"); 
+    return 0;
   }
   
   /// InsertBranch - Insert a branch into the end of the specified
   /// MachineBasicBlock.  This operands to this method are the same as those
   /// returned by AnalyzeBranch.  This is invoked in cases where AnalyzeBranch
   /// returns success and when an unconditional branch (TBB is non-null, FBB is
-  /// null, Cond is empty) needs to be inserted.
-  virtual void InsertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB,
+  /// null, Cond is empty) needs to be inserted. It returns the number of
+  /// instructions inserted.
+  virtual unsigned InsertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB,
                             MachineBasicBlock *FBB,
                             const std::vector<MachineOperand> &Cond) const {
     assert(0 && "Target didn't implement TargetInstrInfo::InsertBranch!"); 
+    return 0;
   }
   
   /// BlockHasNoFallThrough - Return true if the specified block does not
@@ -383,18 +420,28 @@ public:
     abort();
   }
 
-  /// isPredicatable - True if the instruction can be converted into a
-  /// predicated instruction.
-  virtual bool isPredicatable(MachineInstr *MI) const {
+  /// isPredicated - Returns true if the instruction is already predicated.
+  ///
+  virtual bool isPredicated(const MachineInstr *MI) const {
     return false;
   }
 
+  /// isUnpredicatedTerminator - Returns true if the instruction is a
+  /// terminator instruction that has not been predicated.
+  virtual bool isUnpredicatedTerminator(const MachineInstr *MI) const;
+
   /// PredicateInstruction - Convert the instruction into a predicated
-  /// instruction.
-  virtual void PredicateInstruction(MachineInstr *MI,
-                                    std::vector<MachineOperand> &Cond) const {
-    assert(0 && "Target didn't implement PredicateInstruction!");
-    abort();
+  /// instruction. It returns true if the operation was successful.
+  virtual
+  bool PredicateInstruction(MachineInstr *MI,
+                            const std::vector<MachineOperand> &Pred) const;
+
+  /// SubsumesPredicate - Returns true if the first specified predicate
+  /// subsumes the second, e.g. GE subsumes GT.
+  virtual
+  bool SubsumesPredicate(const std::vector<MachineOperand> &Pred1,
+                         const std::vector<MachineOperand> &Pred2) const {
+    return false;
   }
 
   /// getPointerRegClass - Returns a TargetRegisterClass used for pointer