OSDN Git Service

Daily bump.
[pf3gnuchains/gcc-fork.git] / gcc / genattrtab.c
index 374f50f..8ac90c6 100644 (file)
@@ -34,7 +34,7 @@ Boston, MA 02111-1307, USA.  */
 
    If the attribute `alternative', or a random C expression is present,
    `constrain_operands' is called.  If either of these cases of a reference to
-   an operand is found, `insn_extract' is called.
+   an operand is found, `extract_insn' is called.
 
    The special attribute `length' is also recognized.  For this operand, 
    expressions involving the address of an operand or the current insn,
@@ -96,12 +96,6 @@ Boston, MA 02111-1307, USA.  */
 
 
 #include "hconfig.h"
-/* varargs must always be included after *config.h.  */
-#ifdef __STDC__
-#include <stdarg.h>
-#else
-#include <varargs.h>
-#endif
 #include "system.h"
 #include "rtl.h"
 #include "insn-config.h"       /* For REGISTER_CONSTRAINTS */
@@ -125,8 +119,9 @@ struct obstack *temp_obstack = &obstack2;
 /* Define this so we can link with print-rtl.o to get debug_rtx function.  */
 char **insn_name_ptr = 0;
 
-static void fatal ();
-void fancy_abort PROTO((void));
+static void fatal PVPROTO ((char *, ...))
+  ATTRIBUTE_PRINTF_1 ATTRIBUTE_NORETURN;
+void fancy_abort PROTO((void)) ATTRIBUTE_NORETURN;
 
 /* enough space to reserve for printing out ints */
 #define MAX_DIGITS (HOST_BITS_PER_INT * 3 / 10 + 3)
@@ -178,11 +173,13 @@ struct attr_desc
 {
   char *name;                  /* Name of attribute.  */
   struct attr_desc *next;      /* Next attribute.  */
-  int is_numeric;              /* Values of this attribute are numeric.  */
-  int negative_ok;             /* Allow negative numeric values.  */
-  int unsigned_p;              /* Make the output function unsigned int.  */
-  int is_const;                        /* Attribute value constant for each run.  */
-  int is_special;              /* Don't call `write_attr_set'.  */
+  unsigned is_numeric  : 1;    /* Values of this attribute are numeric.  */
+  unsigned negative_ok : 1;    /* Allow negative numeric values.  */
+  unsigned unsigned_p  : 1;    /* Make the output function unsigned int.  */
+  unsigned is_const    : 1;    /* Attribute value constant for each run.  */
+  unsigned is_special  : 1;    /* Don't call `write_attr_set'.  */
+  unsigned func_units_p        : 1;    /* this is the function_units attribute */
+  unsigned blockage_p  : 1;    /* this is the blockage range function */
   struct attr_value *first_value; /* First value of this attribute.  */
   struct attr_value *default_val; /* Default value for this attribute.  */
 };
@@ -339,7 +336,9 @@ static char *alternative_name;
 
 int reload_completed = 0;
 
-/* Similarly since PRESERVE_DEATH_INFO_REGNO_P might reference "optimize".  */
+/* Some machines test `optimize' in macros called from rtlanal.c, so we need
+   to define it here.  */
+
 int optimize = 0;
 
 /* Simplify an expression.  Only call the routine if there is something to
@@ -363,18 +362,15 @@ int optimize = 0;
 struct _global_rtl global_rtl;
 rtx pic_offset_table_rtx;
 
+static void attr_hash_add_rtx  PROTO((int, rtx));
+static void attr_hash_add_string PROTO((int, char *));
 static rtx attr_rtx            PVPROTO((enum rtx_code, ...));
-#ifdef HAVE_VPRINTF
 static char *attr_printf       PVPROTO((int, char *, ...));
-#else
-static char *attr_printf ();
-#endif
-
 static char *attr_string        PROTO((char *, int));
 static rtx check_attr_test     PROTO((rtx, int));
 static rtx check_attr_value    PROTO((rtx, struct attr_desc *));
-static rtx convert_set_attr_alternative PROTO((rtx, int, int, int));
-static rtx convert_set_attr    PROTO((rtx, int, int, int));
+static rtx convert_set_attr_alternative PROTO((rtx, int, int));
+static rtx convert_set_attr    PROTO((rtx, int, int));
 static void check_defs         PROTO((void));
 #if 0
 static rtx convert_const_symbol_ref PROTO((rtx, struct attr_desc *));
@@ -396,6 +392,7 @@ static rtx identity_fn              PROTO((rtx));
 static rtx zero_fn             PROTO((rtx));
 static rtx one_fn              PROTO((rtx));
 static rtx max_fn              PROTO((rtx));
+static void write_length_unit_log PROTO ((void));
 static rtx simplify_cond       PROTO((rtx, int, int));
 #if 0
 static rtx simplify_by_alternatives PROTO((rtx, int, int));
@@ -437,6 +434,7 @@ static void write_attr_set  PROTO((struct attr_desc *, int, rtx, char *,
                                       char *, rtx, int, int));
 static void write_attr_case    PROTO((struct attr_desc *, struct attr_value *,
                                       int, char *, char *, int, rtx));
+static void write_unit_name    PROTO((char *, int, char *));
 static void write_attr_valueq  PROTO((struct attr_desc *, char *));
 static void write_attr_value   PROTO((struct attr_desc *, rtx));
 static void write_upcase       PROTO((char *));
@@ -733,8 +731,6 @@ attr_rtx VPROTO((enum rtx_code code, ...))
 
    rtx attr_printf (len, format, [arg1, ..., argn])  */
 
-#ifdef HAVE_VPRINTF
-
 /*VARARGS2*/
 static char *
 attr_printf VPROTO((register int len, char *fmt, ...))
@@ -761,24 +757,6 @@ attr_printf VPROTO((register int len, char *fmt, ...))
   return attr_string (str, strlen (str));
 }
 
-#else /* not HAVE_VPRINTF */
-
-static char *
-attr_printf (len, fmt, arg1, arg2, arg3)
-     int len;
-     char *fmt;
-     char *arg1, *arg2, *arg3; /* also int */
-{
-  register char *str;
-
-  /* Print the string into a temporary location.  */
-  str = (char *) alloca (len);
-  sprintf (str, fmt, arg1, arg2, arg3);
-
-  return attr_string (str, strlen (str));
-}
-#endif /* not HAVE_VPRINTF */
-
 rtx
 attr_eq (name, value)
      char *name, *value;
@@ -974,12 +952,12 @@ check_attr_test (exp, is_const)
                  return exp;
                }
              else
-               fatal ("Unknown attribute `%s' in EQ_ATTR", XEXP (exp, 0));
+               fatal ("Unknown attribute `%s' in EQ_ATTR", XSTR (exp, 0));
            }
 
          if (is_const && ! attr->is_const)
            fatal ("Constant expression uses insn attribute `%s' in EQ_ATTR",
-                  XEXP (exp, 0));
+                  XSTR (exp, 0));
 
          /* Copy this just to make it permanent,
             so expressions using it can be permanent too.  */
@@ -996,7 +974,7 @@ check_attr_test (exp, is_const)
              for (p = XSTR (exp, 1); *p; p++)
                if (*p < '0' || *p > '9')
                   fatal ("Attribute `%s' takes only numeric values", 
-                         XEXP (exp, 0));
+                         XSTR (exp, 0));
            }
          else
            {
@@ -1007,7 +985,7 @@ check_attr_test (exp, is_const)
 
              if (av == NULL)
                fatal ("Unknown value `%s' for `%s' attribute",
-                      XEXP (exp, 1), XEXP (exp, 0));
+                      XSTR (exp, 1), XSTR (exp, 0));
            }
        }
       else
@@ -1189,10 +1167,10 @@ check_attr_value (exp, attr)
    It becomes a COND with each test being (eq_attr "alternative "n") */
 
 static rtx
-convert_set_attr_alternative (exp, num_alt, insn_code, insn_index)
+convert_set_attr_alternative (exp, num_alt, insn_index)
      rtx exp;
      int num_alt;
-     int insn_code, insn_index;
+     int insn_index;
 {
   rtx condexp;
   int i;
@@ -1230,10 +1208,10 @@ convert_set_attr_alternative (exp, num_alt, insn_code, insn_index)
    list of values is given, convert to SET_ATTR_ALTERNATIVE first.  */
 
 static rtx
-convert_set_attr (exp, num_alt, insn_code, insn_index)
+convert_set_attr (exp, num_alt, insn_index)
      rtx exp;
      int num_alt;
-     int insn_code, insn_index;
+     int insn_index;
 {
   rtx newexp;
   char *name_ptr;
@@ -1257,7 +1235,7 @@ convert_set_attr (exp, num_alt, insn_code, insn_index)
   while ((p = next_comma_elt (&name_ptr)) != NULL)
     XVECEXP (newexp, 1, n++) = attr_rtx (CONST_STRING, p);
 
-  return convert_set_attr_alternative (newexp, num_alt, insn_code, insn_index);
+  return convert_set_attr_alternative (newexp, num_alt, insn_index);
 }
 \f
 /* Scan all definitions, checking for validity.  Also, convert any SET_ATTR
@@ -1290,13 +1268,12 @@ check_defs ()
            case SET_ATTR_ALTERNATIVE:
              value = convert_set_attr_alternative (value,
                                                    id->num_alternatives,
-                                                   id->insn_code,
                                                    id->insn_index);
              break;
 
            case SET_ATTR:
              value = convert_set_attr (value, id->num_alternatives,
-                                       id->insn_code, id->insn_index);
+                                       id->insn_index);
              break;
 
            default:
@@ -1931,7 +1908,7 @@ expand_units ()
       unitsmask = attr_rtx (FFS, unitsmask);
     }
 
-  make_internal_attr ("*function_units_used", unitsmask, 2);
+  make_internal_attr ("*function_units_used", unitsmask, 10);
 
   /* Create an array of ops for each unit.  Add an extra unit for the
      result_ready_cost function that has the ops of all other units.  */
@@ -2144,13 +2121,13 @@ expand_units ()
          if (unit->needs_range_function)
            {
              /* Compute the blockage range function and make an attribute
-                for writing it's value.  */
+                for writing its value.  */
              newexp = operate_exp (RANGE_OP, min_blockage, max_blockage);
              newexp = simplify_knowing (newexp, unit->condexp);
 
              str = attr_printf (strlen (unit->name) + sizeof ("*_unit_blockage_range"),
                                 "*%s_unit_blockage_range", unit->name);
-             make_internal_attr (str, newexp, 4);
+             make_internal_attr (str, newexp, 20);
            }
 
          str = attr_printf (strlen (unit->name) + sizeof ("*_unit_ready_cost"),
@@ -2414,7 +2391,7 @@ make_length_attrs ()
                              "*insn_current_length"};
   static rtx (*no_address_fn[]) PROTO((rtx)) = {identity_fn, zero_fn, zero_fn};
   static rtx (*address_fn[]) PROTO((rtx)) = {max_fn, one_fn, identity_fn};
-  int i;
+  size_t i;
   struct attr_desc *length_attr, *new_attr;
   struct attr_value *av, *new_av;
   struct insn_ent *ie, *new_ie;
@@ -2465,14 +2442,14 @@ identity_fn (exp)
 
 static rtx
 zero_fn (exp)
-     rtx exp;
+     rtx exp ATTRIBUTE_UNUSED;
 {
   return make_numeric_value (0);
 }
 
 static rtx
 one_fn (exp)
-     rtx exp;
+     rtx exp ATTRIBUTE_UNUSED;
 {
   return make_numeric_value (1);
 }
@@ -4052,7 +4029,7 @@ clear_struct_flag (x)
 }
 
 /* Return the number of RTX objects making up the expression X.
-   But if we count more more than MAX objects, stop counting.  */
+   But if we count more than MAX objects, stop counting.  */
 
 static int
 count_sub_rtxs (x, max)
@@ -4423,8 +4400,7 @@ gen_unit (def)
   unit->condexp = insert_right_side (IOR, unit->condexp, op->condexp, -2, -2);
 }
 \f
-/* Given a piece of RTX, print a C expression to test it's truth value.
-
+/* Given a piece of RTX, print a C expression to test its truth value.
    We use AND and IOR both for logical and bit-wise operations, so 
    interpret them as logical unless they are inside a comparison expression.
    The first bit of FLAGS will be non-zero in that case.
@@ -5087,14 +5063,14 @@ write_attr_case (attr, av, write_case_lines, prefix, suffix, indent,
   if (must_extract)
     {
       write_indent (indent + 2);
-      printf ("insn_extract (insn);\n");
+      printf ("extract_insn (insn);\n");
     }
 
   if (must_constrain)
     {
 #ifdef REGISTER_CONSTRAINTS
       write_indent (indent + 2);
-      printf ("if (! constrain_operands (INSN_CODE (insn), reload_completed))\n");
+      printf ("if (! constrain_operands (reload_completed))\n");
       write_indent (indent + 2);
       printf ("  fatal_insn_not_found (insn);\n");
 #endif
@@ -5199,16 +5175,61 @@ write_toplevel_expr (p)
 /* Utilities to write names in various forms.  */
 
 static void
+write_unit_name (prefix, num, suffix)
+     char *prefix;
+     int num;
+     char *suffix;
+{
+  struct function_unit *unit;
+
+  for (unit = units; unit; unit = unit->next)
+    if (unit->num == num)
+      {
+       printf ("%s%s%s", prefix, unit->name, suffix);
+       return;
+      }
+
+  printf ("%s<unknown>%s", prefix, suffix);
+}
+
+static void
 write_attr_valueq (attr, s)
      struct attr_desc *attr;
      char *s;
 {
   if (attr->is_numeric)
     {
-      printf ("%s", s);
-      /* Make the blockage range values easier to read.  */
-      if (strlen (s) > 1)
-       printf (" /* 0x%x */", atoi (s));
+      int num = atoi (s);
+
+      printf ("%d", num);
+
+      /* Make the blockage range values and function units used values easier
+         to read.  */
+      if (attr->func_units_p)
+       {
+         if (num == -1)
+           printf (" /* units: none */");
+         else if (num >= 0)
+           write_unit_name (" /* units: ", num, " */");
+         else
+           {
+             int i;
+             char *sep = " /* units: ";
+             for (i = 0, num = ~num; num; i++, num >>= 1)
+               if (num & 1)
+                 {
+                   write_unit_name (sep, i, (num == 1) ? " */" : "");
+                   sep = ", ";
+                 }
+           }
+       }
+
+      else if (attr->blockage_p)
+       printf (" /* min %d, max %d */", num >> (HOST_BITS_PER_INT / 2),
+               num & ((1 << (HOST_BITS_PER_INT / 2)) - 1));
+
+      else if (num > 9 || num < 0)
+       printf (" /* 0x%x */", num);
     }
   else
     {
@@ -5648,6 +5669,8 @@ make_internal_attr (name, value, special)
   attr->is_special = (special & 1) != 0;
   attr->negative_ok = (special & 2) != 0;
   attr->unsigned_p = (special & 4) != 0;
+  attr->func_units_p = (special & 8) != 0;
+  attr->blockage_p = (special & 16) != 0;
   attr->default_val = get_attr_value (value, attr, -2);
 }
 
@@ -5791,12 +5814,22 @@ copy_rtx_unchanging (orig)
 }
 
 static void
-fatal (s, a1, a2)
-     char *s;
-     char *a1, *a2;
+fatal VPROTO ((char *format, ...))
 {
+#ifndef __STDC__
+  char *format;
+#endif
+  va_list ap;
+
+  VA_START (ap, format);
+
+#ifndef __STDC__
+  format = va_arg (ap, char *);
+#endif
+
   fprintf (stderr, "genattrtab: ");
-  fprintf (stderr, s, a1, a2);
+  vfprintf (stderr, format, ap);
+  va_end (ap);
   fprintf (stderr, "\n");
   exit (FATAL_EXIT_CODE);
 }
@@ -5967,6 +6000,7 @@ from the machine description file `md'.  */\n\n");
   printf ("#include \"real.h\"\n");
   printf ("#include \"output.h\"\n");
   printf ("#include \"insn-attr.h\"\n");
+  printf ("#include \"toplev.h\"\n");
   printf ("\n");  
   printf ("#define operands recog_operand\n\n");