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 (8/69)


The previous patch pays dividends, allowing us to get rid of some
redundant constants and simplify some of the coprocessor parsers.

	* config/tc-arm.c (enum wreg_type): Delete.
	(IWMMXT_REG_WR, IWMMXT_REG_WC, IWMMXT_REG_WCG): All occurrences
	replaced with REG_TYPE_MMXWR, REG_TYPE_MMXWC, REG_TYPE_MMXWCG
	respectively.
	(arm_reg_parse_multi): New function.
	(arm_reg_parse, wreg_required_here, mav_reg_required_here)
	(s_arm_unwind_save): Rewrite in terms of arm_reg_parse_multi.

===================================================================
Index: gas/config/tc-arm.c
--- gas/config/tc-arm.c	(revision 9)
+++ gas/config/tc-arm.c	(revision 10)
@@ -481,13 +481,6 @@
   {"SPSR_cxsf",	FALSE, PSR_c | PSR_x | PSR_s | PSR_f},
 };
 
-enum wreg_type
-  {
-    IWMMXT_REG_WR = 0,
-    IWMMXT_REG_WC = 1,
-    IWMMXT_REG_WCG
-  };
-
 enum iwmmxt_insn_type
 {
   check_rd,
@@ -1275,11 +1268,11 @@
 
 /* Generic register parser.  CCP points to what should be the
    beginning of a register name.  If it is indeed a valid register
-   name, of type TYPE, return the associated register number.  If it
-   is not, return FAIL.  Does not issue diagnostics.  */
+   name, advance CCP over it and return the reg_entry structure;
+   otherwise return NULL.  Does not issue diagnostics.  */
 
-static int
-arm_reg_parse (char **ccp, enum arm_reg_type type)
+static struct reg_entry *
+arm_reg_parse_multi (char **ccp)
 {
   char *start = *ccp;
   char *p;
@@ -1297,7 +1290,7 @@
 
   p = start;
   if (!ISALPHA (*p) || !is_name_beginner (*p))
-    return FAIL;
+    return NULL;
 
   do
     p++;
@@ -1305,13 +1298,29 @@
 
   reg = (struct reg_entry *) hash_find_n (arm_reg_hsh, start, p - start);
 
-  if (!reg || reg->type != type)
-    return FAIL;
+  if (!reg)
+    return NULL;
   
   *ccp = p;
-  return reg->number;
+  return reg;
 }
 
+/* As above, but the register must be of type TYPE, and the return
+   value is the register number or NULL.  */
+
+static int
+arm_reg_parse (char **ccp, enum arm_reg_type type)
+{
+  char *start = *ccp;
+  struct reg_entry *reg = arm_reg_parse_multi (ccp);
+
+  if (reg && reg->type == type)
+    return reg->number;
+
+  *ccp = start;
+  return FAIL;
+}
+
 /* A standard register must be given at this point.  SHIFT is the
    place to put it in inst.instruction.  Restores input start point on
    error.  Returns the reg#, or FAIL.  */
@@ -1512,44 +1521,21 @@
    Returns the reg#, or FAIL.  */
 
 static int
-wreg_required_here (char **str, int shift, enum wreg_type reg_type)
+wreg_required_here (char **str, int shift, enum arm_reg_type regtype)
 {
   int reg;
 
-  switch (reg_type)
+  if ((reg = arm_reg_parse (str, regtype)) == FAIL)
     {
-    case IWMMXT_REG_WR:
-      if ((reg = arm_reg_parse (str, REG_TYPE_MMXWR)) == FAIL)
-	{
-	  inst.error = gettext (reg_expected_msgs[REG_TYPE_MMXWR]);
-	  return FAIL;
-	}
-      break;
-
-    case IWMMXT_REG_WC:
-      if ((reg = arm_reg_parse (str, REG_TYPE_MMXWC)) == FAIL)
-	{
-	  inst.error = gettext (reg_expected_msgs[REG_TYPE_MMXWC]);
-	  return FAIL;
-	}
-      break;
-
-    case IWMMXT_REG_WCG:
-      if ((reg = arm_reg_parse (str, REG_TYPE_MMXWCG)) == FAIL)
-	{
-	  inst.error = gettext (reg_expected_msgs[REG_TYPE_MMXWCG]);
-	  return FAIL;
-	}
-      break;
-
-    default:
-      abort ();
+      inst.error = gettext (reg_expected_msgs[regtype]);
+      return FAIL;
     }
-
-  if (shift >= 0)
-    inst.instruction |= reg << shift;
-
-  return reg;
+  else
+    {
+      if (shift >= 0)
+	inst.instruction |= reg << shift;
+      return reg;
+    }
 }
 
 /* A register must be given at this point.
@@ -1562,43 +1548,27 @@
 static int
 mav_reg_required_here (char ** str, int shift, enum arm_reg_type regtype)
 {
-  int   reg;
+  struct reg_entry *reg;
   char *start = *str;
 
-  if ((reg = arm_reg_parse (str, regtype)) != FAIL)
+  reg = arm_reg_parse_multi (str);
+  if (!reg
+      || (reg->type != regtype
+	  /* Accept generic coprocessor register if applicable.  */
+	  && (reg->type != REG_TYPE_CN || (regtype != REG_TYPE_MVF
+					   && regtype != REG_TYPE_MVD
+					   && regtype != REG_TYPE_MVFX
+					   && regtype != REG_TYPE_MVDX))))
     {
-      if (shift >= 0)
-	inst.instruction |= reg << shift;
-
-      return reg;
-    }
-
-  /* Restore the start point.  */
-  *str = start;
-
-  /* Try generic coprocessor name if applicable.  */
-  if (regtype == REG_TYPE_MVF ||
-      regtype == REG_TYPE_MVD ||
-      regtype == REG_TYPE_MVFX ||
-      regtype == REG_TYPE_MVDX)
-    {
-      if ((reg = arm_reg_parse (str, REG_TYPE_CN)) != FAIL)
-	{
-	  if (shift >= 0)
-	    inst.instruction |= reg << shift;
-
-	  return reg;
-	}
-
-      /* Restore the start point.  */
+      inst.error = gettext (reg_expected_msgs[regtype]);
       *str = start;
+      return FAIL;
     }
 
-  /* In the few cases where we might be able to accept something else
-     this error can be overridden.  */
-  inst.error = gettext (reg_expected_msgs[regtype]);
+  if (shift >= 0)
+    inst.instruction |= reg->number << shift;
 
-  return FAIL;
+  return reg->number;
 }
 
 /* Expects *str -> the characters "acc0", possibly with leading blanks.
@@ -4522,59 +4492,50 @@
 static void
 s_arm_unwind_save (int ignored ATTRIBUTE_UNUSED)
 {
-  char *saved_ptr;
-  int reg;
+  char *peek;
+  struct reg_entry *reg;
+  bfd_boolean had_brace = FALSE;
 
   /* Figure out what sort of save we have.  */
-  SKIP_WHITESPACE ();
-  saved_ptr = input_line_pointer;
+  peek = input_line_pointer;
+  skip_whitespace (peek);
 
-  reg = arm_reg_parse (&input_line_pointer, REG_TYPE_FN);
-  if (reg != FAIL)
+  if (*peek == '{')
     {
-      s_arm_unwind_save_fpa (reg);
-      return;
+      had_brace = TRUE;
+      peek++;
     }
 
-  if (*input_line_pointer == '{')
-    input_line_pointer++;
+  reg = arm_reg_parse_multi (&peek);
 
-  SKIP_WHITESPACE ();
-
-  reg = arm_reg_parse (&input_line_pointer, REG_TYPE_RN);
-  if (reg != FAIL)
+  if (!reg)
     {
-      input_line_pointer = saved_ptr;
-      s_arm_unwind_save_core ();
+      as_bad (_("register expected"));
+      ignore_rest_of_line ();
       return;
     }
 
-  reg = arm_reg_parse (&input_line_pointer, REG_TYPE_DN);
-  if (reg != FAIL)
+  switch (reg->type)
     {
-      input_line_pointer = saved_ptr;
-      s_arm_unwind_save_vfp ();
+    case REG_TYPE_FN:
+      if (had_brace)
+	{
+	  as_bad (_("FPA .unwind_save does not take a register list"));
+	  ignore_rest_of_line ();
+	  return;
+	}
+      s_arm_unwind_save_fpa (reg->number);
       return;
-    }
 
-  reg = arm_reg_parse (&input_line_pointer, REG_TYPE_MMXWR);
-  if (reg != FAIL)
-    {
-      input_line_pointer = saved_ptr;
-      s_arm_unwind_save_mmxwr ();
-      return;
-    }
+    case REG_TYPE_RN:     s_arm_unwind_save_core ();   return;
+    case REG_TYPE_DN:     s_arm_unwind_save_vfp ();    return;
+    case REG_TYPE_MMXWR:  s_arm_unwind_save_mmxwr ();  return;
+    case REG_TYPE_MMXWCG: s_arm_unwind_save_mmxwcg (); return;
 
-  reg = arm_reg_parse (&input_line_pointer, REG_TYPE_MMXWCG);
-  if (reg != FAIL)
-    {
-      input_line_pointer = saved_ptr;
-      s_arm_unwind_save_mmxwcg ();
-      return;
+    default:
+      as_bad (_(".unwind_save does not support this kind of register"));
+      ignore_rest_of_line ();
     }
-
-  /* TODO: Maverick registers.  */
-  as_bad (_("unrecognised register"));
 }
 
 
@@ -8741,37 +8702,37 @@
       break;
 
     case check_wr:
-       if ((wreg_required_here (&str, 0, IWMMXT_REG_WR)) == FAIL)
+       if ((wreg_required_here (&str, 0, REG_TYPE_MMXWR)) == FAIL)
 	 return FAIL;
        break;
 
     case check_wrwr:
-      if ((wreg_required_here (&str, 12, IWMMXT_REG_WR) == FAIL
+      if ((wreg_required_here (&str, 12, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 16, IWMMXT_REG_WR) == FAIL))
+	   || wreg_required_here (&str, 16, REG_TYPE_MMXWR) == FAIL))
 	return FAIL;
       break;
 
     case check_wrwrwr:
-      if ((wreg_required_here (&str, 12, IWMMXT_REG_WR) == FAIL
+      if ((wreg_required_here (&str, 12, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 16, IWMMXT_REG_WR) == FAIL
+	   || wreg_required_here (&str, 16, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 0, IWMMXT_REG_WR) == FAIL))
+	   || wreg_required_here (&str, 0, REG_TYPE_MMXWR) == FAIL))
 	return FAIL;
       break;
 
     case check_wrwrwcg:
-      if ((wreg_required_here (&str, 12, IWMMXT_REG_WR) == FAIL
+      if ((wreg_required_here (&str, 12, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 16, IWMMXT_REG_WR) == FAIL
+	   || wreg_required_here (&str, 16, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 0, IWMMXT_REG_WCG) == FAIL))
+	   || wreg_required_here (&str, 0, REG_TYPE_MMXWCG) == FAIL))
 	return FAIL;
       break;
 
     case check_tbcst:
-      if ((wreg_required_here (&str, 16, IWMMXT_REG_WR) == FAIL
+      if ((wreg_required_here (&str, 16, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
 	   || reg_required_here (&str, 12, FALSE) == FAIL))
 	return FAIL;
@@ -8780,12 +8741,12 @@
     case check_tmovmsk:
       if ((reg_required_here (&str, 12, FALSE) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 16, IWMMXT_REG_WR) == FAIL))
+	   || wreg_required_here (&str, 16, REG_TYPE_MMXWR) == FAIL))
 	return FAIL;
       break;
 
     case check_tmia:
-      if ((wreg_required_here (&str, 5, IWMMXT_REG_WR) == FAIL
+      if ((wreg_required_here (&str, 5, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
 	   || reg_required_here (&str, 0, FALSE) == FAIL
 	   || skip_past_comma (&str) == FAIL
@@ -8794,7 +8755,7 @@
       break;
 
     case check_tmcrr:
-      if ((wreg_required_here (&str, 0, IWMMXT_REG_WR) == FAIL
+      if ((wreg_required_here (&str, 0, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
 	   || reg_required_here (&str, 12, FALSE) == FAIL
 	   || skip_past_comma (&str) == FAIL
@@ -8807,12 +8768,12 @@
 	   || skip_past_comma (&str) == FAIL
 	   || reg_required_here (&str, 16, FALSE) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 0, IWMMXT_REG_WR) == FAIL))
+	   || wreg_required_here (&str, 0, REG_TYPE_MMXWR) == FAIL))
 	return FAIL;
       break;
 
     case check_tmcr:
-      if ((wreg_required_here (&str, 16, IWMMXT_REG_WC) == FAIL
+      if ((wreg_required_here (&str, 16, REG_TYPE_MMXWC) == FAIL
 	   || skip_past_comma (&str) == FAIL
 	   || reg_required_here (&str, 12, FALSE) == FAIL))
 	return FAIL;
@@ -8821,12 +8782,12 @@
     case check_tmrc:
       if ((reg_required_here (&str, 12, FALSE) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 16, IWMMXT_REG_WC) == FAIL))
+	   || wreg_required_here (&str, 16, REG_TYPE_MMXWC) == FAIL))
 	return FAIL;
       break;
 
     case check_tinsr:
-      if ((wreg_required_here (&str, 16, IWMMXT_REG_WR) == FAIL
+      if ((wreg_required_here (&str, 16, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
 	   || reg_required_here (&str, 12, FALSE) == FAIL
 	   || skip_past_comma (&str) == FAIL))
@@ -8840,11 +8801,11 @@
       break;
 
     case check_waligni:
-      if ((wreg_required_here (&str, 12, IWMMXT_REG_WR) == FAIL
+      if ((wreg_required_here (&str, 12, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 16, IWMMXT_REG_WR) == FAIL
+	   || wreg_required_here (&str, 16, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 0, IWMMXT_REG_WR) == FAIL
+	   || wreg_required_here (&str, 0, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL))
 	return FAIL;
       break;
@@ -8852,15 +8813,15 @@
     case check_textrm:
       if ((reg_required_here (&str, 12, FALSE) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 16, IWMMXT_REG_WR) == FAIL
+	   || wreg_required_here (&str, 16, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL))
 	return FAIL;
       break;
 
     case check_wshufh:
-      if ((wreg_required_here (&str, 12, IWMMXT_REG_WR) == FAIL
+      if ((wreg_required_here (&str, 12, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL
-	   || wreg_required_here (&str, 16, IWMMXT_REG_WR) == FAIL
+	   || wreg_required_here (&str, 16, REG_TYPE_MMXWR) == FAIL
 	   || skip_past_comma (&str) == FAIL))
 	return FAIL;
       break;
@@ -8894,7 +8855,7 @@
 
   skip_whitespace (str);
 
-  if ((reg = wreg_required_here (&str, 12, IWMMXT_REG_WR)) == FAIL
+  if ((reg = wreg_required_here (&str, 12, REG_TYPE_MMXWR)) == FAIL
       || skip_past_comma (& str) == FAIL
       || cp_byte_address_required_here (&str) == FAIL)
     {
@@ -9028,10 +8989,10 @@
 
   skip_whitespace (str);
 
-  if ((reg = wreg_required_here (&str, 12, IWMMXT_REG_WR)) == FAIL)
+  if ((reg = wreg_required_here (&str, 12, REG_TYPE_MMXWR)) == FAIL)
     {
       inst.error = 0;
-      if ((reg = wreg_required_here (&str, 12, IWMMXT_REG_WC)) == FAIL)
+      if ((reg = wreg_required_here (&str, 12, REG_TYPE_MMXWC)) == FAIL)
 	return;
       
       if ((inst.instruction & COND_MASK) != COND_ALWAYS)

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