AsmMatcher custom operand parser failure enhancements.
[oota-llvm.git] / lib / Target / ARM / ARMInstrInfo.td
index 765a714ca7e5892da28322c7e83e8561701ebbf5..2fd25328d3b3eadf94011a7f0769293a9dde10e8 100644 (file)
@@ -293,20 +293,36 @@ def fsub_mlx : PatFrag<(ops node:$lhs, node:$rhs),(fsub node:$lhs, node:$rhs),[{
 //
 
 // Branch target.
+// FIXME: rename brtarget to t2_brtarget
 def brtarget : Operand<OtherVT> {
   let EncoderMethod = "getBranchTargetOpValue";
 }
 
+// FIXME: get rid of this one?
 def uncondbrtarget : Operand<OtherVT> {
   let EncoderMethod = "getUnconditionalBranchTargetOpValue";
 }
 
+// Branch target for ARM. Handles conditional/unconditional
+def br_target : Operand<OtherVT> {
+  let EncoderMethod = "getARMBranchTargetOpValue";
+}
+
 // Call target.
+// FIXME: rename bltarget to t2_bl_target?
 def bltarget : Operand<i32> {
   // Encoded the same as branch targets.
   let EncoderMethod = "getBranchTargetOpValue";
 }
 
+// Call target for ARM. Handles conditional/unconditional
+// FIXME: rename bl_target to t2_bltarget?
+def bl_target : Operand<i32> {
+  // Encoded the same as branch targets.
+  let EncoderMethod = "getARMBranchTargetOpValue";
+}
+
+
 // A list of registers separated by comma. Used by load/store multiple.
 def RegListAsmOperand : AsmOperandClass {
   let Name = "RegList";
@@ -391,10 +407,7 @@ def shift_so_reg : Operand<i32>,    // reg reg imm
 }
 
 // so_imm - Match a 32-bit shifter_operand immediate operand, which is an
-// 8-bit immediate rotated by an arbitrary number of bits.  so_imm values are
-// represented in the imm field in the same 12-bit form that they are encoded
-// into so_imm instructions: the 8-bit immediate is the least significant bits
-// [bits 0-7], the 4-bit shift amount is the next 4 bits [bits 8-11].
+// 8-bit immediate rotated by an arbitrary number of bits.
 def so_imm : Operand<i32>, PatLeaf<(imm), [{ return Pred_so_imm(N); }]> {
   let EncoderMethod = "getSOImmOpValue";
   let PrintMethod = "printSOImmOperand";
@@ -539,7 +552,7 @@ def addrmode5 : Operand<i32>,
   let EncoderMethod = "getAddrMode5OpValue";
 }
 
-// addrmode6 := reg with optional writeback
+// addrmode6 := reg with optional alignment
 //
 def addrmode6 : Operand<i32>,
                 ComplexPattern<i32, 2, "SelectAddrMode6", [], [SDNPWantParent]>{
@@ -575,12 +588,26 @@ def nohash_imm : Operand<i32> {
   let PrintMethod = "printNoHashImmediate";
 }
 
+def CoprocNumAsmOperand : AsmOperandClass {
+  let Name = "CoprocNum";
+  let SuperClasses = [];
+  let ParserMethod = "tryParseCoprocNumOperand";
+}
+
+def CoprocRegAsmOperand : AsmOperandClass {
+  let Name = "CoprocReg";
+  let SuperClasses = [];
+  let ParserMethod = "tryParseCoprocRegOperand";
+}
+
 def p_imm : Operand<i32> {
   let PrintMethod = "printPImmediate";
+  let ParserMatchClass = CoprocNumAsmOperand;
 }
 
 def c_imm : Operand<i32> {
   let PrintMethod = "printCImmediate";
+  let ParserMatchClass = CoprocRegAsmOperand;
 }
 
 //===----------------------------------------------------------------------===//
@@ -1107,14 +1134,13 @@ multiclass APreLoad<bits<1> read, bits<1> data, string opc> {
     let Inst{22} = read;
     let Inst{21-20} = 0b01;
     let Inst{19-16} = addr{16-13};  // Rn
-    let Inst{15-12} = Rt;
+    let Inst{15-12} = 0b1111;
     let Inst{11-0}  = addr{11-0};   // imm12
   }
 
   def rs : AXI<(outs), (ins ldst_so_reg:$shift), MiscFrm, IIC_Preload,
                !strconcat(opc, "\t$shift"),
                [(ARMPreload ldst_so_reg:$shift, (i32 read), (i32 data))]> {
-    bits<4> Rt;
     bits<17> shift;
     let Inst{31-26} = 0b111101;
     let Inst{25} = 1; // 1 for register form
@@ -1123,6 +1149,7 @@ multiclass APreLoad<bits<1> read, bits<1> data, string opc> {
     let Inst{22} = read;
     let Inst{21-20} = 0b01;
     let Inst{19-16} = shift{16-13}; // Rn
+    let Inst{15-12} = 0b1111;
     let Inst{11-0}  = shift{11-0};
   }
 }
@@ -1271,7 +1298,7 @@ let isCall = 1,
           D16, D17, D18, D19, D20, D21, D22, D23,
           D24, D25, D26, D27, D28, D29, D30, D31, CPSR, FPSCR],
   Uses = [SP] in {
-  def BL  : ABXI<0b1011, (outs), (ins bltarget:$func, variable_ops),
+  def BL  : ABXI<0b1011, (outs), (ins bl_target:$func, variable_ops),
                 IIC_Br, "bl\t$func",
                 [(ARMcall tglobaladdr:$func)]>,
             Requires<[IsARM, IsNotDarwin]> {
@@ -1280,7 +1307,7 @@ let isCall = 1,
     let Inst{23-0} = func;
   }
 
-  def BL_pred : ABI<0b1011, (outs), (ins bltarget:$func, variable_ops),
+  def BL_pred : ABI<0b1011, (outs), (ins bl_target:$func, variable_ops),
                    IIC_Br, "bl", "\t$func",
                    [(ARMcall_pred tglobaladdr:$func)]>,
                 Requires<[IsARM, IsNotDarwin]> {
@@ -1456,7 +1483,7 @@ let isBranch = 1, isTerminator = 1 in {
 
   // FIXME: should be able to write a pattern for ARMBrcond, but can't use
   // a two-value operand where a dag node expects two operands. :(
-  def Bcc : ABI<0b1010, (outs), (ins brtarget:$target),
+  def Bcc : ABI<0b1010, (outs), (ins br_target:$target),
                IIC_Br, "b", "\t$target",
                [/*(ARMbrcond bb:$target, imm:$cc, CCR:$ccr)*/]> {
     bits<24> target;
@@ -3164,6 +3191,7 @@ def MVNCCi : AI1<0b1111, (outs GPR:$Rd),
 
 def memb_opt : Operand<i32> {
   let PrintMethod = "printMemBOption";
+  let ParserMatchClass = MemBarrierOptOperand;
 }
 
 // memory barriers protect the atomic sequences