ARM parsing and encoding for SVC instruction.
authorJim Grosbach <grosbach@apple.com>
Tue, 26 Jul 2011 16:24:27 +0000 (16:24 +0000)
committerJim Grosbach <grosbach@apple.com>
Tue, 26 Jul 2011 16:24:27 +0000 (16:24 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@136090 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Target/ARM/ARMInstrInfo.td
lib/Target/ARM/ARMInstrThumb.td
lib/Target/ARM/AsmParser/ARMAsmParser.cpp
test/MC/ARM/basic-arm-instructions.s
test/MC/ARM/diagnostics.s
utils/TableGen/EDEmitter.cpp

index 83a25148040b0d87120cfb03d17d80e0adef7e06..c7ed266ec906025f021302850a6f5ae82d6e7426 100644 (file)
@@ -515,6 +515,15 @@ def imm0_65535_expr : Operand<i32> {
   let ParserMatchClass = Imm0_65535ExprAsmOperand;
 }
 
+/// imm24b - True if the 32-bit immediate is encodable in 24 bits.
+def Imm24bitAsmOperand: AsmOperandClass { let Name = "Imm24bit"; }
+def imm24b : Operand<i32>, ImmLeaf<i32, [{
+  return Imm >= 0 && Imm <= 0xffffff;
+}]> {
+  let ParserMatchClass = Imm24bitAsmOperand;
+}
+
+
 /// bf_inv_mask_imm predicate - An AND mask to clear an arbitrary width bitfield
 /// e.g., 0xf000ffff
 def bf_inv_mask_imm : Operand<i32>,
@@ -1730,10 +1739,9 @@ def SMC : ABI<0b0001, (outs), (ins imm0_15:$opt), NoItinerary, "smc", "\t$opt",
   let Inst{3-0} = opt;
 }
 
-// Supervisor Call (Software Interrupt) -- for disassembly only
+// Supervisor Call (Software Interrupt)
 let isCall = 1, Uses = [SP] in {
-def SVC : ABI<0b1111, (outs), (ins i32imm:$svc), IIC_Br, "svc", "\t$svc",
-              [/* For disassembly only; pattern left blank */]> {
+def SVC : ABI<0b1111, (outs), (ins imm24b:$svc), IIC_Br, "svc", "\t$svc", []> {
   bits<24> svc;
   let Inst{23-0} = svc;
 }
index cb242cec2c068237e5b1474814bdda228560797f..19182db109b56ee67495aa3e0aaf4d659c285e76 100644 (file)
@@ -547,7 +547,7 @@ let isCall = 1, isTerminator = 1, isReturn = 1, isBarrier = 1 in {
 // A8.6.16 B: Encoding T1
 // If Inst{11-8} == 0b1111 then SEE SVC
 let isCall = 1, Uses = [SP] in
-def tSVC : T1pI<(outs), (ins i32imm:$imm), IIC_Br,
+def tSVC : T1pI<(outs), (ins imm0_255:$imm), IIC_Br,
                 "svc", "\t$imm", []>, Encoding16 {
   bits<8> imm;
   let Inst{15-12} = 0b1101;
index 39ca9530a1941257f46e8250840a9e670bce9cf9..c252ce8358a2c482960ec76ea4e7d1ea9fbb7706 100644 (file)
@@ -467,6 +467,14 @@ public:
     int64_t Value = CE->getValue();
     return Value >= 0 && Value < 65536;
   }
+  bool isImm24bit() const {
+    if (Kind != Immediate)
+      return false;
+    const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
+    if (!CE) return false;
+    int64_t Value = CE->getValue();
+    return Value >= 0 && Value <= 0xffffff;
+  }
   bool isPKHLSLImm() const {
     if (Kind != Immediate)
       return false;
@@ -738,6 +746,11 @@ public:
     addExpr(Inst, getImm());
   }
 
+  void addImm24bitOperands(MCInst &Inst, unsigned N) const {
+    assert(N == 1 && "Invalid number of operands!");
+    addExpr(Inst, getImm());
+  }
+
   void addPKHLSLImmOperands(MCInst &Inst, unsigned N) const {
     assert(N == 1 && "Invalid number of operands!");
     addExpr(Inst, getImm());
index 466d16e64768df04995d539bedec510c315735f5..13afd8b583ea1a82dcad43ad78ed001ad1a68866 100644 (file)
@@ -1752,3 +1752,14 @@ _func:
 @ CHECK: sub   r6, r6, r7, asr r9      @ encoding: [0x57,0x69,0x46,0xe0]
 @ CHECK: sub   r6, r6, r7, ror r9      @ encoding: [0x77,0x69,0x46,0xe0]
 
+
+@------------------------------------------------------------------------------
+@ SVC
+@------------------------------------------------------------------------------
+        svc #16
+        svc #0
+        svc #0xffffff
+
+@ CHECK: svc   #16                     @ encoding: [0x10,0x00,0x00,0xef]
+@ CHECK: svc   #0                      @ encoding: [0x00,0x00,0x00,0xef]
+@ CHECK: svc   #16777215               @ encoding: [0xff,0xff,0xff,0xef]
index afbbb36ed7425bfb4626a80d49b172e108ecb846..0c51887c7a29887cf927c3ee6692822a26674071 100644 (file)
 @ CHECK-ERRORS: warning: register not in ascending order in register list
 @ CHECK-ERRORS:         stmda     sp!, {r5, r2}
 @ CHECK-ERRORS:                            ^
+
+
+        @ Out of range immediate on SVC
+        svc #0x1000000
+@ CHECK-ERRORS: error: invalid operand for instruction
+@ CHECK-ERRORS:   svc #0x1000000
+@ CHECK-ERRORS:       ^
index c9542cb8e75c6280a25271ad956f239393932f45..83d93cb83f20bcbb7193efaa0f3bb504d460d257 100644 (file)
@@ -596,6 +596,7 @@ static int ARMFlagFromOpName(LiteralConstantEmitter *type,
   IMM("imm0_4095");
   IMM("imm0_65535");
   IMM("imm0_65535_expr");
+  IMM("imm24b");
   IMM("pkh_lsl_amt");
   IMM("pkh_asr_amt");
   IMM("jt2block_operand");