This is the mail archive of the binutils@sources.redhat.com mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Thumb32 assembler (54/69)


We were allowing three arguments for a bunch of Thumb instructions
where the ARM equivalent takes only two.  This corrects that error.

zw

	* config/tc-arm.c (do_t_arit): Split 3-argument mode out to...
	(do_t_arit3): ...this new function.
	(do_t_mov_cmp): Forward hireg move/compare to do_t_cpy.
	(tinsns): Use do_t_arit3 for adc, and, bic, eor, mul, orr, ror, sbc.
	Allow only two arguments for cmn, mvn, neg, tst, rev, rev16, revsh,
	sxth, sxtb, uxtb, uxth.

===================================================================
Index: gas/config/tc-arm.c
--- gas/config/tc-arm.c	(revision 56)
+++ gas/config/tc-arm.c	(revision 57)
@@ -5138,19 +5138,21 @@
 static void
 do_t_arit (void)
 {
+  if (inst.instruction == T_OPCODE_MUL
+      && inst.operands[0].reg == inst.operands[1].reg)
+    as_tsktsk (_("Rs and Rd must be different in MUL"));
+
+  inst.instruction |= inst.operands[0].reg;
+  inst.instruction |= inst.operands[1].reg << 3;
+}
+
+/* Fake three-argument form for instructions that take three arguments
+   in ARM mode, e.g. you may write "adc r0,r0,r1" instead of "adc r0,r1".  */
+static void
+do_t_arit3 (void)
+{
   if (inst.operands[2].present)
     {
-      /* Three operand format not allowed for TST, CMN, NEG and MVN.
-	 (It isn't allowed for CMP either, but that isn't handled by this
-	 function.)  */
-      if (inst.instruction == T_OPCODE_TST
-	  || inst.instruction == T_OPCODE_CMN
-	  || inst.instruction == T_OPCODE_NEG
-	  || inst.instruction == T_OPCODE_MVN)
-	{
-	  inst.error = BAD_ARGS;
-	  return;
-	}
       if (inst.operands[0].reg != inst.operands[1].reg)
 	{
 	  inst.error = _("dest and source1 must be the same register");
@@ -5158,12 +5160,7 @@
 	}
       inst.operands[1].reg = inst.operands[2].reg;
     }
-  if (inst.instruction == T_OPCODE_MUL
-      && inst.operands[0].reg == inst.operands[2].reg)
-    as_tsktsk (_("Rs and Rd must be different in MUL"));
-
-  inst.instruction |= inst.operands[0].reg;
-  inst.instruction |= inst.operands[1].reg << 3;
+  do_t_arit ();
 }
 
 /* ARM V5 Thumb BLX (argument parse)
@@ -5396,12 +5393,7 @@
 	  inst.instruction |= inst.operands[1].reg << 3;
 	}
       else
-	{
-	  /* Opcode in inst.instruction is already correct.  */
-	  inst.instruction |= (inst.operands[0].reg & 0x8) << 4;
-	  inst.instruction |= (inst.operands[0].reg & 0x7);
-	  inst.instruction |= inst.operands[1].reg << 3;
-	}
+	do_t_cpy ();
     }
   else
     {
@@ -7629,9 +7621,9 @@
 static const struct asm_opcode tinsns[] =
 {
 #define THUMB_VARIANT ARM_EXT_V4T  /* Thumb v1 (ARMv4T).  */
-  TI(adc,    4140,     3, (RL, RL, oRL),	 t_arit),
+  TI(adc,    4140,     3, (RL, RL, oRL),	 t_arit3),
   TI(add,    0000,     3, (RR, RR_EXi, oRR_EXi), t_add_sub),
-  TI(and,    4000,     3, (RL, RL, oRL),	 t_arit),
+  TI(and,    4000,     3, (RL, RL, oRL),	 t_arit3),
   TI(asr,    4100,     3, (RL, RL_EXi, oRL_EXi), t_shift),
   TI(b,	     e7fe,     1, (EXP),		 t_branch12),
   TI(beq,    d0fe,     1, (EXP),		 t_branch9),
@@ -7652,12 +7644,12 @@
   TI(bgt,    dcfe,     1, (EXP),		 t_branch9),
   TI(ble,    ddfe,     1, (EXP),		 t_branch9),
   TI(bal,    defe,     1, (EXP),		 t_branch9),
-  TI(bic,    4380,     3, (RL, RL, oRL),	 t_arit),
+  TI(bic,    4380,     3, (RL, RL, oRL),	 t_arit3),
   TI(bl,     f7fffffe, 1, (EXP),		 t_branch23),
   TI(bx,     4700,     1, (RR),			 t_bx),
-  TI(cmn,    42c0,     3, (RL, RL, oRL),	 t_arit),
+  TI(cmn,    42c0,     2, (RL, RL),		 t_arit),
   TI(cmp,    4280,     2, (RR, RR_EXi),		 t_mov_cmp),
-  TI(eor,    4040,     3, (RL, RL, oRL),	 t_arit),
+  TI(eor,    4040,     3, (RL, RL, oRL),	 t_arit3),
   TI(ldmia,  c800,     2, (RLw, REGLST),	 t_ldmstm),
   TI(ldr,    5800,     2, (RL, ADDR),		 t_ldst),
   TI(ldrb,   5c00,     2, (RL, ADDR),		 t_ldst),
@@ -7669,21 +7661,21 @@
   TI(lsl,    4080,     3, (RL, RL_EXi, oRL_EXi), t_shift),
   TI(lsr,    40c0,     3, (RL, RL_EXi, oRL_EXi), t_shift),
   TI(mov,    4600,     2, (RR, RR_EXi),		 t_mov_cmp),
-  TI(mul,    4340,     3, (RL, RL, oRL),	 t_arit),
-  TI(mvn,    43c0,     3, (RL, RL, oRL),	 t_arit),
-  TI(neg,    4240,     3, (RL, RL, oRL),	 t_arit),
-  TI(orr,    4300,     3, (RL, RL, oRL),	 t_arit),
+  TI(mul,    4340,     3, (RL, RL, oRL),	 t_arit3),
+  TI(mvn,    43c0,     2, (RL, RL),	 	 t_arit),
+  TI(neg,    4240,     2, (RL, RL),		 t_arit),
+  TI(orr,    4300,     3, (RL, RL, oRL),	 t_arit3),
   TI(pop,    bc00,     1, (REGLST),		 t_push_pop),
   TI(push,   b400,     1, (REGLST),		 t_push_pop),
-  TI(ror,    41c0,     3, (RL, RL, oRL),	 t_arit),
-  TI(sbc,    4180,     3, (RL, RL, oRL),	 t_arit),
+  TI(ror,    41c0,     3, (RL, RL, oRL),	 t_arit3),
+  TI(sbc,    4180,     3, (RL, RL, oRL),	 t_arit3),
   TI(stmia,  c000,     2, (RLw, REGLST),	 t_ldmstm),
   TI(str,    5000,     2, (RL, ADDR),		 t_ldst),
   TI(strb,   5400,     2, (RL, ADDR),		 t_ldst),
   TI(strh,   5200,     2, (RL, ADDR),		 t_ldst),
   TI(swi,    df00,     1, (EXP),		 t_swi),
   TI(sub,    8000,     3, (RR, RR_EXi, oRR_EXi), t_add_sub),
-  TI(tst,    4200,     3, (RL, RL, oRL),	 t_arit),
+  TI(tst,    4200,     2, (RL, RL),		 t_arit),
   /* Pseudo ops:  */
   TI(adr,    000f,     2, (RL, EXP),		 t_adr),
   TI(nop,    46c0,     0, (),			 noargs), /* mov r8,r8  */
@@ -7698,14 +7690,14 @@
   TI(cpsie,  b660,     1, (CPSF),		 imm0),
   TI(cpsid,  b670,     1, (CPSF),		 imm0),
   TI(cpy,    4600,     2, (RR, RR),		 t_cpy),
-  TI(rev,    ba00,     3, (RL, RL, oRL),	 t_arit),
-  TI(rev16,  ba40,     3, (RL, RL, oRL),	 t_arit),
-  TI(revsh,  bac0,     3, (RL, RL, oRL),	 t_arit),
+  TI(rev,    ba00,     2, (RL, RL),		 t_arit),
+  TI(rev16,  ba40,     2, (RL, RL),		 t_arit),
+  TI(revsh,  bac0,     2, (RL, RL),		 t_arit),
   TI(setend, b650,     1, (ENDI),		 t_setend),
-  TI(sxth,   b200,     3, (RL, RL, oRL),	 t_arit),
-  TI(sxtb,   b240,     3, (RL, RL, oRL),	 t_arit),
-  TI(uxth,   b280,     3, (RL, RL, oRL),	 t_arit),
-  TI(uxtb,   b2c0,     3, (RL, RL, oRL),	 t_arit),
+  TI(sxth,   b200,     2, (RL, RL),		 t_arit),
+  TI(sxtb,   b240,     2, (RL, RL),		 t_arit),
+  TI(uxth,   b280,     2, (RL, RL),		 t_arit),
+  TI(uxtb,   b2c0,     2, (RL, RL),		 t_arit),
 
 #undef THUMB_VARIANT
 #define THUMB_VARIANT ARM_EXT_V6K

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]