OSDN Git Service

* genattr.c: Wrap prototype of `free' in NEED_DECLARATION_FREE.
[pf3gnuchains/gcc-fork.git] / gcc / genattrtab.c
1 /* Generate code from machine description to compute values of attributes.
2    Copyright (C) 1991, 93, 94, 95, 96, 97, 1998 Free Software Foundation, Inc.
3    Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu)
4
5 This file is part of GNU CC.
6
7 GNU CC is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
10 any later version.
11
12 GNU CC is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with GNU CC; see the file COPYING.  If not, write to
19 the Free Software Foundation, 59 Temple Place - Suite 330,
20 Boston, MA 02111-1307, USA.  */
21
22 /* This program handles insn attributes and the DEFINE_DELAY and
23    DEFINE_FUNCTION_UNIT definitions.
24
25    It produces a series of functions named `get_attr_...', one for each insn
26    attribute.  Each of these is given the rtx for an insn and returns a member
27    of the enum for the attribute.
28
29    These subroutines have the form of a `switch' on the INSN_CODE (via
30    `recog_memoized').  Each case either returns a constant attribute value
31    or a value that depends on tests on other attributes, the form of
32    operands, or some random C expression (encoded with a SYMBOL_REF
33    expression).
34
35    If the attribute `alternative', or a random C expression is present,
36    `constrain_operands' is called.  If either of these cases of a reference to
37    an operand is found, `insn_extract' is called.
38
39    The special attribute `length' is also recognized.  For this operand, 
40    expressions involving the address of an operand or the current insn,
41    (address (pc)), are valid.  In this case, an initial pass is made to
42    set all lengths that do not depend on address.  Those that do are set to
43    the maximum length.  Then each insn that depends on an address is checked
44    and possibly has its length changed.  The process repeats until no further
45    changed are made.  The resulting lengths are saved for use by
46    `get_attr_length'.
47
48    A special form of DEFINE_ATTR, where the expression for default value is a
49    CONST expression, indicates an attribute that is constant for a given run
50    of the compiler.  The subroutine generated for these attributes has no
51    parameters as it does not depend on any particular insn.  Constant
52    attributes are typically used to specify which variety of processor is
53    used.
54    
55    Internal attributes are defined to handle DEFINE_DELAY and
56    DEFINE_FUNCTION_UNIT.  Special routines are output for these cases.
57
58    This program works by keeping a list of possible values for each attribute.
59    These include the basic attribute choices, default values for attribute, and
60    all derived quantities.
61
62    As the description file is read, the definition for each insn is saved in a
63    `struct insn_def'.   When the file reading is complete, a `struct insn_ent'
64    is created for each insn and chained to the corresponding attribute value,
65    either that specified, or the default.
66
67    An optimization phase is then run.  This simplifies expressions for each
68    insn.  EQ_ATTR tests are resolved, whenever possible, to a test that
69    indicates when the attribute has the specified value for the insn.  This
70    avoids recursive calls during compilation.
71
72    The strategy used when processing DEFINE_DELAY and DEFINE_FUNCTION_UNIT
73    definitions is to create arbitrarily complex expressions and have the
74    optimization simplify them.
75
76    Once optimization is complete, any required routines and definitions
77    will be written.
78
79    An optimization that is not yet implemented is to hoist the constant
80    expressions entirely out of the routines and definitions that are written.
81    A way to do this is to iterate over all possible combinations of values
82    for constant attributes and generate a set of functions for that given
83    combination.  An initialization function would be written that evaluates
84    the attributes and installs the corresponding set of routines and
85    definitions (each would be accessed through a pointer).
86
87    We use the flags in an RTX as follows:
88    `unchanging' (RTX_UNCHANGING_P): This rtx is fully simplified
89       independent of the insn code.
90    `in_struct' (MEM_IN_STRUCT_P): This rtx is fully simplified
91       for the insn code currently being processed (see optimize_attrs).
92    `integrated' (RTX_INTEGRATED_P): This rtx is permanent and unique
93       (see attr_rtx).
94    `volatil' (MEM_VOLATILE_P): During simplify_by_exploding the value of an
95       EQ_ATTR rtx is true if !volatil and false if volatil.  */
96
97
98 #include "hconfig.h"
99 /* varargs must always be included after *config.h.  */
100 #ifdef __STDC__
101 #include <stdarg.h>
102 #else
103 #include <varargs.h>
104 #endif
105 #include <stdio.h>
106 #include "rtl.h"
107 #include "insn-config.h"        /* For REGISTER_CONSTRAINTS */
108
109 #ifdef TIME_WITH_SYS_TIME
110 # include <sys/time.h>
111 # include <time.h>
112 #else
113 # if HAVE_SYS_TIME_H
114 # include <sys/time.h>
115 # else
116 #  include <time.h>
117 #endif
118 #endif
119
120 #ifdef HAVE_SYS_RESOURCE_H
121 # include <sys/resource.h>
122 #endif
123
124 #ifdef HAVE_STDLIB_H
125 #include <stdlib.h>
126 #endif
127
128 /* We must include obstack.h after <sys/time.h>, to avoid lossage with
129    /usr/include/sys/stdtypes.h on Sun OS 4.x.  */
130 #include "obstack.h"
131
132 static struct obstack obstack, obstack1, obstack2;
133 struct obstack *rtl_obstack = &obstack;
134 struct obstack *hash_obstack = &obstack1;
135 struct obstack *temp_obstack = &obstack2;
136
137 #define obstack_chunk_alloc xmalloc
138 #define obstack_chunk_free free
139
140 /* Define this so we can link with print-rtl.o to get debug_rtx function.  */
141 char **insn_name_ptr = 0;
142
143 #ifdef NEED_DECLARATION_FREE
144 extern void free ();
145 #endif
146 extern rtx read_rtx ();
147
148 static void fatal ();
149 void fancy_abort ();
150
151 /* enough space to reserve for printing out ints */
152 #define MAX_DIGITS (HOST_BITS_PER_INT * 3 / 10 + 3)
153
154 /* Define structures used to record attributes and values.  */
155
156 /* As each DEFINE_INSN, DEFINE_PEEPHOLE, or DEFINE_ASM_ATTRIBUTES is
157    encountered, we store all the relevant information into a
158    `struct insn_def'.  This is done to allow attribute definitions to occur
159    anywhere in the file.  */
160
161 struct insn_def
162 {
163   int insn_code;                /* Instruction number.  */
164   int insn_index;               /* Expression numer in file, for errors.  */
165   struct insn_def *next;        /* Next insn in chain.  */
166   rtx def;                      /* The DEFINE_...  */
167   int num_alternatives;         /* Number of alternatives.  */
168   int vec_idx;                  /* Index of attribute vector in `def'.  */
169 };
170
171 /* Once everything has been read in, we store in each attribute value a list
172    of insn codes that have that value.  Here is the structure used for the
173    list.  */
174
175 struct insn_ent
176 {
177   int insn_code;                /* Instruction number.  */
178   int insn_index;               /* Index of definition in file */
179   struct insn_ent *next;        /* Next in chain.  */
180 };
181
182 /* Each value of an attribute (either constant or computed) is assigned a
183    structure which is used as the listhead of the insns that have that
184    value.  */
185
186 struct attr_value
187 {
188   rtx value;                    /* Value of attribute.  */
189   struct attr_value *next;      /* Next attribute value in chain.  */
190   struct insn_ent *first_insn;  /* First insn with this value.  */
191   int num_insns;                /* Number of insns with this value.  */
192   int has_asm_insn;             /* True if this value used for `asm' insns */
193 };
194
195 /* Structure for each attribute.  */
196
197 struct attr_desc
198 {
199   char *name;                   /* Name of attribute.  */
200   struct attr_desc *next;       /* Next attribute.  */
201   int is_numeric;               /* Values of this attribute are numeric.  */
202   int negative_ok;              /* Allow negative numeric values.  */
203   int unsigned_p;               /* Make the output function unsigned int.  */
204   int is_const;                 /* Attribute value constant for each run.  */
205   int is_special;               /* Don't call `write_attr_set'.  */
206   struct attr_value *first_value; /* First value of this attribute.  */
207   struct attr_value *default_val; /* Default value for this attribute.  */
208 };
209
210 #define NULL_ATTR (struct attr_desc *) NULL
211
212 /* A range of values.  */
213
214 struct range
215 {
216   int min;
217   int max;
218 };
219
220 /* Structure for each DEFINE_DELAY.  */
221
222 struct delay_desc
223 {
224   rtx def;                      /* DEFINE_DELAY expression.  */
225   struct delay_desc *next;      /* Next DEFINE_DELAY.  */
226   int num;                      /* Number of DEFINE_DELAY, starting at 1.  */
227 };
228
229 /* Record information about each DEFINE_FUNCTION_UNIT.  */
230
231 struct function_unit_op
232 {
233   rtx condexp;                  /* Expression TRUE for applicable insn.  */
234   struct function_unit_op *next; /* Next operation for this function unit.  */
235   int num;                      /* Ordinal for this operation type in unit.  */
236   int ready;                    /* Cost until data is ready.  */
237   int issue_delay;              /* Cost until unit can accept another insn.  */
238   rtx conflict_exp;             /* Expression TRUE for insns incurring issue delay.  */
239   rtx issue_exp;                /* Expression computing issue delay.  */
240 };
241
242 /* Record information about each function unit mentioned in a
243    DEFINE_FUNCTION_UNIT.  */
244
245 struct function_unit
246 {
247   char *name;                   /* Function unit name.  */
248   struct function_unit *next;   /* Next function unit.  */
249   int num;                      /* Ordinal of this unit type.  */
250   int multiplicity;             /* Number of units of this type.  */
251   int simultaneity;             /* Maximum number of simultaneous insns
252                                    on this function unit or 0 if unlimited.  */
253   rtx condexp;                  /* Expression TRUE for insn needing unit.  */
254   int num_opclasses;            /* Number of different operation types.  */
255   struct function_unit_op *ops; /* Pointer to first operation type.  */
256   int needs_conflict_function;  /* Nonzero if a conflict function required.  */
257   int needs_blockage_function;  /* Nonzero if a blockage function required.  */
258   int needs_range_function;     /* Nonzero if blockage range function needed.*/
259   rtx default_cost;             /* Conflict cost, if constant.  */
260   struct range issue_delay;     /* Range of issue delay values.  */
261   int max_blockage;             /* Maximum time an insn blocks the unit.  */
262 };
263
264 /* Listheads of above structures.  */
265
266 /* This one is indexed by the first character of the attribute name.  */
267 #define MAX_ATTRS_INDEX 256
268 static struct attr_desc *attrs[MAX_ATTRS_INDEX];
269 static struct insn_def *defs;
270 static struct delay_desc *delays;
271 static struct function_unit *units;
272
273 /* An expression where all the unknown terms are EQ_ATTR tests can be
274    rearranged into a COND provided we can enumerate all possible
275    combinations of the unknown values.  The set of combinations become the
276    tests of the COND; the value of the expression given that combination is
277    computed and becomes the corresponding value.  To do this, we must be
278    able to enumerate all values for each attribute used in the expression
279    (currently, we give up if we find a numeric attribute).
280    
281    If the set of EQ_ATTR tests used in an expression tests the value of N
282    different attributes, the list of all possible combinations can be made
283    by walking the N-dimensional attribute space defined by those
284    attributes.  We record each of these as a struct dimension.
285
286    The algorithm relies on sharing EQ_ATTR nodes: if two nodes in an
287    expression are the same, the will also have the same address.  We find
288    all the EQ_ATTR nodes by marking them MEM_VOLATILE_P.  This bit later
289    represents the value of an EQ_ATTR node, so once all nodes are marked,
290    they are also given an initial value of FALSE.
291
292    We then separate the set of EQ_ATTR nodes into dimensions for each
293    attribute and put them on the VALUES list.  Terms are added as needed by
294    `add_values_to_cover' so that all possible values of the attribute are
295    tested.
296
297    Each dimension also has a current value.  This is the node that is
298    currently considered to be TRUE.  If this is one of the nodes added by
299    `add_values_to_cover', all the EQ_ATTR tests in the original expression
300    will be FALSE.  Otherwise, only the CURRENT_VALUE will be true.
301
302    NUM_VALUES is simply the length of the VALUES list and is there for
303    convenience.
304
305    Once the dimensions are created, the algorithm enumerates all possible
306    values and computes the current value of the given expression.  */
307
308 struct dimension 
309 {
310   struct attr_desc *attr;       /* Attribute for this dimension.  */
311   rtx values;                   /* List of attribute values used.  */
312   rtx current_value;            /* Position in the list for the TRUE value.  */
313   int num_values;               /* Length of the values list.  */
314 };
315
316 /* Other variables.  */
317
318 static int insn_code_number;
319 static int insn_index_number;
320 static int got_define_asm_attributes;
321 static int must_extract;
322 static int must_constrain;
323 static int address_used;
324 static int length_used;
325 static int num_delays;
326 static int have_annul_true, have_annul_false;
327 static int num_units, num_unit_opclasses;
328 static int num_insn_ents;
329
330 /* Used as operand to `operate_exp':  */
331
332 enum operator {PLUS_OP, MINUS_OP, POS_MINUS_OP, EQ_OP, OR_OP, ORX_OP, MAX_OP, MIN_OP, RANGE_OP};
333
334 /* Stores, for each insn code, the number of constraint alternatives.  */
335
336 static int *insn_n_alternatives;
337
338 /* Stores, for each insn code, a bitmap that has bits on for each possible
339    alternative.  */
340
341 static int *insn_alternatives;
342
343 /* If nonzero, assume that the `alternative' attr has this value.
344    This is the hashed, unique string for the numeral
345    whose value is chosen alternative.  */
346
347 static char *current_alternative_string;
348
349 /* Used to simplify expressions.  */
350
351 static rtx true_rtx, false_rtx;
352
353 /* Used to reduce calls to `strcmp' */
354
355 static char *alternative_name;
356
357 /* Indicate that REG_DEAD notes are valid if dead_or_set_p is ever
358    called.  */
359
360 int reload_completed = 0;
361
362 /* Similarly since PRESERVE_DEATH_INFO_REGNO_P might reference "optimize".  */
363 int optimize = 0;
364
365 /* Simplify an expression.  Only call the routine if there is something to
366    simplify.  */
367 #define SIMPLIFY_TEST_EXP(EXP,INSN_CODE,INSN_INDEX)     \
368   (RTX_UNCHANGING_P (EXP) || MEM_IN_STRUCT_P (EXP) ? (EXP)      \
369    : simplify_test_exp (EXP, INSN_CODE, INSN_INDEX))
370   
371 /* Simplify (eq_attr ("alternative") ...)
372    when we are working with a particular alternative.  */
373 #define SIMPLIFY_ALTERNATIVE(EXP)                               \
374   if (current_alternative_string                                \
375       && GET_CODE ((EXP)) == EQ_ATTR                            \
376       && XSTR ((EXP), 0) == alternative_name)                   \
377     (EXP) = (XSTR ((EXP), 1) == current_alternative_string      \
378             ? true_rtx : false_rtx);
379
380 /* These are referenced by rtlanal.c and hence need to be defined somewhere.
381    They won't actually be used.  */
382
383 struct _global_rtl global_rtl;
384
385 static rtx attr_rtx             PVPROTO((enum rtx_code, ...));
386 #ifdef HAVE_VPRINTF
387 static char *attr_printf        PVPROTO((int, char *, ...));
388 #else
389 static char *attr_printf ();
390 #endif
391
392 static char *attr_string        PROTO((char *, int));
393 static rtx check_attr_test      PROTO((rtx, int));
394 static rtx check_attr_value     PROTO((rtx, struct attr_desc *));
395 static rtx convert_set_attr_alternative PROTO((rtx, int, int, int));
396 static rtx convert_set_attr     PROTO((rtx, int, int, int));
397 static void check_defs          PROTO((void));
398 #if 0
399 static rtx convert_const_symbol_ref PROTO((rtx, struct attr_desc *));
400 #endif
401 static rtx make_canonical       PROTO((struct attr_desc *, rtx));
402 static struct attr_value *get_attr_value PROTO((rtx, struct attr_desc *, int));
403 static rtx copy_rtx_unchanging  PROTO((rtx));
404 static rtx copy_boolean         PROTO((rtx));
405 static void expand_delays       PROTO((void));
406 static rtx operate_exp          PROTO((enum operator, rtx, rtx));
407 static void expand_units        PROTO((void));
408 static rtx simplify_knowing     PROTO((rtx, rtx));
409 static rtx encode_units_mask    PROTO((rtx));
410 static void fill_attr           PROTO((struct attr_desc *));
411 /* dpx2 compiler chokes if we specify the arg types of the args.  */
412 static rtx substitute_address   PROTO((rtx, rtx (*) (), rtx (*) ()));
413 static void make_length_attrs   PROTO((void));
414 static rtx identity_fn          PROTO((rtx));
415 static rtx zero_fn              PROTO((rtx));
416 static rtx one_fn               PROTO((rtx));
417 static rtx max_fn               PROTO((rtx));
418 static rtx simplify_cond        PROTO((rtx, int, int));
419 #if 0
420 static rtx simplify_by_alternatives PROTO((rtx, int, int));
421 #endif
422 static rtx simplify_by_exploding PROTO((rtx));
423 static int find_and_mark_used_attributes PROTO((rtx, rtx *, int *));
424 static void unmark_used_attributes PROTO((rtx, struct dimension *, int));
425 static int add_values_to_cover  PROTO((struct dimension *));
426 static int increment_current_value PROTO((struct dimension *, int));
427 static rtx test_for_current_value PROTO((struct dimension *, int));
428 static rtx simplify_with_current_value PROTO((rtx, struct dimension *, int));
429 static rtx simplify_with_current_value_aux PROTO((rtx));
430 static void clear_struct_flag PROTO((rtx));
431 static int count_sub_rtxs    PROTO((rtx, int));
432 static void remove_insn_ent  PROTO((struct attr_value *, struct insn_ent *));
433 static void insert_insn_ent  PROTO((struct attr_value *, struct insn_ent *));
434 static rtx insert_right_side    PROTO((enum rtx_code, rtx, rtx, int, int));
435 static rtx make_alternative_compare PROTO((int));
436 static int compute_alternative_mask PROTO((rtx, enum rtx_code));
437 static rtx evaluate_eq_attr     PROTO((rtx, rtx, int, int));
438 static rtx simplify_and_tree    PROTO((rtx, rtx *, int, int));
439 static rtx simplify_or_tree     PROTO((rtx, rtx *, int, int));
440 static rtx simplify_test_exp    PROTO((rtx, int, int));
441 static void optimize_attrs      PROTO((void));
442 static void gen_attr            PROTO((rtx));
443 static int count_alternatives   PROTO((rtx));
444 static int compares_alternatives_p PROTO((rtx));
445 static int contained_in_p       PROTO((rtx, rtx));
446 static void gen_insn            PROTO((rtx));
447 static void gen_delay           PROTO((rtx));
448 static void gen_unit            PROTO((rtx));
449 static void write_test_expr     PROTO((rtx, int));
450 static int max_attr_value       PROTO((rtx));
451 static void walk_attr_value     PROTO((rtx));
452 static void write_attr_get      PROTO((struct attr_desc *));
453 static rtx eliminate_known_true PROTO((rtx, rtx, int, int));
454 static void write_attr_set      PROTO((struct attr_desc *, int, rtx, char *,
455                                        char *, rtx, int, int));
456 static void write_attr_case     PROTO((struct attr_desc *, struct attr_value *,
457                                        int, char *, char *, int, rtx));
458 static void write_attr_valueq   PROTO((struct attr_desc *, char *));
459 static void write_attr_value    PROTO((struct attr_desc *, rtx));
460 static void write_upcase        PROTO((char *));
461 static void write_indent        PROTO((int));
462 static void write_eligible_delay PROTO((char *));
463 static void write_function_unit_info PROTO((void));
464 static void write_complex_function PROTO((struct function_unit *, char *,
465                                           char *));
466 static int write_expr_attr_cache PROTO((rtx, struct attr_desc *));
467 static void write_toplevel_expr PROTO((rtx));
468 static int n_comma_elts         PROTO((char *));
469 static char *next_comma_elt     PROTO((char **));
470 static struct attr_desc *find_attr PROTO((char *, int));
471 static void make_internal_attr  PROTO((char *, rtx, int));
472 static struct attr_value *find_most_used  PROTO((struct attr_desc *));
473 static rtx find_single_value    PROTO((struct attr_desc *));
474 static rtx make_numeric_value   PROTO((int));
475 static void extend_range        PROTO((struct range *, int, int));
476 char *xrealloc                  PROTO((char *, unsigned));
477 char *xmalloc                   PROTO((unsigned));
478
479 #define oballoc(size) obstack_alloc (hash_obstack, size)
480
481 \f
482 /* Hash table for sharing RTL and strings.  */
483
484 /* Each hash table slot is a bucket containing a chain of these structures.
485    Strings are given negative hash codes; RTL expressions are given positive
486    hash codes.  */
487
488 struct attr_hash
489 {
490   struct attr_hash *next;       /* Next structure in the bucket.  */
491   int hashcode;                 /* Hash code of this rtx or string.  */
492   union
493     {
494       char *str;                /* The string (negative hash codes) */
495       rtx rtl;                  /* or the RTL recorded here.  */
496     } u;
497 };
498
499 /* Now here is the hash table.  When recording an RTL, it is added to
500    the slot whose index is the hash code mod the table size.  Note
501    that the hash table is used for several kinds of RTL (see attr_rtx)
502    and for strings.  While all these live in the same table, they are
503    completely independent, and the hash code is computed differently
504    for each.  */
505
506 #define RTL_HASH_SIZE 4093
507 struct attr_hash *attr_hash_table[RTL_HASH_SIZE];
508
509 /* Here is how primitive or already-shared RTL's hash
510    codes are made.  */
511 #define RTL_HASH(RTL) ((long) (RTL) & 0777777)
512
513 /* Add an entry to the hash table for RTL with hash code HASHCODE.  */
514
515 static void
516 attr_hash_add_rtx (hashcode, rtl)
517      int hashcode;
518      rtx rtl;
519 {
520   register struct attr_hash *h;
521
522   h = (struct attr_hash *) obstack_alloc (hash_obstack,
523                                           sizeof (struct attr_hash));
524   h->hashcode = hashcode;
525   h->u.rtl = rtl;
526   h->next = attr_hash_table[hashcode % RTL_HASH_SIZE];
527   attr_hash_table[hashcode % RTL_HASH_SIZE] = h;
528 }
529
530 /* Add an entry to the hash table for STRING with hash code HASHCODE.  */
531
532 static void
533 attr_hash_add_string (hashcode, str)
534      int hashcode;
535      char *str;
536 {
537   register struct attr_hash *h;
538
539   h = (struct attr_hash *) obstack_alloc (hash_obstack,
540                                           sizeof (struct attr_hash));
541   h->hashcode = -hashcode;
542   h->u.str = str;
543   h->next = attr_hash_table[hashcode % RTL_HASH_SIZE];
544   attr_hash_table[hashcode % RTL_HASH_SIZE] = h;
545 }
546
547 /* Generate an RTL expression, but avoid duplicates.
548    Set the RTX_INTEGRATED_P flag for these permanent objects.
549
550    In some cases we cannot uniquify; then we return an ordinary
551    impermanent rtx with RTX_INTEGRATED_P clear.
552
553    Args are like gen_rtx, but without the mode:
554
555    rtx attr_rtx (code, [element1, ..., elementn])  */
556
557 /*VARARGS1*/
558 static rtx
559 attr_rtx VPROTO((enum rtx_code code, ...))
560 {
561 #ifndef __STDC__
562   enum rtx_code code;
563 #endif
564   va_list p;
565   register int i;               /* Array indices...                     */
566   register char *fmt;           /* Current rtx's format...              */
567   register rtx rt_val;          /* RTX to return to caller...           */
568   int hashcode;
569   register struct attr_hash *h;
570   struct obstack *old_obstack = rtl_obstack;
571
572   VA_START (p, code);
573
574 #ifndef __STDC__
575   code = va_arg (p, enum rtx_code);
576 #endif
577
578   /* For each of several cases, search the hash table for an existing entry.
579      Use that entry if one is found; otherwise create a new RTL and add it
580      to the table.  */
581
582   if (GET_RTX_CLASS (code) == '1')
583     {
584       rtx arg0 = va_arg (p, rtx);
585
586       /* A permanent object cannot point to impermanent ones.  */
587       if (! RTX_INTEGRATED_P (arg0))
588         {
589           rt_val = rtx_alloc (code);
590           XEXP (rt_val, 0) = arg0;
591           va_end (p);
592           return rt_val;
593         }
594
595       hashcode = ((HOST_WIDE_INT) code + RTL_HASH (arg0));
596       for (h = attr_hash_table[hashcode % RTL_HASH_SIZE]; h; h = h->next)
597         if (h->hashcode == hashcode
598             && GET_CODE (h->u.rtl) == code
599             && XEXP (h->u.rtl, 0) == arg0)
600           goto found;
601
602       if (h == 0)
603         {
604           rtl_obstack = hash_obstack;
605           rt_val = rtx_alloc (code);
606           XEXP (rt_val, 0) = arg0;
607         }
608     }
609   else if (GET_RTX_CLASS (code) == 'c'
610            || GET_RTX_CLASS (code) == '2'
611            || GET_RTX_CLASS (code) == '<')
612     {
613       rtx arg0 = va_arg (p, rtx);
614       rtx arg1 = va_arg (p, rtx);
615
616       /* A permanent object cannot point to impermanent ones.  */
617       if (! RTX_INTEGRATED_P (arg0) || ! RTX_INTEGRATED_P (arg1))
618         {
619           rt_val = rtx_alloc (code);
620           XEXP (rt_val, 0) = arg0;
621           XEXP (rt_val, 1) = arg1;
622           va_end (p);
623           return rt_val;
624         }
625
626       hashcode = ((HOST_WIDE_INT) code + RTL_HASH (arg0) + RTL_HASH (arg1));
627       for (h = attr_hash_table[hashcode % RTL_HASH_SIZE]; h; h = h->next)
628         if (h->hashcode == hashcode
629             && GET_CODE (h->u.rtl) == code
630             && XEXP (h->u.rtl, 0) == arg0
631             && XEXP (h->u.rtl, 1) == arg1)
632           goto found;
633
634       if (h == 0)
635         {
636           rtl_obstack = hash_obstack;
637           rt_val = rtx_alloc (code);
638           XEXP (rt_val, 0) = arg0;
639           XEXP (rt_val, 1) = arg1;
640         }
641     }
642   else if (GET_RTX_LENGTH (code) == 1
643            && GET_RTX_FORMAT (code)[0] == 's')
644     {
645       char * arg0 = va_arg (p, char *);
646
647       if (code == SYMBOL_REF)
648         arg0 = attr_string (arg0, strlen (arg0));
649
650       hashcode = ((HOST_WIDE_INT) code + RTL_HASH (arg0));
651       for (h = attr_hash_table[hashcode % RTL_HASH_SIZE]; h; h = h->next)
652         if (h->hashcode == hashcode
653             && GET_CODE (h->u.rtl) == code
654             && XSTR (h->u.rtl, 0) == arg0)
655           goto found;
656
657       if (h == 0)
658         {
659           rtl_obstack = hash_obstack;
660           rt_val = rtx_alloc (code);
661           XSTR (rt_val, 0) = arg0;
662         }
663     }
664   else if (GET_RTX_LENGTH (code) == 2
665            && GET_RTX_FORMAT (code)[0] == 's'
666            && GET_RTX_FORMAT (code)[1] == 's')
667     {
668       char *arg0 = va_arg (p, char *);
669       char *arg1 = va_arg (p, char *);
670
671       hashcode = ((HOST_WIDE_INT) code + RTL_HASH (arg0) + RTL_HASH (arg1));
672       for (h = attr_hash_table[hashcode % RTL_HASH_SIZE]; h; h = h->next)
673         if (h->hashcode == hashcode
674             && GET_CODE (h->u.rtl) == code
675             && XSTR (h->u.rtl, 0) == arg0
676             && XSTR (h->u.rtl, 1) == arg1)
677           goto found;
678
679       if (h == 0)
680         {
681           rtl_obstack = hash_obstack;
682           rt_val = rtx_alloc (code);
683           XSTR (rt_val, 0) = arg0;
684           XSTR (rt_val, 1) = arg1;
685         }
686     }
687   else if (code == CONST_INT)
688     {
689       HOST_WIDE_INT arg0 = va_arg (p, HOST_WIDE_INT);
690       if (arg0 == 0)
691         return false_rtx;
692       if (arg0 == 1)
693         return true_rtx;
694       goto nohash;
695     }
696   else
697     {
698     nohash:
699       rt_val = rtx_alloc (code);        /* Allocate the storage space.  */
700       
701       fmt = GET_RTX_FORMAT (code);      /* Find the right format...  */
702       for (i = 0; i < GET_RTX_LENGTH (code); i++)
703         {
704           switch (*fmt++)
705             {
706             case '0':           /* Unused field.  */
707               break;
708
709             case 'i':           /* An integer?  */
710               XINT (rt_val, i) = va_arg (p, int);
711               break;
712
713             case 'w':           /* A wide integer? */
714               XWINT (rt_val, i) = va_arg (p, HOST_WIDE_INT);
715               break;
716
717             case 's':           /* A string?  */
718               XSTR (rt_val, i) = va_arg (p, char *);
719               break;
720
721             case 'e':           /* An expression?  */
722             case 'u':           /* An insn?  Same except when printing.  */
723               XEXP (rt_val, i) = va_arg (p, rtx);
724               break;
725
726             case 'E':           /* An RTX vector?  */
727               XVEC (rt_val, i) = va_arg (p, rtvec);
728               break;
729
730             default:
731               abort();
732             }
733         }
734       va_end (p);
735       return rt_val;
736     }
737
738   rtl_obstack = old_obstack;
739   va_end (p);
740   attr_hash_add_rtx (hashcode, rt_val);
741   RTX_INTEGRATED_P (rt_val) = 1;
742   return rt_val;
743
744  found:
745   va_end (p);
746   return h->u.rtl;
747 }
748
749 /* Create a new string printed with the printf line arguments into a space
750    of at most LEN bytes:
751
752    rtx attr_printf (len, format, [arg1, ..., argn])  */
753
754 #ifdef HAVE_VPRINTF
755
756 /*VARARGS2*/
757 static char *
758 attr_printf VPROTO((register int len, char *fmt, ...))
759 {
760 #ifndef __STDC__
761   register int len;
762   char *fmt;
763 #endif
764   va_list p;
765   register char *str;
766
767   VA_START (p, fmt);
768
769 #ifndef __STDC__
770   len = va_arg (p, int);
771   fmt = va_arg (p, char *);
772 #endif
773
774   /* Print the string into a temporary location.  */
775   str = (char *) alloca (len);
776   vsprintf (str, fmt, p);
777   va_end (p);
778
779   return attr_string (str, strlen (str));
780 }
781
782 #else /* not HAVE_VPRINTF */
783
784 static char *
785 attr_printf (len, fmt, arg1, arg2, arg3)
786      int len;
787      char *fmt;
788      char *arg1, *arg2, *arg3; /* also int */
789 {
790   register char *str;
791
792   /* Print the string into a temporary location.  */
793   str = (char *) alloca (len);
794   sprintf (str, fmt, arg1, arg2, arg3);
795
796   return attr_string (str, strlen (str));
797 }
798 #endif /* not HAVE_VPRINTF */
799
800 rtx
801 attr_eq (name, value)
802      char *name, *value;
803 {
804   return attr_rtx (EQ_ATTR, attr_string (name, strlen (name)),
805                    attr_string (value, strlen (value)));
806 }
807
808 char *
809 attr_numeral (n)
810      int n;
811 {
812   return XSTR (make_numeric_value (n), 0);
813 }
814
815 /* Return a permanent (possibly shared) copy of a string STR (not assumed
816    to be null terminated) with LEN bytes.  */
817
818 static char *
819 attr_string (str, len)
820      char *str;
821      int len;
822 {
823   register struct attr_hash *h;
824   int hashcode;
825   int i;
826   register char *new_str;
827
828   /* Compute the hash code.  */
829   hashcode = (len + 1) * 613 + (unsigned)str[0];
830   for (i = 1; i <= len; i += 2)
831     hashcode = ((hashcode * 613) + (unsigned)str[i]);
832   if (hashcode < 0)
833     hashcode = -hashcode;
834
835   /* Search the table for the string.  */
836   for (h = attr_hash_table[hashcode % RTL_HASH_SIZE]; h; h = h->next)
837     if (h->hashcode == -hashcode && h->u.str[0] == str[0]
838         && !strncmp (h->u.str, str, len))
839       return h->u.str;                  /* <-- return if found.  */
840
841   /* Not found; create a permanent copy and add it to the hash table.  */
842   new_str = (char *) obstack_alloc (hash_obstack, len + 1);
843   bcopy (str, new_str, len);
844   new_str[len] = '\0';
845   attr_hash_add_string (hashcode, new_str);
846
847   return new_str;                       /* Return the new string.  */
848 }
849
850 /* Check two rtx's for equality of contents,
851    taking advantage of the fact that if both are hashed
852    then they can't be equal unless they are the same object.  */
853
854 int
855 attr_equal_p (x, y)
856      rtx x, y;
857 {
858   return (x == y || (! (RTX_INTEGRATED_P (x) && RTX_INTEGRATED_P (y))
859                      && rtx_equal_p (x, y)));
860 }
861 \f
862 /* Copy an attribute value expression,
863    descending to all depths, but not copying any
864    permanent hashed subexpressions.  */
865
866 rtx
867 attr_copy_rtx (orig)
868      register rtx orig;
869 {
870   register rtx copy;
871   register int i, j;
872   register RTX_CODE code;
873   register char *format_ptr;
874
875   /* No need to copy a permanent object.  */
876   if (RTX_INTEGRATED_P (orig))
877     return orig;
878
879   code = GET_CODE (orig);
880
881   switch (code)
882     {
883     case REG:
884     case QUEUED:
885     case CONST_INT:
886     case CONST_DOUBLE:
887     case SYMBOL_REF:
888     case CODE_LABEL:
889     case PC:
890     case CC0:
891       return orig;
892
893     default:
894       break;
895     }
896
897   copy = rtx_alloc (code);
898   PUT_MODE (copy, GET_MODE (orig));
899   copy->in_struct = orig->in_struct;
900   copy->volatil = orig->volatil;
901   copy->unchanging = orig->unchanging;
902   copy->integrated = orig->integrated;
903   
904   format_ptr = GET_RTX_FORMAT (GET_CODE (copy));
905
906   for (i = 0; i < GET_RTX_LENGTH (GET_CODE (copy)); i++)
907     {
908       switch (*format_ptr++)
909         {
910         case 'e':
911           XEXP (copy, i) = XEXP (orig, i);
912           if (XEXP (orig, i) != NULL)
913             XEXP (copy, i) = attr_copy_rtx (XEXP (orig, i));
914           break;
915
916         case 'E':
917         case 'V':
918           XVEC (copy, i) = XVEC (orig, i);
919           if (XVEC (orig, i) != NULL)
920             {
921               XVEC (copy, i) = rtvec_alloc (XVECLEN (orig, i));
922               for (j = 0; j < XVECLEN (copy, i); j++)
923                 XVECEXP (copy, i, j) = attr_copy_rtx (XVECEXP (orig, i, j));
924             }
925           break;
926
927         case 'n':
928         case 'i':
929           XINT (copy, i) = XINT (orig, i);
930           break;
931
932         case 'w':
933           XWINT (copy, i) = XWINT (orig, i);
934           break;
935
936         case 's':
937         case 'S':
938           XSTR (copy, i) = XSTR (orig, i);
939           break;
940
941         default:
942           abort ();
943         }
944     }
945   return copy;
946 }
947 \f
948 /* Given a test expression for an attribute, ensure it is validly formed.
949    IS_CONST indicates whether the expression is constant for each compiler
950    run (a constant expression may not test any particular insn).
951
952    Convert (eq_attr "att" "a1,a2") to (ior (eq_attr ... ) (eq_attrq ..))
953    and (eq_attr "att" "!a1") to (not (eq_attr "att" "a1")).  Do the latter
954    test first so that (eq_attr "att" "!a1,a2,a3") works as expected.
955
956    Update the string address in EQ_ATTR expression to be the same used
957    in the attribute (or `alternative_name') to speed up subsequent
958    `find_attr' calls and eliminate most `strcmp' calls.
959
960    Return the new expression, if any.   */
961
962 static rtx
963 check_attr_test (exp, is_const)
964      rtx exp;
965      int is_const;
966 {
967   struct attr_desc *attr;
968   struct attr_value *av;
969   char *name_ptr, *p;
970   rtx orexp, newexp;
971
972   switch (GET_CODE (exp))
973     {
974     case EQ_ATTR:
975       /* Handle negation test.  */
976       if (XSTR (exp, 1)[0] == '!')
977         return check_attr_test (attr_rtx (NOT,
978                                           attr_eq (XSTR (exp, 0),
979                                                    &XSTR (exp, 1)[1])),
980                                 is_const);
981
982       else if (n_comma_elts (XSTR (exp, 1)) == 1)
983         {
984           attr = find_attr (XSTR (exp, 0), 0);
985           if (attr == NULL)
986             {
987               if (! strcmp (XSTR (exp, 0), "alternative"))
988                 {
989                   XSTR (exp, 0) = alternative_name;
990                   /* This can't be simplified any further.  */
991                   RTX_UNCHANGING_P (exp) = 1;
992                   return exp;
993                 }
994               else
995                 fatal ("Unknown attribute `%s' in EQ_ATTR", XEXP (exp, 0));
996             }
997
998           if (is_const && ! attr->is_const)
999             fatal ("Constant expression uses insn attribute `%s' in EQ_ATTR",
1000                    XEXP (exp, 0));
1001
1002           /* Copy this just to make it permanent,
1003              so expressions using it can be permanent too.  */
1004           exp = attr_eq (XSTR (exp, 0), XSTR (exp, 1));
1005
1006           /* It shouldn't be possible to simplify the value given to a
1007              constant attribute, so don't expand this until it's time to
1008              write the test expression.  */            
1009           if (attr->is_const)
1010             RTX_UNCHANGING_P (exp) = 1;
1011
1012           if (attr->is_numeric)
1013             {
1014               for (p = XSTR (exp, 1); *p; p++)
1015                 if (*p < '0' || *p > '9')
1016                    fatal ("Attribute `%s' takes only numeric values", 
1017                           XEXP (exp, 0));
1018             }
1019           else
1020             {
1021               for (av = attr->first_value; av; av = av->next)
1022                 if (GET_CODE (av->value) == CONST_STRING
1023                     && ! strcmp (XSTR (exp, 1), XSTR (av->value, 0)))
1024                   break;
1025
1026               if (av == NULL)
1027                 fatal ("Unknown value `%s' for `%s' attribute",
1028                        XEXP (exp, 1), XEXP (exp, 0));
1029             }
1030         }
1031       else
1032         {
1033           /* Make an IOR tree of the possible values.  */
1034           orexp = false_rtx;
1035           name_ptr = XSTR (exp, 1);
1036           while ((p = next_comma_elt (&name_ptr)) != NULL)
1037             {
1038               newexp = attr_eq (XSTR (exp, 0), p);
1039               orexp = insert_right_side (IOR, orexp, newexp, -2, -2);
1040             }
1041
1042           return check_attr_test (orexp, is_const);
1043         }
1044       break;
1045
1046     case ATTR_FLAG:
1047       break;
1048
1049     case CONST_INT:
1050       /* Either TRUE or FALSE.  */
1051       if (XWINT (exp, 0))
1052         return true_rtx;
1053       else
1054         return false_rtx;
1055
1056     case IOR:
1057     case AND:
1058       XEXP (exp, 0) = check_attr_test (XEXP (exp, 0), is_const);
1059       XEXP (exp, 1) = check_attr_test (XEXP (exp, 1), is_const);
1060       break;
1061
1062     case NOT:
1063       XEXP (exp, 0) = check_attr_test (XEXP (exp, 0), is_const);
1064       break;
1065
1066     case MATCH_OPERAND:
1067       if (is_const)
1068         fatal ("RTL operator \"%s\" not valid in constant attribute test",
1069                GET_RTX_NAME (MATCH_OPERAND));
1070       /* These cases can't be simplified.  */
1071       RTX_UNCHANGING_P (exp) = 1;
1072       break;
1073  
1074     case LE:  case LT:  case GT:  case GE:
1075     case LEU: case LTU: case GTU: case GEU:
1076     case NE:  case EQ:
1077       if (GET_CODE (XEXP (exp, 0)) == SYMBOL_REF
1078           && GET_CODE (XEXP (exp, 1)) == SYMBOL_REF)
1079         exp = attr_rtx (GET_CODE (exp),
1080                         attr_rtx (SYMBOL_REF, XSTR (XEXP (exp, 0), 0)),
1081                         attr_rtx (SYMBOL_REF, XSTR (XEXP (exp, 1), 0)));
1082       /* These cases can't be simplified.  */
1083       RTX_UNCHANGING_P (exp) = 1;
1084       break;
1085
1086     case SYMBOL_REF:
1087       if (is_const)
1088         {
1089           /* These cases are valid for constant attributes, but can't be
1090              simplified.  */
1091           exp = attr_rtx (SYMBOL_REF, XSTR (exp, 0));
1092           RTX_UNCHANGING_P (exp) = 1;
1093           break;
1094         }
1095     default:
1096       fatal ("RTL operator \"%s\" not valid in attribute test",
1097              GET_RTX_NAME (GET_CODE (exp)));
1098     }
1099
1100   return exp;
1101 }
1102 \f
1103 /* Given an expression, ensure that it is validly formed and that all named
1104    attribute values are valid for the given attribute.  Issue a fatal error
1105    if not.  If no attribute is specified, assume a numeric attribute.
1106
1107    Return a perhaps modified replacement expression for the value.  */
1108
1109 static rtx
1110 check_attr_value (exp, attr)
1111      rtx exp;
1112      struct attr_desc *attr;
1113 {
1114   struct attr_value *av;
1115   char *p;
1116   int i;
1117
1118   switch (GET_CODE (exp))
1119     {
1120     case CONST_INT:
1121       if (attr && ! attr->is_numeric)
1122         fatal ("CONST_INT not valid for non-numeric `%s' attribute",
1123                attr->name);
1124
1125       if (INTVAL (exp) < 0)
1126         fatal ("Negative numeric value specified for `%s' attribute",
1127                attr->name);
1128
1129       break;
1130
1131     case CONST_STRING:
1132       if (! strcmp (XSTR (exp, 0), "*"))
1133         break;
1134
1135       if (attr == 0 || attr->is_numeric)
1136         {
1137           p = XSTR (exp, 0);
1138           if (attr && attr->negative_ok && *p == '-')
1139             p++;
1140           for (; *p; p++)
1141             if (*p > '9' || *p < '0')
1142               fatal ("Non-numeric value for numeric `%s' attribute",
1143                      attr ? attr->name : "internal");
1144           break;
1145         }
1146
1147       for (av = attr->first_value; av; av = av->next)
1148         if (GET_CODE (av->value) == CONST_STRING
1149             && ! strcmp (XSTR (av->value, 0), XSTR (exp, 0)))
1150           break;
1151
1152       if (av == NULL)
1153         fatal ("Unknown value `%s' for `%s' attribute",
1154                XSTR (exp, 0), attr ? attr->name : "internal");
1155
1156       break;
1157
1158     case IF_THEN_ELSE:
1159       XEXP (exp, 0) = check_attr_test (XEXP (exp, 0),
1160                                        attr ? attr->is_const : 0);
1161       XEXP (exp, 1) = check_attr_value (XEXP (exp, 1), attr);
1162       XEXP (exp, 2) = check_attr_value (XEXP (exp, 2), attr);
1163       break;
1164
1165     case IOR:
1166     case AND:
1167       XEXP (exp, 0) = check_attr_value (XEXP (exp, 0), attr);
1168       XEXP (exp, 1) = check_attr_value (XEXP (exp, 1), attr);
1169       break;
1170
1171     case FFS:
1172       XEXP (exp, 0) = check_attr_value (XEXP (exp, 0), attr);
1173       break;
1174
1175     case COND:
1176       if (XVECLEN (exp, 0) % 2 != 0)
1177         fatal ("First operand of COND must have even length");
1178
1179       for (i = 0; i < XVECLEN (exp, 0); i += 2)
1180         {
1181           XVECEXP (exp, 0, i) = check_attr_test (XVECEXP (exp, 0, i),
1182                                                  attr ? attr->is_const : 0);
1183           XVECEXP (exp, 0, i + 1)
1184             = check_attr_value (XVECEXP (exp, 0, i + 1), attr);
1185         }
1186
1187       XEXP (exp, 1) = check_attr_value (XEXP (exp, 1), attr);
1188       break;
1189
1190     case SYMBOL_REF:
1191       if (attr && attr->is_const)
1192         /* A constant SYMBOL_REF is valid as a constant attribute test and
1193            is expanded later by make_canonical into a COND.  */
1194         return attr_rtx (SYMBOL_REF, XSTR (exp, 0));
1195       /* Otherwise, fall through...  */
1196
1197     default:
1198       fatal ("Invalid operation `%s' for attribute value",
1199              GET_RTX_NAME (GET_CODE (exp)));
1200     }
1201
1202   return exp;
1203 }
1204 \f
1205 /* Given an SET_ATTR_ALTERNATIVE expression, convert to the canonical SET.
1206    It becomes a COND with each test being (eq_attr "alternative "n") */
1207
1208 static rtx
1209 convert_set_attr_alternative (exp, num_alt, insn_code, insn_index)
1210      rtx exp;
1211      int num_alt;
1212      int insn_code, insn_index;
1213 {
1214   rtx condexp;
1215   int i;
1216
1217   if (XVECLEN (exp, 1) != num_alt)
1218     fatal ("Bad number of entries in SET_ATTR_ALTERNATIVE for insn %d",
1219            insn_index);
1220
1221   /* Make a COND with all tests but the last.  Select the last value via the
1222      default.  */
1223   condexp = rtx_alloc (COND);
1224   XVEC (condexp, 0) = rtvec_alloc ((num_alt - 1) * 2);
1225
1226   for (i = 0; i < num_alt - 1; i++)
1227     {
1228       char *p;
1229       p = attr_numeral (i);
1230
1231       XVECEXP (condexp, 0, 2 * i) = attr_eq (alternative_name, p);
1232 #if 0
1233       /* Sharing this EQ_ATTR rtl causes trouble.  */   
1234       XVECEXP (condexp, 0, 2 * i) = rtx_alloc (EQ_ATTR);
1235       XSTR (XVECEXP (condexp, 0, 2 * i), 0) = alternative_name;
1236       XSTR (XVECEXP (condexp, 0, 2 * i), 1) = p;
1237 #endif
1238       XVECEXP (condexp, 0, 2 * i + 1) = XVECEXP (exp, 1, i);
1239     }
1240
1241   XEXP (condexp, 1) = XVECEXP (exp, 1, i);
1242
1243   return attr_rtx (SET, attr_rtx (ATTR, XSTR (exp, 0)), condexp);
1244 }
1245 \f
1246 /* Given a SET_ATTR, convert to the appropriate SET.  If a comma-separated
1247    list of values is given, convert to SET_ATTR_ALTERNATIVE first.  */
1248
1249 static rtx
1250 convert_set_attr (exp, num_alt, insn_code, insn_index)
1251      rtx exp;
1252      int num_alt;
1253      int insn_code, insn_index;
1254 {
1255   rtx newexp;
1256   char *name_ptr;
1257   char *p;
1258   int n;
1259
1260   /* See how many alternative specified.  */
1261   n = n_comma_elts (XSTR (exp, 1));
1262   if (n == 1)
1263     return attr_rtx (SET,
1264                      attr_rtx (ATTR, XSTR (exp, 0)),
1265                      attr_rtx (CONST_STRING, XSTR (exp, 1)));
1266
1267   newexp = rtx_alloc (SET_ATTR_ALTERNATIVE);
1268   XSTR (newexp, 0) = XSTR (exp, 0);
1269   XVEC (newexp, 1) = rtvec_alloc (n);
1270
1271   /* Process each comma-separated name.  */
1272   name_ptr = XSTR (exp, 1);
1273   n = 0;
1274   while ((p = next_comma_elt (&name_ptr)) != NULL)
1275     XVECEXP (newexp, 1, n++) = attr_rtx (CONST_STRING, p);
1276
1277   return convert_set_attr_alternative (newexp, num_alt, insn_code, insn_index);
1278 }
1279 \f
1280 /* Scan all definitions, checking for validity.  Also, convert any SET_ATTR
1281    and SET_ATTR_ALTERNATIVE expressions to the corresponding SET
1282    expressions.  */
1283
1284 static void
1285 check_defs ()
1286 {
1287   struct insn_def *id;
1288   struct attr_desc *attr;
1289   int i;
1290   rtx value;
1291
1292   for (id = defs; id; id = id->next)
1293     {
1294       if (XVEC (id->def, id->vec_idx) == NULL)
1295         continue;
1296
1297       for (i = 0; i < XVECLEN (id->def, id->vec_idx); i++)
1298         {
1299           value = XVECEXP (id->def, id->vec_idx, i);
1300           switch (GET_CODE (value))
1301             {
1302             case SET:
1303               if (GET_CODE (XEXP (value, 0)) != ATTR)
1304                 fatal ("Bad attribute set in pattern %d", id->insn_index);
1305               break;
1306
1307             case SET_ATTR_ALTERNATIVE:
1308               value = convert_set_attr_alternative (value,
1309                                                     id->num_alternatives,
1310                                                     id->insn_code,
1311                                                     id->insn_index);
1312               break;
1313
1314             case SET_ATTR:
1315               value = convert_set_attr (value, id->num_alternatives,
1316                                         id->insn_code, id->insn_index);
1317               break;
1318
1319             default:
1320               fatal ("Invalid attribute code `%s' for pattern %d",
1321                      GET_RTX_NAME (GET_CODE (value)), id->insn_index);
1322             }
1323
1324           if ((attr = find_attr (XSTR (XEXP (value, 0), 0), 0)) == NULL)
1325             fatal ("Unknown attribute `%s' for pattern number %d",
1326                    XSTR (XEXP (value, 0), 0), id->insn_index);
1327
1328           XVECEXP (id->def, id->vec_idx, i) = value;
1329           XEXP (value, 1) = check_attr_value (XEXP (value, 1), attr);
1330         }
1331     }
1332 }
1333 \f
1334 #if 0
1335 /* Given a constant SYMBOL_REF expression, convert to a COND that
1336    explicitly tests each enumerated value.  */
1337
1338 static rtx
1339 convert_const_symbol_ref (exp, attr)
1340      rtx exp;
1341      struct attr_desc *attr;
1342 {
1343   rtx condexp;
1344   struct attr_value *av;
1345   int i;
1346   int num_alt = 0;
1347
1348   for (av = attr->first_value; av; av = av->next)
1349     num_alt++;
1350
1351   /* Make a COND with all tests but the last, and in the original order.
1352      Select the last value via the default.  Note that the attr values
1353      are constructed in reverse order.  */
1354
1355   condexp = rtx_alloc (COND);
1356   XVEC (condexp, 0) = rtvec_alloc ((num_alt - 1) * 2);
1357   av = attr->first_value;
1358   XEXP (condexp, 1) = av->value;
1359
1360   for (i = num_alt - 2; av = av->next, i >= 0; i--)
1361     {
1362       char *p, *string;
1363       rtx value;
1364
1365       string = p = (char *) oballoc (2
1366                                      + strlen (attr->name)
1367                                      + strlen (XSTR (av->value, 0)));
1368       strcpy (p, attr->name);
1369       strcat (p, "_");
1370       strcat (p, XSTR (av->value, 0));
1371       for (; *p != '\0'; p++)
1372         if (*p >= 'a' && *p <= 'z')
1373           *p -= 'a' - 'A';
1374
1375       value = attr_rtx (SYMBOL_REF, string);
1376       RTX_UNCHANGING_P (value) = 1;
1377       
1378       XVECEXP (condexp, 0, 2 * i) = attr_rtx (EQ, exp, value);
1379
1380       XVECEXP (condexp, 0, 2 * i + 1) = av->value;
1381     }
1382
1383   return condexp;
1384 }
1385 #endif
1386 \f
1387 /* Given a valid expression for an attribute value, remove any IF_THEN_ELSE
1388    expressions by converting them into a COND.  This removes cases from this
1389    program.  Also, replace an attribute value of "*" with the default attribute
1390    value.  */
1391
1392 static rtx
1393 make_canonical (attr, exp)
1394      struct attr_desc *attr;
1395      rtx exp;
1396 {
1397   int i;
1398   rtx newexp;
1399
1400   switch (GET_CODE (exp))
1401     {
1402     case CONST_INT:
1403       exp = make_numeric_value (INTVAL (exp));
1404       break;
1405
1406     case CONST_STRING:
1407       if (! strcmp (XSTR (exp, 0), "*"))
1408         {
1409           if (attr == 0 || attr->default_val == 0)
1410             fatal ("(attr_value \"*\") used in invalid context.");
1411           exp = attr->default_val->value;
1412         }
1413
1414       break;
1415
1416     case SYMBOL_REF:
1417       if (!attr->is_const || RTX_UNCHANGING_P (exp))
1418         break;
1419       /* The SYMBOL_REF is constant for a given run, so mark it as unchanging.
1420          This makes the COND something that won't be considered an arbitrary
1421          expression by walk_attr_value.  */
1422       RTX_UNCHANGING_P (exp) = 1;
1423 #if 0
1424       /* ??? Why do we do this?  With attribute values { A B C D E }, this
1425          tends to generate (!(x==A) && !(x==B) && !(x==C) && !(x==D)) rather
1426          than (x==E). */
1427       exp = convert_const_symbol_ref (exp, attr);
1428       RTX_UNCHANGING_P (exp) = 1;
1429       exp = check_attr_value (exp, attr);
1430       /* Goto COND case since this is now a COND.  Note that while the
1431          new expression is rescanned, all symbol_ref notes are marked as
1432          unchanging.  */
1433       goto cond;
1434 #else
1435       exp = check_attr_value (exp, attr);
1436       break;
1437 #endif
1438
1439     case IF_THEN_ELSE:
1440       newexp = rtx_alloc (COND);
1441       XVEC (newexp, 0) = rtvec_alloc (2);
1442       XVECEXP (newexp, 0, 0) = XEXP (exp, 0);
1443       XVECEXP (newexp, 0, 1) = XEXP (exp, 1);
1444
1445       XEXP (newexp, 1) = XEXP (exp, 2);
1446
1447       exp = newexp;
1448       /* Fall through to COND case since this is now a COND.  */
1449
1450     case COND:
1451       {
1452         int allsame = 1;
1453         rtx defval;
1454
1455         /* First, check for degenerate COND.  */
1456         if (XVECLEN (exp, 0) == 0)
1457           return make_canonical (attr, XEXP (exp, 1));
1458         defval = XEXP (exp, 1) = make_canonical (attr, XEXP (exp, 1));
1459
1460         for (i = 0; i < XVECLEN (exp, 0); i += 2)
1461           {
1462             XVECEXP (exp, 0, i) = copy_boolean (XVECEXP (exp, 0, i));
1463             XVECEXP (exp, 0, i + 1)
1464               = make_canonical (attr, XVECEXP (exp, 0, i + 1));
1465             if (! rtx_equal_p (XVECEXP (exp, 0, i + 1), defval))
1466               allsame = 0;
1467           }
1468         if (allsame)
1469           return defval;
1470       }
1471       break;
1472
1473     default:
1474       break;
1475     }
1476
1477   return exp;
1478 }
1479
1480 static rtx
1481 copy_boolean (exp)
1482      rtx exp;
1483 {
1484   if (GET_CODE (exp) == AND || GET_CODE (exp) == IOR)
1485     return attr_rtx (GET_CODE (exp), copy_boolean (XEXP (exp, 0)),
1486                      copy_boolean (XEXP (exp, 1)));
1487   return exp;
1488 }
1489 \f
1490 /* Given a value and an attribute description, return a `struct attr_value *'
1491    that represents that value.  This is either an existing structure, if the
1492    value has been previously encountered, or a newly-created structure.
1493
1494    `insn_code' is the code of an insn whose attribute has the specified
1495    value (-2 if not processing an insn).  We ensure that all insns for
1496    a given value have the same number of alternatives if the value checks
1497    alternatives.  */
1498
1499 static struct attr_value *
1500 get_attr_value (value, attr, insn_code)
1501      rtx value;
1502      struct attr_desc *attr;
1503      int insn_code;
1504 {
1505   struct attr_value *av;
1506   int num_alt = 0;
1507
1508   value = make_canonical (attr, value);
1509   if (compares_alternatives_p (value))
1510     {
1511       if (insn_code < 0 || insn_alternatives == NULL)
1512         fatal ("(eq_attr \"alternatives\" ...) used in non-insn context");
1513       else
1514         num_alt = insn_alternatives[insn_code];
1515     }
1516
1517   for (av = attr->first_value; av; av = av->next)
1518     if (rtx_equal_p (value, av->value)
1519         && (num_alt == 0 || av->first_insn == NULL
1520             || insn_alternatives[av->first_insn->insn_code]))
1521       return av;
1522
1523   av = (struct attr_value *) oballoc (sizeof (struct attr_value));
1524   av->value = value;
1525   av->next = attr->first_value;
1526   attr->first_value = av;
1527   av->first_insn = NULL;
1528   av->num_insns = 0;
1529   av->has_asm_insn = 0;
1530
1531   return av;
1532 }
1533 \f
1534 /* After all DEFINE_DELAYs have been read in, create internal attributes
1535    to generate the required routines.
1536
1537    First, we compute the number of delay slots for each insn (as a COND of
1538    each of the test expressions in DEFINE_DELAYs).  Then, if more than one
1539    delay type is specified, we compute a similar function giving the
1540    DEFINE_DELAY ordinal for each insn.
1541
1542    Finally, for each [DEFINE_DELAY, slot #] pair, we compute an attribute that
1543    tells whether a given insn can be in that delay slot.
1544
1545    Normal attribute filling and optimization expands these to contain the
1546    information needed to handle delay slots.  */
1547
1548 static void
1549 expand_delays ()
1550 {
1551   struct delay_desc *delay;
1552   rtx condexp;
1553   rtx newexp;
1554   int i;
1555   char *p;
1556
1557   /* First, generate data for `num_delay_slots' function.  */
1558
1559   condexp = rtx_alloc (COND);
1560   XVEC (condexp, 0) = rtvec_alloc (num_delays * 2);
1561   XEXP (condexp, 1) = make_numeric_value (0);
1562
1563   for (i = 0, delay = delays; delay; i += 2, delay = delay->next)
1564     {
1565       XVECEXP (condexp, 0, i) = XEXP (delay->def, 0);
1566       XVECEXP (condexp, 0, i + 1)
1567         = make_numeric_value (XVECLEN (delay->def, 1) / 3);
1568     }
1569
1570   make_internal_attr ("*num_delay_slots", condexp, 0);
1571
1572   /* If more than one delay type, do the same for computing the delay type.  */
1573   if (num_delays > 1)
1574     {
1575       condexp = rtx_alloc (COND);
1576       XVEC (condexp, 0) = rtvec_alloc (num_delays * 2);
1577       XEXP (condexp, 1) = make_numeric_value (0);
1578
1579       for (i = 0, delay = delays; delay; i += 2, delay = delay->next)
1580         {
1581           XVECEXP (condexp, 0, i) = XEXP (delay->def, 0);
1582           XVECEXP (condexp, 0, i + 1) = make_numeric_value (delay->num);
1583         }
1584
1585       make_internal_attr ("*delay_type", condexp, 1);
1586     }
1587
1588   /* For each delay possibility and delay slot, compute an eligibility
1589      attribute for non-annulled insns and for each type of annulled (annul
1590      if true and annul if false).  */
1591  for (delay = delays; delay; delay = delay->next)
1592    {
1593      for (i = 0; i < XVECLEN (delay->def, 1); i += 3)
1594        {
1595          condexp = XVECEXP (delay->def, 1, i);
1596          if (condexp == 0) condexp = false_rtx;
1597          newexp = attr_rtx (IF_THEN_ELSE, condexp,
1598                             make_numeric_value (1), make_numeric_value (0));
1599
1600          p = attr_printf (sizeof ("*delay__") + MAX_DIGITS*2, "*delay_%d_%d",
1601                           delay->num, i / 3);
1602          make_internal_attr (p, newexp, 1);
1603
1604          if (have_annul_true)
1605            {
1606              condexp = XVECEXP (delay->def, 1, i + 1);
1607              if (condexp == 0) condexp = false_rtx;
1608              newexp = attr_rtx (IF_THEN_ELSE, condexp,
1609                                 make_numeric_value (1),
1610                                 make_numeric_value (0));
1611              p = attr_printf (sizeof ("*annul_true__") + MAX_DIGITS*2,
1612                               "*annul_true_%d_%d", delay->num, i / 3);
1613              make_internal_attr (p, newexp, 1);
1614            }
1615
1616          if (have_annul_false)
1617            {
1618              condexp = XVECEXP (delay->def, 1, i + 2);
1619              if (condexp == 0) condexp = false_rtx;
1620              newexp = attr_rtx (IF_THEN_ELSE, condexp,
1621                                 make_numeric_value (1),
1622                                 make_numeric_value (0));
1623              p = attr_printf (sizeof ("*annul_false__") + MAX_DIGITS*2,
1624                               "*annul_false_%d_%d", delay->num, i / 3);
1625              make_internal_attr (p, newexp, 1);
1626            }
1627        }
1628    }
1629 }
1630 \f
1631 /* This function is given a left and right side expression and an operator.
1632    Each side is a conditional expression, each alternative of which has a
1633    numerical value.  The function returns another conditional expression
1634    which, for every possible set of condition values, returns a value that is
1635    the operator applied to the values of the two sides.
1636
1637    Since this is called early, it must also support IF_THEN_ELSE.  */
1638
1639 static rtx
1640 operate_exp (op, left, right)
1641      enum operator op;
1642      rtx left, right;
1643 {
1644   int left_value, right_value;
1645   rtx newexp;
1646   int i;
1647
1648   /* If left is a string, apply operator to it and the right side.  */
1649   if (GET_CODE (left) == CONST_STRING)
1650     {
1651       /* If right is also a string, just perform the operation.  */
1652       if (GET_CODE (right) == CONST_STRING)
1653         {
1654           left_value = atoi (XSTR (left, 0));
1655           right_value = atoi (XSTR (right, 0));
1656           switch (op)
1657             {
1658             case PLUS_OP:
1659               i = left_value + right_value;
1660               break;
1661
1662             case MINUS_OP:
1663               i = left_value - right_value;
1664               break;
1665
1666             case POS_MINUS_OP:  /* The positive part of LEFT - RIGHT.  */
1667               if (left_value > right_value)
1668                 i = left_value - right_value;
1669               else
1670                 i = 0;
1671               break;
1672
1673             case OR_OP:
1674             case ORX_OP:
1675               i = left_value | right_value;
1676               break;
1677
1678             case EQ_OP:
1679               i = left_value == right_value;
1680               break;
1681
1682             case RANGE_OP:
1683               i = (left_value << (HOST_BITS_PER_INT / 2)) | right_value;
1684               break;
1685
1686             case MAX_OP:
1687               if (left_value > right_value)
1688                 i = left_value;
1689               else
1690                 i = right_value;
1691               break;
1692
1693             case MIN_OP:
1694               if (left_value < right_value)
1695                 i = left_value;
1696               else
1697                 i = right_value;
1698               break;
1699
1700             default:
1701               abort ();
1702             }
1703
1704           if (i == left_value)
1705             return left;
1706           if (i == right_value)
1707             return right;
1708           return make_numeric_value (i);
1709         }
1710       else if (GET_CODE (right) == IF_THEN_ELSE)
1711         {
1712           /* Apply recursively to all values within.  */
1713           rtx newleft = operate_exp (op, left, XEXP (right, 1));
1714           rtx newright = operate_exp (op, left, XEXP (right, 2));
1715           if (rtx_equal_p (newleft, newright))
1716             return newleft;
1717           return attr_rtx (IF_THEN_ELSE, XEXP (right, 0), newleft, newright);
1718         }
1719       else if (GET_CODE (right) == COND)
1720         {
1721           int allsame = 1;
1722           rtx defval;
1723
1724           newexp = rtx_alloc (COND);
1725           XVEC (newexp, 0) = rtvec_alloc (XVECLEN (right, 0));
1726           defval = XEXP (newexp, 1) = operate_exp (op, left, XEXP (right, 1));
1727
1728           for (i = 0; i < XVECLEN (right, 0); i += 2)
1729             {
1730               XVECEXP (newexp, 0, i) = XVECEXP (right, 0, i);
1731               XVECEXP (newexp, 0, i + 1)
1732                 = operate_exp (op, left, XVECEXP (right, 0, i + 1));
1733               if (! rtx_equal_p (XVECEXP (newexp, 0, i + 1),
1734                                  defval))     
1735                 allsame = 0;
1736             }
1737
1738           /* If the resulting cond is trivial (all alternatives
1739              give the same value), optimize it away.  */
1740           if (allsame)
1741             {
1742               obstack_free (rtl_obstack, newexp);
1743               return operate_exp (op, left, XEXP (right, 1));
1744             }
1745
1746           /* If the result is the same as the RIGHT operand,
1747              just use that.  */
1748           if (rtx_equal_p (newexp, right))
1749             {
1750               obstack_free (rtl_obstack, newexp);
1751               return right;
1752             }
1753
1754           return newexp;
1755         }
1756       else
1757         fatal ("Badly formed attribute value");
1758     }
1759
1760   /* A hack to prevent expand_units from completely blowing up: ORX_OP does
1761      not associate through IF_THEN_ELSE.  */
1762   else if (op == ORX_OP && GET_CODE (right) == IF_THEN_ELSE)
1763     {
1764       return attr_rtx (IOR, left, right);
1765     }
1766
1767   /* Otherwise, do recursion the other way.  */
1768   else if (GET_CODE (left) == IF_THEN_ELSE)
1769     {
1770       rtx newleft = operate_exp (op, XEXP (left, 1), right);
1771       rtx newright = operate_exp (op, XEXP (left, 2), right);
1772       if (rtx_equal_p (newleft, newright))
1773         return newleft;
1774       return attr_rtx (IF_THEN_ELSE, XEXP (left, 0), newleft, newright);
1775     }
1776   else if (GET_CODE (left) == COND)
1777     {
1778       int allsame = 1;
1779       rtx defval;
1780
1781       newexp = rtx_alloc (COND);
1782       XVEC (newexp, 0) = rtvec_alloc (XVECLEN (left, 0));
1783       defval = XEXP (newexp, 1) = operate_exp (op, XEXP (left, 1), right);
1784
1785       for (i = 0; i < XVECLEN (left, 0); i += 2)
1786         {
1787           XVECEXP (newexp, 0, i) = XVECEXP (left, 0, i);
1788           XVECEXP (newexp, 0, i + 1)
1789             = operate_exp (op, XVECEXP (left, 0, i + 1), right);
1790           if (! rtx_equal_p (XVECEXP (newexp, 0, i + 1),
1791                              defval))     
1792             allsame = 0;
1793         }
1794
1795       /* If the cond is trivial (all alternatives give the same value),
1796          optimize it away.  */
1797       if (allsame)
1798         {
1799           obstack_free (rtl_obstack, newexp);
1800           return operate_exp (op, XEXP (left, 1), right);
1801         }
1802
1803       /* If the result is the same as the LEFT operand,
1804          just use that.  */
1805       if (rtx_equal_p (newexp, left))
1806         {
1807           obstack_free (rtl_obstack, newexp);
1808           return left;
1809         }
1810
1811       return newexp;
1812     }
1813
1814   else
1815     fatal ("Badly formed attribute value.");
1816   /* NOTREACHED */
1817   return NULL;
1818 }
1819 \f
1820 /* Once all attributes and DEFINE_FUNCTION_UNITs have been read, we
1821    construct a number of attributes.
1822
1823    The first produces a function `function_units_used' which is given an
1824    insn and produces an encoding showing which function units are required
1825    for the execution of that insn.  If the value is non-negative, the insn
1826    uses that unit; otherwise, the value is a one's compliment mask of units
1827    used.
1828
1829    The second produces a function `result_ready_cost' which is used to
1830    determine the time that the result of an insn will be ready and hence
1831    a worst-case schedule.
1832
1833    Both of these produce quite complex expressions which are then set as the
1834    default value of internal attributes.  Normal attribute simplification
1835    should produce reasonable expressions.
1836
1837    For each unit, a `<name>_unit_ready_cost' function will take an
1838    insn and give the delay until that unit will be ready with the result
1839    and a `<name>_unit_conflict_cost' function is given an insn already
1840    executing on the unit and a candidate to execute and will give the
1841    cost from the time the executing insn started until the candidate
1842    can start (ignore limitations on the number of simultaneous insns).
1843
1844    For each unit, a `<name>_unit_blockage' function is given an insn
1845    already executing on the unit and a candidate to execute and will
1846    give the delay incurred due to function unit conflicts.  The range of
1847    blockage cost values for a given executing insn is given by the
1848    `<name>_unit_blockage_range' function.  These values are encoded in
1849    an int where the upper half gives the minimum value and the lower
1850    half gives the maximum value.  */
1851
1852 static void
1853 expand_units ()
1854 {
1855   struct function_unit *unit, **unit_num;
1856   struct function_unit_op *op, **op_array, ***unit_ops;
1857   rtx unitsmask;
1858   rtx readycost;
1859   rtx newexp;
1860   char *str;
1861   int i, j, u, num, nvalues;
1862
1863   /* Rebuild the condition for the unit to share the RTL expressions.
1864      Sharing is required by simplify_by_exploding.  Build the issue delay
1865      expressions.  Validate the expressions we were given for the conditions
1866      and conflict vector.  Then make attributes for use in the conflict
1867      function.  */
1868
1869   for (unit = units; unit; unit = unit->next)
1870     {
1871       unit->condexp = check_attr_test (unit->condexp, 0);
1872
1873       for (op = unit->ops; op; op = op->next)
1874         {
1875           rtx issue_delay = make_numeric_value (op->issue_delay);
1876           rtx issue_exp = issue_delay;
1877
1878           /* Build, validate, and simplify the issue delay expression.  */
1879           if (op->conflict_exp != true_rtx)
1880             issue_exp = attr_rtx (IF_THEN_ELSE, op->conflict_exp,
1881                                   issue_exp, make_numeric_value (0));
1882           issue_exp = check_attr_value (make_canonical (NULL_ATTR,
1883                                                         issue_exp),
1884                                         NULL_ATTR);
1885           issue_exp = simplify_knowing (issue_exp, unit->condexp);
1886           op->issue_exp = issue_exp;
1887
1888           /* Make an attribute for use in the conflict function if needed.  */
1889           unit->needs_conflict_function = (unit->issue_delay.min
1890                                            != unit->issue_delay.max);
1891           if (unit->needs_conflict_function)
1892             {
1893               str = attr_printf (strlen (unit->name) + sizeof ("*_cost_") + MAX_DIGITS,
1894                                  "*%s_cost_%d", unit->name, op->num);
1895               make_internal_attr (str, issue_exp, 1);
1896             }
1897
1898           /* Validate the condition.  */
1899           op->condexp = check_attr_test (op->condexp, 0);
1900         }
1901     }
1902
1903   /* Compute the mask of function units used.  Initially, the unitsmask is
1904      zero.   Set up a conditional to compute each unit's contribution.  */
1905   unitsmask = make_numeric_value (0);
1906   newexp = rtx_alloc (IF_THEN_ELSE);
1907   XEXP (newexp, 2) = make_numeric_value (0);
1908
1909   /* If we have just a few units, we may be all right expanding the whole
1910      thing.  But the expansion is 2**N in space on the number of opclasses,
1911      so we can't do this for very long -- Alpha and MIPS in particular have
1912      problems with this.  So in that situation, we fall back on an alternate
1913      implementation method.  */
1914 #define NUM_UNITOP_CUTOFF 20
1915
1916   if (num_unit_opclasses < NUM_UNITOP_CUTOFF)
1917     {
1918       /* Merge each function unit into the unit mask attributes.  */
1919       for (unit = units; unit; unit = unit->next)
1920         {
1921           XEXP (newexp, 0) = unit->condexp;
1922           XEXP (newexp, 1) = make_numeric_value (1 << unit->num);
1923           unitsmask = operate_exp (OR_OP, unitsmask, newexp);
1924         }
1925     }
1926   else
1927     {
1928       /* Merge each function unit into the unit mask attributes.  */
1929       for (unit = units; unit; unit = unit->next)
1930         {
1931           XEXP (newexp, 0) = unit->condexp;
1932           XEXP (newexp, 1) = make_numeric_value (1 << unit->num);
1933           unitsmask = operate_exp (ORX_OP, unitsmask, attr_copy_rtx (newexp));
1934         }
1935     }
1936
1937   /* Simplify the unit mask expression, encode it, and make an attribute
1938      for the function_units_used function.  */
1939   unitsmask = simplify_by_exploding (unitsmask);
1940
1941   if (num_unit_opclasses < NUM_UNITOP_CUTOFF)
1942     unitsmask = encode_units_mask (unitsmask);
1943   else
1944     {
1945       /* We can no longer encode unitsmask at compile time, so emit code to
1946          calculate it at runtime.  Rather, put a marker for where we'd do
1947          the code, and actually output it in write_attr_get().  */
1948       unitsmask = attr_rtx (FFS, unitsmask);
1949     }
1950
1951   make_internal_attr ("*function_units_used", unitsmask, 2);
1952
1953   /* Create an array of ops for each unit.  Add an extra unit for the
1954      result_ready_cost function that has the ops of all other units.  */
1955   unit_ops = (struct function_unit_op ***)
1956     alloca ((num_units + 1) * sizeof (struct function_unit_op **));
1957   unit_num = (struct function_unit **)
1958     alloca ((num_units + 1) * sizeof (struct function_unit *));
1959
1960   unit_num[num_units] = unit = (struct function_unit *)
1961     alloca (sizeof (struct function_unit));
1962   unit->num = num_units;
1963   unit->num_opclasses = 0;
1964
1965   for (unit = units; unit; unit = unit->next)
1966     {
1967       unit_num[num_units]->num_opclasses += unit->num_opclasses;
1968       unit_num[unit->num] = unit;
1969       unit_ops[unit->num] = op_array = (struct function_unit_op **)
1970         alloca (unit->num_opclasses * sizeof (struct function_unit_op *));
1971
1972       for (op = unit->ops; op; op = op->next)
1973         op_array[op->num] = op;
1974     }
1975
1976   /* Compose the array of ops for the extra unit.  */
1977   unit_ops[num_units] = op_array = (struct function_unit_op **)
1978     alloca (unit_num[num_units]->num_opclasses
1979             * sizeof (struct function_unit_op *));
1980
1981   for (unit = units, i = 0; unit; i += unit->num_opclasses, unit = unit->next)
1982     bcopy ((char *) unit_ops[unit->num], (char *) &op_array[i],
1983            unit->num_opclasses * sizeof (struct function_unit_op *));
1984
1985   /* Compute the ready cost function for each unit by computing the
1986      condition for each non-default value.  */
1987   for (u = 0; u <= num_units; u++)
1988     {
1989       rtx orexp;
1990       int value;
1991
1992       unit = unit_num[u];
1993       op_array = unit_ops[unit->num];
1994       num = unit->num_opclasses;
1995
1996       /* Sort the array of ops into increasing ready cost order.  */
1997       for (i = 0; i < num; i++)
1998         for (j = num - 1; j > i; j--)
1999           if (op_array[j-1]->ready < op_array[j]->ready)
2000             {
2001               op = op_array[j];
2002               op_array[j] = op_array[j-1];
2003               op_array[j-1] = op;
2004             }
2005
2006       /* Determine how many distinct non-default ready cost values there
2007          are.  We use a default ready cost value of 1.  */
2008       nvalues = 0; value = 1;
2009       for (i = num - 1; i >= 0; i--)
2010         if (op_array[i]->ready > value)
2011           {
2012             value = op_array[i]->ready;
2013             nvalues++;
2014           }
2015
2016       if (nvalues == 0)
2017         readycost = make_numeric_value (1);
2018       else
2019         {
2020           /* Construct the ready cost expression as a COND of each value from
2021              the largest to the smallest.  */
2022           readycost = rtx_alloc (COND);
2023           XVEC (readycost, 0) = rtvec_alloc (nvalues * 2);
2024           XEXP (readycost, 1) = make_numeric_value (1);
2025
2026           nvalues = 0; orexp = false_rtx; value = op_array[0]->ready;
2027           for (i = 0; i < num; i++)
2028             {
2029               op = op_array[i];
2030               if (op->ready <= 1)
2031                 break;
2032               else if (op->ready == value)
2033                 orexp = insert_right_side (IOR, orexp, op->condexp, -2, -2);
2034               else
2035                 {
2036                   XVECEXP (readycost, 0, nvalues * 2) = orexp;
2037                   XVECEXP (readycost, 0, nvalues * 2 + 1)
2038                     = make_numeric_value (value);
2039                   nvalues++;
2040                   value = op->ready;
2041                   orexp = op->condexp;
2042                 }
2043             }
2044           XVECEXP (readycost, 0, nvalues * 2) = orexp;
2045           XVECEXP (readycost, 0, nvalues * 2 + 1) = make_numeric_value (value);
2046         }
2047
2048       if (u < num_units)
2049         {
2050           rtx max_blockage = 0, min_blockage = 0;
2051
2052           /* Simplify the readycost expression by only considering insns
2053              that use the unit.  */
2054           readycost = simplify_knowing (readycost, unit->condexp);
2055
2056           /* Determine the blockage cost the executing insn (E) given
2057              the candidate insn (C).  This is the maximum of the issue
2058              delay, the pipeline delay, and the simultaneity constraint.
2059              Each function_unit_op represents the characteristics of the
2060              candidate insn, so in the expressions below, C is a known
2061              term and E is an unknown term.
2062
2063              We compute the blockage cost for each E for every possible C.
2064              Thus OP represents E, and READYCOST is a list of values for
2065              every possible C.
2066
2067              The issue delay function for C is op->issue_exp and is used to
2068              write the `<name>_unit_conflict_cost' function.  Symbolicly
2069              this is "ISSUE-DELAY (E,C)".
2070
2071              The pipeline delay results form the FIFO constraint on the
2072              function unit and is "READY-COST (E) + 1 - READY-COST (C)".
2073
2074              The simultaneity constraint is based on how long it takes to
2075              fill the unit given the minimum issue delay.  FILL-TIME is the
2076              constant "MIN (ISSUE-DELAY (*,*)) * (SIMULTANEITY - 1)", and
2077              the simultaneity constraint is "READY-COST (E) - FILL-TIME"
2078              if SIMULTANEITY is non-zero and zero otherwise.
2079
2080              Thus, BLOCKAGE (E,C) when SIMULTANEITY is zero is
2081
2082                  MAX (ISSUE-DELAY (E,C),
2083                       READY-COST (E) - (READY-COST (C) - 1))
2084
2085              and otherwise
2086
2087                  MAX (ISSUE-DELAY (E,C),
2088                       READY-COST (E) - (READY-COST (C) - 1),
2089                       READY-COST (E) - FILL-TIME)
2090
2091              The `<name>_unit_blockage' function is computed by determining
2092              this value for each candidate insn.  As these values are
2093              computed, we also compute the upper and lower bounds for
2094              BLOCKAGE (E,*).  These are combined to form the function
2095              `<name>_unit_blockage_range'.  Finally, the maximum blockage
2096              cost, MAX (BLOCKAGE (*,*)), is computed.  */
2097
2098           for (op = unit->ops; op; op = op->next)
2099             {
2100 #ifdef HAIFA
2101               rtx blockage = op->issue_exp;
2102 #else
2103               rtx blockage = operate_exp (POS_MINUS_OP, readycost,
2104                                           make_numeric_value (1));
2105
2106               if (unit->simultaneity != 0)
2107                 {
2108                   rtx filltime = make_numeric_value ((unit->simultaneity - 1)
2109                                                      * unit->issue_delay.min);
2110                   blockage = operate_exp (MIN_OP, blockage, filltime);
2111                 }
2112
2113               blockage = operate_exp (POS_MINUS_OP,
2114                                       make_numeric_value (op->ready),
2115                                       blockage);
2116
2117               blockage = operate_exp (MAX_OP, blockage, op->issue_exp);
2118 #endif
2119               blockage = simplify_knowing (blockage, unit->condexp);
2120
2121               /* Add this op's contribution to MAX (BLOCKAGE (E,*)) and
2122                  MIN (BLOCKAGE (E,*)).  */
2123               if (max_blockage == 0)
2124                 max_blockage = min_blockage = blockage;
2125               else
2126                 {
2127                   max_blockage
2128                     = simplify_knowing (operate_exp (MAX_OP, max_blockage,
2129                                                      blockage),
2130                                         unit->condexp);
2131                   min_blockage
2132                     = simplify_knowing (operate_exp (MIN_OP, min_blockage,
2133                                                      blockage),
2134                                         unit->condexp);
2135                 }
2136
2137               /* Make an attribute for use in the blockage function.  */
2138               str = attr_printf (strlen (unit->name) + sizeof ("*_block_") + MAX_DIGITS,
2139                                  "*%s_block_%d", unit->name, op->num);
2140               make_internal_attr (str, blockage, 1);
2141             }
2142
2143           /* Record MAX (BLOCKAGE (*,*)).  */
2144           unit->max_blockage = max_attr_value (max_blockage);
2145
2146           /* See if the upper and lower bounds of BLOCKAGE (E,*) are the
2147              same.  If so, the blockage function carries no additional
2148              information and is not written.  */
2149           newexp = operate_exp (EQ_OP, max_blockage, min_blockage);
2150           newexp = simplify_knowing (newexp, unit->condexp);
2151           unit->needs_blockage_function
2152             = (GET_CODE (newexp) != CONST_STRING
2153                || atoi (XSTR (newexp, 0)) != 1);
2154
2155           /* If the all values of BLOCKAGE (E,C) have the same value,
2156              neither blockage function is written.  */    
2157           unit->needs_range_function
2158             = (unit->needs_blockage_function
2159                || GET_CODE (max_blockage) != CONST_STRING);
2160
2161           if (unit->needs_range_function)
2162             {
2163               /* Compute the blockage range function and make an attribute
2164                  for writing it's value.  */
2165               newexp = operate_exp (RANGE_OP, min_blockage, max_blockage);
2166               newexp = simplify_knowing (newexp, unit->condexp);
2167
2168               str = attr_printf (strlen (unit->name) + sizeof ("*_unit_blockage_range"),
2169                                  "*%s_unit_blockage_range", unit->name);
2170               make_internal_attr (str, newexp, 4);
2171             }
2172
2173           str = attr_printf (strlen (unit->name) + sizeof ("*_unit_ready_cost"),
2174                              "*%s_unit_ready_cost", unit->name);
2175         }
2176       else
2177         str = "*result_ready_cost";
2178
2179       /* Make an attribute for the ready_cost function.  Simplifying
2180          further with simplify_by_exploding doesn't win.  */
2181       make_internal_attr (str, readycost, 0);
2182     }
2183
2184   /* For each unit that requires a conflict cost function, make an attribute
2185      that maps insns to the operation number.  */
2186   for (unit = units; unit; unit = unit->next)
2187     {
2188       rtx caseexp;
2189
2190       if (! unit->needs_conflict_function
2191           && ! unit->needs_blockage_function)
2192         continue;
2193
2194       caseexp = rtx_alloc (COND);
2195       XVEC (caseexp, 0) = rtvec_alloc ((unit->num_opclasses - 1) * 2);
2196
2197       for (op = unit->ops; op; op = op->next)
2198         {
2199           /* Make our adjustment to the COND being computed.  If we are the
2200              last operation class, place our values into the default of the
2201              COND.  */
2202           if (op->num == unit->num_opclasses - 1)
2203             {
2204               XEXP (caseexp, 1) = make_numeric_value (op->num);
2205             }
2206           else
2207             {
2208               XVECEXP (caseexp, 0, op->num * 2) = op->condexp;
2209               XVECEXP (caseexp, 0, op->num * 2 + 1)
2210                 = make_numeric_value (op->num);
2211             }
2212         }
2213
2214       /* Simplifying caseexp with simplify_by_exploding doesn't win.  */
2215       str = attr_printf (strlen (unit->name) + sizeof ("*_cases"),
2216                          "*%s_cases", unit->name);
2217       make_internal_attr (str, caseexp, 1);
2218     }
2219 }
2220
2221 /* Simplify EXP given KNOWN_TRUE.  */
2222
2223 static rtx
2224 simplify_knowing (exp, known_true)
2225      rtx exp, known_true;
2226 {
2227   if (GET_CODE (exp) != CONST_STRING)
2228     {
2229       exp = attr_rtx (IF_THEN_ELSE, known_true, exp,
2230                       make_numeric_value (max_attr_value (exp)));
2231       exp = simplify_by_exploding (exp);
2232     }
2233   return exp;
2234 }
2235
2236 /* Translate the CONST_STRING expressions in X to change the encoding of
2237    value.  On input, the value is a bitmask with a one bit for each unit
2238    used; on output, the value is the unit number (zero based) if one
2239    and only one unit is used or the one's compliment of the bitmask.  */
2240
2241 static rtx
2242 encode_units_mask (x)
2243      rtx x;
2244 {
2245   register int i;
2246   register int j;
2247   register enum rtx_code code;
2248   register char *fmt;
2249
2250   code = GET_CODE (x);
2251
2252   switch (code)
2253     {
2254     case CONST_STRING:
2255       i = atoi (XSTR (x, 0));
2256       if (i < 0)
2257         abort (); /* The sign bit encodes a one's compliment mask.  */
2258       else if (i != 0 && i == (i & -i))
2259         /* Only one bit is set, so yield that unit number.  */
2260         for (j = 0; (i >>= 1) != 0; j++)
2261           ;
2262       else
2263         j = ~i;
2264       return attr_rtx (CONST_STRING, attr_printf (MAX_DIGITS, "%d", j));
2265
2266     case REG:
2267     case QUEUED:
2268     case CONST_INT:
2269     case CONST_DOUBLE:
2270     case SYMBOL_REF:
2271     case CODE_LABEL:
2272     case PC:
2273     case CC0:
2274     case EQ_ATTR:
2275       return x;
2276       
2277     default:
2278       break;
2279     }
2280
2281   /* Compare the elements.  If any pair of corresponding elements
2282      fail to match, return 0 for the whole things.  */
2283
2284   fmt = GET_RTX_FORMAT (code);
2285   for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
2286     {
2287       switch (fmt[i])
2288         {
2289         case 'V':
2290         case 'E':
2291           for (j = 0; j < XVECLEN (x, i); j++)
2292             XVECEXP (x, i, j) = encode_units_mask (XVECEXP (x, i, j));
2293           break;
2294
2295         case 'e':
2296           XEXP (x, i) = encode_units_mask (XEXP (x, i));
2297           break;
2298         }
2299     }
2300   return x;
2301 }
2302 \f
2303 /* Once all attributes and insns have been read and checked, we construct for
2304    each attribute value a list of all the insns that have that value for
2305    the attribute.  */
2306
2307 static void
2308 fill_attr (attr)
2309      struct attr_desc *attr;
2310 {
2311   struct attr_value *av;
2312   struct insn_ent *ie;
2313   struct insn_def *id;
2314   int i;
2315   rtx value;
2316
2317   /* Don't fill constant attributes.  The value is independent of
2318      any particular insn.  */
2319   if (attr->is_const)
2320     return;
2321
2322   for (id = defs; id; id = id->next)
2323     {
2324       /* If no value is specified for this insn for this attribute, use the
2325          default.  */
2326       value = NULL;
2327       if (XVEC (id->def, id->vec_idx))
2328         for (i = 0; i < XVECLEN (id->def, id->vec_idx); i++)
2329           if (! strcmp (XSTR (XEXP (XVECEXP (id->def, id->vec_idx, i), 0), 0), 
2330                         attr->name))
2331             value = XEXP (XVECEXP (id->def, id->vec_idx, i), 1);
2332
2333       if (value == NULL)
2334         av = attr->default_val;
2335       else
2336         av = get_attr_value (value, attr, id->insn_code);
2337
2338       ie = (struct insn_ent *) oballoc (sizeof (struct insn_ent));
2339       ie->insn_code = id->insn_code;
2340       ie->insn_index = id->insn_code;
2341       insert_insn_ent (av, ie);
2342     }
2343 }
2344 \f
2345 /* Given an expression EXP, see if it is a COND or IF_THEN_ELSE that has a
2346    test that checks relative positions of insns (uses MATCH_DUP or PC).
2347    If so, replace it with what is obtained by passing the expression to
2348    ADDRESS_FN.  If not but it is a COND or IF_THEN_ELSE, call this routine
2349    recursively on each value (including the default value).  Otherwise,
2350    return the value returned by NO_ADDRESS_FN applied to EXP.  */
2351
2352 static rtx
2353 substitute_address (exp, no_address_fn, address_fn)
2354      rtx exp;
2355      rtx (*no_address_fn) ();
2356      rtx (*address_fn) ();
2357 {
2358   int i;
2359   rtx newexp;
2360
2361   if (GET_CODE (exp) == COND)
2362     {
2363       /* See if any tests use addresses.  */
2364       address_used = 0;
2365       for (i = 0; i < XVECLEN (exp, 0); i += 2)
2366         walk_attr_value (XVECEXP (exp, 0, i));
2367
2368       if (address_used)
2369         return (*address_fn) (exp);
2370
2371       /* Make a new copy of this COND, replacing each element.  */
2372       newexp = rtx_alloc (COND);
2373       XVEC (newexp, 0) = rtvec_alloc (XVECLEN (exp, 0));
2374       for (i = 0; i < XVECLEN (exp, 0); i += 2)
2375         {
2376           XVECEXP (newexp, 0, i) = XVECEXP (exp, 0, i);
2377           XVECEXP (newexp, 0, i + 1)
2378             = substitute_address (XVECEXP (exp, 0, i + 1),
2379                                   no_address_fn, address_fn);
2380         }
2381
2382       XEXP (newexp, 1) = substitute_address (XEXP (exp, 1),
2383                                              no_address_fn, address_fn);
2384
2385       return newexp;
2386     }
2387
2388   else if (GET_CODE (exp) == IF_THEN_ELSE)
2389     {
2390       address_used = 0;
2391       walk_attr_value (XEXP (exp, 0));
2392       if (address_used)
2393         return (*address_fn) (exp);
2394
2395       return attr_rtx (IF_THEN_ELSE,
2396                        substitute_address (XEXP (exp, 0),
2397                                            no_address_fn, address_fn),
2398                        substitute_address (XEXP (exp, 1),
2399                                            no_address_fn, address_fn),
2400                        substitute_address (XEXP (exp, 2),
2401                                            no_address_fn, address_fn));
2402     }
2403
2404   return (*no_address_fn) (exp);
2405 }
2406 \f
2407 /* Make new attributes from the `length' attribute.  The following are made,
2408    each corresponding to a function called from `shorten_branches' or
2409    `get_attr_length':
2410
2411    *insn_default_length         This is the length of the insn to be returned
2412                                 by `get_attr_length' before `shorten_branches'
2413                                 has been called.  In each case where the length
2414                                 depends on relative addresses, the largest
2415                                 possible is used.  This routine is also used
2416                                 to compute the initial size of the insn.
2417
2418    *insn_variable_length_p      This returns 1 if the insn's length depends
2419                                 on relative addresses, zero otherwise.
2420
2421    *insn_current_length         This is only called when it is known that the
2422                                 insn has a variable length and returns the
2423                                 current length, based on relative addresses.
2424   */
2425
2426 static void
2427 make_length_attrs ()
2428 {
2429   static char *new_names[] = {"*insn_default_length",
2430                               "*insn_variable_length_p",
2431                               "*insn_current_length"};
2432   static rtx (*no_address_fn[]) PROTO((rtx)) = {identity_fn, zero_fn, zero_fn};
2433   static rtx (*address_fn[]) PROTO((rtx)) = {max_fn, one_fn, identity_fn};
2434   int i;
2435   struct attr_desc *length_attr, *new_attr;
2436   struct attr_value *av, *new_av;
2437   struct insn_ent *ie, *new_ie;
2438
2439   /* See if length attribute is defined.  If so, it must be numeric.  Make
2440      it special so we don't output anything for it.  */
2441   length_attr = find_attr ("length", 0);
2442   if (length_attr == 0)
2443     return;
2444
2445   if (! length_attr->is_numeric)
2446     fatal ("length attribute must be numeric.");
2447
2448   length_attr->is_const = 0;
2449   length_attr->is_special = 1;
2450
2451   /* Make each new attribute, in turn.  */
2452   for (i = 0; i < sizeof new_names / sizeof new_names[0]; i++)
2453     {
2454       make_internal_attr (new_names[i],
2455                           substitute_address (length_attr->default_val->value,
2456                                               no_address_fn[i], address_fn[i]),
2457                           0);
2458       new_attr = find_attr (new_names[i], 0);
2459       for (av = length_attr->first_value; av; av = av->next)
2460         for (ie = av->first_insn; ie; ie = ie->next)
2461           {
2462             new_av = get_attr_value (substitute_address (av->value,
2463                                                          no_address_fn[i],
2464                                                          address_fn[i]),
2465                                      new_attr, ie->insn_code);
2466             new_ie = (struct insn_ent *) oballoc (sizeof (struct insn_ent));
2467             new_ie->insn_code = ie->insn_code;
2468             new_ie->insn_index = ie->insn_index;
2469             insert_insn_ent (new_av, new_ie);
2470           }
2471     }
2472 }
2473
2474 /* Utility functions called from above routine.  */
2475
2476 static rtx
2477 identity_fn (exp)
2478      rtx exp;
2479 {
2480   return exp;
2481 }
2482
2483 static rtx
2484 zero_fn (exp)
2485      rtx exp;
2486 {
2487   return make_numeric_value (0);
2488 }
2489
2490 static rtx
2491 one_fn (exp)
2492      rtx exp;
2493 {
2494   return make_numeric_value (1);
2495 }
2496
2497 static rtx
2498 max_fn (exp)
2499      rtx exp;
2500 {
2501   return make_numeric_value (max_attr_value (exp));
2502 }
2503 \f
2504 /* Take a COND expression and see if any of the conditions in it can be
2505    simplified.  If any are known true or known false for the particular insn
2506    code, the COND can be further simplified.
2507
2508    Also call ourselves on any COND operations that are values of this COND.
2509
2510    We do not modify EXP; rather, we make and return a new rtx.  */
2511
2512 static rtx
2513 simplify_cond (exp, insn_code, insn_index)
2514      rtx exp;
2515      int insn_code, insn_index;
2516 {
2517   int i, j;
2518   /* We store the desired contents here,
2519      then build a new expression if they don't match EXP.  */
2520   rtx defval = XEXP (exp, 1);
2521   rtx new_defval = XEXP (exp, 1);
2522   int len = XVECLEN (exp, 0);
2523   rtunion *tests = (rtunion *) alloca (len * sizeof (rtunion));
2524   int allsame = 1;
2525   char *first_spacer;
2526
2527   /* This lets us free all storage allocated below, if appropriate.  */
2528   first_spacer = (char *) obstack_finish (rtl_obstack);
2529
2530   bcopy ((char *) XVEC (exp, 0)->elem, (char *) tests, len * sizeof (rtunion));
2531
2532   /* See if default value needs simplification.  */
2533   if (GET_CODE (defval) == COND)
2534     new_defval = simplify_cond (defval, insn_code, insn_index);
2535
2536   /* Simplify the subexpressions, and see what tests we can get rid of.  */
2537
2538   for (i = 0; i < len; i += 2)
2539     {
2540       rtx newtest, newval;
2541
2542       /* Simplify this test.  */
2543       newtest = SIMPLIFY_TEST_EXP (tests[i].rtx, insn_code, insn_index);
2544       tests[i].rtx = newtest;
2545
2546       newval = tests[i + 1].rtx;
2547       /* See if this value may need simplification.  */
2548       if (GET_CODE (newval) == COND)
2549         newval = simplify_cond (newval, insn_code, insn_index);
2550
2551       /* Look for ways to delete or combine this test.  */
2552       if (newtest == true_rtx)
2553         {
2554           /* If test is true, make this value the default
2555              and discard this + any following tests.  */
2556           len = i;
2557           defval = tests[i + 1].rtx;
2558           new_defval = newval;
2559         }
2560
2561       else if (newtest == false_rtx)
2562         {
2563           /* If test is false, discard it and its value.  */
2564           for (j = i; j < len - 2; j++)
2565             tests[j].rtx = tests[j + 2].rtx;
2566           len -= 2;
2567         }
2568
2569       else if (i > 0 && attr_equal_p (newval, tests[i - 1].rtx))
2570         {
2571           /* If this value and the value for the prev test are the same,
2572              merge the tests.  */
2573
2574           tests[i - 2].rtx
2575             = insert_right_side (IOR, tests[i - 2].rtx, newtest,
2576                                  insn_code, insn_index);
2577
2578           /* Delete this test/value.  */
2579           for (j = i; j < len - 2; j++)
2580             tests[j].rtx = tests[j + 2].rtx;
2581           len -= 2;
2582         }
2583
2584       else
2585         tests[i + 1].rtx = newval;
2586     }
2587
2588   /* If the last test in a COND has the same value
2589      as the default value, that test isn't needed.  */
2590
2591   while (len > 0 && attr_equal_p (tests[len - 1].rtx, new_defval))
2592     len -= 2;
2593
2594   /* See if we changed anything.  */
2595   if (len != XVECLEN (exp, 0) || new_defval != XEXP (exp, 1))
2596     allsame = 0;
2597   else
2598     for (i = 0; i < len; i++)
2599       if (! attr_equal_p (tests[i].rtx, XVECEXP (exp, 0, i)))
2600         {
2601           allsame = 0;
2602           break;
2603         }
2604
2605   if (len == 0)
2606     {
2607       obstack_free (rtl_obstack, first_spacer);
2608       if (GET_CODE (defval) == COND)
2609         return simplify_cond (defval, insn_code, insn_index);
2610       return defval;
2611     }
2612   else if (allsame)
2613     {
2614       obstack_free (rtl_obstack, first_spacer);
2615       return exp;
2616     }
2617   else
2618     {
2619       rtx newexp = rtx_alloc (COND);
2620
2621       XVEC (newexp, 0) = rtvec_alloc (len);
2622       bcopy ((char *) tests, (char *) XVEC (newexp, 0)->elem,
2623              len * sizeof (rtunion));
2624       XEXP (newexp, 1) = new_defval;
2625       return newexp;
2626     }
2627 }
2628 \f
2629 /* Remove an insn entry from an attribute value.  */
2630
2631 static void
2632 remove_insn_ent (av, ie)
2633      struct attr_value *av;
2634      struct insn_ent *ie;
2635 {
2636   struct insn_ent *previe;
2637
2638   if (av->first_insn == ie)
2639     av->first_insn = ie->next;
2640   else
2641     {
2642       for (previe = av->first_insn; previe->next != ie; previe = previe->next)
2643         ;
2644       previe->next = ie->next;
2645     }
2646
2647   av->num_insns--;
2648   if (ie->insn_code == -1)
2649     av->has_asm_insn = 0;
2650
2651   num_insn_ents--;
2652 }
2653
2654 /* Insert an insn entry in an attribute value list.  */
2655
2656 static void
2657 insert_insn_ent (av, ie)
2658      struct attr_value *av;
2659      struct insn_ent *ie;
2660 {
2661   ie->next = av->first_insn;
2662   av->first_insn = ie;
2663   av->num_insns++;
2664   if (ie->insn_code == -1)
2665     av->has_asm_insn = 1;
2666
2667   num_insn_ents++;
2668 }
2669 \f
2670 /* This is a utility routine to take an expression that is a tree of either
2671    AND or IOR expressions and insert a new term.  The new term will be
2672    inserted at the right side of the first node whose code does not match
2673    the root.  A new node will be created with the root's code.  Its left
2674    side will be the old right side and its right side will be the new
2675    term.
2676
2677    If the `term' is itself a tree, all its leaves will be inserted.  */
2678
2679 static rtx
2680 insert_right_side (code, exp, term, insn_code, insn_index)
2681      enum rtx_code code;
2682      rtx exp;
2683      rtx term;
2684      int insn_code, insn_index;
2685 {
2686   rtx newexp;
2687
2688   /* Avoid consing in some special cases.  */
2689   if (code == AND && term == true_rtx)
2690     return exp;
2691   if (code == AND && term == false_rtx)
2692     return false_rtx;
2693   if (code == AND && exp == true_rtx)
2694     return term;
2695   if (code == AND && exp == false_rtx)
2696     return false_rtx;
2697   if (code == IOR && term == true_rtx)
2698     return true_rtx;
2699   if (code == IOR && term == false_rtx)
2700     return exp;
2701   if (code == IOR && exp == true_rtx)
2702     return true_rtx;
2703   if (code == IOR && exp == false_rtx)
2704     return term;
2705   if (attr_equal_p (exp, term))
2706     return exp;
2707
2708   if (GET_CODE (term) == code)
2709     {
2710       exp = insert_right_side (code, exp, XEXP (term, 0),
2711                                insn_code, insn_index);
2712       exp = insert_right_side (code, exp, XEXP (term, 1),
2713                                insn_code, insn_index);
2714
2715       return exp;
2716     }
2717
2718   if (GET_CODE (exp) == code)
2719     {
2720       rtx new = insert_right_side (code, XEXP (exp, 1),
2721                                    term, insn_code, insn_index);
2722       if (new != XEXP (exp, 1))
2723         /* Make a copy of this expression and call recursively.  */
2724         newexp = attr_rtx (code, XEXP (exp, 0), new);
2725       else
2726         newexp = exp;
2727     }
2728   else
2729     {
2730       /* Insert the new term.  */
2731       newexp = attr_rtx (code, exp, term);
2732     }
2733
2734   return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
2735 }
2736 \f
2737 /* If we have an expression which AND's a bunch of
2738         (not (eq_attrq "alternative" "n"))
2739    terms, we may have covered all or all but one of the possible alternatives.
2740    If so, we can optimize.  Similarly for IOR's of EQ_ATTR.
2741
2742    This routine is passed an expression and either AND or IOR.  It returns a
2743    bitmask indicating which alternatives are mentioned within EXP.  */
2744
2745 static int
2746 compute_alternative_mask (exp, code)
2747      rtx exp;
2748      enum rtx_code code;
2749 {
2750   char *string;
2751   if (GET_CODE (exp) == code)
2752     return compute_alternative_mask (XEXP (exp, 0), code)
2753            | compute_alternative_mask (XEXP (exp, 1), code);
2754
2755   else if (code == AND && GET_CODE (exp) == NOT
2756            && GET_CODE (XEXP (exp, 0)) == EQ_ATTR
2757            && XSTR (XEXP (exp, 0), 0) == alternative_name)
2758     string = XSTR (XEXP (exp, 0), 1);
2759
2760   else if (code == IOR && GET_CODE (exp) == EQ_ATTR
2761            && XSTR (exp, 0) == alternative_name)
2762     string = XSTR (exp, 1);
2763
2764   else
2765     return 0;
2766
2767   if (string[1] == 0)
2768     return 1 << (string[0] - '0');
2769   return 1 << atoi (string);
2770 }
2771
2772 /* Given I, a single-bit mask, return RTX to compare the `alternative'
2773    attribute with the value represented by that bit.  */
2774
2775 static rtx
2776 make_alternative_compare (mask)
2777      int mask;
2778 {
2779   rtx newexp;
2780   int i;
2781
2782   /* Find the bit.  */
2783   for (i = 0; (mask & (1 << i)) == 0; i++)
2784     ;
2785
2786   newexp = attr_rtx (EQ_ATTR, alternative_name, attr_numeral (i));
2787   RTX_UNCHANGING_P (newexp) = 1;
2788
2789   return newexp;
2790 }
2791 \f
2792 /* If we are processing an (eq_attr "attr" "value") test, we find the value
2793    of "attr" for this insn code.  From that value, we can compute a test
2794    showing when the EQ_ATTR will be true.  This routine performs that
2795    computation.  If a test condition involves an address, we leave the EQ_ATTR
2796    intact because addresses are only valid for the `length' attribute. 
2797
2798    EXP is the EQ_ATTR expression and VALUE is the value of that attribute
2799    for the insn corresponding to INSN_CODE and INSN_INDEX.  */
2800
2801 static rtx
2802 evaluate_eq_attr (exp, value, insn_code, insn_index)
2803      rtx exp;
2804      rtx value;
2805      int insn_code, insn_index;
2806 {
2807   rtx orexp, andexp;
2808   rtx right;
2809   rtx newexp;
2810   int i;
2811
2812   if (GET_CODE (value) == CONST_STRING)
2813     {
2814       if (! strcmp (XSTR (value, 0), XSTR (exp, 1)))
2815         newexp = true_rtx;
2816       else
2817         newexp = false_rtx;
2818     }
2819   else if (GET_CODE (value) == SYMBOL_REF)
2820     {
2821       char *p, *string;
2822
2823       if (GET_CODE (exp) != EQ_ATTR)
2824         abort();
2825
2826       string = (char *) alloca (2 + strlen (XSTR (exp, 0))
2827                                 + strlen (XSTR (exp, 1)));
2828       strcpy (string, XSTR (exp, 0));
2829       strcat (string, "_");
2830       strcat (string, XSTR (exp, 1));
2831       for (p = string; *p ; p++)
2832         if (*p >= 'a' && *p <= 'z')
2833           *p -= 'a' - 'A';
2834       
2835       newexp = attr_rtx (EQ, value,
2836                          attr_rtx (SYMBOL_REF,
2837                                    attr_string(string, strlen(string))));
2838     }
2839   else if (GET_CODE (value) == COND)
2840     {
2841       /* We construct an IOR of all the cases for which the requested attribute
2842          value is present.  Since we start with FALSE, if it is not present,
2843          FALSE will be returned.
2844
2845          Each case is the AND of the NOT's of the previous conditions with the
2846          current condition; in the default case the current condition is TRUE. 
2847
2848          For each possible COND value, call ourselves recursively.
2849
2850          The extra TRUE and FALSE expressions will be eliminated by another
2851          call to the simplification routine.  */
2852
2853       orexp = false_rtx;
2854       andexp = true_rtx;
2855
2856       if (current_alternative_string)
2857         clear_struct_flag (value);
2858
2859       for (i = 0; i < XVECLEN (value, 0); i += 2)
2860         {
2861           rtx this = SIMPLIFY_TEST_EXP (XVECEXP (value, 0, i),
2862                                         insn_code, insn_index);
2863
2864           SIMPLIFY_ALTERNATIVE (this);
2865
2866           right = insert_right_side (AND, andexp, this,
2867                                      insn_code, insn_index);
2868           right = insert_right_side (AND, right,
2869                                      evaluate_eq_attr (exp,
2870                                                        XVECEXP (value, 0,
2871                                                                 i + 1),
2872                                                        insn_code, insn_index),
2873                                      insn_code, insn_index);
2874           orexp = insert_right_side (IOR, orexp, right,
2875                                      insn_code, insn_index);
2876
2877           /* Add this condition into the AND expression.  */
2878           newexp = attr_rtx (NOT, this);
2879           andexp = insert_right_side (AND, andexp, newexp,
2880                                       insn_code, insn_index);
2881         }
2882
2883       /* Handle the default case.  */
2884       right = insert_right_side (AND, andexp,
2885                                  evaluate_eq_attr (exp, XEXP (value, 1),
2886                                                    insn_code, insn_index),
2887                                  insn_code, insn_index);
2888       newexp = insert_right_side (IOR, orexp, right, insn_code, insn_index);
2889     }
2890   else
2891     abort ();
2892
2893   /* If uses an address, must return original expression.  But set the
2894      RTX_UNCHANGING_P bit so we don't try to simplify it again.  */
2895
2896   address_used = 0;
2897   walk_attr_value (newexp);
2898
2899   if (address_used)
2900     {
2901       /* This had `&& current_alternative_string', which seems to be wrong.  */
2902       if (! RTX_UNCHANGING_P (exp))
2903         return copy_rtx_unchanging (exp);
2904       return exp;
2905     }
2906   else
2907     return newexp;
2908 }
2909 \f
2910 /* This routine is called when an AND of a term with a tree of AND's is
2911    encountered.  If the term or its complement is present in the tree, it
2912    can be replaced with TRUE or FALSE, respectively.
2913
2914    Note that (eq_attr "att" "v1") and (eq_attr "att" "v2") cannot both
2915    be true and hence are complementary.  
2916
2917    There is one special case:  If we see
2918         (and (not (eq_attr "att" "v1"))
2919              (eq_attr "att" "v2"))
2920    this can be replaced by (eq_attr "att" "v2").  To do this we need to
2921    replace the term, not anything in the AND tree.  So we pass a pointer to
2922    the term.  */
2923
2924 static rtx
2925 simplify_and_tree (exp, pterm, insn_code, insn_index)
2926      rtx exp;
2927      rtx *pterm;
2928      int insn_code, insn_index;
2929 {
2930   rtx left, right;
2931   rtx newexp;
2932   rtx temp;
2933   int left_eliminates_term, right_eliminates_term;
2934
2935   if (GET_CODE (exp) == AND)
2936     {
2937       left = simplify_and_tree (XEXP (exp, 0), pterm,  insn_code, insn_index);
2938       right = simplify_and_tree (XEXP (exp, 1), pterm, insn_code, insn_index);
2939       if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
2940         {
2941           newexp = attr_rtx (GET_CODE (exp), left, right);
2942
2943           exp = SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
2944         }
2945     }
2946
2947   else if (GET_CODE (exp) == IOR)
2948     {
2949       /* For the IOR case, we do the same as above, except that we can
2950          only eliminate `term' if both sides of the IOR would do so.  */
2951       temp = *pterm;
2952       left = simplify_and_tree (XEXP (exp, 0), &temp,  insn_code, insn_index);
2953       left_eliminates_term = (temp == true_rtx);
2954
2955       temp = *pterm;
2956       right = simplify_and_tree (XEXP (exp, 1), &temp, insn_code, insn_index);
2957       right_eliminates_term = (temp == true_rtx);
2958
2959       if (left_eliminates_term && right_eliminates_term)
2960         *pterm = true_rtx;
2961
2962       if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
2963         {
2964           newexp = attr_rtx (GET_CODE (exp), left, right);
2965
2966           exp = SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
2967         }
2968     }
2969
2970   /* Check for simplifications.  Do some extra checking here since this
2971      routine is called so many times.  */
2972
2973   if (exp == *pterm)
2974     return true_rtx;
2975
2976   else if (GET_CODE (exp) == NOT && XEXP (exp, 0) == *pterm)
2977     return false_rtx;
2978
2979   else if (GET_CODE (*pterm) == NOT && exp == XEXP (*pterm, 0))
2980     return false_rtx;
2981
2982   else if (GET_CODE (exp) == EQ_ATTR && GET_CODE (*pterm) == EQ_ATTR)
2983     {
2984       if (XSTR (exp, 0) != XSTR (*pterm, 0))
2985         return exp;
2986
2987       if (! strcmp (XSTR (exp, 1), XSTR (*pterm, 1)))
2988         return true_rtx;
2989       else
2990         return false_rtx;
2991     }
2992
2993   else if (GET_CODE (*pterm) == EQ_ATTR && GET_CODE (exp) == NOT
2994            && GET_CODE (XEXP (exp, 0)) == EQ_ATTR)
2995     {
2996       if (XSTR (*pterm, 0) != XSTR (XEXP (exp, 0), 0))
2997         return exp;
2998
2999       if (! strcmp (XSTR (*pterm, 1), XSTR (XEXP (exp, 0), 1)))
3000         return false_rtx;
3001       else
3002         return true_rtx;
3003     }
3004
3005   else if (GET_CODE (exp) == EQ_ATTR && GET_CODE (*pterm) == NOT
3006            && GET_CODE (XEXP (*pterm, 0)) == EQ_ATTR)
3007     {
3008       if (XSTR (exp, 0) != XSTR (XEXP (*pterm, 0), 0))
3009         return exp;
3010
3011       if (! strcmp (XSTR (exp, 1), XSTR (XEXP (*pterm, 0), 1)))
3012         return false_rtx;
3013       else
3014         *pterm = true_rtx;
3015     }
3016
3017   else if (GET_CODE (exp) == NOT && GET_CODE (*pterm) == NOT)
3018     {
3019       if (attr_equal_p (XEXP (exp, 0), XEXP (*pterm, 0)))
3020         return true_rtx;
3021     }
3022
3023   else if (GET_CODE (exp) == NOT)
3024     {
3025       if (attr_equal_p (XEXP (exp, 0), *pterm))
3026         return false_rtx;
3027     }
3028
3029   else if (GET_CODE (*pterm) == NOT)
3030     {
3031       if (attr_equal_p (XEXP (*pterm, 0), exp))
3032         return false_rtx;
3033     }
3034
3035   else if (attr_equal_p (exp, *pterm))
3036     return true_rtx;
3037
3038   return exp;
3039 }
3040 \f
3041 /* Similar to `simplify_and_tree', but for IOR trees.  */
3042
3043 static rtx
3044 simplify_or_tree (exp, pterm, insn_code, insn_index)
3045      rtx exp;
3046      rtx *pterm;
3047      int insn_code, insn_index;
3048 {
3049   rtx left, right;
3050   rtx newexp;
3051   rtx temp;
3052   int left_eliminates_term, right_eliminates_term;
3053
3054   if (GET_CODE (exp) == IOR)
3055     {
3056       left = simplify_or_tree (XEXP (exp, 0), pterm,  insn_code, insn_index);
3057       right = simplify_or_tree (XEXP (exp, 1), pterm, insn_code, insn_index);
3058       if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
3059         {
3060           newexp = attr_rtx (GET_CODE (exp), left, right);
3061
3062           exp = SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
3063         }
3064     }
3065
3066   else if (GET_CODE (exp) == AND)
3067     {
3068       /* For the AND case, we do the same as above, except that we can
3069          only eliminate `term' if both sides of the AND would do so.  */
3070       temp = *pterm;
3071       left = simplify_or_tree (XEXP (exp, 0), &temp,  insn_code, insn_index);
3072       left_eliminates_term = (temp == false_rtx);
3073
3074       temp = *pterm;
3075       right = simplify_or_tree (XEXP (exp, 1), &temp, insn_code, insn_index);
3076       right_eliminates_term = (temp == false_rtx);
3077
3078       if (left_eliminates_term && right_eliminates_term)
3079         *pterm = false_rtx;
3080
3081       if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
3082         {
3083           newexp = attr_rtx (GET_CODE (exp), left, right);
3084
3085           exp = SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
3086         }
3087     }
3088
3089   if (attr_equal_p (exp, *pterm))
3090     return false_rtx;
3091
3092   else if (GET_CODE (exp) == NOT && attr_equal_p (XEXP (exp, 0), *pterm))
3093     return true_rtx;
3094
3095   else if (GET_CODE (*pterm) == NOT && attr_equal_p (XEXP (*pterm, 0), exp))
3096     return true_rtx;
3097
3098   else if (GET_CODE (*pterm) == EQ_ATTR && GET_CODE (exp) == NOT
3099            && GET_CODE (XEXP (exp, 0)) == EQ_ATTR
3100            && XSTR (*pterm, 0) == XSTR (XEXP (exp, 0), 0))
3101     *pterm = false_rtx;
3102
3103   else if (GET_CODE (exp) == EQ_ATTR && GET_CODE (*pterm) == NOT
3104            && GET_CODE (XEXP (*pterm, 0)) == EQ_ATTR
3105            && XSTR (exp, 0) == XSTR (XEXP (*pterm, 0), 0))
3106     return false_rtx;
3107
3108   return exp;
3109 }
3110 \f
3111 /* Given an expression, see if it can be simplified for a particular insn
3112    code based on the values of other attributes being tested.  This can
3113    eliminate nested get_attr_... calls.
3114
3115    Note that if an endless recursion is specified in the patterns, the 
3116    optimization will loop.  However, it will do so in precisely the cases where
3117    an infinite recursion loop could occur during compilation.  It's better that
3118    it occurs here!  */
3119
3120 static rtx
3121 simplify_test_exp (exp, insn_code, insn_index)
3122      rtx exp;
3123      int insn_code, insn_index;
3124 {
3125   rtx left, right;
3126   struct attr_desc *attr;
3127   struct attr_value *av;
3128   struct insn_ent *ie;
3129   int i;
3130   rtx newexp = exp;
3131   char *spacer = (char *) obstack_finish (rtl_obstack);
3132
3133   /* Don't re-simplify something we already simplified.  */
3134   if (RTX_UNCHANGING_P (exp) || MEM_IN_STRUCT_P (exp))
3135     return exp;
3136
3137   switch (GET_CODE (exp))
3138     {
3139     case AND:
3140       left = SIMPLIFY_TEST_EXP (XEXP (exp, 0), insn_code, insn_index);
3141       SIMPLIFY_ALTERNATIVE (left);
3142       if (left == false_rtx)
3143         {
3144           obstack_free (rtl_obstack, spacer);
3145           return false_rtx;
3146         }
3147       right = SIMPLIFY_TEST_EXP (XEXP (exp, 1), insn_code, insn_index);
3148       SIMPLIFY_ALTERNATIVE (right);
3149       if (left == false_rtx)
3150         {
3151           obstack_free (rtl_obstack, spacer);
3152           return false_rtx;
3153         }
3154
3155       /* If either side is an IOR and we have (eq_attr "alternative" ..")
3156          present on both sides, apply the distributive law since this will
3157          yield simplifications.  */
3158       if ((GET_CODE (left) == IOR || GET_CODE (right) == IOR)
3159           && compute_alternative_mask (left, IOR)
3160           && compute_alternative_mask (right, IOR))
3161         {
3162           if (GET_CODE (left) == IOR)
3163             {
3164               rtx tem = left;
3165               left = right;
3166               right = tem;
3167             }
3168
3169           newexp = attr_rtx (IOR,
3170                              attr_rtx (AND, left, XEXP (right, 0)),
3171                              attr_rtx (AND, left, XEXP (right, 1)));
3172
3173           return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
3174         }
3175
3176       /* Try with the term on both sides.  */
3177       right = simplify_and_tree (right, &left, insn_code, insn_index);
3178       if (left == XEXP (exp, 0) && right == XEXP (exp, 1))
3179         left = simplify_and_tree (left, &right, insn_code, insn_index);
3180
3181       if (left == false_rtx || right == false_rtx)
3182         {
3183           obstack_free (rtl_obstack, spacer);
3184           return false_rtx;
3185         }
3186       else if (left == true_rtx)
3187         {
3188           return right;
3189         }
3190       else if (right == true_rtx)
3191         {
3192           return left;
3193         }
3194       /* See if all or all but one of the insn's alternatives are specified
3195          in this tree.  Optimize if so.  */
3196
3197       else if (insn_code >= 0
3198                && (GET_CODE (left) == AND
3199                    || (GET_CODE (left) == NOT
3200                        && GET_CODE (XEXP (left, 0)) == EQ_ATTR
3201                        && XSTR (XEXP (left, 0), 0) == alternative_name)
3202                    || GET_CODE (right) == AND
3203                    || (GET_CODE (right) == NOT
3204                        && GET_CODE (XEXP (right, 0)) == EQ_ATTR
3205                        && XSTR (XEXP (right, 0), 0) == alternative_name)))
3206         {
3207           i = compute_alternative_mask (exp, AND);
3208           if (i & ~insn_alternatives[insn_code])
3209             fatal ("Invalid alternative specified for pattern number %d",
3210                    insn_index);
3211
3212           /* If all alternatives are excluded, this is false.  */
3213           i ^= insn_alternatives[insn_code];
3214           if (i == 0)
3215             return false_rtx;
3216           else if ((i & (i - 1)) == 0 && insn_alternatives[insn_code] > 1)
3217             {
3218               /* If just one excluded, AND a comparison with that one to the
3219                  front of the tree.  The others will be eliminated by
3220                  optimization.  We do not want to do this if the insn has one
3221                  alternative and we have tested none of them!  */
3222               left = make_alternative_compare (i);
3223               right = simplify_and_tree (exp, &left, insn_code, insn_index);
3224               newexp = attr_rtx (AND, left, right);
3225
3226               return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
3227             }
3228         }
3229
3230       if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
3231         {
3232           newexp = attr_rtx (AND, left, right);
3233           return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
3234         }
3235       break;
3236
3237     case IOR:
3238       left = SIMPLIFY_TEST_EXP (XEXP (exp, 0), insn_code, insn_index);
3239       SIMPLIFY_ALTERNATIVE (left);
3240       if (left == true_rtx)
3241         {
3242           obstack_free (rtl_obstack, spacer);
3243           return true_rtx;
3244         }
3245       right = SIMPLIFY_TEST_EXP (XEXP (exp, 1), insn_code, insn_index);
3246       SIMPLIFY_ALTERNATIVE (right);
3247       if (right == true_rtx)
3248         {
3249           obstack_free (rtl_obstack, spacer);
3250           return true_rtx;
3251         }
3252
3253       right = simplify_or_tree (right, &left, insn_code, insn_index);
3254       if (left == XEXP (exp, 0) && right == XEXP (exp, 1))
3255         left = simplify_or_tree (left, &right, insn_code, insn_index);
3256
3257       if (right == true_rtx || left == true_rtx)
3258         {
3259           obstack_free (rtl_obstack, spacer);
3260           return true_rtx;
3261         }
3262       else if (left == false_rtx)
3263         {
3264           return right;
3265         }
3266       else if (right == false_rtx)
3267         {
3268           return left;
3269         }
3270
3271       /* Test for simple cases where the distributive law is useful.  I.e.,
3272             convert (ior (and (x) (y))
3273                          (and (x) (z)))
3274             to      (and (x)
3275                          (ior (y) (z)))
3276        */
3277
3278       else if (GET_CODE (left) == AND && GET_CODE (right) == AND
3279           && attr_equal_p (XEXP (left, 0), XEXP (right, 0)))
3280         {
3281           newexp = attr_rtx (IOR, XEXP (left, 1), XEXP (right, 1));
3282
3283           left = XEXP (left, 0);
3284           right = newexp;
3285           newexp = attr_rtx (AND, left, right);
3286           return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
3287         }
3288
3289       /* See if all or all but one of the insn's alternatives are specified
3290          in this tree.  Optimize if so.  */
3291
3292       else if (insn_code >= 0
3293           && (GET_CODE (left) == IOR
3294               || (GET_CODE (left) == EQ_ATTR
3295                   && XSTR (left, 0) == alternative_name)
3296               || GET_CODE (right) == IOR
3297               || (GET_CODE (right) == EQ_ATTR
3298                   && XSTR (right, 0) == alternative_name)))
3299         {
3300           i = compute_alternative_mask (exp, IOR);
3301           if (i & ~insn_alternatives[insn_code])
3302             fatal ("Invalid alternative specified for pattern number %d",
3303                    insn_index);
3304
3305           /* If all alternatives are included, this is true.  */
3306           i ^= insn_alternatives[insn_code];
3307           if (i == 0)
3308             return true_rtx;
3309           else if ((i & (i - 1)) == 0 && insn_alternatives[insn_code] > 1)
3310             {
3311               /* If just one excluded, IOR a comparison with that one to the
3312                  front of the tree.  The others will be eliminated by
3313                  optimization.  We do not want to do this if the insn has one
3314                  alternative and we have tested none of them!  */
3315               left = make_alternative_compare (i);
3316               right = simplify_and_tree (exp, &left, insn_code, insn_index);
3317               newexp = attr_rtx (IOR, attr_rtx (NOT, left), right);
3318
3319               return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
3320             }
3321         }
3322
3323       if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
3324         {
3325           newexp = attr_rtx (IOR, left, right);
3326           return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
3327         }
3328       break;
3329
3330     case NOT:
3331       if (GET_CODE (XEXP (exp, 0)) == NOT)
3332         {
3333           left = SIMPLIFY_TEST_EXP (XEXP (XEXP (exp, 0), 0),
3334                                     insn_code, insn_index);
3335           SIMPLIFY_ALTERNATIVE (left);
3336           return left;
3337         }
3338
3339       left = SIMPLIFY_TEST_EXP (XEXP (exp, 0), insn_code, insn_index);
3340       SIMPLIFY_ALTERNATIVE (left);
3341       if (GET_CODE (left) == NOT)
3342         return XEXP (left, 0);
3343
3344       if (left == false_rtx)
3345         {
3346           obstack_free (rtl_obstack, spacer);
3347           return true_rtx;
3348         }
3349       else if (left == true_rtx)
3350         {
3351           obstack_free (rtl_obstack, spacer);
3352           return false_rtx;
3353         }
3354
3355       /* Try to apply De`Morgan's laws.  */
3356       else if (GET_CODE (left) == IOR)
3357         {
3358           newexp = attr_rtx (AND,
3359                              attr_rtx (NOT, XEXP (left, 0)),
3360                              attr_rtx (NOT, XEXP (left, 1)));
3361
3362           newexp = SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
3363         }
3364       else if (GET_CODE (left) == AND)
3365         {
3366           newexp = attr_rtx (IOR,
3367                              attr_rtx (NOT, XEXP (left, 0)),
3368                              attr_rtx (NOT, XEXP (left, 1)));
3369
3370           newexp = SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
3371         }
3372       else if (left != XEXP (exp, 0))
3373         {
3374           newexp = attr_rtx (NOT, left);
3375         }
3376       break;
3377
3378     case EQ_ATTR:
3379       if (current_alternative_string && XSTR (exp, 0) == alternative_name)
3380         return (XSTR (exp, 1) == current_alternative_string
3381                 ? true_rtx : false_rtx);
3382         
3383       /* Look at the value for this insn code in the specified attribute.
3384          We normally can replace this comparison with the condition that
3385          would give this insn the values being tested for.   */
3386       if (XSTR (exp, 0) != alternative_name
3387           && (attr = find_attr (XSTR (exp, 0), 0)) != NULL)
3388         for (av = attr->first_value; av; av = av->next)
3389           for (ie = av->first_insn; ie; ie = ie->next)
3390             if (ie->insn_code == insn_code)
3391               return evaluate_eq_attr (exp, av->value, insn_code, insn_index);
3392       break;
3393       
3394     default:
3395       break;
3396     }
3397
3398   /* We have already simplified this expression.  Simplifying it again
3399      won't buy anything unless we weren't given a valid insn code
3400      to process (i.e., we are canonicalizing something.).  */
3401   if (insn_code != -2 /* Seems wrong: && current_alternative_string.  */
3402       && ! RTX_UNCHANGING_P (newexp))
3403     return copy_rtx_unchanging (newexp);
3404
3405   return newexp;
3406 }
3407 \f
3408 /* Optimize the attribute lists by seeing if we can determine conditional
3409    values from the known values of other attributes.  This will save subroutine
3410    calls during the compilation.  */
3411
3412 static void
3413 optimize_attrs ()
3414 {
3415   struct attr_desc *attr;
3416   struct attr_value *av;
3417   struct insn_ent *ie;
3418   rtx newexp;
3419   int something_changed = 1;
3420   int i;
3421   struct attr_value_list { struct attr_value *av;
3422                            struct insn_ent *ie;
3423                            struct attr_desc * attr;
3424                            struct attr_value_list *next; };
3425   struct attr_value_list **insn_code_values;
3426   struct attr_value_list *ivbuf;
3427   struct attr_value_list *iv;
3428
3429   /* For each insn code, make a list of all the insn_ent's for it,
3430      for all values for all attributes.  */
3431
3432   if (num_insn_ents == 0)
3433     return;
3434
3435   /* Make 2 extra elements, for "code" values -2 and -1.  */
3436   insn_code_values
3437     = (struct attr_value_list **) alloca ((insn_code_number + 2)
3438                                           * sizeof (struct attr_value_list *));
3439   bzero ((char *) insn_code_values,
3440          (insn_code_number + 2) * sizeof (struct attr_value_list *));
3441
3442   /* Offset the table address so we can index by -2 or -1.  */
3443   insn_code_values += 2;
3444
3445   /* Allocate the attr_value_list structures using xmalloc rather than
3446      alloca, because using alloca can overflow the maximum permitted
3447      stack limit on SPARC Lynx.  */
3448   iv = ivbuf = ((struct attr_value_list *)
3449                 xmalloc (num_insn_ents * sizeof (struct attr_value_list)));
3450
3451   for (i = 0; i < MAX_ATTRS_INDEX; i++)
3452     for (attr = attrs[i]; attr; attr = attr->next)
3453       for (av = attr->first_value; av; av = av->next)
3454         for (ie = av->first_insn; ie; ie = ie->next)
3455           {
3456             iv->attr = attr;
3457             iv->av = av;
3458             iv->ie = ie;
3459             iv->next = insn_code_values[ie->insn_code];
3460             insn_code_values[ie->insn_code] = iv;
3461             iv++;
3462           }
3463
3464   /* Sanity check on num_insn_ents.  */
3465   if (iv != ivbuf + num_insn_ents)
3466     abort ();
3467
3468   /* Process one insn code at a time.  */
3469   for (i = -2; i < insn_code_number; i++)
3470     {
3471       /* Clear the MEM_IN_STRUCT_P flag everywhere relevant.
3472          We use it to mean "already simplified for this insn".  */
3473       for (iv = insn_code_values[i]; iv; iv = iv->next)
3474         clear_struct_flag (iv->av->value);
3475
3476       /* Loop until nothing changes for one iteration.  */
3477       something_changed = 1;
3478       while (something_changed)
3479         {
3480           something_changed = 0;
3481           for (iv = insn_code_values[i]; iv; iv = iv->next)
3482             {
3483               struct obstack *old = rtl_obstack;
3484               char *spacer = (char *) obstack_finish (temp_obstack);
3485
3486               attr = iv->attr;
3487               av = iv->av;
3488               ie = iv->ie;
3489               if (GET_CODE (av->value) != COND)
3490                 continue;
3491
3492               rtl_obstack = temp_obstack;
3493 #if 0 /* This was intended as a speed up, but it was slower.  */
3494               if (insn_n_alternatives[ie->insn_code] > 6
3495                   && count_sub_rtxs (av->value, 200) >= 200)
3496                 newexp = simplify_by_alternatives (av->value, ie->insn_code,
3497                                                    ie->insn_index);
3498               else
3499 #endif
3500                 newexp = simplify_cond (av->value, ie->insn_code,
3501                                         ie->insn_index);
3502
3503               rtl_obstack = old;
3504               if (newexp != av->value)
3505                 {
3506                   newexp = attr_copy_rtx (newexp);
3507                   remove_insn_ent (av, ie);
3508                   av = get_attr_value (newexp, attr, ie->insn_code);
3509                   iv->av = av;
3510                   insert_insn_ent (av, ie);
3511                   something_changed = 1;
3512                 }
3513               obstack_free (temp_obstack, spacer);
3514             }
3515         }
3516     }
3517
3518   free (ivbuf);
3519 }
3520
3521 #if 0
3522 static rtx
3523 simplify_by_alternatives (exp, insn_code, insn_index)
3524      rtx exp;
3525      int insn_code, insn_index;
3526 {
3527   int i;
3528   int len = insn_n_alternatives[insn_code];
3529   rtx newexp = rtx_alloc (COND);
3530   rtx ultimate;
3531
3532
3533   XVEC (newexp, 0) = rtvec_alloc (len * 2);
3534
3535   /* It will not matter what value we use as the default value
3536      of the new COND, since that default will never be used.
3537      Choose something of the right type.  */
3538   for (ultimate = exp; GET_CODE (ultimate) == COND;)
3539     ultimate = XEXP (ultimate, 1);
3540   XEXP (newexp, 1) = ultimate;
3541
3542   for (i = 0; i < insn_n_alternatives[insn_code]; i++)
3543     {
3544       current_alternative_string = attr_numeral (i);
3545       XVECEXP (newexp, 0, i * 2) = make_alternative_compare (1 << i);
3546       XVECEXP (newexp, 0, i * 2 + 1)
3547         = simplify_cond (exp, insn_code, insn_index);
3548     }
3549
3550   current_alternative_string = 0;
3551   return simplify_cond (newexp, insn_code, insn_index);
3552 }
3553 #endif
3554 \f
3555 /* If EXP is a suitable expression, reorganize it by constructing an
3556    equivalent expression that is a COND with the tests being all combinations
3557    of attribute values and the values being simple constants.  */
3558
3559 static rtx
3560 simplify_by_exploding (exp)
3561      rtx exp;
3562 {
3563   rtx list = 0, link, condexp, defval;
3564   struct dimension *space;
3565   rtx *condtest, *condval;
3566   int i, j, total, ndim = 0;
3567   int most_tests, num_marks, new_marks;
3568
3569   /* Locate all the EQ_ATTR expressions.  */
3570   if (! find_and_mark_used_attributes (exp, &list, &ndim) || ndim == 0)
3571     {
3572       unmark_used_attributes (list, 0, 0);
3573       return exp;
3574     }
3575
3576   /* Create an attribute space from the list of used attributes.  For each
3577      dimension in the attribute space, record the attribute, list of values
3578      used, and number of values used.  Add members to the list of values to
3579      cover the domain of the attribute.  This makes the expanded COND form
3580      order independent.  */
3581
3582   space = (struct dimension *) alloca (ndim * sizeof (struct dimension));
3583
3584   total = 1;
3585   for (ndim = 0; list; ndim++)
3586     {
3587       /* Pull the first attribute value from the list and record that
3588          attribute as another dimension in the attribute space.  */
3589       char *name = XSTR (XEXP (list, 0), 0);
3590       rtx *prev;
3591
3592       if ((space[ndim].attr = find_attr (name, 0)) == 0
3593           || space[ndim].attr->is_numeric)
3594         {
3595           unmark_used_attributes (list, space, ndim);
3596           return exp;
3597         }
3598
3599       /* Add all remaining attribute values that refer to this attribute.  */
3600       space[ndim].num_values = 0;
3601       space[ndim].values = 0;
3602       prev = &list;
3603       for (link = list; link; link = *prev)
3604         if (! strcmp (XSTR (XEXP (link, 0), 0), name))
3605           {
3606             space[ndim].num_values++;
3607             *prev = XEXP (link, 1);
3608             XEXP (link, 1) = space[ndim].values;
3609             space[ndim].values = link;
3610           }
3611         else
3612           prev = &XEXP (link, 1);
3613
3614       /* Add sufficient members to the list of values to make the list
3615          mutually exclusive and record the total size of the attribute
3616          space.  */
3617       total *= add_values_to_cover (&space[ndim]);
3618     }
3619
3620   /* Sort the attribute space so that the attributes go from non-constant
3621      to constant and from most values to least values.  */
3622   for (i = 0; i < ndim; i++)
3623     for (j = ndim - 1; j > i; j--)
3624       if ((space[j-1].attr->is_const && !space[j].attr->is_const)
3625           || space[j-1].num_values < space[j].num_values)
3626         {
3627           struct dimension tmp;
3628           tmp = space[j];
3629           space[j] = space[j-1];
3630           space[j-1] = tmp;
3631         }
3632
3633   /* Establish the initial current value.  */
3634   for (i = 0; i < ndim; i++)
3635     space[i].current_value = space[i].values;
3636
3637   condtest = (rtx *) alloca (total * sizeof (rtx));
3638   condval = (rtx *) alloca (total * sizeof (rtx));
3639
3640   /* Expand the tests and values by iterating over all values in the
3641      attribute space.  */
3642   for (i = 0;; i++)
3643     {
3644       condtest[i] = test_for_current_value (space, ndim);
3645       condval[i] = simplify_with_current_value (exp, space, ndim);
3646       if (! increment_current_value (space, ndim))
3647         break;
3648     }
3649   if (i != total - 1)
3650     abort ();
3651
3652   /* We are now finished with the original expression.  */
3653   unmark_used_attributes (0, space, ndim);
3654
3655   /* Find the most used constant value and make that the default.  */
3656   most_tests = -1;
3657   for (i = num_marks = 0; i < total; i++)
3658     if (GET_CODE (condval[i]) == CONST_STRING
3659         && ! MEM_VOLATILE_P (condval[i]))
3660       {
3661         /* Mark the unmarked constant value and count how many are marked.  */
3662         MEM_VOLATILE_P (condval[i]) = 1;
3663         for (j = new_marks = 0; j < total; j++)
3664           if (GET_CODE (condval[j]) == CONST_STRING
3665               && MEM_VOLATILE_P (condval[j]))
3666             new_marks++;
3667         if (new_marks - num_marks > most_tests)
3668           {
3669             most_tests = new_marks - num_marks;
3670             defval = condval[i];
3671           }
3672         num_marks = new_marks;
3673       }
3674   /* Clear all the marks.  */
3675   for (i = 0; i < total; i++)
3676     MEM_VOLATILE_P (condval[i]) = 0;
3677
3678   /* Give up if nothing is constant.  */
3679   if (num_marks == 0)
3680     return exp;
3681
3682   /* If all values are the default, use that.  */
3683   if (total == most_tests)
3684     return defval;
3685
3686   /* Make a COND with the most common constant value the default.  (A more
3687      complex method where tests with the same value were combined didn't
3688      seem to improve things.)  */
3689   condexp = rtx_alloc (COND);
3690   XVEC (condexp, 0) = rtvec_alloc ((total - most_tests) * 2);
3691   XEXP (condexp, 1) = defval;
3692   for (i = j = 0; i < total; i++)
3693     if (condval[i] != defval)
3694       {
3695         XVECEXP (condexp, 0, 2 * j) = condtest[i];
3696         XVECEXP (condexp, 0, 2 * j + 1) = condval[i];
3697         j++;
3698       }
3699
3700   return condexp;
3701 }
3702
3703 /* Set the MEM_VOLATILE_P flag for all EQ_ATTR expressions in EXP and
3704    verify that EXP can be simplified to a constant term if all the EQ_ATTR
3705    tests have known value.  */
3706
3707 static int
3708 find_and_mark_used_attributes (exp, terms, nterms)
3709      rtx exp, *terms;
3710      int *nterms;
3711 {
3712   int i;
3713
3714   switch (GET_CODE (exp))
3715     {
3716     case EQ_ATTR:
3717       if (! MEM_VOLATILE_P (exp))
3718         {
3719           rtx link = rtx_alloc (EXPR_LIST);
3720           XEXP (link, 0) = exp;
3721           XEXP (link, 1) = *terms;
3722           *terms = link;
3723           *nterms += 1;
3724           MEM_VOLATILE_P (exp) = 1;
3725         }
3726     case CONST_STRING:
3727     case CONST_INT:
3728       return 1;
3729
3730     case IF_THEN_ELSE:
3731       if (! find_and_mark_used_attributes (XEXP (exp, 2), terms, nterms))
3732         return 0;
3733     case IOR:
3734     case AND:
3735       if (! find_and_mark_used_attributes (XEXP (exp, 1), terms, nterms))
3736         return 0;
3737     case NOT:
3738       if (! find_and_mark_used_attributes (XEXP (exp, 0), terms, nterms))
3739         return 0;
3740       return 1;
3741
3742     case COND:
3743       for (i = 0; i < XVECLEN (exp, 0); i++)
3744         if (! find_and_mark_used_attributes (XVECEXP (exp, 0, i), terms, nterms))
3745           return 0;
3746       if (! find_and_mark_used_attributes (XEXP (exp, 1), terms, nterms))
3747         return 0;
3748       return 1;
3749
3750     default:
3751       return 0;
3752     }
3753 }
3754
3755 /* Clear the MEM_VOLATILE_P flag in all EQ_ATTR expressions on LIST and
3756    in the values of the NDIM-dimensional attribute space SPACE.  */
3757
3758 static void
3759 unmark_used_attributes (list, space, ndim)
3760      rtx list;
3761      struct dimension *space;
3762      int ndim;
3763 {
3764   rtx link, exp;
3765   int i;
3766
3767   for (i = 0; i < ndim; i++)
3768     unmark_used_attributes (space[i].values, 0, 0);
3769
3770   for (link = list; link; link = XEXP (link, 1))
3771     {
3772       exp = XEXP (link, 0);
3773       if (GET_CODE (exp) == EQ_ATTR)
3774         MEM_VOLATILE_P (exp) = 0;
3775     }
3776 }
3777
3778 /* Update the attribute dimension DIM so that all values of the attribute
3779    are tested.  Return the updated number of values.  */
3780
3781 static int
3782 add_values_to_cover (dim)
3783      struct dimension *dim;
3784 {
3785   struct attr_value *av;
3786   rtx exp, link, *prev;
3787   int nalt = 0;
3788
3789   for (av = dim->attr->first_value; av; av = av->next)
3790     if (GET_CODE (av->value) == CONST_STRING)
3791       nalt++;
3792
3793   if (nalt < dim->num_values)
3794     abort ();
3795   else if (nalt == dim->num_values)
3796     ; /* Ok.  */
3797   else if (nalt * 2 < dim->num_values * 3)
3798     {
3799       /* Most all the values of the attribute are used, so add all the unused
3800          values.  */
3801       prev = &dim->values;
3802       for (link = dim->values; link; link = *prev)
3803         prev = &XEXP (link, 1);
3804
3805       for (av = dim->attr->first_value; av; av = av->next)
3806         if (GET_CODE (av->value) == CONST_STRING)
3807           {
3808             exp = attr_eq (dim->attr->name, XSTR (av->value, 0));
3809             if (MEM_VOLATILE_P (exp))
3810               continue;
3811
3812             link = rtx_alloc (EXPR_LIST);
3813             XEXP (link, 0) = exp;
3814             XEXP (link, 1) = 0;
3815             *prev = link;
3816             prev = &XEXP (link, 1);
3817           }
3818       dim->num_values = nalt;
3819     }
3820   else
3821     {
3822       rtx orexp = false_rtx;
3823
3824       /* Very few values are used, so compute a mutually exclusive
3825          expression.  (We could do this for numeric values if that becomes
3826          important.)  */
3827       prev = &dim->values;
3828       for (link = dim->values; link; link = *prev)
3829         {
3830           orexp = insert_right_side (IOR, orexp, XEXP (link, 0), -2, -2);
3831           prev = &XEXP (link, 1);
3832         }
3833       link = rtx_alloc (EXPR_LIST);
3834       XEXP (link, 0) = attr_rtx (NOT, orexp);
3835       XEXP (link, 1) = 0;
3836       *prev = link;
3837       dim->num_values++;
3838     }
3839   return dim->num_values;
3840 }
3841
3842 /* Increment the current value for the NDIM-dimensional attribute space SPACE
3843    and return FALSE if the increment overflowed.  */
3844
3845 static int
3846 increment_current_value (space, ndim)
3847      struct dimension *space;
3848      int ndim;
3849 {
3850   int i;
3851
3852   for (i = ndim - 1; i >= 0; i--)
3853     {
3854       if ((space[i].current_value = XEXP (space[i].current_value, 1)) == 0)
3855         space[i].current_value = space[i].values;
3856       else
3857         return 1;
3858     }
3859   return 0;
3860 }
3861
3862 /* Construct an expression corresponding to the current value for the
3863    NDIM-dimensional attribute space SPACE.  */
3864
3865 static rtx
3866 test_for_current_value (space, ndim)
3867      struct dimension *space;
3868      int ndim;
3869 {
3870   int i;
3871   rtx exp = true_rtx;
3872
3873   for (i = 0; i < ndim; i++)
3874     exp = insert_right_side (AND, exp, XEXP (space[i].current_value, 0),
3875                              -2, -2);
3876
3877   return exp;
3878 }
3879
3880 /* Given the current value of the NDIM-dimensional attribute space SPACE,
3881    set the corresponding EQ_ATTR expressions to that value and reduce
3882    the expression EXP as much as possible.  On input [and output], all
3883    known EQ_ATTR expressions are set to FALSE.  */
3884
3885 static rtx
3886 simplify_with_current_value (exp, space, ndim)
3887      rtx exp;
3888      struct dimension *space;
3889      int ndim;
3890 {
3891   int i;
3892   rtx x;
3893
3894   /* Mark each current value as TRUE.  */
3895   for (i = 0; i < ndim; i++)
3896     {
3897       x = XEXP (space[i].current_value, 0);
3898       if (GET_CODE (x) == EQ_ATTR)
3899         MEM_VOLATILE_P (x) = 0;
3900     }
3901
3902   exp = simplify_with_current_value_aux (exp);
3903
3904   /* Change each current value back to FALSE.  */
3905   for (i = 0; i < ndim; i++)
3906     {
3907       x = XEXP (space[i].current_value, 0);
3908       if (GET_CODE (x) == EQ_ATTR)
3909         MEM_VOLATILE_P (x) = 1;
3910     }
3911
3912   return exp;
3913 }
3914
3915 /* Reduce the expression EXP based on the MEM_VOLATILE_P settings of
3916    all EQ_ATTR expressions.  */
3917
3918 static rtx
3919 simplify_with_current_value_aux (exp)
3920      rtx exp;
3921 {
3922   register int i;
3923   rtx cond;
3924
3925   switch (GET_CODE (exp))
3926     {
3927     case EQ_ATTR:
3928       if (MEM_VOLATILE_P (exp))
3929         return false_rtx;
3930       else
3931         return true_rtx;
3932     case CONST_STRING:
3933     case CONST_INT:
3934       return exp;
3935
3936     case IF_THEN_ELSE:
3937       cond = simplify_with_current_value_aux (XEXP (exp, 0));
3938       if (cond == true_rtx)
3939         return simplify_with_current_value_aux (XEXP (exp, 1));
3940       else if (cond == false_rtx)
3941         return simplify_with_current_value_aux (XEXP (exp, 2));
3942       else
3943         return attr_rtx (IF_THEN_ELSE, cond,
3944                          simplify_with_current_value_aux (XEXP (exp, 1)),
3945                          simplify_with_current_value_aux (XEXP (exp, 2)));
3946
3947     case IOR:
3948       cond = simplify_with_current_value_aux (XEXP (exp, 1));
3949       if (cond == true_rtx)
3950         return cond;
3951       else if (cond == false_rtx)
3952         return simplify_with_current_value_aux (XEXP (exp, 0));
3953       else
3954         return attr_rtx (IOR, cond,
3955                          simplify_with_current_value_aux (XEXP (exp, 0)));
3956
3957     case AND:
3958       cond = simplify_with_current_value_aux (XEXP (exp, 1));
3959       if (cond == true_rtx)
3960         return simplify_with_current_value_aux (XEXP (exp, 0));
3961       else if (cond == false_rtx)
3962         return cond;
3963       else
3964         return attr_rtx (AND, cond,
3965                          simplify_with_current_value_aux (XEXP (exp, 0)));
3966
3967     case NOT:
3968       cond = simplify_with_current_value_aux (XEXP (exp, 0));
3969       if (cond == true_rtx)
3970         return false_rtx;
3971       else if (cond == false_rtx)
3972         return true_rtx;
3973       else
3974         return attr_rtx (NOT, cond);
3975
3976     case COND:
3977       for (i = 0; i < XVECLEN (exp, 0); i += 2)
3978         {
3979           cond = simplify_with_current_value_aux (XVECEXP (exp, 0, i));
3980           if (cond == true_rtx)
3981             return simplify_with_current_value_aux (XVECEXP (exp, 0, i + 1));
3982           else if (cond == false_rtx)
3983             continue;
3984           else
3985             abort (); /* With all EQ_ATTR's of known value, a case should
3986                          have been selected.  */
3987         }
3988       return simplify_with_current_value_aux (XEXP (exp, 1));
3989
3990     default:
3991       abort ();
3992     }
3993 }
3994 \f
3995 /* Clear the MEM_IN_STRUCT_P flag in EXP and its subexpressions.  */
3996
3997 static void
3998 clear_struct_flag (x)
3999      rtx x;
4000 {
4001   register int i;
4002   register int j;
4003   register enum rtx_code code;
4004   register char *fmt;
4005
4006   MEM_IN_STRUCT_P (x) = 0;
4007   if (RTX_UNCHANGING_P (x))
4008     return;
4009
4010   code = GET_CODE (x);
4011
4012   switch (code)
4013     {
4014     case REG:
4015     case QUEUED:
4016     case CONST_INT:
4017     case CONST_DOUBLE:
4018     case SYMBOL_REF:
4019     case CODE_LABEL:
4020     case PC:
4021     case CC0:
4022     case EQ_ATTR:
4023     case ATTR_FLAG:
4024       return;
4025       
4026     default:
4027       break;
4028     }
4029
4030   /* Compare the elements.  If any pair of corresponding elements
4031      fail to match, return 0 for the whole things.  */
4032
4033   fmt = GET_RTX_FORMAT (code);
4034   for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
4035     {
4036       switch (fmt[i])
4037         {
4038         case 'V':
4039         case 'E':
4040           for (j = 0; j < XVECLEN (x, i); j++)
4041             clear_struct_flag (XVECEXP (x, i, j));
4042           break;
4043
4044         case 'e':
4045           clear_struct_flag (XEXP (x, i));
4046           break;
4047         }
4048     }
4049 }
4050
4051 /* Return the number of RTX objects making up the expression X.
4052    But if we count more more than MAX objects, stop counting.  */
4053
4054 static int
4055 count_sub_rtxs (x, max)
4056      rtx x;
4057      int max;
4058 {
4059   register int i;
4060   register int j;
4061   register enum rtx_code code;
4062   register char *fmt;
4063   int total = 0;
4064
4065   code = GET_CODE (x);
4066
4067   switch (code)
4068     {
4069     case REG:
4070     case QUEUED:
4071     case CONST_INT:
4072     case CONST_DOUBLE:
4073     case SYMBOL_REF:
4074     case CODE_LABEL:
4075     case PC:
4076     case CC0:
4077     case EQ_ATTR:
4078     case ATTR_FLAG:
4079       return 1;
4080       
4081     default:
4082       break;
4083     }
4084
4085   /* Compare the elements.  If any pair of corresponding elements
4086      fail to match, return 0 for the whole things.  */
4087
4088   fmt = GET_RTX_FORMAT (code);
4089   for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
4090     {
4091       if (total >= max)
4092         return total;
4093
4094       switch (fmt[i])
4095         {
4096         case 'V':
4097         case 'E':
4098           for (j = 0; j < XVECLEN (x, i); j++)
4099             total += count_sub_rtxs (XVECEXP (x, i, j), max);
4100           break;
4101
4102         case 'e':
4103           total += count_sub_rtxs (XEXP (x, i), max);
4104           break;
4105         }
4106     }
4107   return total;
4108
4109 }
4110 \f
4111 /* Create table entries for DEFINE_ATTR.  */
4112
4113 static void
4114 gen_attr (exp)
4115      rtx exp;
4116 {
4117   struct attr_desc *attr;
4118   struct attr_value *av;
4119   char *name_ptr;
4120   char *p;
4121
4122   /* Make a new attribute structure.  Check for duplicate by looking at
4123      attr->default_val, since it is initialized by this routine.  */
4124   attr = find_attr (XSTR (exp, 0), 1);
4125   if (attr->default_val)
4126     fatal ("Duplicate definition for `%s' attribute", attr->name);
4127
4128   if (*XSTR (exp, 1) == '\0')
4129       attr->is_numeric = 1;
4130   else
4131     {
4132       name_ptr = XSTR (exp, 1);
4133       while ((p = next_comma_elt (&name_ptr)) != NULL)
4134         {
4135           av = (struct attr_value *) oballoc (sizeof (struct attr_value));
4136           av->value = attr_rtx (CONST_STRING, p);
4137           av->next = attr->first_value;
4138           attr->first_value = av;
4139           av->first_insn = NULL;
4140           av->num_insns = 0;
4141           av->has_asm_insn = 0;
4142         }
4143     }
4144
4145   if (GET_CODE (XEXP (exp, 2)) == CONST)
4146     {
4147       attr->is_const = 1;
4148       if (attr->is_numeric)
4149         fatal ("Constant attributes may not take numeric values");
4150       /* Get rid of the CONST node.  It is allowed only at top-level.  */
4151       XEXP (exp, 2) = XEXP (XEXP (exp, 2), 0);
4152     }
4153
4154   if (! strcmp (attr->name, "length") && ! attr->is_numeric)
4155     fatal ("`length' attribute must take numeric values");
4156
4157   /* Set up the default value.  */
4158   XEXP (exp, 2) = check_attr_value (XEXP (exp, 2), attr);
4159   attr->default_val = get_attr_value (XEXP (exp, 2), attr, -2);
4160 }
4161 \f
4162 /* Given a pattern for DEFINE_PEEPHOLE or DEFINE_INSN, return the number of
4163    alternatives in the constraints.  Assume all MATCH_OPERANDs have the same
4164    number of alternatives as this should be checked elsewhere.  */
4165
4166 static int
4167 count_alternatives (exp)
4168      rtx exp;
4169 {
4170   int i, j, n;
4171   char *fmt;
4172   
4173   if (GET_CODE (exp) == MATCH_OPERAND)
4174     return n_comma_elts (XSTR (exp, 2));
4175
4176   for (i = 0, fmt = GET_RTX_FORMAT (GET_CODE (exp));
4177        i < GET_RTX_LENGTH (GET_CODE (exp)); i++)
4178     switch (*fmt++)
4179       {
4180       case 'e':
4181       case 'u':
4182         n = count_alternatives (XEXP (exp, i));
4183         if (n)
4184           return n;
4185         break;
4186
4187       case 'E':
4188       case 'V':
4189         if (XVEC (exp, i) != NULL)
4190           for (j = 0; j < XVECLEN (exp, i); j++)
4191             {
4192               n = count_alternatives (XVECEXP (exp, i, j));
4193               if (n)
4194                 return n;
4195             }
4196       }
4197
4198   return 0;
4199 }
4200 \f
4201 /* Returns non-zero if the given expression contains an EQ_ATTR with the
4202    `alternative' attribute.  */
4203
4204 static int
4205 compares_alternatives_p (exp)
4206      rtx exp;
4207 {
4208   int i, j;
4209   char *fmt;
4210
4211   if (GET_CODE (exp) == EQ_ATTR && XSTR (exp, 0) == alternative_name)
4212     return 1;
4213
4214   for (i = 0, fmt = GET_RTX_FORMAT (GET_CODE (exp));
4215        i < GET_RTX_LENGTH (GET_CODE (exp)); i++)
4216     switch (*fmt++)
4217       {
4218       case 'e':
4219       case 'u':
4220         if (compares_alternatives_p (XEXP (exp, i)))
4221           return 1;
4222         break;
4223
4224       case 'E':
4225         for (j = 0; j < XVECLEN (exp, i); j++)
4226           if (compares_alternatives_p (XVECEXP (exp, i, j)))
4227             return 1;
4228         break;
4229       }
4230
4231   return 0;
4232 }
4233 \f
4234 /* Returns non-zero is INNER is contained in EXP.  */
4235
4236 static int
4237 contained_in_p (inner, exp)
4238      rtx inner;
4239      rtx exp;
4240 {
4241   int i, j;
4242   char *fmt;
4243
4244   if (rtx_equal_p (inner, exp))
4245     return 1;
4246
4247   for (i = 0, fmt = GET_RTX_FORMAT (GET_CODE (exp));
4248        i < GET_RTX_LENGTH (GET_CODE (exp)); i++)
4249     switch (*fmt++)
4250       {
4251       case 'e':
4252       case 'u':
4253         if (contained_in_p (inner, XEXP (exp, i)))
4254           return 1;
4255         break;
4256
4257       case 'E':
4258         for (j = 0; j < XVECLEN (exp, i); j++)
4259           if (contained_in_p (inner, XVECEXP (exp, i, j)))
4260             return 1;
4261         break;
4262       }
4263
4264   return 0;
4265 }
4266 \f       
4267 /* Process DEFINE_PEEPHOLE, DEFINE_INSN, and DEFINE_ASM_ATTRIBUTES.  */
4268
4269 static void
4270 gen_insn (exp)
4271      rtx exp;
4272 {
4273   struct insn_def *id;
4274
4275   id = (struct insn_def *) oballoc (sizeof (struct insn_def));
4276   id->next = defs;
4277   defs = id;
4278   id->def = exp;
4279
4280   switch (GET_CODE (exp))
4281     {
4282     case DEFINE_INSN:
4283       id->insn_code = insn_code_number++;
4284       id->insn_index = insn_index_number++;
4285       id->num_alternatives = count_alternatives (exp);
4286       if (id->num_alternatives == 0)
4287         id->num_alternatives = 1;
4288       id->vec_idx = 4;
4289       break;
4290
4291     case DEFINE_PEEPHOLE:
4292       id->insn_code = insn_code_number++;
4293       id->insn_index = insn_index_number++;
4294       id->num_alternatives = count_alternatives (exp);
4295       if (id->num_alternatives == 0)
4296         id->num_alternatives = 1;
4297       id->vec_idx = 3;
4298       break;
4299
4300     case DEFINE_ASM_ATTRIBUTES:
4301       id->insn_code = -1;
4302       id->insn_index = -1;
4303       id->num_alternatives = 1;
4304       id->vec_idx = 0;
4305       got_define_asm_attributes = 1;
4306       break;
4307       
4308     default:
4309       abort ();
4310     }
4311 }
4312 \f
4313 /* Process a DEFINE_DELAY.  Validate the vector length, check if annul
4314    true or annul false is specified, and make a `struct delay_desc'.  */
4315
4316 static void
4317 gen_delay (def)
4318      rtx def;
4319 {
4320   struct delay_desc *delay;
4321   int i;
4322
4323   if (XVECLEN (def, 1) % 3 != 0)
4324     fatal ("Number of elements in DEFINE_DELAY must be multiple of three.");
4325
4326   for (i = 0; i < XVECLEN (def, 1); i += 3)
4327     {
4328       if (XVECEXP (def, 1, i + 1))
4329         have_annul_true = 1;
4330       if (XVECEXP (def, 1, i + 2))
4331         have_annul_false = 1;
4332     }
4333   
4334   delay = (struct delay_desc *) oballoc (sizeof (struct delay_desc));
4335   delay->def = def;
4336   delay->num = ++num_delays;
4337   delay->next = delays;
4338   delays = delay;
4339 }
4340 \f
4341 /* Process a DEFINE_FUNCTION_UNIT.  
4342
4343    This gives information about a function unit contained in the CPU.
4344    We fill in a `struct function_unit_op' and a `struct function_unit'
4345    with information used later by `expand_unit'.  */
4346
4347 static void
4348 gen_unit (def)
4349      rtx def;
4350 {
4351   struct function_unit *unit;
4352   struct function_unit_op *op;
4353   char *name = XSTR (def, 0);
4354   int multiplicity = XINT (def, 1);
4355   int simultaneity = XINT (def, 2);
4356   rtx condexp = XEXP (def, 3);
4357   int ready_cost = MAX (XINT (def, 4), 1);
4358   int issue_delay = MAX (XINT (def, 5), 1);
4359
4360   /* See if we have already seen this function unit.  If so, check that
4361      the multiplicity and simultaneity values are the same.  If not, make
4362      a structure for this function unit.  */
4363   for (unit = units; unit; unit = unit->next)
4364     if (! strcmp (unit->name, name))
4365       {
4366         if (unit->multiplicity != multiplicity
4367             || unit->simultaneity != simultaneity)
4368           fatal ("Differing specifications given for `%s' function unit.",
4369                  unit->name);
4370         break;
4371       }
4372
4373   if (unit == 0)
4374     {
4375       unit = (struct function_unit *) oballoc (sizeof (struct function_unit));
4376       unit->name = name;
4377       unit->multiplicity = multiplicity;
4378       unit->simultaneity = simultaneity;
4379       unit->issue_delay.min = unit->issue_delay.max = issue_delay;
4380       unit->num = num_units++;
4381       unit->num_opclasses = 0;
4382       unit->condexp = false_rtx;
4383       unit->ops = 0;
4384       unit->next = units;
4385       units = unit;
4386     }
4387
4388   /* Make a new operation class structure entry and initialize it.  */
4389   op = (struct function_unit_op *) oballoc (sizeof (struct function_unit_op));
4390   op->condexp = condexp;
4391   op->num = unit->num_opclasses++;
4392   op->ready = ready_cost;
4393   op->issue_delay = issue_delay;
4394   op->next = unit->ops;
4395   unit->ops = op;
4396   num_unit_opclasses++;
4397
4398   /* Set our issue expression based on whether or not an optional conflict
4399      vector was specified.  */
4400   if (XVEC (def, 6))
4401     {
4402       /* Compute the IOR of all the specified expressions.  */
4403       rtx orexp = false_rtx;
4404       int i;
4405
4406       for (i = 0; i < XVECLEN (def, 6); i++)
4407         orexp = insert_right_side (IOR, orexp, XVECEXP (def, 6, i), -2, -2);
4408
4409       op->conflict_exp = orexp;
4410       extend_range (&unit->issue_delay, 1, issue_delay);
4411     }
4412   else
4413     {
4414       op->conflict_exp = true_rtx;
4415       extend_range (&unit->issue_delay, issue_delay, issue_delay);
4416     }
4417
4418   /* Merge our conditional into that of the function unit so we can determine
4419      which insns are used by the function unit.  */
4420   unit->condexp = insert_right_side (IOR, unit->condexp, op->condexp, -2, -2);
4421 }
4422 \f
4423 /* Given a piece of RTX, print a C expression to test it's truth value.
4424
4425    We use AND and IOR both for logical and bit-wise operations, so 
4426    interpret them as logical unless they are inside a comparison expression.
4427    The first bit of FLAGS will be non-zero in that case.
4428
4429    Set the second bit of FLAGS to make references to attribute values use
4430    a cached local variable instead of calling a function.  */
4431
4432 static void
4433 write_test_expr (exp, flags)
4434      rtx exp;
4435      int flags;
4436 {
4437   int comparison_operator = 0;
4438   RTX_CODE code;
4439   struct attr_desc *attr;
4440
4441   /* In order not to worry about operator precedence, surround our part of
4442      the expression with parentheses.  */
4443
4444   printf ("(");
4445   code = GET_CODE (exp);
4446   switch (code)
4447     {
4448     /* Binary operators.  */
4449     case EQ: case NE:
4450     case GE: case GT: case GEU: case GTU:
4451     case LE: case LT: case LEU: case LTU:
4452       comparison_operator = 1;
4453
4454     case PLUS:   case MINUS:  case MULT:     case DIV:      case MOD:
4455     case AND:    case IOR:    case XOR:
4456     case ASHIFT: case LSHIFTRT: case ASHIFTRT:
4457       write_test_expr (XEXP (exp, 0), flags | comparison_operator);
4458       switch (code)
4459         {
4460         case EQ:
4461           printf (" == ");
4462           break;
4463         case NE:
4464           printf (" != ");
4465           break;
4466         case GE:
4467           printf (" >= ");
4468           break;
4469         case GT:
4470           printf (" > ");
4471           break;
4472         case GEU:
4473           printf (" >= (unsigned) ");
4474           break;
4475         case GTU:
4476           printf (" > (unsigned) ");
4477           break;
4478         case LE:
4479           printf (" <= ");
4480           break;
4481         case LT:
4482           printf (" < ");
4483           break;
4484         case LEU:
4485           printf (" <= (unsigned) ");
4486           break;
4487         case LTU:
4488           printf (" < (unsigned) ");
4489           break;
4490         case PLUS:
4491           printf (" + ");
4492           break;
4493         case MINUS:
4494           printf (" - ");
4495           break;
4496         case MULT:
4497           printf (" * ");
4498           break;
4499         case DIV:
4500           printf (" / ");
4501           break;
4502         case MOD:
4503           printf (" %% ");
4504           break;
4505         case AND:
4506           if (flags & 1)
4507             printf (" & ");
4508           else
4509             printf (" && ");
4510           break;
4511         case IOR:
4512           if (flags & 1)
4513             printf (" | ");
4514           else
4515             printf (" || ");
4516           break;
4517         case XOR:
4518           printf (" ^ ");
4519           break;
4520         case ASHIFT:
4521           printf (" << ");
4522           break;
4523         case LSHIFTRT:
4524         case ASHIFTRT:
4525           printf (" >> ");
4526           break;
4527         default:
4528           abort ();
4529         }
4530
4531       write_test_expr (XEXP (exp, 1), flags | comparison_operator);
4532       break;
4533
4534     case NOT:
4535       /* Special-case (not (eq_attrq "alternative" "x")) */
4536       if (! (flags & 1) && GET_CODE (XEXP (exp, 0)) == EQ_ATTR
4537           && XSTR (XEXP (exp, 0), 0) == alternative_name)
4538         {
4539           printf ("which_alternative != %s", XSTR (XEXP (exp, 0), 1));
4540           break;
4541         }
4542
4543       /* Otherwise, fall through to normal unary operator.  */
4544
4545     /* Unary operators.  */   
4546     case ABS:  case NEG:
4547       switch (code)
4548         {
4549         case NOT:
4550           if (flags & 1)
4551             printf ("~ ");
4552           else
4553             printf ("! ");
4554           break;
4555         case ABS:
4556           printf ("abs ");
4557           break;
4558         case NEG:
4559           printf ("-");
4560           break;
4561         default:
4562           abort ();
4563         }
4564
4565       write_test_expr (XEXP (exp, 0), flags);
4566       break;
4567
4568     /* Comparison test of an attribute with a value.  Most of these will
4569        have been removed by optimization.   Handle "alternative"
4570        specially and give error if EQ_ATTR present inside a comparison.  */
4571     case EQ_ATTR:
4572       if (flags & 1)
4573         fatal ("EQ_ATTR not valid inside comparison");
4574
4575       if (XSTR (exp, 0) == alternative_name)
4576         {
4577           printf ("which_alternative == %s", XSTR (exp, 1));
4578           break;
4579         }
4580
4581       attr = find_attr (XSTR (exp, 0), 0);
4582       if (! attr) abort ();
4583
4584       /* Now is the time to expand the value of a constant attribute.  */
4585       if (attr->is_const)
4586         {
4587           write_test_expr (evaluate_eq_attr (exp, attr->default_val->value,
4588                                              -2, -2),
4589                            flags);
4590         }
4591       else
4592         {
4593           if (flags & 2)
4594             printf ("attr_%s", attr->name);
4595           else
4596             printf ("get_attr_%s (insn)", attr->name);
4597           printf (" == ");
4598           write_attr_valueq (attr, XSTR (exp, 1));
4599         }
4600       break;
4601
4602     /* Comparison test of flags for define_delays.  */
4603     case ATTR_FLAG:
4604       if (flags & 1)
4605         fatal ("ATTR_FLAG not valid inside comparison");
4606       printf ("(flags & ATTR_FLAG_%s) != 0", XSTR (exp, 0));
4607       break;
4608
4609     /* See if an operand matches a predicate.  */
4610     case MATCH_OPERAND:
4611       /* If only a mode is given, just ensure the mode matches the operand.
4612          If neither a mode nor predicate is given, error.  */
4613      if (XSTR (exp, 1) == NULL || *XSTR (exp, 1) == '\0')
4614         {
4615           if (GET_MODE (exp) == VOIDmode)
4616             fatal ("Null MATCH_OPERAND specified as test");
4617           else
4618             printf ("GET_MODE (operands[%d]) == %smode",
4619                     XINT (exp, 0), GET_MODE_NAME (GET_MODE (exp)));
4620         }
4621       else
4622         printf ("%s (operands[%d], %smode)",
4623                 XSTR (exp, 1), XINT (exp, 0), GET_MODE_NAME (GET_MODE (exp)));
4624       break;
4625
4626     /* Constant integer.  */
4627     case CONST_INT:
4628       printf (HOST_WIDE_INT_PRINT_DEC, XWINT (exp, 0));
4629       break;
4630
4631     /* A random C expression.  */
4632     case SYMBOL_REF:
4633       printf ("%s", XSTR (exp, 0));
4634       break;
4635
4636     /* The address of the branch target.  */
4637     case MATCH_DUP:
4638       printf ("insn_addresses[INSN_UID (GET_CODE (operands[%d]) == LABEL_REF ? XEXP (operands[%d], 0) : operands[%d])]",
4639               XINT (exp, 0), XINT (exp, 0), XINT (exp, 0));
4640       break;
4641
4642     /* The address of the current insn.  It would be more consistent with
4643        other usage to make this the address of the NEXT insn, but this gets
4644        too confusing because of the ambiguity regarding the length of the
4645        current insn.  */
4646     case PC:
4647       printf ("insn_current_address");
4648       break;
4649
4650     case CONST_STRING:
4651       printf ("%s", XSTR (exp, 0));
4652       break;
4653
4654     case IF_THEN_ELSE:
4655       write_test_expr (XEXP (exp, 0), flags & 2);
4656       printf (" ? ");
4657       write_test_expr (XEXP (exp, 1), flags | 1);
4658       printf (" : ");
4659       write_test_expr (XEXP (exp, 2), flags | 1);
4660       break;
4661
4662     default:
4663       fatal ("bad RTX code `%s' in attribute calculation\n",
4664              GET_RTX_NAME (code));
4665     }
4666
4667   printf (")");
4668 }
4669 \f
4670 /* Given an attribute value, return the maximum CONST_STRING argument
4671    encountered.  It is assumed that they are all numeric.  */
4672
4673 static int
4674 max_attr_value (exp)
4675      rtx exp;
4676 {
4677   int current_max = 0;
4678   int n;
4679   int i;
4680
4681   if (GET_CODE (exp) == CONST_STRING)
4682     return atoi (XSTR (exp, 0));
4683
4684   else if (GET_CODE (exp) == COND)
4685     {
4686       for (i = 0; i < XVECLEN (exp, 0); i += 2)
4687         {
4688           n = max_attr_value (XVECEXP (exp, 0, i + 1));
4689           if (n > current_max)
4690             current_max = n;
4691         }
4692
4693       n = max_attr_value (XEXP (exp, 1));
4694       if (n > current_max)
4695         current_max = n;
4696     }
4697
4698   else if (GET_CODE (exp) == IF_THEN_ELSE)
4699     {
4700       current_max = max_attr_value (XEXP (exp, 1));
4701       n = max_attr_value (XEXP (exp, 2));
4702       if (n > current_max)
4703         current_max = n;
4704     }
4705
4706   else
4707     abort ();
4708
4709   return current_max;
4710 }
4711 \f
4712 /* Scan an attribute value, possibly a conditional, and record what actions
4713    will be required to do any conditional tests in it.
4714
4715    Specifically, set
4716         `must_extract'    if we need to extract the insn operands
4717         `must_constrain'  if we must compute `which_alternative'
4718         `address_used'    if an address expression was used
4719         `length_used'     if an (eq_attr "length" ...) was used
4720  */
4721
4722 static void
4723 walk_attr_value (exp)
4724      rtx exp;
4725 {
4726   register int i, j;
4727   register char *fmt;
4728   RTX_CODE code;
4729
4730   if (exp == NULL)
4731     return;
4732
4733   code = GET_CODE (exp);
4734   switch (code)
4735     {
4736     case SYMBOL_REF:
4737       if (! RTX_UNCHANGING_P (exp))
4738         /* Since this is an arbitrary expression, it can look at anything.
4739            However, constant expressions do not depend on any particular
4740            insn.  */
4741         must_extract = must_constrain = 1;
4742       return;
4743
4744     case MATCH_OPERAND:
4745       must_extract = 1;
4746       return;
4747
4748     case EQ_ATTR:
4749       if (XSTR (exp, 0) == alternative_name)
4750         must_extract = must_constrain = 1;
4751       else if (strcmp (XSTR (exp, 0), "length") == 0)
4752         length_used = 1;
4753       return;
4754
4755     case MATCH_DUP:
4756       must_extract = 1;
4757       address_used = 1;
4758       return;
4759
4760     case PC:
4761       address_used = 1;
4762       return;
4763
4764     case ATTR_FLAG:
4765       return;
4766
4767     default:
4768       break;
4769     }
4770
4771   for (i = 0, fmt = GET_RTX_FORMAT (code); i < GET_RTX_LENGTH (code); i++)
4772     switch (*fmt++)
4773       {
4774       case 'e':
4775       case 'u':
4776         walk_attr_value (XEXP (exp, i));
4777         break;
4778
4779       case 'E':
4780         if (XVEC (exp, i) != NULL)
4781           for (j = 0; j < XVECLEN (exp, i); j++)
4782             walk_attr_value (XVECEXP (exp, i, j));
4783         break;
4784       }
4785 }
4786 \f
4787 /* Write out a function to obtain the attribute for a given INSN.  */
4788
4789 static void
4790 write_attr_get (attr)
4791      struct attr_desc *attr;
4792 {
4793   struct attr_value *av, *common_av;
4794
4795   /* Find the most used attribute value.  Handle that as the `default' of the
4796      switch we will generate.  */
4797   common_av = find_most_used (attr);
4798
4799   /* Write out start of function, then all values with explicit `case' lines,
4800      then a `default', then the value with the most uses.  */
4801   if (!attr->is_numeric)
4802     printf ("enum attr_%s\n", attr->name);
4803   else if (attr->unsigned_p)
4804     printf ("unsigned int\n");
4805   else
4806     printf ("int\n");
4807
4808   /* If the attribute name starts with a star, the remainder is the name of
4809      the subroutine to use, instead of `get_attr_...'.  */
4810   if (attr->name[0] == '*')
4811     printf ("%s (insn)\n", &attr->name[1]);
4812   else if (attr->is_const == 0)
4813     printf ("get_attr_%s (insn)\n", attr->name);
4814   else
4815     {
4816       printf ("get_attr_%s ()\n", attr->name);
4817       printf ("{\n");
4818
4819       for (av = attr->first_value; av; av = av->next)
4820         if (av->num_insns != 0)
4821           write_attr_set (attr, 2, av->value, "return", ";",
4822                           true_rtx, av->first_insn->insn_code,
4823                           av->first_insn->insn_index);
4824
4825       printf ("}\n\n");
4826       return;
4827     }
4828
4829   printf ("     rtx insn;\n");
4830   printf ("{\n");
4831
4832   if (GET_CODE (common_av->value) == FFS)
4833     {
4834       rtx p = XEXP (common_av->value, 0);
4835
4836       /* No need to emit code to abort if the insn is unrecognized; the 
4837          other get_attr_foo functions will do that when we call them.  */
4838
4839       write_toplevel_expr (p);
4840
4841       printf ("\n  if (accum && accum == (accum & -accum))\n");
4842       printf ("    {\n");
4843       printf ("      int i;\n");
4844       printf ("      for (i = 0; accum >>= 1; ++i) continue;\n");
4845       printf ("      accum = i;\n");
4846       printf ("    }\n  else\n");
4847       printf ("    accum = ~accum;\n");
4848       printf ("  return accum;\n}\n\n");
4849     }
4850   else
4851     {
4852       printf ("  switch (recog_memoized (insn))\n");
4853       printf ("    {\n");
4854
4855       for (av = attr->first_value; av; av = av->next)
4856         if (av != common_av)
4857           write_attr_case (attr, av, 1, "return", ";", 4, true_rtx);
4858
4859       write_attr_case (attr, common_av, 0, "return", ";", 4, true_rtx);
4860       printf ("    }\n}\n\n");
4861     }
4862 }
4863 \f
4864 /* Given an AND tree of known true terms (because we are inside an `if' with
4865    that as the condition or are in an `else' clause) and an expression,
4866    replace any known true terms with TRUE.  Use `simplify_and_tree' to do
4867    the bulk of the work.  */
4868
4869 static rtx
4870 eliminate_known_true (known_true, exp, insn_code, insn_index)
4871      rtx known_true;
4872      rtx exp;
4873      int insn_code, insn_index;
4874 {
4875   rtx term;
4876
4877   known_true = SIMPLIFY_TEST_EXP (known_true, insn_code, insn_index);
4878
4879   if (GET_CODE (known_true) == AND)
4880     {
4881       exp = eliminate_known_true (XEXP (known_true, 0), exp,
4882                                   insn_code, insn_index);
4883       exp = eliminate_known_true (XEXP (known_true, 1), exp,
4884                                   insn_code, insn_index);
4885     }
4886   else
4887     {
4888       term = known_true;
4889       exp = simplify_and_tree (exp, &term, insn_code, insn_index);
4890     }
4891
4892   return exp;
4893 }
4894 \f
4895 /* Write out a series of tests and assignment statements to perform tests and
4896    sets of an attribute value.  We are passed an indentation amount and prefix
4897    and suffix strings to write around each attribute value (e.g., "return"
4898    and ";").  */
4899
4900 static void
4901 write_attr_set (attr, indent, value, prefix, suffix, known_true,
4902                 insn_code, insn_index)
4903      struct attr_desc *attr;
4904      int indent;
4905      rtx value;
4906      char *prefix;
4907      char *suffix;
4908      rtx known_true;
4909      int insn_code, insn_index;
4910 {
4911   if (GET_CODE (value) == CONST_STRING)
4912     {
4913       write_indent (indent);
4914       printf ("%s ", prefix);
4915       write_attr_value (attr, value);
4916       printf ("%s\n", suffix);
4917     }
4918   else if (GET_CODE (value) == COND)
4919     {
4920       /* Assume the default value will be the default of the COND unless we
4921          find an always true expression.  */
4922       rtx default_val = XEXP (value, 1);
4923       rtx our_known_true = known_true;
4924       rtx newexp;
4925       int first_if = 1;
4926       int i;
4927
4928       for (i = 0; i < XVECLEN (value, 0); i += 2)
4929         {
4930           rtx testexp;
4931           rtx inner_true;
4932
4933           testexp = eliminate_known_true (our_known_true,
4934                                           XVECEXP (value, 0, i),
4935                                           insn_code, insn_index);
4936           newexp = attr_rtx (NOT, testexp);
4937           newexp  = insert_right_side (AND, our_known_true, newexp,
4938                                        insn_code, insn_index);
4939
4940           /* If the test expression is always true or if the next `known_true'
4941              expression is always false, this is the last case, so break
4942              out and let this value be the `else' case.  */
4943           if (testexp == true_rtx || newexp == false_rtx)
4944             {
4945               default_val = XVECEXP (value, 0, i + 1);
4946               break;
4947             }
4948
4949           /* Compute the expression to pass to our recursive call as being
4950              known true.  */
4951           inner_true = insert_right_side (AND, our_known_true,
4952                                           testexp, insn_code, insn_index);
4953
4954           /* If this is always false, skip it.  */
4955           if (inner_true == false_rtx)
4956             continue;
4957
4958           write_indent (indent);
4959           printf ("%sif ", first_if ? "" : "else ");
4960           first_if = 0;
4961           write_test_expr (testexp, 0);
4962           printf ("\n");
4963           write_indent (indent + 2);
4964           printf ("{\n");
4965
4966           write_attr_set (attr, indent + 4,  
4967                           XVECEXP (value, 0, i + 1), prefix, suffix,
4968                           inner_true, insn_code, insn_index);
4969           write_indent (indent + 2);
4970           printf ("}\n");
4971           our_known_true = newexp;
4972         }
4973
4974       if (! first_if)
4975         {
4976           write_indent (indent);
4977           printf ("else\n");
4978           write_indent (indent + 2);
4979           printf ("{\n");
4980         }
4981
4982       write_attr_set (attr, first_if ? indent : indent + 4, default_val,
4983                       prefix, suffix, our_known_true, insn_code, insn_index);
4984
4985       if (! first_if)
4986         {
4987           write_indent (indent + 2);
4988           printf ("}\n");
4989         }
4990     }
4991   else
4992     abort ();
4993 }
4994 \f
4995 /* Write out the computation for one attribute value.  */
4996
4997 static void
4998 write_attr_case (attr, av, write_case_lines, prefix, suffix, indent,
4999                  known_true)
5000      struct attr_desc *attr;
5001      struct attr_value *av;
5002      int write_case_lines;
5003      char *prefix, *suffix;
5004      int indent;
5005      rtx known_true;
5006 {
5007   struct insn_ent *ie;
5008
5009   if (av->num_insns == 0)
5010     return;
5011
5012   if (av->has_asm_insn)
5013     {
5014       write_indent (indent);
5015       printf ("case -1:\n");
5016       write_indent (indent + 2);
5017       printf ("if (GET_CODE (PATTERN (insn)) != ASM_INPUT\n");
5018       write_indent (indent + 2);
5019       printf ("    && asm_noperands (PATTERN (insn)) < 0)\n");
5020       write_indent (indent + 2);
5021       printf ("  fatal_insn_not_found (insn);\n");
5022     }
5023
5024   if (write_case_lines)
5025     {
5026       for (ie = av->first_insn; ie; ie = ie->next)
5027         if (ie->insn_code != -1)
5028           {
5029             write_indent (indent);
5030             printf ("case %d:\n", ie->insn_code);
5031           }
5032     }
5033   else
5034     {
5035       write_indent (indent);
5036       printf ("default:\n");
5037     }
5038
5039   /* See what we have to do to output this value.  */
5040   must_extract = must_constrain = address_used = 0;
5041   walk_attr_value (av->value);
5042
5043   if (must_extract)
5044     {
5045       write_indent (indent + 2);
5046       printf ("insn_extract (insn);\n");
5047     }
5048
5049   if (must_constrain)
5050     {
5051 #ifdef REGISTER_CONSTRAINTS
5052       write_indent (indent + 2);
5053       printf ("if (! constrain_operands (INSN_CODE (insn), reload_completed))\n");
5054       write_indent (indent + 2);
5055       printf ("  fatal_insn_not_found (insn);\n");
5056 #endif
5057     }
5058
5059   write_attr_set (attr, indent + 2, av->value, prefix, suffix,
5060                   known_true, av->first_insn->insn_code,
5061                   av->first_insn->insn_index);
5062
5063   if (strncmp (prefix, "return", 6))
5064     {
5065       write_indent (indent + 2);
5066       printf ("break;\n");
5067     }
5068   printf ("\n");
5069 }
5070 \f
5071 /* Search for uses of non-const attributes and write code to cache them.  */
5072
5073 static int
5074 write_expr_attr_cache (p, attr)
5075      rtx p;
5076      struct attr_desc *attr;
5077 {
5078   char *fmt;
5079   int i, ie, j, je;
5080
5081   if (GET_CODE (p) == EQ_ATTR)
5082     {
5083       if (XSTR (p, 0) != attr->name)
5084         return 0;
5085
5086       if (!attr->is_numeric)
5087         printf ("  register enum attr_%s ", attr->name);
5088       else if (attr->unsigned_p)
5089         printf ("  register unsigned int ");
5090       else
5091         printf ("  register int ");
5092
5093       printf ("attr_%s = get_attr_%s (insn);\n", attr->name, attr->name);
5094       return 1;
5095     }
5096
5097   fmt = GET_RTX_FORMAT (GET_CODE (p));
5098   ie = GET_RTX_LENGTH (GET_CODE (p));
5099   for (i = 0; i < ie; i++)
5100     {
5101       switch (*fmt++)
5102         {
5103         case 'e':
5104           if (write_expr_attr_cache (XEXP (p, i), attr))
5105             return 1;
5106           break;
5107
5108         case 'E':
5109           je = XVECLEN (p, i);
5110           for (j = 0; j < je; ++j)
5111             if (write_expr_attr_cache (XVECEXP (p, i, j), attr))
5112               return 1;
5113           break;
5114         }
5115     }
5116
5117   return 0;
5118 }
5119
5120 /* Evaluate an expression at top level.  A front end to write_test_expr,
5121    in which we cache attribute values and break up excessively large
5122    expressions to cater to older compilers.  */
5123
5124 static void
5125 write_toplevel_expr (p)
5126      rtx p;
5127 {
5128   struct attr_desc *attr;
5129   int i;
5130
5131   for (i = 0; i < MAX_ATTRS_INDEX; ++i)
5132     for (attr = attrs[i]; attr ; attr = attr->next)
5133       if (!attr->is_const)
5134         write_expr_attr_cache (p, attr);
5135
5136   printf("  register unsigned long accum = 0;\n\n");
5137
5138   while (GET_CODE (p) == IOR)
5139     {
5140       rtx e;
5141       if (GET_CODE (XEXP (p, 0)) == IOR)
5142         e = XEXP (p, 1), p = XEXP (p, 0);
5143       else
5144         e = XEXP (p, 0), p = XEXP (p, 1);
5145
5146       printf ("  accum |= ");
5147       write_test_expr (e, 3);
5148       printf (";\n");
5149     }
5150   printf ("  accum |= ");
5151   write_test_expr (p, 3);
5152   printf (";\n");
5153 }
5154 \f
5155 /* Utilities to write names in various forms.  */
5156
5157 static void
5158 write_attr_valueq (attr, s)
5159      struct attr_desc *attr;
5160      char *s;
5161 {
5162   if (attr->is_numeric)
5163     {
5164       printf ("%s", s);
5165       /* Make the blockage range values easier to read.  */
5166       if (strlen (s) > 1)
5167         printf (" /* 0x%x */", atoi (s));
5168     }
5169   else
5170     {
5171       write_upcase (attr->name);
5172       printf ("_");
5173       write_upcase (s);
5174     }
5175 }
5176
5177 static void
5178 write_attr_value (attr, value)
5179      struct attr_desc *attr;
5180      rtx value;
5181 {
5182   if (GET_CODE (value) != CONST_STRING)
5183     abort ();
5184
5185   write_attr_valueq (attr, XSTR (value, 0));
5186 }
5187
5188 static void
5189 write_upcase (str)
5190      char *str;
5191 {
5192   while (*str)
5193     if (*str < 'a' || *str > 'z')
5194       printf ("%c", *str++);
5195     else
5196       printf ("%c", *str++ - 'a' + 'A');
5197 }
5198
5199 static void
5200 write_indent (indent)
5201      int indent;
5202 {
5203   for (; indent > 8; indent -= 8)
5204     printf ("\t");
5205
5206   for (; indent; indent--)
5207     printf (" ");
5208 }
5209 \f
5210 /* Write a subroutine that is given an insn that requires a delay slot, a
5211    delay slot ordinal, and a candidate insn.  It returns non-zero if the
5212    candidate can be placed in the specified delay slot of the insn.
5213
5214    We can write as many as three subroutines.  `eligible_for_delay'
5215    handles normal delay slots, `eligible_for_annul_true' indicates that
5216    the specified insn can be annulled if the branch is true, and likewise
5217    for `eligible_for_annul_false'.
5218
5219    KIND is a string distinguishing these three cases ("delay", "annul_true",
5220    or "annul_false").  */
5221
5222 static void
5223 write_eligible_delay (kind)
5224      char *kind;
5225 {
5226   struct delay_desc *delay;
5227   int max_slots;
5228   char str[50];
5229   struct attr_desc *attr;
5230   struct attr_value *av, *common_av;
5231   int i;
5232
5233   /* Compute the maximum number of delay slots required.  We use the delay
5234      ordinal times this number plus one, plus the slot number as an index into
5235      the appropriate predicate to test.  */
5236
5237   for (delay = delays, max_slots = 0; delay; delay = delay->next)
5238     if (XVECLEN (delay->def, 1) / 3 > max_slots)
5239       max_slots = XVECLEN (delay->def, 1) / 3;
5240
5241   /* Write function prelude.  */
5242
5243   printf ("int\n");
5244   printf ("eligible_for_%s (delay_insn, slot, candidate_insn, flags)\n", 
5245            kind);
5246   printf ("     rtx delay_insn;\n");
5247   printf ("     int slot;\n");
5248   printf ("     rtx candidate_insn;\n");
5249   printf ("     int flags;\n");
5250   printf ("{\n");
5251   printf ("  rtx insn;\n");
5252   printf ("\n");
5253   printf ("  if (slot >= %d)\n", max_slots);
5254   printf ("    abort ();\n");
5255   printf ("\n");
5256
5257   /* If more than one delay type, find out which type the delay insn is.  */
5258
5259   if (num_delays > 1)
5260     {
5261       attr = find_attr ("*delay_type", 0);
5262       if (! attr) abort ();
5263       common_av = find_most_used (attr);
5264
5265       printf ("  insn = delay_insn;\n");
5266       printf ("  switch (recog_memoized (insn))\n");
5267       printf ("    {\n");
5268
5269       sprintf (str, " * %d;\n      break;", max_slots);
5270       for (av = attr->first_value; av; av = av->next)
5271         if (av != common_av)
5272           write_attr_case (attr, av, 1, "slot +=", str, 4, true_rtx);
5273
5274       write_attr_case (attr, common_av, 0, "slot +=", str, 4, true_rtx);
5275       printf ("    }\n\n");
5276
5277       /* Ensure matched.  Otherwise, shouldn't have been called.  */
5278       printf ("  if (slot < %d)\n", max_slots);
5279       printf ("    abort ();\n\n");
5280     }
5281
5282   /* If just one type of delay slot, write simple switch.  */
5283   if (num_delays == 1 && max_slots == 1)
5284     {
5285       printf ("  insn = candidate_insn;\n");
5286       printf ("  switch (recog_memoized (insn))\n");
5287       printf ("    {\n");
5288
5289       attr = find_attr ("*delay_1_0", 0);
5290       if (! attr) abort ();
5291       common_av = find_most_used (attr);
5292
5293       for (av = attr->first_value; av; av = av->next)
5294         if (av != common_av)
5295           write_attr_case (attr, av, 1, "return", ";", 4, true_rtx);
5296
5297       write_attr_case (attr, common_av, 0, "return", ";", 4, true_rtx);
5298       printf ("    }\n");
5299     }
5300
5301   else
5302     {
5303       /* Write a nested CASE.  The first indicates which condition we need to
5304          test, and the inner CASE tests the condition.  */
5305       printf ("  insn = candidate_insn;\n");
5306       printf ("  switch (slot)\n");
5307       printf ("    {\n");
5308
5309       for (delay = delays; delay; delay = delay->next)
5310         for (i = 0; i < XVECLEN (delay->def, 1); i += 3)
5311           {
5312             printf ("    case %d:\n",
5313                     (i / 3) + (num_delays == 1 ? 0 : delay->num * max_slots));
5314             printf ("      switch (recog_memoized (insn))\n");
5315             printf ("\t{\n");
5316
5317             sprintf (str, "*%s_%d_%d", kind, delay->num, i / 3);
5318             attr = find_attr (str, 0);
5319             if (! attr) abort ();
5320             common_av = find_most_used (attr);
5321
5322             for (av = attr->first_value; av; av = av->next)
5323               if (av != common_av)
5324                 write_attr_case (attr, av, 1, "return", ";", 8, true_rtx);
5325
5326             write_attr_case (attr, common_av, 0, "return", ";", 8, true_rtx);
5327             printf ("      }\n");
5328           }
5329
5330       printf ("    default:\n");
5331       printf ("      abort ();\n");     
5332       printf ("    }\n");
5333     }
5334
5335   printf ("}\n\n");
5336 }
5337 \f
5338 /* Write routines to compute conflict cost for function units.  Then write a
5339    table describing the available function units.  */
5340
5341 static void
5342 write_function_unit_info ()
5343 {
5344   struct function_unit *unit;
5345   int i;
5346
5347   /* Write out conflict routines for function units.  Don't bother writing
5348      one if there is only one issue delay value.  */
5349
5350   for (unit = units; unit; unit = unit->next)
5351     {
5352       if (unit->needs_blockage_function)
5353         write_complex_function (unit, "blockage", "block");
5354
5355       /* If the minimum and maximum conflict costs are the same, there
5356          is only one value, so we don't need a function.  */
5357       if (! unit->needs_conflict_function)
5358         {
5359           unit->default_cost = make_numeric_value (unit->issue_delay.max);
5360           continue;
5361         }
5362
5363       /* The function first computes the case from the candidate insn.  */
5364       unit->default_cost = make_numeric_value (0);
5365       write_complex_function (unit, "conflict_cost", "cost");
5366     }
5367
5368   /* Now that all functions have been written, write the table describing
5369      the function units.   The name is included for documentation purposes
5370      only.  */
5371
5372   printf ("struct function_unit_desc function_units[] = {\n");
5373
5374   /* Write out the descriptions in numeric order, but don't force that order
5375      on the list.  Doing so increases the runtime of genattrtab.c.  */
5376   for (i = 0; i < num_units; i++)
5377     {
5378       for (unit = units; unit; unit = unit->next)
5379         if (unit->num == i)
5380           break;
5381
5382       printf ("  {\"%s\", %d, %d, %d, %s, %d, %s_unit_ready_cost, ",
5383               unit->name, 1 << unit->num, unit->multiplicity,
5384               unit->simultaneity, XSTR (unit->default_cost, 0),
5385               unit->issue_delay.max, unit->name);
5386
5387       if (unit->needs_conflict_function)
5388         printf ("%s_unit_conflict_cost, ", unit->name);
5389       else
5390         printf ("0, ");
5391
5392       printf ("%d, ", unit->max_blockage);
5393
5394       if (unit->needs_range_function)
5395         printf ("%s_unit_blockage_range, ", unit->name);
5396       else
5397         printf ("0, ");
5398
5399       if (unit->needs_blockage_function)
5400         printf ("%s_unit_blockage", unit->name);
5401       else
5402         printf ("0");
5403
5404       printf ("}, \n");
5405     }
5406
5407   printf ("};\n\n");
5408 }
5409
5410 static void
5411 write_complex_function (unit, name, connection)
5412      struct function_unit *unit;
5413      char *name, *connection;
5414 {
5415   struct attr_desc *case_attr, *attr;
5416   struct attr_value *av, *common_av;
5417   rtx value;
5418   char *str;
5419   int using_case;
5420   int i;
5421
5422   printf ("static int\n");
5423   printf ("%s_unit_%s (executing_insn, candidate_insn)\n",
5424           unit->name, name);
5425   printf ("     rtx executing_insn;\n");
5426   printf ("     rtx candidate_insn;\n");
5427   printf ("{\n");
5428   printf ("  rtx insn;\n");
5429   printf ("  int casenum;\n\n");
5430   printf ("  insn = executing_insn;\n");
5431   printf ("  switch (recog_memoized (insn))\n");
5432   printf ("    {\n");
5433
5434   /* Write the `switch' statement to get the case value.  */
5435   str = (char *) alloca (strlen (unit->name) + strlen (name) + strlen (connection) + 10);
5436   sprintf (str, "*%s_cases", unit->name);
5437   case_attr = find_attr (str, 0);
5438   if (! case_attr) abort ();
5439   common_av = find_most_used (case_attr);
5440
5441   for (av = case_attr->first_value; av; av = av->next)
5442     if (av != common_av)
5443       write_attr_case (case_attr, av, 1,
5444                        "casenum =", ";", 4, unit->condexp);
5445
5446   write_attr_case (case_attr, common_av, 0,
5447                    "casenum =", ";", 4, unit->condexp);
5448   printf ("    }\n\n");
5449
5450   /* Now write an outer switch statement on each case.  Then write
5451      the tests on the executing function within each.  */
5452   printf ("  insn = candidate_insn;\n");
5453   printf ("  switch (casenum)\n");
5454   printf ("    {\n");
5455
5456   for (i = 0; i < unit->num_opclasses; i++)
5457     {
5458       /* Ensure using this case.  */
5459       using_case = 0;
5460       for (av = case_attr->first_value; av; av = av->next)
5461         if (av->num_insns
5462             && contained_in_p (make_numeric_value (i), av->value))
5463           using_case = 1;
5464
5465       if (! using_case)
5466         continue;
5467
5468       printf ("    case %d:\n", i);
5469       sprintf (str, "*%s_%s_%d", unit->name, connection, i);
5470       attr = find_attr (str, 0);
5471       if (! attr) abort ();
5472
5473       /* If single value, just write it.  */
5474       value = find_single_value (attr);
5475       if (value)
5476         write_attr_set (attr, 6, value, "return", ";\n", true_rtx, -2, -2);
5477       else
5478         {
5479           common_av = find_most_used (attr);
5480           printf ("      switch (recog_memoized (insn))\n");
5481           printf ("\t{\n");
5482
5483           for (av = attr->first_value; av; av = av->next)
5484             if (av != common_av)
5485               write_attr_case (attr, av, 1,
5486                                "return", ";", 8, unit->condexp);
5487
5488           write_attr_case (attr, common_av, 0,
5489                            "return", ";", 8, unit->condexp);
5490           printf ("      }\n\n");
5491         }
5492     }
5493
5494   printf ("    }\n}\n\n");
5495 }
5496 \f
5497 /* This page contains miscellaneous utility routines.  */
5498
5499 /* Given a string, return the number of comma-separated elements in it.
5500    Return 0 for the null string.  */
5501
5502 static int
5503 n_comma_elts (s)
5504      char *s;
5505 {
5506   int n;
5507
5508   if (*s == '\0')
5509     return 0;
5510
5511   for (n = 1; *s; s++)
5512     if (*s == ',')
5513       n++;
5514
5515   return n;
5516 }
5517
5518 /* Given a pointer to a (char *), return a malloc'ed string containing the
5519    next comma-separated element.  Advance the pointer to after the string
5520    scanned, or the end-of-string.  Return NULL if at end of string.  */
5521
5522 static char *
5523 next_comma_elt (pstr)
5524      char **pstr;
5525 {
5526   char *out_str;
5527   char *p;
5528
5529   if (**pstr == '\0')
5530     return NULL;
5531
5532   /* Find end of string to compute length.  */
5533   for (p = *pstr; *p != ',' && *p != '\0'; p++)
5534     ;
5535
5536   out_str = attr_string (*pstr, p - *pstr);
5537   *pstr = p;
5538
5539   if (**pstr == ',')
5540     (*pstr)++;
5541
5542   return out_str;
5543 }
5544
5545 /* Return a `struct attr_desc' pointer for a given named attribute.  If CREATE
5546    is non-zero, build a new attribute, if one does not exist.  */
5547
5548 static struct attr_desc *
5549 find_attr (name, create)
5550      char *name;
5551      int create;
5552 {
5553   struct attr_desc *attr;
5554   int index;
5555
5556   /* Before we resort to using `strcmp', see if the string address matches
5557      anywhere.  In most cases, it should have been canonicalized to do so.  */
5558   if (name == alternative_name)
5559     return NULL;
5560
5561   index = name[0] & (MAX_ATTRS_INDEX - 1);
5562   for (attr = attrs[index]; attr; attr = attr->next)
5563     if (name == attr->name)
5564       return attr;
5565
5566   /* Otherwise, do it the slow way.  */
5567   for (attr = attrs[index]; attr; attr = attr->next)
5568     if (name[0] == attr->name[0] && ! strcmp (name, attr->name))
5569       return attr;
5570
5571   if (! create)
5572     return NULL;
5573
5574   attr = (struct attr_desc *) oballoc (sizeof (struct attr_desc));
5575   attr->name = attr_string (name, strlen (name));
5576   attr->first_value = attr->default_val = NULL;
5577   attr->is_numeric = attr->negative_ok = attr->is_const = attr->is_special = 0;
5578   attr->next = attrs[index];
5579   attrs[index] = attr;
5580
5581   return attr;
5582 }
5583
5584 /* Create internal attribute with the given default value.  */
5585
5586 static void
5587 make_internal_attr (name, value, special)
5588      char *name;
5589      rtx value;
5590      int special;
5591 {
5592   struct attr_desc *attr;
5593
5594   attr = find_attr (name, 1);
5595   if (attr->default_val)
5596     abort ();
5597
5598   attr->is_numeric = 1;
5599   attr->is_const = 0;
5600   attr->is_special = (special & 1) != 0;
5601   attr->negative_ok = (special & 2) != 0;
5602   attr->unsigned_p = (special & 4) != 0;
5603   attr->default_val = get_attr_value (value, attr, -2);
5604 }
5605
5606 /* Find the most used value of an attribute.  */
5607
5608 static struct attr_value *
5609 find_most_used (attr)
5610      struct attr_desc *attr;
5611 {
5612   struct attr_value *av;
5613   struct attr_value *most_used;
5614   int nuses;
5615
5616   most_used = NULL;
5617   nuses = -1;
5618
5619   for (av = attr->first_value; av; av = av->next)
5620     if (av->num_insns > nuses)
5621       nuses = av->num_insns, most_used = av;
5622
5623   return most_used;
5624 }
5625
5626 /* If an attribute only has a single value used, return it.  Otherwise
5627    return NULL.  */
5628
5629 static rtx
5630 find_single_value (attr)
5631      struct attr_desc *attr;
5632 {
5633   struct attr_value *av;
5634   rtx unique_value;
5635
5636   unique_value = NULL;
5637   for (av = attr->first_value; av; av = av->next)
5638     if (av->num_insns)
5639       {
5640         if (unique_value)
5641           return NULL;
5642         else
5643           unique_value = av->value;
5644       }
5645
5646   return unique_value;
5647 }
5648
5649 /* Return (attr_value "n") */
5650
5651 static rtx
5652 make_numeric_value (n)
5653      int n;
5654 {
5655   static rtx int_values[20];
5656   rtx exp;
5657   char *p;
5658
5659   if (n < 0)
5660     abort ();
5661
5662   if (n < 20 && int_values[n])
5663     return int_values[n];
5664
5665   p = attr_printf (MAX_DIGITS, "%d", n);
5666   exp = attr_rtx (CONST_STRING, p);
5667
5668   if (n < 20)
5669     int_values[n] = exp;
5670
5671   return exp;
5672 }
5673 \f
5674 static void
5675 extend_range (range, min, max)
5676      struct range *range;
5677      int min;
5678      int max;
5679 {
5680   if (range->min > min) range->min = min;
5681   if (range->max < max) range->max = max;
5682 }
5683
5684 char *
5685 xrealloc (ptr, size)
5686      char *ptr;
5687      unsigned size;
5688 {
5689   char *result = (char *) realloc (ptr, size);
5690   if (!result)
5691     fatal ("virtual memory exhausted");
5692   return result;
5693 }
5694
5695 char *
5696 xmalloc (size)
5697      unsigned size;
5698 {
5699   register char *val = (char *) malloc (size);
5700
5701   if (val == 0)
5702     fatal ("virtual memory exhausted");
5703   return val;
5704 }
5705
5706 static rtx
5707 copy_rtx_unchanging (orig)
5708      register rtx orig;
5709 {
5710 #if 0
5711   register rtx copy;
5712   register RTX_CODE code;
5713 #endif
5714
5715   if (RTX_UNCHANGING_P (orig) || MEM_IN_STRUCT_P (orig))
5716     return orig;
5717
5718   MEM_IN_STRUCT_P (orig) = 1;
5719   return orig;
5720
5721 #if 0
5722   code = GET_CODE (orig);
5723   switch (code)
5724     {
5725     case CONST_INT:
5726     case CONST_DOUBLE:
5727     case SYMBOL_REF:
5728     case CODE_LABEL:
5729       return orig;
5730       
5731     default:
5732       break;
5733     }
5734
5735   copy = rtx_alloc (code);
5736   PUT_MODE (copy, GET_MODE (orig));
5737   RTX_UNCHANGING_P (copy) = 1;
5738   
5739   bcopy ((char *) &XEXP (orig, 0), (char *) &XEXP (copy, 0),
5740          GET_RTX_LENGTH (GET_CODE (copy)) * sizeof (rtx));
5741   return copy;
5742 #endif
5743 }
5744
5745 static void
5746 fatal (s, a1, a2)
5747      char *s;
5748      char *a1, *a2;
5749 {
5750   fprintf (stderr, "genattrtab: ");
5751   fprintf (stderr, s, a1, a2);
5752   fprintf (stderr, "\n");
5753   exit (FATAL_EXIT_CODE);
5754 }
5755
5756 /* More 'friendly' abort that prints the line and file.
5757    config.h can #define abort fancy_abort if you like that sort of thing.  */
5758
5759 void
5760 fancy_abort ()
5761 {
5762   fatal ("Internal gcc abort.");
5763 }
5764
5765 /* Determine if an insn has a constant number of delay slots, i.e., the
5766    number of delay slots is not a function of the length of the insn.  */
5767
5768 void
5769 write_const_num_delay_slots ()
5770 {
5771   struct attr_desc *attr = find_attr ("*num_delay_slots", 0);
5772   struct attr_value *av;
5773   struct insn_ent *ie;
5774
5775   if (attr)
5776     {
5777       printf ("int\nconst_num_delay_slots (insn)\n");
5778       printf ("     rtx insn;\n");
5779       printf ("{\n");
5780       printf ("  switch (recog_memoized (insn))\n");
5781       printf ("    {\n");
5782
5783       for (av = attr->first_value; av; av = av->next)
5784         {
5785           length_used = 0;
5786           walk_attr_value (av->value);
5787           if (length_used)
5788             {
5789               for (ie = av->first_insn; ie; ie = ie->next)
5790               if (ie->insn_code != -1)
5791                 printf ("    case %d:\n", ie->insn_code);
5792               printf ("      return 0;\n");
5793             }
5794         }
5795
5796       printf ("    default:\n");
5797       printf ("      return 1;\n");
5798       printf ("    }\n}\n");
5799     }
5800 }
5801
5802 \f
5803 int
5804 main (argc, argv)
5805      int argc;
5806      char **argv;
5807 {
5808   rtx desc;
5809   FILE *infile;
5810   register int c;
5811   struct attr_desc *attr;
5812   struct insn_def *id;
5813   rtx tem;
5814   int i;
5815
5816 #if defined (RLIMIT_STACK) && defined (HAVE_GETRLIMIT) && defined (HAVE_SETRLIMIT)
5817   /* Get rid of any avoidable limit on stack size.  */
5818   {
5819     struct rlimit rlim;
5820
5821     /* Set the stack limit huge so that alloca does not fail.  */
5822     getrlimit (RLIMIT_STACK, &rlim);
5823     rlim.rlim_cur = rlim.rlim_max;
5824     setrlimit (RLIMIT_STACK, &rlim);
5825   }
5826 #endif
5827
5828   obstack_init (rtl_obstack);
5829   obstack_init (hash_obstack);
5830   obstack_init (temp_obstack);
5831
5832   if (argc <= 1)
5833     fatal ("No input file name.");
5834
5835   infile = fopen (argv[1], "r");
5836   if (infile == 0)
5837     {
5838       perror (argv[1]);
5839       exit (FATAL_EXIT_CODE);
5840     }
5841
5842   init_rtl ();
5843
5844   /* Set up true and false rtx's */
5845   true_rtx = rtx_alloc (CONST_INT);
5846   XWINT (true_rtx, 0) = 1;
5847   false_rtx = rtx_alloc (CONST_INT);
5848   XWINT (false_rtx, 0) = 0;
5849   RTX_UNCHANGING_P (true_rtx) = RTX_UNCHANGING_P (false_rtx) = 1;
5850   RTX_INTEGRATED_P (true_rtx) = RTX_INTEGRATED_P (false_rtx) = 1;
5851
5852   alternative_name = attr_string ("alternative", strlen ("alternative"));
5853
5854   printf ("/* Generated automatically by the program `genattrtab'\n\
5855 from the machine description file `md'.  */\n\n");
5856
5857   /* Read the machine description.  */
5858
5859   while (1)
5860     {
5861       c = read_skip_spaces (infile);
5862       if (c == EOF)
5863         break;
5864       ungetc (c, infile);
5865
5866       desc = read_rtx (infile);
5867       if (GET_CODE (desc) == DEFINE_INSN
5868           || GET_CODE (desc) == DEFINE_PEEPHOLE
5869           || GET_CODE (desc) == DEFINE_ASM_ATTRIBUTES)
5870         gen_insn (desc);
5871
5872       else if (GET_CODE (desc) == DEFINE_EXPAND)
5873         insn_code_number++, insn_index_number++;
5874
5875       else if (GET_CODE (desc) == DEFINE_SPLIT)
5876         insn_code_number++, insn_index_number++;
5877
5878       else if (GET_CODE (desc) == DEFINE_ATTR)
5879         {
5880           gen_attr (desc);
5881           insn_index_number++;
5882         }
5883
5884       else if (GET_CODE (desc) == DEFINE_DELAY)
5885         {
5886           gen_delay (desc);
5887           insn_index_number++;
5888         }
5889
5890       else if (GET_CODE (desc) == DEFINE_FUNCTION_UNIT)
5891         {
5892           gen_unit (desc);
5893           insn_index_number++;
5894         }
5895     }
5896
5897   /* If we didn't have a DEFINE_ASM_ATTRIBUTES, make a null one.  */
5898   if (! got_define_asm_attributes)
5899     {
5900       tem = rtx_alloc (DEFINE_ASM_ATTRIBUTES);
5901       XVEC (tem, 0) = rtvec_alloc (0);
5902       gen_insn (tem);
5903     }
5904
5905   /* Expand DEFINE_DELAY information into new attribute.  */
5906   if (num_delays)
5907     expand_delays ();
5908
5909   /* Expand DEFINE_FUNCTION_UNIT information into new attributes.  */
5910   if (num_units)
5911     expand_units ();
5912
5913   printf ("#include \"config.h\"\n");
5914   printf ("#include <stdio.h>\n");
5915   printf ("#include \"rtl.h\"\n");
5916   printf ("#include \"insn-config.h\"\n");
5917   printf ("#include \"recog.h\"\n");
5918   printf ("#include \"regs.h\"\n");
5919   printf ("#include \"real.h\"\n");
5920   printf ("#include \"output.h\"\n");
5921   printf ("#include \"insn-attr.h\"\n");
5922   printf ("\n");  
5923   printf ("#define operands recog_operand\n\n");
5924
5925   /* Make `insn_alternatives'.  */
5926   insn_alternatives = (int *) oballoc (insn_code_number * sizeof (int));
5927   for (id = defs; id; id = id->next)
5928     if (id->insn_code >= 0)
5929       insn_alternatives[id->insn_code] = (1 << id->num_alternatives) - 1;
5930
5931   /* Make `insn_n_alternatives'.  */
5932   insn_n_alternatives = (int *) oballoc (insn_code_number * sizeof (int));
5933   for (id = defs; id; id = id->next)
5934     if (id->insn_code >= 0)
5935       insn_n_alternatives[id->insn_code] = id->num_alternatives;
5936
5937   /* Prepare to write out attribute subroutines by checking everything stored
5938      away and building the attribute cases.  */
5939
5940   check_defs ();
5941   for (i = 0; i < MAX_ATTRS_INDEX; i++)
5942     for (attr = attrs[i]; attr; attr = attr->next)
5943       {
5944         attr->default_val->value
5945           = check_attr_value (attr->default_val->value, attr);
5946         fill_attr (attr);
5947       }
5948
5949   /* Construct extra attributes for `length'.  */
5950   make_length_attrs ();
5951
5952   /* Perform any possible optimizations to speed up compilation.  */
5953   optimize_attrs ();
5954
5955   /* Now write out all the `gen_attr_...' routines.  Do these before the
5956      special routines (specifically before write_function_unit_info), so
5957      that they get defined before they are used.  */
5958
5959   for (i = 0; i < MAX_ATTRS_INDEX; i++)
5960     for (attr = attrs[i]; attr; attr = attr->next)
5961       {
5962         if (! attr->is_special && ! attr->is_const)
5963           write_attr_get (attr);
5964       }
5965
5966   /* Write out delay eligibility information, if DEFINE_DELAY present.
5967      (The function to compute the number of delay slots will be written
5968      below.)  */
5969   if (num_delays)
5970     {
5971       write_eligible_delay ("delay");
5972       if (have_annul_true)
5973         write_eligible_delay ("annul_true");
5974       if (have_annul_false)
5975         write_eligible_delay ("annul_false");
5976     }
5977
5978   /* Write out information about function units.  */
5979   if (num_units)
5980     write_function_unit_info ();
5981
5982   /* Write out constant delay slot info */
5983   write_const_num_delay_slots ();
5984
5985   fflush (stdout);
5986   exit (ferror (stdout) != 0 ? FATAL_EXIT_CODE : SUCCESS_EXIT_CODE);
5987   /* NOTREACHED */
5988   return 0;
5989 }