gcc/
[official-gcc.git] / gcc / genattrtab.c
blob60aa59c49246875926f388af98035b8e0d63a8a1
1 /* Generate code from machine description to compute values of attributes.
2 Copyright (C) 1991, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
3 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2012
4 Free Software Foundation, Inc.
5 Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu)
7 This file is part of GCC.
9 GCC is free software; you can redistribute it and/or modify it under
10 the terms of the GNU General Public License as published by the Free
11 Software Foundation; either version 3, or (at your option) any later
12 version.
14 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
15 WARRANTY; without even the implied warranty of MERCHANTABILITY or
16 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
17 for more details.
19 You should have received a copy of the GNU General Public License
20 along with GCC; see the file COPYING3. If not see
21 <http://www.gnu.org/licenses/>. */
23 /* This program handles insn attributes and the DEFINE_DELAY and
24 DEFINE_INSN_RESERVATION definitions.
26 It produces a series of functions named `get_attr_...', one for each insn
27 attribute. Each of these is given the rtx for an insn and returns a member
28 of the enum for the attribute.
30 These subroutines have the form of a `switch' on the INSN_CODE (via
31 `recog_memoized'). Each case either returns a constant attribute value
32 or a value that depends on tests on other attributes, the form of
33 operands, or some random C expression (encoded with a SYMBOL_REF
34 expression).
36 If the attribute `alternative', or a random C expression is present,
37 `constrain_operands' is called. If either of these cases of a reference to
38 an operand is found, `extract_insn' is called.
40 The special attribute `length' is also recognized. For this operand,
41 expressions involving the address of an operand or the current insn,
42 (address (pc)), are valid. In this case, an initial pass is made to
43 set all lengths that do not depend on address. Those that do are set to
44 the maximum length. Then each insn that depends on an address is checked
45 and possibly has its length changed. The process repeats until no further
46 changed are made. The resulting lengths are saved for use by
47 `get_attr_length'.
49 A special form of DEFINE_ATTR, where the expression for default value is a
50 CONST expression, indicates an attribute that is constant for a given run
51 of the compiler. The subroutine generated for these attributes has no
52 parameters as it does not depend on any particular insn. Constant
53 attributes are typically used to specify which variety of processor is
54 used.
56 Internal attributes are defined to handle DEFINE_DELAY and
57 DEFINE_INSN_RESERVATION. Special routines are output for these cases.
59 This program works by keeping a list of possible values for each attribute.
60 These include the basic attribute choices, default values for attribute, and
61 all derived quantities.
63 As the description file is read, the definition for each insn is saved in a
64 `struct insn_def'. When the file reading is complete, a `struct insn_ent'
65 is created for each insn and chained to the corresponding attribute value,
66 either that specified, or the default.
68 An optimization phase is then run. This simplifies expressions for each
69 insn. EQ_ATTR tests are resolved, whenever possible, to a test that
70 indicates when the attribute has the specified value for the insn. This
71 avoids recursive calls during compilation.
73 The strategy used when processing DEFINE_DELAY definitions is to create
74 arbitrarily complex expressions and have the optimization simplify them.
76 Once optimization is complete, any required routines and definitions
77 will be written.
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).
87 We use the flags in an RTX as follows:
88 `unchanging' (ATTR_IND_SIMPLIFIED_P): This rtx is fully simplified
89 independent of the insn code.
90 `in_struct' (ATTR_CURR_SIMPLIFIED_P): This rtx is fully simplified
91 for the insn code currently being processed (see optimize_attrs).
92 `return_val' (ATTR_PERMANENT_P): This rtx is permanent and unique
93 (see attr_rtx). */
95 #define ATTR_IND_SIMPLIFIED_P(RTX) (RTX_FLAG((RTX), unchanging))
96 #define ATTR_CURR_SIMPLIFIED_P(RTX) (RTX_FLAG((RTX), in_struct))
97 #define ATTR_PERMANENT_P(RTX) (RTX_FLAG((RTX), return_val))
99 #if 0
100 #define strcmp_check(S1, S2) ((S1) == (S2) \
101 ? 0 \
102 : (gcc_assert (strcmp ((S1), (S2))), 1))
103 #else
104 #define strcmp_check(S1, S2) ((S1) != (S2))
105 #endif
107 #include "bconfig.h"
108 #include "system.h"
109 #include "coretypes.h"
110 #include "tm.h"
111 #include "rtl.h"
112 #include "obstack.h"
113 #include "errors.h"
114 #include "read-md.h"
115 #include "gensupport.h"
116 #include "vecprim.h"
117 #include "fnmatch.h"
119 /* Flags for make_internal_attr's `special' parameter. */
120 #define ATTR_NONE 0
121 #define ATTR_SPECIAL (1 << 0)
123 static struct obstack obstack1, obstack2;
124 static struct obstack *hash_obstack = &obstack1;
125 static struct obstack *temp_obstack = &obstack2;
127 /* enough space to reserve for printing out ints */
128 #define MAX_DIGITS (HOST_BITS_PER_INT * 3 / 10 + 3)
130 /* Define structures used to record attributes and values. */
132 /* As each DEFINE_INSN, DEFINE_PEEPHOLE, or DEFINE_ASM_ATTRIBUTES is
133 encountered, we store all the relevant information into a
134 `struct insn_def'. This is done to allow attribute definitions to occur
135 anywhere in the file. */
137 struct insn_def
139 struct insn_def *next; /* Next insn in chain. */
140 rtx def; /* The DEFINE_... */
141 int insn_code; /* Instruction number. */
142 int insn_index; /* Expression number in file, for errors. */
143 int lineno; /* Line number. */
144 int num_alternatives; /* Number of alternatives. */
145 int vec_idx; /* Index of attribute vector in `def'. */
148 /* Once everything has been read in, we store in each attribute value a list
149 of insn codes that have that value. Here is the structure used for the
150 list. */
152 struct insn_ent
154 struct insn_ent *next; /* Next in chain. */
155 struct insn_def *def; /* Instruction definition. */
158 /* Each value of an attribute (either constant or computed) is assigned a
159 structure which is used as the listhead of the insns that have that
160 value. */
162 struct attr_value
164 rtx value; /* Value of attribute. */
165 struct attr_value *next; /* Next attribute value in chain. */
166 struct insn_ent *first_insn; /* First insn with this value. */
167 int num_insns; /* Number of insns with this value. */
168 int has_asm_insn; /* True if this value used for `asm' insns */
171 /* Structure for each attribute. */
173 struct attr_desc
175 char *name; /* Name of attribute. */
176 const char *enum_name; /* Enum name for DEFINE_ENUM_NAME. */
177 struct attr_desc *next; /* Next attribute. */
178 struct attr_value *first_value; /* First value of this attribute. */
179 struct attr_value *default_val; /* Default value for this attribute. */
180 int lineno : 24; /* Line number. */
181 unsigned is_numeric : 1; /* Values of this attribute are numeric. */
182 unsigned is_const : 1; /* Attribute value constant for each run. */
183 unsigned is_special : 1; /* Don't call `write_attr_set'. */
186 /* Structure for each DEFINE_DELAY. */
188 struct delay_desc
190 rtx def; /* DEFINE_DELAY expression. */
191 struct delay_desc *next; /* Next DEFINE_DELAY. */
192 int num; /* Number of DEFINE_DELAY, starting at 1. */
193 int lineno; /* Line number. */
196 struct attr_value_list
198 struct attr_value *av;
199 struct insn_ent *ie;
200 struct attr_desc *attr;
201 struct attr_value_list *next;
204 /* Listheads of above structures. */
206 /* This one is indexed by the first character of the attribute name. */
207 #define MAX_ATTRS_INDEX 256
208 static struct attr_desc *attrs[MAX_ATTRS_INDEX];
209 static struct insn_def *defs;
210 static struct delay_desc *delays;
211 struct attr_value_list **insn_code_values;
213 /* Other variables. */
215 static int insn_code_number;
216 static int insn_index_number;
217 static int got_define_asm_attributes;
218 static int must_extract;
219 static int must_constrain;
220 static int address_used;
221 static int length_used;
222 static int num_delays;
223 static int have_annul_true, have_annul_false;
224 static int num_insn_ents;
226 /* Stores, for each insn code, the number of constraint alternatives. */
228 static int *insn_n_alternatives;
230 /* Stores, for each insn code, a bitmap that has bits on for each possible
231 alternative. */
233 static int *insn_alternatives;
235 /* Used to simplify expressions. */
237 static rtx true_rtx, false_rtx;
239 /* Used to reduce calls to `strcmp' */
241 static const char *alternative_name;
242 static const char *length_str;
243 static const char *delay_type_str;
244 static const char *delay_1_0_str;
245 static const char *num_delay_slots_str;
247 /* Simplify an expression. Only call the routine if there is something to
248 simplify. */
249 #define SIMPLIFY_TEST_EXP(EXP,INSN_CODE,INSN_INDEX) \
250 (ATTR_IND_SIMPLIFIED_P (EXP) || ATTR_CURR_SIMPLIFIED_P (EXP) ? (EXP) \
251 : simplify_test_exp (EXP, INSN_CODE, INSN_INDEX))
253 #define DEF_ATTR_STRING(S) (attr_string ((S), strlen (S)))
255 /* Forward declarations of functions used before their definitions, only. */
256 static char *attr_string (const char *, int);
257 static char *attr_printf (unsigned int, const char *, ...)
258 ATTRIBUTE_PRINTF_2;
259 static rtx make_numeric_value (int);
260 static struct attr_desc *find_attr (const char **, int);
261 static rtx mk_attr_alt (int);
262 static char *next_comma_elt (const char **);
263 static rtx insert_right_side (enum rtx_code, rtx, rtx, int, int);
264 static rtx copy_boolean (rtx);
265 static int compares_alternatives_p (rtx);
266 static void make_internal_attr (const char *, rtx, int);
267 static void insert_insn_ent (struct attr_value *, struct insn_ent *);
268 static void walk_attr_value (rtx);
269 static int max_attr_value (rtx, int*);
270 static int min_attr_value (rtx, int*);
271 static int or_attr_value (rtx, int*);
272 static rtx simplify_test_exp (rtx, int, int);
273 static rtx simplify_test_exp_in_temp (rtx, int, int);
274 static rtx copy_rtx_unchanging (rtx);
275 static bool attr_alt_subset_p (rtx, rtx);
276 static bool attr_alt_subset_of_compl_p (rtx, rtx);
277 static void clear_struct_flag (rtx);
278 static void write_attr_valueq (FILE *, struct attr_desc *, const char *);
279 static struct attr_value *find_most_used (struct attr_desc *);
280 static void write_attr_set (FILE *, struct attr_desc *, int, rtx,
281 const char *, const char *, rtx,
282 int, int, unsigned int);
283 static void write_attr_case (FILE *, struct attr_desc *,
284 struct attr_value *,
285 int, const char *, const char *, int, rtx);
286 static void write_attr_value (FILE *, struct attr_desc *, rtx);
287 static void write_upcase (FILE *, const char *);
288 static void write_indent (FILE *, int);
289 static rtx identity_fn (rtx);
290 static rtx zero_fn (rtx);
291 static rtx one_fn (rtx);
292 static rtx max_fn (rtx);
293 static rtx min_fn (rtx);
295 #define oballoc(T) XOBNEW (hash_obstack, T)
296 #define oballocvec(T, N) XOBNEWVEC (hash_obstack, T, (N))
298 /* This gen* file is unique, in that it writes out multiple files.
300 Before GCC 4.8, insn-attrtab.c was written out containing many large
301 functions and tables. This made insn-attrtab.c _the_ bottle-neck in
302 a parallel build, and even made it impossible to build GCC on machines
303 with relatively small RAM space (PR other/29442). Therefore, the
304 atrribute functions/tables are now written out to three separate
305 files: all "*insn_default_latency" functions go to LATENCY_FILE_NAME,
306 all "*internal_dfa_insn_code" functions go to DFA_FILE_NAME, and the
307 rest goes to ATTR_FILE_NAME. */
309 static const char *attr_file_name = NULL;
310 static const char *dfa_file_name = NULL;
311 static const char *latency_file_name = NULL;
313 static FILE *attr_file, *dfa_file, *latency_file;
315 /* Hash table for sharing RTL and strings. */
317 /* Each hash table slot is a bucket containing a chain of these structures.
318 Strings are given negative hash codes; RTL expressions are given positive
319 hash codes. */
321 struct attr_hash
323 struct attr_hash *next; /* Next structure in the bucket. */
324 int hashcode; /* Hash code of this rtx or string. */
325 union
327 char *str; /* The string (negative hash codes) */
328 rtx rtl; /* or the RTL recorded here. */
329 } u;
332 /* Now here is the hash table. When recording an RTL, it is added to
333 the slot whose index is the hash code mod the table size. Note
334 that the hash table is used for several kinds of RTL (see attr_rtx)
335 and for strings. While all these live in the same table, they are
336 completely independent, and the hash code is computed differently
337 for each. */
339 #define RTL_HASH_SIZE 4093
340 static struct attr_hash *attr_hash_table[RTL_HASH_SIZE];
342 /* Here is how primitive or already-shared RTL's hash
343 codes are made. */
344 #define RTL_HASH(RTL) ((intptr_t) (RTL) & 0777777)
346 /* Add an entry to the hash table for RTL with hash code HASHCODE. */
348 static void
349 attr_hash_add_rtx (int hashcode, rtx rtl)
351 struct attr_hash *h;
353 h = XOBNEW (hash_obstack, struct attr_hash);
354 h->hashcode = hashcode;
355 h->u.rtl = rtl;
356 h->next = attr_hash_table[hashcode % RTL_HASH_SIZE];
357 attr_hash_table[hashcode % RTL_HASH_SIZE] = h;
360 /* Add an entry to the hash table for STRING with hash code HASHCODE. */
362 static void
363 attr_hash_add_string (int hashcode, char *str)
365 struct attr_hash *h;
367 h = XOBNEW (hash_obstack, struct attr_hash);
368 h->hashcode = -hashcode;
369 h->u.str = str;
370 h->next = attr_hash_table[hashcode % RTL_HASH_SIZE];
371 attr_hash_table[hashcode % RTL_HASH_SIZE] = h;
374 /* Generate an RTL expression, but avoid duplicates.
375 Set the ATTR_PERMANENT_P flag for these permanent objects.
377 In some cases we cannot uniquify; then we return an ordinary
378 impermanent rtx with ATTR_PERMANENT_P clear.
380 Args are as follows:
382 rtx attr_rtx (code, [element1, ..., elementn]) */
384 static rtx
385 attr_rtx_1 (enum rtx_code code, va_list p)
387 rtx rt_val = NULL_RTX;/* RTX to return to caller... */
388 int hashcode;
389 struct attr_hash *h;
390 struct obstack *old_obstack = rtl_obstack;
392 /* For each of several cases, search the hash table for an existing entry.
393 Use that entry if one is found; otherwise create a new RTL and add it
394 to the table. */
396 if (GET_RTX_CLASS (code) == RTX_UNARY)
398 rtx arg0 = va_arg (p, rtx);
400 /* A permanent object cannot point to impermanent ones. */
401 if (! ATTR_PERMANENT_P (arg0))
403 rt_val = rtx_alloc (code);
404 XEXP (rt_val, 0) = arg0;
405 return rt_val;
408 hashcode = ((HOST_WIDE_INT) code + RTL_HASH (arg0));
409 for (h = attr_hash_table[hashcode % RTL_HASH_SIZE]; h; h = h->next)
410 if (h->hashcode == hashcode
411 && GET_CODE (h->u.rtl) == code
412 && XEXP (h->u.rtl, 0) == arg0)
413 return h->u.rtl;
415 if (h == 0)
417 rtl_obstack = hash_obstack;
418 rt_val = rtx_alloc (code);
419 XEXP (rt_val, 0) = arg0;
422 else if (GET_RTX_CLASS (code) == RTX_BIN_ARITH
423 || GET_RTX_CLASS (code) == RTX_COMM_ARITH
424 || GET_RTX_CLASS (code) == RTX_COMPARE
425 || GET_RTX_CLASS (code) == RTX_COMM_COMPARE)
427 rtx arg0 = va_arg (p, rtx);
428 rtx arg1 = va_arg (p, rtx);
430 /* A permanent object cannot point to impermanent ones. */
431 if (! ATTR_PERMANENT_P (arg0) || ! ATTR_PERMANENT_P (arg1))
433 rt_val = rtx_alloc (code);
434 XEXP (rt_val, 0) = arg0;
435 XEXP (rt_val, 1) = arg1;
436 return rt_val;
439 hashcode = ((HOST_WIDE_INT) code + RTL_HASH (arg0) + RTL_HASH (arg1));
440 for (h = attr_hash_table[hashcode % RTL_HASH_SIZE]; h; h = h->next)
441 if (h->hashcode == hashcode
442 && GET_CODE (h->u.rtl) == code
443 && XEXP (h->u.rtl, 0) == arg0
444 && XEXP (h->u.rtl, 1) == arg1)
445 return h->u.rtl;
447 if (h == 0)
449 rtl_obstack = hash_obstack;
450 rt_val = rtx_alloc (code);
451 XEXP (rt_val, 0) = arg0;
452 XEXP (rt_val, 1) = arg1;
455 else if (code == SYMBOL_REF
456 || (GET_RTX_LENGTH (code) == 1
457 && GET_RTX_FORMAT (code)[0] == 's'))
459 char *arg0 = va_arg (p, char *);
461 arg0 = DEF_ATTR_STRING (arg0);
463 hashcode = ((HOST_WIDE_INT) code + RTL_HASH (arg0));
464 for (h = attr_hash_table[hashcode % RTL_HASH_SIZE]; h; h = h->next)
465 if (h->hashcode == hashcode
466 && GET_CODE (h->u.rtl) == code
467 && XSTR (h->u.rtl, 0) == arg0)
468 return h->u.rtl;
470 if (h == 0)
472 rtl_obstack = hash_obstack;
473 rt_val = rtx_alloc (code);
474 XSTR (rt_val, 0) = arg0;
475 if (code == SYMBOL_REF)
477 X0EXP (rt_val, 1) = NULL_RTX;
478 X0EXP (rt_val, 2) = NULL_RTX;
482 else if (GET_RTX_LENGTH (code) == 2
483 && GET_RTX_FORMAT (code)[0] == 's'
484 && GET_RTX_FORMAT (code)[1] == 's')
486 char *arg0 = va_arg (p, char *);
487 char *arg1 = va_arg (p, char *);
489 hashcode = ((HOST_WIDE_INT) code + RTL_HASH (arg0) + RTL_HASH (arg1));
490 for (h = attr_hash_table[hashcode % RTL_HASH_SIZE]; h; h = h->next)
491 if (h->hashcode == hashcode
492 && GET_CODE (h->u.rtl) == code
493 && XSTR (h->u.rtl, 0) == arg0
494 && XSTR (h->u.rtl, 1) == arg1)
495 return h->u.rtl;
497 if (h == 0)
499 rtl_obstack = hash_obstack;
500 rt_val = rtx_alloc (code);
501 XSTR (rt_val, 0) = arg0;
502 XSTR (rt_val, 1) = arg1;
505 else if (code == CONST_INT)
507 HOST_WIDE_INT arg0 = va_arg (p, HOST_WIDE_INT);
508 if (arg0 == 0)
509 return false_rtx;
510 else if (arg0 == 1)
511 return true_rtx;
512 else
513 goto nohash;
515 else
517 int i; /* Array indices... */
518 const char *fmt; /* Current rtx's format... */
519 nohash:
520 rt_val = rtx_alloc (code); /* Allocate the storage space. */
522 fmt = GET_RTX_FORMAT (code); /* Find the right format... */
523 for (i = 0; i < GET_RTX_LENGTH (code); i++)
525 switch (*fmt++)
527 case '0': /* Unused field. */
528 break;
530 case 'i': /* An integer? */
531 XINT (rt_val, i) = va_arg (p, int);
532 break;
534 case 'w': /* A wide integer? */
535 XWINT (rt_val, i) = va_arg (p, HOST_WIDE_INT);
536 break;
538 case 's': /* A string? */
539 XSTR (rt_val, i) = va_arg (p, char *);
540 break;
542 case 'e': /* An expression? */
543 case 'u': /* An insn? Same except when printing. */
544 XEXP (rt_val, i) = va_arg (p, rtx);
545 break;
547 case 'E': /* An RTX vector? */
548 XVEC (rt_val, i) = va_arg (p, rtvec);
549 break;
551 default:
552 gcc_unreachable ();
555 return rt_val;
558 rtl_obstack = old_obstack;
559 attr_hash_add_rtx (hashcode, rt_val);
560 ATTR_PERMANENT_P (rt_val) = 1;
561 return rt_val;
564 static rtx
565 attr_rtx (enum rtx_code code, ...)
567 rtx result;
568 va_list p;
570 va_start (p, code);
571 result = attr_rtx_1 (code, p);
572 va_end (p);
573 return result;
576 /* Create a new string printed with the printf line arguments into a space
577 of at most LEN bytes:
579 rtx attr_printf (len, format, [arg1, ..., argn]) */
581 static char *
582 attr_printf (unsigned int len, const char *fmt, ...)
584 char str[256];
585 va_list p;
587 va_start (p, fmt);
589 gcc_assert (len < sizeof str); /* Leave room for \0. */
591 vsprintf (str, fmt, p);
592 va_end (p);
594 return DEF_ATTR_STRING (str);
597 static rtx
598 attr_eq (const char *name, const char *value)
600 return attr_rtx (EQ_ATTR, DEF_ATTR_STRING (name), DEF_ATTR_STRING (value));
603 static const char *
604 attr_numeral (int n)
606 return XSTR (make_numeric_value (n), 0);
609 /* Return a permanent (possibly shared) copy of a string STR (not assumed
610 to be null terminated) with LEN bytes. */
612 static char *
613 attr_string (const char *str, int len)
615 struct attr_hash *h;
616 int hashcode;
617 int i;
618 char *new_str;
620 /* Compute the hash code. */
621 hashcode = (len + 1) * 613 + (unsigned) str[0];
622 for (i = 1; i < len; i += 2)
623 hashcode = ((hashcode * 613) + (unsigned) str[i]);
624 if (hashcode < 0)
625 hashcode = -hashcode;
627 /* Search the table for the string. */
628 for (h = attr_hash_table[hashcode % RTL_HASH_SIZE]; h; h = h->next)
629 if (h->hashcode == -hashcode && h->u.str[0] == str[0]
630 && !strncmp (h->u.str, str, len))
631 return h->u.str; /* <-- return if found. */
633 /* Not found; create a permanent copy and add it to the hash table. */
634 new_str = XOBNEWVAR (hash_obstack, char, len + 1);
635 memcpy (new_str, str, len);
636 new_str[len] = '\0';
637 attr_hash_add_string (hashcode, new_str);
638 copy_md_ptr_loc (new_str, str);
640 return new_str; /* Return the new string. */
643 /* Check two rtx's for equality of contents,
644 taking advantage of the fact that if both are hashed
645 then they can't be equal unless they are the same object. */
647 static int
648 attr_equal_p (rtx x, rtx y)
650 return (x == y || (! (ATTR_PERMANENT_P (x) && ATTR_PERMANENT_P (y))
651 && rtx_equal_p (x, y)));
654 /* Copy an attribute value expression,
655 descending to all depths, but not copying any
656 permanent hashed subexpressions. */
658 static rtx
659 attr_copy_rtx (rtx orig)
661 rtx copy;
662 int i, j;
663 RTX_CODE code;
664 const char *format_ptr;
666 /* No need to copy a permanent object. */
667 if (ATTR_PERMANENT_P (orig))
668 return orig;
670 code = GET_CODE (orig);
672 switch (code)
674 case REG:
675 case CONST_INT:
676 case CONST_DOUBLE:
677 case CONST_VECTOR:
678 case SYMBOL_REF:
679 case MATCH_TEST:
680 case CODE_LABEL:
681 case PC:
682 case CC0:
683 return orig;
685 default:
686 break;
689 copy = rtx_alloc (code);
690 PUT_MODE (copy, GET_MODE (orig));
691 ATTR_IND_SIMPLIFIED_P (copy) = ATTR_IND_SIMPLIFIED_P (orig);
692 ATTR_CURR_SIMPLIFIED_P (copy) = ATTR_CURR_SIMPLIFIED_P (orig);
693 ATTR_PERMANENT_P (copy) = ATTR_PERMANENT_P (orig);
695 format_ptr = GET_RTX_FORMAT (GET_CODE (copy));
697 for (i = 0; i < GET_RTX_LENGTH (GET_CODE (copy)); i++)
699 switch (*format_ptr++)
701 case 'e':
702 XEXP (copy, i) = XEXP (orig, i);
703 if (XEXP (orig, i) != NULL)
704 XEXP (copy, i) = attr_copy_rtx (XEXP (orig, i));
705 break;
707 case 'E':
708 case 'V':
709 XVEC (copy, i) = XVEC (orig, i);
710 if (XVEC (orig, i) != NULL)
712 XVEC (copy, i) = rtvec_alloc (XVECLEN (orig, i));
713 for (j = 0; j < XVECLEN (copy, i); j++)
714 XVECEXP (copy, i, j) = attr_copy_rtx (XVECEXP (orig, i, j));
716 break;
718 case 'n':
719 case 'i':
720 XINT (copy, i) = XINT (orig, i);
721 break;
723 case 'w':
724 XWINT (copy, i) = XWINT (orig, i);
725 break;
727 case 's':
728 case 'S':
729 XSTR (copy, i) = XSTR (orig, i);
730 break;
732 default:
733 gcc_unreachable ();
736 return copy;
739 /* Given a test expression for an attribute, ensure it is validly formed.
740 IS_CONST indicates whether the expression is constant for each compiler
741 run (a constant expression may not test any particular insn).
743 Convert (eq_attr "att" "a1,a2") to (ior (eq_attr ... ) (eq_attrq ..))
744 and (eq_attr "att" "!a1") to (not (eq_attr "att" "a1")). Do the latter
745 test first so that (eq_attr "att" "!a1,a2,a3") works as expected.
747 Update the string address in EQ_ATTR expression to be the same used
748 in the attribute (or `alternative_name') to speed up subsequent
749 `find_attr' calls and eliminate most `strcmp' calls.
751 Return the new expression, if any. */
753 static rtx
754 check_attr_test (rtx exp, int is_const, int lineno)
756 struct attr_desc *attr;
757 struct attr_value *av;
758 const char *name_ptr, *p;
759 rtx orexp, newexp;
761 switch (GET_CODE (exp))
763 case EQ_ATTR:
764 /* Handle negation test. */
765 if (XSTR (exp, 1)[0] == '!')
766 return check_attr_test (attr_rtx (NOT,
767 attr_eq (XSTR (exp, 0),
768 &XSTR (exp, 1)[1])),
769 is_const, lineno);
771 else if (n_comma_elts (XSTR (exp, 1)) == 1)
773 attr = find_attr (&XSTR (exp, 0), 0);
774 if (attr == NULL)
776 if (! strcmp (XSTR (exp, 0), "alternative"))
777 return mk_attr_alt (1 << atoi (XSTR (exp, 1)));
778 else
779 fatal ("unknown attribute `%s' in EQ_ATTR", XSTR (exp, 0));
782 if (is_const && ! attr->is_const)
783 fatal ("constant expression uses insn attribute `%s' in EQ_ATTR",
784 XSTR (exp, 0));
786 /* Copy this just to make it permanent,
787 so expressions using it can be permanent too. */
788 exp = attr_eq (XSTR (exp, 0), XSTR (exp, 1));
790 /* It shouldn't be possible to simplify the value given to a
791 constant attribute, so don't expand this until it's time to
792 write the test expression. */
793 if (attr->is_const)
794 ATTR_IND_SIMPLIFIED_P (exp) = 1;
796 if (attr->is_numeric)
798 for (p = XSTR (exp, 1); *p; p++)
799 if (! ISDIGIT (*p))
800 fatal ("attribute `%s' takes only numeric values",
801 XSTR (exp, 0));
803 else
805 for (av = attr->first_value; av; av = av->next)
806 if (GET_CODE (av->value) == CONST_STRING
807 && ! strcmp (XSTR (exp, 1), XSTR (av->value, 0)))
808 break;
810 if (av == NULL)
811 fatal ("unknown value `%s' for `%s' attribute",
812 XSTR (exp, 1), XSTR (exp, 0));
815 else
817 if (! strcmp (XSTR (exp, 0), "alternative"))
819 int set = 0;
821 name_ptr = XSTR (exp, 1);
822 while ((p = next_comma_elt (&name_ptr)) != NULL)
823 set |= 1 << atoi (p);
825 return mk_attr_alt (set);
827 else
829 /* Make an IOR tree of the possible values. */
830 orexp = false_rtx;
831 name_ptr = XSTR (exp, 1);
832 while ((p = next_comma_elt (&name_ptr)) != NULL)
834 newexp = attr_eq (XSTR (exp, 0), p);
835 orexp = insert_right_side (IOR, orexp, newexp, -2, -2);
838 return check_attr_test (orexp, is_const, lineno);
841 break;
843 case ATTR_FLAG:
844 break;
846 case CONST_INT:
847 /* Either TRUE or FALSE. */
848 if (XWINT (exp, 0))
849 return true_rtx;
850 else
851 return false_rtx;
853 case IOR:
854 case AND:
855 XEXP (exp, 0) = check_attr_test (XEXP (exp, 0), is_const, lineno);
856 XEXP (exp, 1) = check_attr_test (XEXP (exp, 1), is_const, lineno);
857 break;
859 case NOT:
860 XEXP (exp, 0) = check_attr_test (XEXP (exp, 0), is_const, lineno);
861 break;
863 case MATCH_TEST:
864 exp = attr_rtx (MATCH_TEST, XSTR (exp, 0));
865 ATTR_IND_SIMPLIFIED_P (exp) = 1;
866 break;
868 case MATCH_OPERAND:
869 if (is_const)
870 fatal ("RTL operator \"%s\" not valid in constant attribute test",
871 GET_RTX_NAME (GET_CODE (exp)));
872 /* These cases can't be simplified. */
873 ATTR_IND_SIMPLIFIED_P (exp) = 1;
874 break;
876 case LE: case LT: case GT: case GE:
877 case LEU: case LTU: case GTU: case GEU:
878 case NE: case EQ:
879 if (GET_CODE (XEXP (exp, 0)) == SYMBOL_REF
880 && GET_CODE (XEXP (exp, 1)) == SYMBOL_REF)
881 exp = attr_rtx (GET_CODE (exp),
882 attr_rtx (SYMBOL_REF, XSTR (XEXP (exp, 0), 0)),
883 attr_rtx (SYMBOL_REF, XSTR (XEXP (exp, 1), 0)));
884 /* These cases can't be simplified. */
885 ATTR_IND_SIMPLIFIED_P (exp) = 1;
886 break;
888 case SYMBOL_REF:
889 if (is_const)
891 /* These cases are valid for constant attributes, but can't be
892 simplified. */
893 exp = attr_rtx (SYMBOL_REF, XSTR (exp, 0));
894 ATTR_IND_SIMPLIFIED_P (exp) = 1;
895 break;
897 default:
898 fatal ("RTL operator \"%s\" not valid in attribute test",
899 GET_RTX_NAME (GET_CODE (exp)));
902 return exp;
905 /* Given an expression, ensure that it is validly formed and that all named
906 attribute values are valid for the given attribute. Issue a fatal error
907 if not. If no attribute is specified, assume a numeric attribute.
909 Return a perhaps modified replacement expression for the value. */
911 static rtx
912 check_attr_value (rtx exp, struct attr_desc *attr)
914 struct attr_value *av;
915 const char *p;
916 int i;
918 switch (GET_CODE (exp))
920 case CONST_INT:
921 if (attr && ! attr->is_numeric)
923 error_with_line (attr->lineno,
924 "CONST_INT not valid for non-numeric attribute %s",
925 attr->name);
926 break;
929 if (INTVAL (exp) < 0)
931 error_with_line (attr->lineno,
932 "negative numeric value specified for attribute %s",
933 attr->name);
934 break;
936 break;
938 case CONST_STRING:
939 if (! strcmp (XSTR (exp, 0), "*"))
940 break;
942 if (attr == 0 || attr->is_numeric)
944 p = XSTR (exp, 0);
945 for (; *p; p++)
946 if (! ISDIGIT (*p))
948 error_with_line (attr ? attr->lineno : 0,
949 "non-numeric value for numeric attribute %s",
950 attr ? attr->name : "internal");
951 break;
953 break;
956 for (av = attr->first_value; av; av = av->next)
957 if (GET_CODE (av->value) == CONST_STRING
958 && ! strcmp (XSTR (av->value, 0), XSTR (exp, 0)))
959 break;
961 if (av == NULL)
962 error_with_line (attr->lineno,
963 "unknown value `%s' for `%s' attribute",
964 XSTR (exp, 0), attr ? attr->name : "internal");
965 break;
967 case IF_THEN_ELSE:
968 XEXP (exp, 0) = check_attr_test (XEXP (exp, 0),
969 attr ? attr->is_const : 0,
970 attr ? attr->lineno : 0);
971 XEXP (exp, 1) = check_attr_value (XEXP (exp, 1), attr);
972 XEXP (exp, 2) = check_attr_value (XEXP (exp, 2), attr);
973 break;
975 case PLUS:
976 case MINUS:
977 case MULT:
978 case DIV:
979 case MOD:
980 if (attr && !attr->is_numeric)
982 error_with_line (attr->lineno,
983 "invalid operation `%s' for non-numeric"
984 " attribute value", GET_RTX_NAME (GET_CODE (exp)));
985 break;
987 /* Fall through. */
989 case IOR:
990 case AND:
991 XEXP (exp, 0) = check_attr_value (XEXP (exp, 0), attr);
992 XEXP (exp, 1) = check_attr_value (XEXP (exp, 1), attr);
993 break;
995 case FFS:
996 case CLZ:
997 case CTZ:
998 case POPCOUNT:
999 case PARITY:
1000 case BSWAP:
1001 XEXP (exp, 0) = check_attr_value (XEXP (exp, 0), attr);
1002 break;
1004 case COND:
1005 if (XVECLEN (exp, 0) % 2 != 0)
1007 error_with_line (attr->lineno,
1008 "first operand of COND must have even length");
1009 break;
1012 for (i = 0; i < XVECLEN (exp, 0); i += 2)
1014 XVECEXP (exp, 0, i) = check_attr_test (XVECEXP (exp, 0, i),
1015 attr ? attr->is_const : 0,
1016 attr ? attr->lineno : 0);
1017 XVECEXP (exp, 0, i + 1)
1018 = check_attr_value (XVECEXP (exp, 0, i + 1), attr);
1021 XEXP (exp, 1) = check_attr_value (XEXP (exp, 1), attr);
1022 break;
1024 case ATTR:
1026 struct attr_desc *attr2 = find_attr (&XSTR (exp, 0), 0);
1027 if (attr2 == NULL)
1028 error_with_line (attr ? attr->lineno : 0,
1029 "unknown attribute `%s' in ATTR",
1030 XSTR (exp, 0));
1031 else if (attr && attr->is_const && ! attr2->is_const)
1032 error_with_line (attr->lineno,
1033 "non-constant attribute `%s' referenced from `%s'",
1034 XSTR (exp, 0), attr->name);
1035 else if (attr
1036 && attr->is_numeric != attr2->is_numeric)
1037 error_with_line (attr->lineno,
1038 "numeric attribute mismatch calling `%s' from `%s'",
1039 XSTR (exp, 0), attr->name);
1041 break;
1043 case SYMBOL_REF:
1044 /* A constant SYMBOL_REF is valid as a constant attribute test and
1045 is expanded later by make_canonical into a COND. In a non-constant
1046 attribute test, it is left be. */
1047 return attr_rtx (SYMBOL_REF, XSTR (exp, 0));
1049 default:
1050 error_with_line (attr ? attr->lineno : 0,
1051 "invalid operation `%s' for attribute value",
1052 GET_RTX_NAME (GET_CODE (exp)));
1053 break;
1056 return exp;
1059 /* Given an SET_ATTR_ALTERNATIVE expression, convert to the canonical SET.
1060 It becomes a COND with each test being (eq_attr "alternative" "n") */
1062 static rtx
1063 convert_set_attr_alternative (rtx exp, struct insn_def *id)
1065 int num_alt = id->num_alternatives;
1066 rtx condexp;
1067 int i;
1069 if (XVECLEN (exp, 1) != num_alt)
1071 error_with_line (id->lineno,
1072 "bad number of entries in SET_ATTR_ALTERNATIVE");
1073 return NULL_RTX;
1076 /* Make a COND with all tests but the last. Select the last value via the
1077 default. */
1078 condexp = rtx_alloc (COND);
1079 XVEC (condexp, 0) = rtvec_alloc ((num_alt - 1) * 2);
1081 for (i = 0; i < num_alt - 1; i++)
1083 const char *p;
1084 p = attr_numeral (i);
1086 XVECEXP (condexp, 0, 2 * i) = attr_eq (alternative_name, p);
1087 XVECEXP (condexp, 0, 2 * i + 1) = XVECEXP (exp, 1, i);
1090 XEXP (condexp, 1) = XVECEXP (exp, 1, i);
1092 return attr_rtx (SET, attr_rtx (ATTR, XSTR (exp, 0)), condexp);
1095 /* Given a SET_ATTR, convert to the appropriate SET. If a comma-separated
1096 list of values is given, convert to SET_ATTR_ALTERNATIVE first. */
1098 static rtx
1099 convert_set_attr (rtx exp, struct insn_def *id)
1101 rtx newexp;
1102 const char *name_ptr;
1103 char *p;
1104 int n;
1106 /* See how many alternative specified. */
1107 n = n_comma_elts (XSTR (exp, 1));
1108 if (n == 1)
1109 return attr_rtx (SET,
1110 attr_rtx (ATTR, XSTR (exp, 0)),
1111 attr_rtx (CONST_STRING, XSTR (exp, 1)));
1113 newexp = rtx_alloc (SET_ATTR_ALTERNATIVE);
1114 XSTR (newexp, 0) = XSTR (exp, 0);
1115 XVEC (newexp, 1) = rtvec_alloc (n);
1117 /* Process each comma-separated name. */
1118 name_ptr = XSTR (exp, 1);
1119 n = 0;
1120 while ((p = next_comma_elt (&name_ptr)) != NULL)
1121 XVECEXP (newexp, 1, n++) = attr_rtx (CONST_STRING, p);
1123 return convert_set_attr_alternative (newexp, id);
1126 /* Scan all definitions, checking for validity. Also, convert any SET_ATTR
1127 and SET_ATTR_ALTERNATIVE expressions to the corresponding SET
1128 expressions. */
1130 static void
1131 check_defs (void)
1133 struct insn_def *id;
1134 struct attr_desc *attr;
1135 int i;
1136 rtx value;
1138 for (id = defs; id; id = id->next)
1140 if (XVEC (id->def, id->vec_idx) == NULL)
1141 continue;
1143 for (i = 0; i < XVECLEN (id->def, id->vec_idx); i++)
1145 value = XVECEXP (id->def, id->vec_idx, i);
1146 switch (GET_CODE (value))
1148 case SET:
1149 if (GET_CODE (XEXP (value, 0)) != ATTR)
1151 error_with_line (id->lineno, "bad attribute set");
1152 value = NULL_RTX;
1154 break;
1156 case SET_ATTR_ALTERNATIVE:
1157 value = convert_set_attr_alternative (value, id);
1158 break;
1160 case SET_ATTR:
1161 value = convert_set_attr (value, id);
1162 break;
1164 default:
1165 error_with_line (id->lineno, "invalid attribute code %s",
1166 GET_RTX_NAME (GET_CODE (value)));
1167 value = NULL_RTX;
1169 if (value == NULL_RTX)
1170 continue;
1172 if ((attr = find_attr (&XSTR (XEXP (value, 0), 0), 0)) == NULL)
1174 error_with_line (id->lineno, "unknown attribute %s",
1175 XSTR (XEXP (value, 0), 0));
1176 continue;
1179 XVECEXP (id->def, id->vec_idx, i) = value;
1180 XEXP (value, 1) = check_attr_value (XEXP (value, 1), attr);
1185 /* Given a valid expression for an attribute value, remove any IF_THEN_ELSE
1186 expressions by converting them into a COND. This removes cases from this
1187 program. Also, replace an attribute value of "*" with the default attribute
1188 value. */
1190 static rtx
1191 make_canonical (struct attr_desc *attr, rtx exp)
1193 int i;
1194 rtx newexp;
1196 switch (GET_CODE (exp))
1198 case CONST_INT:
1199 exp = make_numeric_value (INTVAL (exp));
1200 break;
1202 case CONST_STRING:
1203 if (! strcmp (XSTR (exp, 0), "*"))
1205 if (attr == 0 || attr->default_val == 0)
1206 fatal ("(attr_value \"*\") used in invalid context");
1207 exp = attr->default_val->value;
1209 else
1210 XSTR (exp, 0) = DEF_ATTR_STRING (XSTR (exp, 0));
1212 break;
1214 case SYMBOL_REF:
1215 if (!attr->is_const || ATTR_IND_SIMPLIFIED_P (exp))
1216 break;
1217 /* The SYMBOL_REF is constant for a given run, so mark it as unchanging.
1218 This makes the COND something that won't be considered an arbitrary
1219 expression by walk_attr_value. */
1220 ATTR_IND_SIMPLIFIED_P (exp) = 1;
1221 exp = check_attr_value (exp, attr);
1222 break;
1224 case IF_THEN_ELSE:
1225 newexp = rtx_alloc (COND);
1226 XVEC (newexp, 0) = rtvec_alloc (2);
1227 XVECEXP (newexp, 0, 0) = XEXP (exp, 0);
1228 XVECEXP (newexp, 0, 1) = XEXP (exp, 1);
1230 XEXP (newexp, 1) = XEXP (exp, 2);
1232 exp = newexp;
1233 /* Fall through to COND case since this is now a COND. */
1235 case COND:
1237 int allsame = 1;
1238 rtx defval;
1240 /* First, check for degenerate COND. */
1241 if (XVECLEN (exp, 0) == 0)
1242 return make_canonical (attr, XEXP (exp, 1));
1243 defval = XEXP (exp, 1) = make_canonical (attr, XEXP (exp, 1));
1245 for (i = 0; i < XVECLEN (exp, 0); i += 2)
1247 XVECEXP (exp, 0, i) = copy_boolean (XVECEXP (exp, 0, i));
1248 XVECEXP (exp, 0, i + 1)
1249 = make_canonical (attr, XVECEXP (exp, 0, i + 1));
1250 if (! rtx_equal_p (XVECEXP (exp, 0, i + 1), defval))
1251 allsame = 0;
1253 if (allsame)
1254 return defval;
1256 break;
1258 default:
1259 break;
1262 return exp;
1265 static rtx
1266 copy_boolean (rtx exp)
1268 if (GET_CODE (exp) == AND || GET_CODE (exp) == IOR)
1269 return attr_rtx (GET_CODE (exp), copy_boolean (XEXP (exp, 0)),
1270 copy_boolean (XEXP (exp, 1)));
1271 if (GET_CODE (exp) == MATCH_OPERAND)
1273 XSTR (exp, 1) = DEF_ATTR_STRING (XSTR (exp, 1));
1274 XSTR (exp, 2) = DEF_ATTR_STRING (XSTR (exp, 2));
1276 else if (GET_CODE (exp) == EQ_ATTR)
1278 XSTR (exp, 0) = DEF_ATTR_STRING (XSTR (exp, 0));
1279 XSTR (exp, 1) = DEF_ATTR_STRING (XSTR (exp, 1));
1282 return exp;
1285 /* Given a value and an attribute description, return a `struct attr_value *'
1286 that represents that value. This is either an existing structure, if the
1287 value has been previously encountered, or a newly-created structure.
1289 `insn_code' is the code of an insn whose attribute has the specified
1290 value (-2 if not processing an insn). We ensure that all insns for
1291 a given value have the same number of alternatives if the value checks
1292 alternatives. */
1294 static struct attr_value *
1295 get_attr_value (rtx value, struct attr_desc *attr, int insn_code)
1297 struct attr_value *av;
1298 int num_alt = 0;
1300 value = make_canonical (attr, value);
1301 if (compares_alternatives_p (value))
1303 if (insn_code < 0 || insn_alternatives == NULL)
1304 fatal ("(eq_attr \"alternatives\" ...) used in non-insn context");
1305 else
1306 num_alt = insn_alternatives[insn_code];
1309 for (av = attr->first_value; av; av = av->next)
1310 if (rtx_equal_p (value, av->value)
1311 && (num_alt == 0 || av->first_insn == NULL
1312 || insn_alternatives[av->first_insn->def->insn_code]))
1313 return av;
1315 av = oballoc (struct attr_value);
1316 av->value = value;
1317 av->next = attr->first_value;
1318 attr->first_value = av;
1319 av->first_insn = NULL;
1320 av->num_insns = 0;
1321 av->has_asm_insn = 0;
1323 return av;
1326 /* After all DEFINE_DELAYs have been read in, create internal attributes
1327 to generate the required routines.
1329 First, we compute the number of delay slots for each insn (as a COND of
1330 each of the test expressions in DEFINE_DELAYs). Then, if more than one
1331 delay type is specified, we compute a similar function giving the
1332 DEFINE_DELAY ordinal for each insn.
1334 Finally, for each [DEFINE_DELAY, slot #] pair, we compute an attribute that
1335 tells whether a given insn can be in that delay slot.
1337 Normal attribute filling and optimization expands these to contain the
1338 information needed to handle delay slots. */
1340 static void
1341 expand_delays (void)
1343 struct delay_desc *delay;
1344 rtx condexp;
1345 rtx newexp;
1346 int i;
1347 char *p;
1349 /* First, generate data for `num_delay_slots' function. */
1351 condexp = rtx_alloc (COND);
1352 XVEC (condexp, 0) = rtvec_alloc (num_delays * 2);
1353 XEXP (condexp, 1) = make_numeric_value (0);
1355 for (i = 0, delay = delays; delay; i += 2, delay = delay->next)
1357 XVECEXP (condexp, 0, i) = XEXP (delay->def, 0);
1358 XVECEXP (condexp, 0, i + 1)
1359 = make_numeric_value (XVECLEN (delay->def, 1) / 3);
1362 make_internal_attr (num_delay_slots_str, condexp, ATTR_NONE);
1364 /* If more than one delay type, do the same for computing the delay type. */
1365 if (num_delays > 1)
1367 condexp = rtx_alloc (COND);
1368 XVEC (condexp, 0) = rtvec_alloc (num_delays * 2);
1369 XEXP (condexp, 1) = make_numeric_value (0);
1371 for (i = 0, delay = delays; delay; i += 2, delay = delay->next)
1373 XVECEXP (condexp, 0, i) = XEXP (delay->def, 0);
1374 XVECEXP (condexp, 0, i + 1) = make_numeric_value (delay->num);
1377 make_internal_attr (delay_type_str, condexp, ATTR_SPECIAL);
1380 /* For each delay possibility and delay slot, compute an eligibility
1381 attribute for non-annulled insns and for each type of annulled (annul
1382 if true and annul if false). */
1383 for (delay = delays; delay; delay = delay->next)
1385 for (i = 0; i < XVECLEN (delay->def, 1); i += 3)
1387 condexp = XVECEXP (delay->def, 1, i);
1388 if (condexp == 0)
1389 condexp = false_rtx;
1390 newexp = attr_rtx (IF_THEN_ELSE, condexp,
1391 make_numeric_value (1), make_numeric_value (0));
1393 p = attr_printf (sizeof "*delay__" + MAX_DIGITS * 2,
1394 "*delay_%d_%d", delay->num, i / 3);
1395 make_internal_attr (p, newexp, ATTR_SPECIAL);
1397 if (have_annul_true)
1399 condexp = XVECEXP (delay->def, 1, i + 1);
1400 if (condexp == 0) condexp = false_rtx;
1401 newexp = attr_rtx (IF_THEN_ELSE, condexp,
1402 make_numeric_value (1),
1403 make_numeric_value (0));
1404 p = attr_printf (sizeof "*annul_true__" + MAX_DIGITS * 2,
1405 "*annul_true_%d_%d", delay->num, i / 3);
1406 make_internal_attr (p, newexp, ATTR_SPECIAL);
1409 if (have_annul_false)
1411 condexp = XVECEXP (delay->def, 1, i + 2);
1412 if (condexp == 0) condexp = false_rtx;
1413 newexp = attr_rtx (IF_THEN_ELSE, condexp,
1414 make_numeric_value (1),
1415 make_numeric_value (0));
1416 p = attr_printf (sizeof "*annul_false__" + MAX_DIGITS * 2,
1417 "*annul_false_%d_%d", delay->num, i / 3);
1418 make_internal_attr (p, newexp, ATTR_SPECIAL);
1424 /* Once all attributes and insns have been read and checked, we construct for
1425 each attribute value a list of all the insns that have that value for
1426 the attribute. */
1428 static void
1429 fill_attr (struct attr_desc *attr)
1431 struct attr_value *av;
1432 struct insn_ent *ie;
1433 struct insn_def *id;
1434 int i;
1435 rtx value;
1437 /* Don't fill constant attributes. The value is independent of
1438 any particular insn. */
1439 if (attr->is_const)
1440 return;
1442 for (id = defs; id; id = id->next)
1444 /* If no value is specified for this insn for this attribute, use the
1445 default. */
1446 value = NULL;
1447 if (XVEC (id->def, id->vec_idx))
1448 for (i = 0; i < XVECLEN (id->def, id->vec_idx); i++)
1449 if (! strcmp_check (XSTR (XEXP (XVECEXP (id->def, id->vec_idx, i), 0), 0),
1450 attr->name))
1451 value = XEXP (XVECEXP (id->def, id->vec_idx, i), 1);
1453 if (value == NULL)
1454 av = attr->default_val;
1455 else
1456 av = get_attr_value (value, attr, id->insn_code);
1458 ie = oballoc (struct insn_ent);
1459 ie->def = id;
1460 insert_insn_ent (av, ie);
1464 /* Given an expression EXP, see if it is a COND or IF_THEN_ELSE that has a
1465 test that checks relative positions of insns (uses MATCH_DUP or PC).
1466 If so, replace it with what is obtained by passing the expression to
1467 ADDRESS_FN. If not but it is a COND or IF_THEN_ELSE, call this routine
1468 recursively on each value (including the default value). Otherwise,
1469 return the value returned by NO_ADDRESS_FN applied to EXP. */
1471 static rtx
1472 substitute_address (rtx exp, rtx (*no_address_fn) (rtx),
1473 rtx (*address_fn) (rtx))
1475 int i;
1476 rtx newexp;
1478 if (GET_CODE (exp) == COND)
1480 /* See if any tests use addresses. */
1481 address_used = 0;
1482 for (i = 0; i < XVECLEN (exp, 0); i += 2)
1483 walk_attr_value (XVECEXP (exp, 0, i));
1485 if (address_used)
1486 return (*address_fn) (exp);
1488 /* Make a new copy of this COND, replacing each element. */
1489 newexp = rtx_alloc (COND);
1490 XVEC (newexp, 0) = rtvec_alloc (XVECLEN (exp, 0));
1491 for (i = 0; i < XVECLEN (exp, 0); i += 2)
1493 XVECEXP (newexp, 0, i) = XVECEXP (exp, 0, i);
1494 XVECEXP (newexp, 0, i + 1)
1495 = substitute_address (XVECEXP (exp, 0, i + 1),
1496 no_address_fn, address_fn);
1499 XEXP (newexp, 1) = substitute_address (XEXP (exp, 1),
1500 no_address_fn, address_fn);
1502 return newexp;
1505 else if (GET_CODE (exp) == IF_THEN_ELSE)
1507 address_used = 0;
1508 walk_attr_value (XEXP (exp, 0));
1509 if (address_used)
1510 return (*address_fn) (exp);
1512 return attr_rtx (IF_THEN_ELSE,
1513 substitute_address (XEXP (exp, 0),
1514 no_address_fn, address_fn),
1515 substitute_address (XEXP (exp, 1),
1516 no_address_fn, address_fn),
1517 substitute_address (XEXP (exp, 2),
1518 no_address_fn, address_fn));
1521 return (*no_address_fn) (exp);
1524 /* Make new attributes from the `length' attribute. The following are made,
1525 each corresponding to a function called from `shorten_branches' or
1526 `get_attr_length':
1528 *insn_default_length This is the length of the insn to be returned
1529 by `get_attr_length' before `shorten_branches'
1530 has been called. In each case where the length
1531 depends on relative addresses, the largest
1532 possible is used. This routine is also used
1533 to compute the initial size of the insn.
1535 *insn_variable_length_p This returns 1 if the insn's length depends
1536 on relative addresses, zero otherwise.
1538 *insn_current_length This is only called when it is known that the
1539 insn has a variable length and returns the
1540 current length, based on relative addresses.
1543 static void
1544 make_length_attrs (void)
1546 static const char *new_names[] =
1548 "*insn_default_length",
1549 "*insn_min_length",
1550 "*insn_variable_length_p",
1551 "*insn_current_length"
1553 static rtx (*const no_address_fn[]) (rtx)
1554 = {identity_fn,identity_fn, zero_fn, zero_fn};
1555 static rtx (*const address_fn[]) (rtx)
1556 = {max_fn, min_fn, one_fn, identity_fn};
1557 size_t i;
1558 struct attr_desc *length_attr, *new_attr;
1559 struct attr_value *av, *new_av;
1560 struct insn_ent *ie, *new_ie;
1562 /* See if length attribute is defined. If so, it must be numeric. Make
1563 it special so we don't output anything for it. */
1564 length_attr = find_attr (&length_str, 0);
1565 if (length_attr == 0)
1566 return;
1568 if (! length_attr->is_numeric)
1569 fatal ("length attribute must be numeric");
1571 length_attr->is_const = 0;
1572 length_attr->is_special = 1;
1574 /* Make each new attribute, in turn. */
1575 for (i = 0; i < ARRAY_SIZE (new_names); i++)
1577 make_internal_attr (new_names[i],
1578 substitute_address (length_attr->default_val->value,
1579 no_address_fn[i], address_fn[i]),
1580 ATTR_NONE);
1581 new_attr = find_attr (&new_names[i], 0);
1582 for (av = length_attr->first_value; av; av = av->next)
1583 for (ie = av->first_insn; ie; ie = ie->next)
1585 new_av = get_attr_value (substitute_address (av->value,
1586 no_address_fn[i],
1587 address_fn[i]),
1588 new_attr, ie->def->insn_code);
1589 new_ie = oballoc (struct insn_ent);
1590 new_ie->def = ie->def;
1591 insert_insn_ent (new_av, new_ie);
1596 /* Utility functions called from above routine. */
1598 static rtx
1599 identity_fn (rtx exp)
1601 return exp;
1604 static rtx
1605 zero_fn (rtx exp ATTRIBUTE_UNUSED)
1607 return make_numeric_value (0);
1610 static rtx
1611 one_fn (rtx exp ATTRIBUTE_UNUSED)
1613 return make_numeric_value (1);
1616 static rtx
1617 max_fn (rtx exp)
1619 int unknown;
1620 return make_numeric_value (max_attr_value (exp, &unknown));
1623 static rtx
1624 min_fn (rtx exp)
1626 int unknown;
1627 return make_numeric_value (min_attr_value (exp, &unknown));
1630 static void
1631 write_length_unit_log (FILE *outf)
1633 struct attr_desc *length_attr = find_attr (&length_str, 0);
1634 struct attr_value *av;
1635 struct insn_ent *ie;
1636 unsigned int length_unit_log, length_or;
1637 int unknown = 0;
1639 if (length_attr == 0)
1640 return;
1641 length_or = or_attr_value (length_attr->default_val->value, &unknown);
1642 for (av = length_attr->first_value; av; av = av->next)
1643 for (ie = av->first_insn; ie; ie = ie->next)
1644 length_or |= or_attr_value (av->value, &unknown);
1646 if (unknown)
1647 length_unit_log = 0;
1648 else
1650 length_or = ~length_or;
1651 for (length_unit_log = 0; length_or & 1; length_or >>= 1)
1652 length_unit_log++;
1654 fprintf (outf, "EXPORTED_CONST int length_unit_log = %u;\n", length_unit_log);
1657 /* Take a COND expression and see if any of the conditions in it can be
1658 simplified. If any are known true or known false for the particular insn
1659 code, the COND can be further simplified.
1661 Also call ourselves on any COND operations that are values of this COND.
1663 We do not modify EXP; rather, we make and return a new rtx. */
1665 static rtx
1666 simplify_cond (rtx exp, int insn_code, int insn_index)
1668 int i, j;
1669 /* We store the desired contents here,
1670 then build a new expression if they don't match EXP. */
1671 rtx defval = XEXP (exp, 1);
1672 rtx new_defval = XEXP (exp, 1);
1673 int len = XVECLEN (exp, 0);
1674 rtx *tests = XNEWVEC (rtx, len);
1675 int allsame = 1;
1676 rtx ret;
1678 /* This lets us free all storage allocated below, if appropriate. */
1679 obstack_finish (rtl_obstack);
1681 memcpy (tests, XVEC (exp, 0)->elem, len * sizeof (rtx));
1683 /* See if default value needs simplification. */
1684 if (GET_CODE (defval) == COND)
1685 new_defval = simplify_cond (defval, insn_code, insn_index);
1687 /* Simplify the subexpressions, and see what tests we can get rid of. */
1689 for (i = 0; i < len; i += 2)
1691 rtx newtest, newval;
1693 /* Simplify this test. */
1694 newtest = simplify_test_exp_in_temp (tests[i], insn_code, insn_index);
1695 tests[i] = newtest;
1697 newval = tests[i + 1];
1698 /* See if this value may need simplification. */
1699 if (GET_CODE (newval) == COND)
1700 newval = simplify_cond (newval, insn_code, insn_index);
1702 /* Look for ways to delete or combine this test. */
1703 if (newtest == true_rtx)
1705 /* If test is true, make this value the default
1706 and discard this + any following tests. */
1707 len = i;
1708 defval = tests[i + 1];
1709 new_defval = newval;
1712 else if (newtest == false_rtx)
1714 /* If test is false, discard it and its value. */
1715 for (j = i; j < len - 2; j++)
1716 tests[j] = tests[j + 2];
1717 i -= 2;
1718 len -= 2;
1721 else if (i > 0 && attr_equal_p (newval, tests[i - 1]))
1723 /* If this value and the value for the prev test are the same,
1724 merge the tests. */
1726 tests[i - 2]
1727 = insert_right_side (IOR, tests[i - 2], newtest,
1728 insn_code, insn_index);
1730 /* Delete this test/value. */
1731 for (j = i; j < len - 2; j++)
1732 tests[j] = tests[j + 2];
1733 len -= 2;
1734 i -= 2;
1737 else
1738 tests[i + 1] = newval;
1741 /* If the last test in a COND has the same value
1742 as the default value, that test isn't needed. */
1744 while (len > 0 && attr_equal_p (tests[len - 1], new_defval))
1745 len -= 2;
1747 /* See if we changed anything. */
1748 if (len != XVECLEN (exp, 0) || new_defval != XEXP (exp, 1))
1749 allsame = 0;
1750 else
1751 for (i = 0; i < len; i++)
1752 if (! attr_equal_p (tests[i], XVECEXP (exp, 0, i)))
1754 allsame = 0;
1755 break;
1758 if (len == 0)
1760 if (GET_CODE (defval) == COND)
1761 ret = simplify_cond (defval, insn_code, insn_index);
1762 else
1763 ret = defval;
1765 else if (allsame)
1766 ret = exp;
1767 else
1769 rtx newexp = rtx_alloc (COND);
1771 XVEC (newexp, 0) = rtvec_alloc (len);
1772 memcpy (XVEC (newexp, 0)->elem, tests, len * sizeof (rtx));
1773 XEXP (newexp, 1) = new_defval;
1774 ret = newexp;
1776 free (tests);
1777 return ret;
1780 /* Remove an insn entry from an attribute value. */
1782 static void
1783 remove_insn_ent (struct attr_value *av, struct insn_ent *ie)
1785 struct insn_ent *previe;
1787 if (av->first_insn == ie)
1788 av->first_insn = ie->next;
1789 else
1791 for (previe = av->first_insn; previe->next != ie; previe = previe->next)
1793 previe->next = ie->next;
1796 av->num_insns--;
1797 if (ie->def->insn_code == -1)
1798 av->has_asm_insn = 0;
1800 num_insn_ents--;
1803 /* Insert an insn entry in an attribute value list. */
1805 static void
1806 insert_insn_ent (struct attr_value *av, struct insn_ent *ie)
1808 ie->next = av->first_insn;
1809 av->first_insn = ie;
1810 av->num_insns++;
1811 if (ie->def->insn_code == -1)
1812 av->has_asm_insn = 1;
1814 num_insn_ents++;
1817 /* This is a utility routine to take an expression that is a tree of either
1818 AND or IOR expressions and insert a new term. The new term will be
1819 inserted at the right side of the first node whose code does not match
1820 the root. A new node will be created with the root's code. Its left
1821 side will be the old right side and its right side will be the new
1822 term.
1824 If the `term' is itself a tree, all its leaves will be inserted. */
1826 static rtx
1827 insert_right_side (enum rtx_code code, rtx exp, rtx term, int insn_code, int insn_index)
1829 rtx newexp;
1831 /* Avoid consing in some special cases. */
1832 if (code == AND && term == true_rtx)
1833 return exp;
1834 if (code == AND && term == false_rtx)
1835 return false_rtx;
1836 if (code == AND && exp == true_rtx)
1837 return term;
1838 if (code == AND && exp == false_rtx)
1839 return false_rtx;
1840 if (code == IOR && term == true_rtx)
1841 return true_rtx;
1842 if (code == IOR && term == false_rtx)
1843 return exp;
1844 if (code == IOR && exp == true_rtx)
1845 return true_rtx;
1846 if (code == IOR && exp == false_rtx)
1847 return term;
1848 if (attr_equal_p (exp, term))
1849 return exp;
1851 if (GET_CODE (term) == code)
1853 exp = insert_right_side (code, exp, XEXP (term, 0),
1854 insn_code, insn_index);
1855 exp = insert_right_side (code, exp, XEXP (term, 1),
1856 insn_code, insn_index);
1858 return exp;
1861 if (GET_CODE (exp) == code)
1863 rtx new_rtx = insert_right_side (code, XEXP (exp, 1),
1864 term, insn_code, insn_index);
1865 if (new_rtx != XEXP (exp, 1))
1866 /* Make a copy of this expression and call recursively. */
1867 newexp = attr_rtx (code, XEXP (exp, 0), new_rtx);
1868 else
1869 newexp = exp;
1871 else
1873 /* Insert the new term. */
1874 newexp = attr_rtx (code, exp, term);
1877 return simplify_test_exp_in_temp (newexp, insn_code, insn_index);
1880 /* If we have an expression which AND's a bunch of
1881 (not (eq_attrq "alternative" "n"))
1882 terms, we may have covered all or all but one of the possible alternatives.
1883 If so, we can optimize. Similarly for IOR's of EQ_ATTR.
1885 This routine is passed an expression and either AND or IOR. It returns a
1886 bitmask indicating which alternatives are mentioned within EXP. */
1888 static int
1889 compute_alternative_mask (rtx exp, enum rtx_code code)
1891 const char *string;
1892 if (GET_CODE (exp) == code)
1893 return compute_alternative_mask (XEXP (exp, 0), code)
1894 | compute_alternative_mask (XEXP (exp, 1), code);
1896 else if (code == AND && GET_CODE (exp) == NOT
1897 && GET_CODE (XEXP (exp, 0)) == EQ_ATTR
1898 && XSTR (XEXP (exp, 0), 0) == alternative_name)
1899 string = XSTR (XEXP (exp, 0), 1);
1901 else if (code == IOR && GET_CODE (exp) == EQ_ATTR
1902 && XSTR (exp, 0) == alternative_name)
1903 string = XSTR (exp, 1);
1905 else if (GET_CODE (exp) == EQ_ATTR_ALT)
1907 if (code == AND && XINT (exp, 1))
1908 return XINT (exp, 0);
1910 if (code == IOR && !XINT (exp, 1))
1911 return XINT (exp, 0);
1913 return 0;
1915 else
1916 return 0;
1918 if (string[1] == 0)
1919 return 1 << (string[0] - '0');
1920 return 1 << atoi (string);
1923 /* Given I, a single-bit mask, return RTX to compare the `alternative'
1924 attribute with the value represented by that bit. */
1926 static rtx
1927 make_alternative_compare (int mask)
1929 return mk_attr_alt (mask);
1932 /* If we are processing an (eq_attr "attr" "value") test, we find the value
1933 of "attr" for this insn code. From that value, we can compute a test
1934 showing when the EQ_ATTR will be true. This routine performs that
1935 computation. If a test condition involves an address, we leave the EQ_ATTR
1936 intact because addresses are only valid for the `length' attribute.
1938 EXP is the EQ_ATTR expression and ATTR is the attribute to which
1939 it refers. VALUE is the value of that attribute for the insn
1940 corresponding to INSN_CODE and INSN_INDEX. */
1942 static rtx
1943 evaluate_eq_attr (rtx exp, struct attr_desc *attr, rtx value,
1944 int insn_code, int insn_index)
1946 rtx orexp, andexp;
1947 rtx right;
1948 rtx newexp;
1949 int i;
1951 while (GET_CODE (value) == ATTR)
1953 struct attr_value *av = NULL;
1955 attr = find_attr (&XSTR (value, 0), 0);
1957 if (insn_code_values)
1959 struct attr_value_list *iv;
1960 for (iv = insn_code_values[insn_code]; iv; iv = iv->next)
1961 if (iv->attr == attr)
1963 av = iv->av;
1964 break;
1967 else
1969 struct insn_ent *ie;
1970 for (av = attr->first_value; av; av = av->next)
1971 for (ie = av->first_insn; ie; ie = ie->next)
1972 if (ie->def->insn_code == insn_code)
1973 goto got_av;
1975 if (av)
1977 got_av:
1978 value = av->value;
1982 switch (GET_CODE (value))
1984 case CONST_STRING:
1985 if (! strcmp_check (XSTR (value, 0), XSTR (exp, 1)))
1986 newexp = true_rtx;
1987 else
1988 newexp = false_rtx;
1989 break;
1991 case SYMBOL_REF:
1993 const char *prefix;
1994 char *string, *p;
1996 gcc_assert (GET_CODE (exp) == EQ_ATTR);
1997 prefix = attr->enum_name ? attr->enum_name : attr->name;
1998 string = ACONCAT ((prefix, "_", XSTR (exp, 1), NULL));
1999 for (p = string; *p; p++)
2000 *p = TOUPPER (*p);
2002 newexp = attr_rtx (EQ, value,
2003 attr_rtx (SYMBOL_REF,
2004 DEF_ATTR_STRING (string)));
2005 break;
2008 case COND:
2009 /* We construct an IOR of all the cases for which the
2010 requested attribute value is present. Since we start with
2011 FALSE, if it is not present, FALSE will be returned.
2013 Each case is the AND of the NOT's of the previous conditions with the
2014 current condition; in the default case the current condition is TRUE.
2016 For each possible COND value, call ourselves recursively.
2018 The extra TRUE and FALSE expressions will be eliminated by another
2019 call to the simplification routine. */
2021 orexp = false_rtx;
2022 andexp = true_rtx;
2024 for (i = 0; i < XVECLEN (value, 0); i += 2)
2026 rtx this_cond = simplify_test_exp_in_temp (XVECEXP (value, 0, i),
2027 insn_code, insn_index);
2029 right = insert_right_side (AND, andexp, this_cond,
2030 insn_code, insn_index);
2031 right = insert_right_side (AND, right,
2032 evaluate_eq_attr (exp, attr,
2033 XVECEXP (value, 0,
2034 i + 1),
2035 insn_code, insn_index),
2036 insn_code, insn_index);
2037 orexp = insert_right_side (IOR, orexp, right,
2038 insn_code, insn_index);
2040 /* Add this condition into the AND expression. */
2041 newexp = attr_rtx (NOT, this_cond);
2042 andexp = insert_right_side (AND, andexp, newexp,
2043 insn_code, insn_index);
2046 /* Handle the default case. */
2047 right = insert_right_side (AND, andexp,
2048 evaluate_eq_attr (exp, attr, XEXP (value, 1),
2049 insn_code, insn_index),
2050 insn_code, insn_index);
2051 newexp = insert_right_side (IOR, orexp, right, insn_code, insn_index);
2052 break;
2054 default:
2055 gcc_unreachable ();
2058 /* If uses an address, must return original expression. But set the
2059 ATTR_IND_SIMPLIFIED_P bit so we don't try to simplify it again. */
2061 address_used = 0;
2062 walk_attr_value (newexp);
2064 if (address_used)
2066 if (! ATTR_IND_SIMPLIFIED_P (exp))
2067 return copy_rtx_unchanging (exp);
2068 return exp;
2070 else
2071 return newexp;
2074 /* This routine is called when an AND of a term with a tree of AND's is
2075 encountered. If the term or its complement is present in the tree, it
2076 can be replaced with TRUE or FALSE, respectively.
2078 Note that (eq_attr "att" "v1") and (eq_attr "att" "v2") cannot both
2079 be true and hence are complementary.
2081 There is one special case: If we see
2082 (and (not (eq_attr "att" "v1"))
2083 (eq_attr "att" "v2"))
2084 this can be replaced by (eq_attr "att" "v2"). To do this we need to
2085 replace the term, not anything in the AND tree. So we pass a pointer to
2086 the term. */
2088 static rtx
2089 simplify_and_tree (rtx exp, rtx *pterm, int insn_code, int insn_index)
2091 rtx left, right;
2092 rtx newexp;
2093 rtx temp;
2094 int left_eliminates_term, right_eliminates_term;
2096 if (GET_CODE (exp) == AND)
2098 left = simplify_and_tree (XEXP (exp, 0), pterm, insn_code, insn_index);
2099 right = simplify_and_tree (XEXP (exp, 1), pterm, insn_code, insn_index);
2100 if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
2102 newexp = attr_rtx (AND, left, right);
2104 exp = simplify_test_exp_in_temp (newexp, insn_code, insn_index);
2108 else if (GET_CODE (exp) == IOR)
2110 /* For the IOR case, we do the same as above, except that we can
2111 only eliminate `term' if both sides of the IOR would do so. */
2112 temp = *pterm;
2113 left = simplify_and_tree (XEXP (exp, 0), &temp, insn_code, insn_index);
2114 left_eliminates_term = (temp == true_rtx);
2116 temp = *pterm;
2117 right = simplify_and_tree (XEXP (exp, 1), &temp, insn_code, insn_index);
2118 right_eliminates_term = (temp == true_rtx);
2120 if (left_eliminates_term && right_eliminates_term)
2121 *pterm = true_rtx;
2123 if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
2125 newexp = attr_rtx (IOR, left, right);
2127 exp = simplify_test_exp_in_temp (newexp, insn_code, insn_index);
2131 /* Check for simplifications. Do some extra checking here since this
2132 routine is called so many times. */
2134 if (exp == *pterm)
2135 return true_rtx;
2137 else if (GET_CODE (exp) == NOT && XEXP (exp, 0) == *pterm)
2138 return false_rtx;
2140 else if (GET_CODE (*pterm) == NOT && exp == XEXP (*pterm, 0))
2141 return false_rtx;
2143 else if (GET_CODE (exp) == EQ_ATTR_ALT && GET_CODE (*pterm) == EQ_ATTR_ALT)
2145 if (attr_alt_subset_p (*pterm, exp))
2146 return true_rtx;
2148 if (attr_alt_subset_of_compl_p (*pterm, exp))
2149 return false_rtx;
2151 if (attr_alt_subset_p (exp, *pterm))
2152 *pterm = true_rtx;
2154 return exp;
2157 else if (GET_CODE (exp) == EQ_ATTR && GET_CODE (*pterm) == EQ_ATTR)
2159 if (XSTR (exp, 0) != XSTR (*pterm, 0))
2160 return exp;
2162 if (! strcmp_check (XSTR (exp, 1), XSTR (*pterm, 1)))
2163 return true_rtx;
2164 else
2165 return false_rtx;
2168 else if (GET_CODE (*pterm) == EQ_ATTR && GET_CODE (exp) == NOT
2169 && GET_CODE (XEXP (exp, 0)) == EQ_ATTR)
2171 if (XSTR (*pterm, 0) != XSTR (XEXP (exp, 0), 0))
2172 return exp;
2174 if (! strcmp_check (XSTR (*pterm, 1), XSTR (XEXP (exp, 0), 1)))
2175 return false_rtx;
2176 else
2177 return true_rtx;
2180 else if (GET_CODE (exp) == EQ_ATTR && GET_CODE (*pterm) == NOT
2181 && GET_CODE (XEXP (*pterm, 0)) == EQ_ATTR)
2183 if (XSTR (exp, 0) != XSTR (XEXP (*pterm, 0), 0))
2184 return exp;
2186 if (! strcmp_check (XSTR (exp, 1), XSTR (XEXP (*pterm, 0), 1)))
2187 return false_rtx;
2188 else
2189 *pterm = true_rtx;
2192 else if (GET_CODE (exp) == NOT && GET_CODE (*pterm) == NOT)
2194 if (attr_equal_p (XEXP (exp, 0), XEXP (*pterm, 0)))
2195 return true_rtx;
2198 else if (GET_CODE (exp) == NOT)
2200 if (attr_equal_p (XEXP (exp, 0), *pterm))
2201 return false_rtx;
2204 else if (GET_CODE (*pterm) == NOT)
2206 if (attr_equal_p (XEXP (*pterm, 0), exp))
2207 return false_rtx;
2210 else if (attr_equal_p (exp, *pterm))
2211 return true_rtx;
2213 return exp;
2216 /* Similar to `simplify_and_tree', but for IOR trees. */
2218 static rtx
2219 simplify_or_tree (rtx exp, rtx *pterm, int insn_code, int insn_index)
2221 rtx left, right;
2222 rtx newexp;
2223 rtx temp;
2224 int left_eliminates_term, right_eliminates_term;
2226 if (GET_CODE (exp) == IOR)
2228 left = simplify_or_tree (XEXP (exp, 0), pterm, insn_code, insn_index);
2229 right = simplify_or_tree (XEXP (exp, 1), pterm, insn_code, insn_index);
2230 if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
2232 newexp = attr_rtx (GET_CODE (exp), left, right);
2234 exp = simplify_test_exp_in_temp (newexp, insn_code, insn_index);
2238 else if (GET_CODE (exp) == AND)
2240 /* For the AND case, we do the same as above, except that we can
2241 only eliminate `term' if both sides of the AND would do so. */
2242 temp = *pterm;
2243 left = simplify_or_tree (XEXP (exp, 0), &temp, insn_code, insn_index);
2244 left_eliminates_term = (temp == false_rtx);
2246 temp = *pterm;
2247 right = simplify_or_tree (XEXP (exp, 1), &temp, insn_code, insn_index);
2248 right_eliminates_term = (temp == false_rtx);
2250 if (left_eliminates_term && right_eliminates_term)
2251 *pterm = false_rtx;
2253 if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
2255 newexp = attr_rtx (GET_CODE (exp), left, right);
2257 exp = simplify_test_exp_in_temp (newexp, insn_code, insn_index);
2261 if (attr_equal_p (exp, *pterm))
2262 return false_rtx;
2264 else if (GET_CODE (exp) == NOT && attr_equal_p (XEXP (exp, 0), *pterm))
2265 return true_rtx;
2267 else if (GET_CODE (*pterm) == NOT && attr_equal_p (XEXP (*pterm, 0), exp))
2268 return true_rtx;
2270 else if (GET_CODE (*pterm) == EQ_ATTR && GET_CODE (exp) == NOT
2271 && GET_CODE (XEXP (exp, 0)) == EQ_ATTR
2272 && XSTR (*pterm, 0) == XSTR (XEXP (exp, 0), 0))
2273 *pterm = false_rtx;
2275 else if (GET_CODE (exp) == EQ_ATTR && GET_CODE (*pterm) == NOT
2276 && GET_CODE (XEXP (*pterm, 0)) == EQ_ATTR
2277 && XSTR (exp, 0) == XSTR (XEXP (*pterm, 0), 0))
2278 return false_rtx;
2280 return exp;
2283 /* Compute approximate cost of the expression. Used to decide whether
2284 expression is cheap enough for inline. */
2285 static int
2286 attr_rtx_cost (rtx x)
2288 int cost = 0;
2289 enum rtx_code code;
2290 if (!x)
2291 return 0;
2292 code = GET_CODE (x);
2293 switch (code)
2295 case MATCH_OPERAND:
2296 if (XSTR (x, 1)[0])
2297 return 10;
2298 else
2299 return 0;
2301 case EQ_ATTR_ALT:
2302 return 0;
2304 case EQ_ATTR:
2305 /* Alternatives don't result into function call. */
2306 if (!strcmp_check (XSTR (x, 0), alternative_name))
2307 return 0;
2308 else
2309 return 5;
2310 default:
2312 int i, j;
2313 const char *fmt = GET_RTX_FORMAT (code);
2314 for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
2316 switch (fmt[i])
2318 case 'V':
2319 case 'E':
2320 for (j = 0; j < XVECLEN (x, i); j++)
2321 cost += attr_rtx_cost (XVECEXP (x, i, j));
2322 break;
2323 case 'e':
2324 cost += attr_rtx_cost (XEXP (x, i));
2325 break;
2329 break;
2331 return cost;
2334 /* Simplify test expression and use temporary obstack in order to avoid
2335 memory bloat. Use ATTR_IND_SIMPLIFIED to avoid unnecessary simplifications
2336 and avoid unnecessary copying if possible. */
2338 static rtx
2339 simplify_test_exp_in_temp (rtx exp, int insn_code, int insn_index)
2341 rtx x;
2342 struct obstack *old;
2343 if (ATTR_IND_SIMPLIFIED_P (exp))
2344 return exp;
2345 old = rtl_obstack;
2346 rtl_obstack = temp_obstack;
2347 x = simplify_test_exp (exp, insn_code, insn_index);
2348 rtl_obstack = old;
2349 if (x == exp || rtl_obstack == temp_obstack)
2350 return x;
2351 return attr_copy_rtx (x);
2354 /* Returns true if S1 is a subset of S2. */
2356 static bool
2357 attr_alt_subset_p (rtx s1, rtx s2)
2359 switch ((XINT (s1, 1) << 1) | XINT (s2, 1))
2361 case (0 << 1) | 0:
2362 return !(XINT (s1, 0) &~ XINT (s2, 0));
2364 case (0 << 1) | 1:
2365 return !(XINT (s1, 0) & XINT (s2, 0));
2367 case (1 << 1) | 0:
2368 return false;
2370 case (1 << 1) | 1:
2371 return !(XINT (s2, 0) &~ XINT (s1, 0));
2373 default:
2374 gcc_unreachable ();
2378 /* Returns true if S1 is a subset of complement of S2. */
2380 static bool
2381 attr_alt_subset_of_compl_p (rtx s1, rtx s2)
2383 switch ((XINT (s1, 1) << 1) | XINT (s2, 1))
2385 case (0 << 1) | 0:
2386 return !(XINT (s1, 0) & XINT (s2, 0));
2388 case (0 << 1) | 1:
2389 return !(XINT (s1, 0) & ~XINT (s2, 0));
2391 case (1 << 1) | 0:
2392 return !(XINT (s2, 0) &~ XINT (s1, 0));
2394 case (1 << 1) | 1:
2395 return false;
2397 default:
2398 gcc_unreachable ();
2402 /* Return EQ_ATTR_ALT expression representing intersection of S1 and S2. */
2404 static rtx
2405 attr_alt_intersection (rtx s1, rtx s2)
2407 rtx result = rtx_alloc (EQ_ATTR_ALT);
2409 switch ((XINT (s1, 1) << 1) | XINT (s2, 1))
2411 case (0 << 1) | 0:
2412 XINT (result, 0) = XINT (s1, 0) & XINT (s2, 0);
2413 break;
2414 case (0 << 1) | 1:
2415 XINT (result, 0) = XINT (s1, 0) & ~XINT (s2, 0);
2416 break;
2417 case (1 << 1) | 0:
2418 XINT (result, 0) = XINT (s2, 0) & ~XINT (s1, 0);
2419 break;
2420 case (1 << 1) | 1:
2421 XINT (result, 0) = XINT (s1, 0) | XINT (s2, 0);
2422 break;
2423 default:
2424 gcc_unreachable ();
2426 XINT (result, 1) = XINT (s1, 1) & XINT (s2, 1);
2428 return result;
2431 /* Return EQ_ATTR_ALT expression representing union of S1 and S2. */
2433 static rtx
2434 attr_alt_union (rtx s1, rtx s2)
2436 rtx result = rtx_alloc (EQ_ATTR_ALT);
2438 switch ((XINT (s1, 1) << 1) | XINT (s2, 1))
2440 case (0 << 1) | 0:
2441 XINT (result, 0) = XINT (s1, 0) | XINT (s2, 0);
2442 break;
2443 case (0 << 1) | 1:
2444 XINT (result, 0) = XINT (s2, 0) & ~XINT (s1, 0);
2445 break;
2446 case (1 << 1) | 0:
2447 XINT (result, 0) = XINT (s1, 0) & ~XINT (s2, 0);
2448 break;
2449 case (1 << 1) | 1:
2450 XINT (result, 0) = XINT (s1, 0) & XINT (s2, 0);
2451 break;
2452 default:
2453 gcc_unreachable ();
2456 XINT (result, 1) = XINT (s1, 1) | XINT (s2, 1);
2457 return result;
2460 /* Return EQ_ATTR_ALT expression representing complement of S. */
2462 static rtx
2463 attr_alt_complement (rtx s)
2465 rtx result = rtx_alloc (EQ_ATTR_ALT);
2467 XINT (result, 0) = XINT (s, 0);
2468 XINT (result, 1) = 1 - XINT (s, 1);
2470 return result;
2473 /* Return EQ_ATTR_ALT expression representing set containing elements set
2474 in E. */
2476 static rtx
2477 mk_attr_alt (int e)
2479 rtx result = rtx_alloc (EQ_ATTR_ALT);
2481 XINT (result, 0) = e;
2482 XINT (result, 1) = 0;
2484 return result;
2487 /* Given an expression, see if it can be simplified for a particular insn
2488 code based on the values of other attributes being tested. This can
2489 eliminate nested get_attr_... calls.
2491 Note that if an endless recursion is specified in the patterns, the
2492 optimization will loop. However, it will do so in precisely the cases where
2493 an infinite recursion loop could occur during compilation. It's better that
2494 it occurs here! */
2496 static rtx
2497 simplify_test_exp (rtx exp, int insn_code, int insn_index)
2499 rtx left, right;
2500 struct attr_desc *attr;
2501 struct attr_value *av;
2502 struct insn_ent *ie;
2503 struct attr_value_list *iv;
2504 int i;
2505 rtx newexp = exp;
2506 bool left_alt, right_alt;
2508 /* Don't re-simplify something we already simplified. */
2509 if (ATTR_IND_SIMPLIFIED_P (exp) || ATTR_CURR_SIMPLIFIED_P (exp))
2510 return exp;
2512 switch (GET_CODE (exp))
2514 case AND:
2515 left = SIMPLIFY_TEST_EXP (XEXP (exp, 0), insn_code, insn_index);
2516 if (left == false_rtx)
2517 return false_rtx;
2518 right = SIMPLIFY_TEST_EXP (XEXP (exp, 1), insn_code, insn_index);
2519 if (right == false_rtx)
2520 return false_rtx;
2522 if (GET_CODE (left) == EQ_ATTR_ALT
2523 && GET_CODE (right) == EQ_ATTR_ALT)
2525 exp = attr_alt_intersection (left, right);
2526 return simplify_test_exp (exp, insn_code, insn_index);
2529 /* If either side is an IOR and we have (eq_attr "alternative" ..")
2530 present on both sides, apply the distributive law since this will
2531 yield simplifications. */
2532 if ((GET_CODE (left) == IOR || GET_CODE (right) == IOR)
2533 && compute_alternative_mask (left, IOR)
2534 && compute_alternative_mask (right, IOR))
2536 if (GET_CODE (left) == IOR)
2538 rtx tem = left;
2539 left = right;
2540 right = tem;
2543 newexp = attr_rtx (IOR,
2544 attr_rtx (AND, left, XEXP (right, 0)),
2545 attr_rtx (AND, left, XEXP (right, 1)));
2547 return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
2550 /* Try with the term on both sides. */
2551 right = simplify_and_tree (right, &left, insn_code, insn_index);
2552 if (left == XEXP (exp, 0) && right == XEXP (exp, 1))
2553 left = simplify_and_tree (left, &right, insn_code, insn_index);
2555 if (left == false_rtx || right == false_rtx)
2556 return false_rtx;
2557 else if (left == true_rtx)
2559 return right;
2561 else if (right == true_rtx)
2563 return left;
2565 /* See if all or all but one of the insn's alternatives are specified
2566 in this tree. Optimize if so. */
2568 if (GET_CODE (left) == NOT)
2569 left_alt = (GET_CODE (XEXP (left, 0)) == EQ_ATTR
2570 && XSTR (XEXP (left, 0), 0) == alternative_name);
2571 else
2572 left_alt = (GET_CODE (left) == EQ_ATTR_ALT
2573 && XINT (left, 1));
2575 if (GET_CODE (right) == NOT)
2576 right_alt = (GET_CODE (XEXP (right, 0)) == EQ_ATTR
2577 && XSTR (XEXP (right, 0), 0) == alternative_name);
2578 else
2579 right_alt = (GET_CODE (right) == EQ_ATTR_ALT
2580 && XINT (right, 1));
2582 if (insn_code >= 0
2583 && (GET_CODE (left) == AND
2584 || left_alt
2585 || GET_CODE (right) == AND
2586 || right_alt))
2588 i = compute_alternative_mask (exp, AND);
2589 if (i & ~insn_alternatives[insn_code])
2590 fatal ("invalid alternative specified for pattern number %d",
2591 insn_index);
2593 /* If all alternatives are excluded, this is false. */
2594 i ^= insn_alternatives[insn_code];
2595 if (i == 0)
2596 return false_rtx;
2597 else if ((i & (i - 1)) == 0 && insn_alternatives[insn_code] > 1)
2599 /* If just one excluded, AND a comparison with that one to the
2600 front of the tree. The others will be eliminated by
2601 optimization. We do not want to do this if the insn has one
2602 alternative and we have tested none of them! */
2603 left = make_alternative_compare (i);
2604 right = simplify_and_tree (exp, &left, insn_code, insn_index);
2605 newexp = attr_rtx (AND, left, right);
2607 return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
2611 if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
2613 newexp = attr_rtx (AND, left, right);
2614 return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
2616 break;
2618 case IOR:
2619 left = SIMPLIFY_TEST_EXP (XEXP (exp, 0), insn_code, insn_index);
2620 if (left == true_rtx)
2621 return true_rtx;
2622 right = SIMPLIFY_TEST_EXP (XEXP (exp, 1), insn_code, insn_index);
2623 if (right == true_rtx)
2624 return true_rtx;
2626 if (GET_CODE (left) == EQ_ATTR_ALT
2627 && GET_CODE (right) == EQ_ATTR_ALT)
2629 exp = attr_alt_union (left, right);
2630 return simplify_test_exp (exp, insn_code, insn_index);
2633 right = simplify_or_tree (right, &left, insn_code, insn_index);
2634 if (left == XEXP (exp, 0) && right == XEXP (exp, 1))
2635 left = simplify_or_tree (left, &right, insn_code, insn_index);
2637 if (right == true_rtx || left == true_rtx)
2638 return true_rtx;
2639 else if (left == false_rtx)
2641 return right;
2643 else if (right == false_rtx)
2645 return left;
2648 /* Test for simple cases where the distributive law is useful. I.e.,
2649 convert (ior (and (x) (y))
2650 (and (x) (z)))
2651 to (and (x)
2652 (ior (y) (z)))
2655 else if (GET_CODE (left) == AND && GET_CODE (right) == AND
2656 && attr_equal_p (XEXP (left, 0), XEXP (right, 0)))
2658 newexp = attr_rtx (IOR, XEXP (left, 1), XEXP (right, 1));
2660 left = XEXP (left, 0);
2661 right = newexp;
2662 newexp = attr_rtx (AND, left, right);
2663 return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
2666 /* See if all or all but one of the insn's alternatives are specified
2667 in this tree. Optimize if so. */
2669 else if (insn_code >= 0
2670 && (GET_CODE (left) == IOR
2671 || (GET_CODE (left) == EQ_ATTR_ALT
2672 && !XINT (left, 1))
2673 || (GET_CODE (left) == EQ_ATTR
2674 && XSTR (left, 0) == alternative_name)
2675 || GET_CODE (right) == IOR
2676 || (GET_CODE (right) == EQ_ATTR_ALT
2677 && !XINT (right, 1))
2678 || (GET_CODE (right) == EQ_ATTR
2679 && XSTR (right, 0) == alternative_name)))
2681 i = compute_alternative_mask (exp, IOR);
2682 if (i & ~insn_alternatives[insn_code])
2683 fatal ("invalid alternative specified for pattern number %d",
2684 insn_index);
2686 /* If all alternatives are included, this is true. */
2687 i ^= insn_alternatives[insn_code];
2688 if (i == 0)
2689 return true_rtx;
2690 else if ((i & (i - 1)) == 0 && insn_alternatives[insn_code] > 1)
2692 /* If just one excluded, IOR a comparison with that one to the
2693 front of the tree. The others will be eliminated by
2694 optimization. We do not want to do this if the insn has one
2695 alternative and we have tested none of them! */
2696 left = make_alternative_compare (i);
2697 right = simplify_and_tree (exp, &left, insn_code, insn_index);
2698 newexp = attr_rtx (IOR, attr_rtx (NOT, left), right);
2700 return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
2704 if (left != XEXP (exp, 0) || right != XEXP (exp, 1))
2706 newexp = attr_rtx (IOR, left, right);
2707 return SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
2709 break;
2711 case NOT:
2712 if (GET_CODE (XEXP (exp, 0)) == NOT)
2714 left = SIMPLIFY_TEST_EXP (XEXP (XEXP (exp, 0), 0),
2715 insn_code, insn_index);
2716 return left;
2719 left = SIMPLIFY_TEST_EXP (XEXP (exp, 0), insn_code, insn_index);
2720 if (GET_CODE (left) == NOT)
2721 return XEXP (left, 0);
2723 if (left == false_rtx)
2724 return true_rtx;
2725 if (left == true_rtx)
2726 return false_rtx;
2728 if (GET_CODE (left) == EQ_ATTR_ALT)
2730 exp = attr_alt_complement (left);
2731 return simplify_test_exp (exp, insn_code, insn_index);
2734 /* Try to apply De`Morgan's laws. */
2735 if (GET_CODE (left) == IOR)
2737 newexp = attr_rtx (AND,
2738 attr_rtx (NOT, XEXP (left, 0)),
2739 attr_rtx (NOT, XEXP (left, 1)));
2741 newexp = SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
2743 else if (GET_CODE (left) == AND)
2745 newexp = attr_rtx (IOR,
2746 attr_rtx (NOT, XEXP (left, 0)),
2747 attr_rtx (NOT, XEXP (left, 1)));
2749 newexp = SIMPLIFY_TEST_EXP (newexp, insn_code, insn_index);
2751 else if (left != XEXP (exp, 0))
2753 newexp = attr_rtx (NOT, left);
2755 break;
2757 case EQ_ATTR_ALT:
2758 if (!XINT (exp, 0))
2759 return XINT (exp, 1) ? true_rtx : false_rtx;
2760 break;
2762 case EQ_ATTR:
2763 if (XSTR (exp, 0) == alternative_name)
2765 newexp = mk_attr_alt (1 << atoi (XSTR (exp, 1)));
2766 break;
2769 /* Look at the value for this insn code in the specified attribute.
2770 We normally can replace this comparison with the condition that
2771 would give this insn the values being tested for. */
2772 if (insn_code >= 0
2773 && (attr = find_attr (&XSTR (exp, 0), 0)) != NULL)
2775 rtx x;
2777 av = NULL;
2778 if (insn_code_values)
2780 for (iv = insn_code_values[insn_code]; iv; iv = iv->next)
2781 if (iv->attr == attr)
2783 av = iv->av;
2784 break;
2787 else
2789 for (av = attr->first_value; av; av = av->next)
2790 for (ie = av->first_insn; ie; ie = ie->next)
2791 if (ie->def->insn_code == insn_code)
2792 goto got_av;
2795 if (av)
2797 got_av:
2798 x = evaluate_eq_attr (exp, attr, av->value,
2799 insn_code, insn_index);
2800 x = SIMPLIFY_TEST_EXP (x, insn_code, insn_index);
2801 if (attr_rtx_cost(x) < 20)
2802 return x;
2805 break;
2807 default:
2808 break;
2811 /* We have already simplified this expression. Simplifying it again
2812 won't buy anything unless we weren't given a valid insn code
2813 to process (i.e., we are canonicalizing something.). */
2814 if (insn_code != -2
2815 && ! ATTR_IND_SIMPLIFIED_P (newexp))
2816 return copy_rtx_unchanging (newexp);
2818 return newexp;
2821 /* Optimize the attribute lists by seeing if we can determine conditional
2822 values from the known values of other attributes. This will save subroutine
2823 calls during the compilation. */
2825 static void
2826 optimize_attrs (void)
2828 struct attr_desc *attr;
2829 struct attr_value *av;
2830 struct insn_ent *ie;
2831 rtx newexp;
2832 int i;
2833 struct attr_value_list *ivbuf;
2834 struct attr_value_list *iv;
2836 /* For each insn code, make a list of all the insn_ent's for it,
2837 for all values for all attributes. */
2839 if (num_insn_ents == 0)
2840 return;
2842 /* Make 2 extra elements, for "code" values -2 and -1. */
2843 insn_code_values = XCNEWVEC (struct attr_value_list *, insn_code_number + 2);
2845 /* Offset the table address so we can index by -2 or -1. */
2846 insn_code_values += 2;
2848 iv = ivbuf = XNEWVEC (struct attr_value_list, num_insn_ents);
2850 for (i = 0; i < MAX_ATTRS_INDEX; i++)
2851 for (attr = attrs[i]; attr; attr = attr->next)
2852 for (av = attr->first_value; av; av = av->next)
2853 for (ie = av->first_insn; ie; ie = ie->next)
2855 iv->attr = attr;
2856 iv->av = av;
2857 iv->ie = ie;
2858 iv->next = insn_code_values[ie->def->insn_code];
2859 insn_code_values[ie->def->insn_code] = iv;
2860 iv++;
2863 /* Sanity check on num_insn_ents. */
2864 gcc_assert (iv == ivbuf + num_insn_ents);
2866 /* Process one insn code at a time. */
2867 for (i = -2; i < insn_code_number; i++)
2869 /* Clear the ATTR_CURR_SIMPLIFIED_P flag everywhere relevant.
2870 We use it to mean "already simplified for this insn". */
2871 for (iv = insn_code_values[i]; iv; iv = iv->next)
2872 clear_struct_flag (iv->av->value);
2874 for (iv = insn_code_values[i]; iv; iv = iv->next)
2876 struct obstack *old = rtl_obstack;
2878 attr = iv->attr;
2879 av = iv->av;
2880 ie = iv->ie;
2881 if (GET_CODE (av->value) != COND)
2882 continue;
2884 rtl_obstack = temp_obstack;
2885 newexp = av->value;
2886 while (GET_CODE (newexp) == COND)
2888 rtx newexp2 = simplify_cond (newexp, ie->def->insn_code,
2889 ie->def->insn_index);
2890 if (newexp2 == newexp)
2891 break;
2892 newexp = newexp2;
2895 rtl_obstack = old;
2896 if (newexp != av->value)
2898 newexp = attr_copy_rtx (newexp);
2899 remove_insn_ent (av, ie);
2900 av = get_attr_value (newexp, attr, ie->def->insn_code);
2901 iv->av = av;
2902 insert_insn_ent (av, ie);
2907 free (ivbuf);
2908 free (insn_code_values - 2);
2909 insn_code_values = NULL;
2912 /* Clear the ATTR_CURR_SIMPLIFIED_P flag in EXP and its subexpressions. */
2914 static void
2915 clear_struct_flag (rtx x)
2917 int i;
2918 int j;
2919 enum rtx_code code;
2920 const char *fmt;
2922 ATTR_CURR_SIMPLIFIED_P (x) = 0;
2923 if (ATTR_IND_SIMPLIFIED_P (x))
2924 return;
2926 code = GET_CODE (x);
2928 switch (code)
2930 case REG:
2931 case CONST_INT:
2932 case CONST_DOUBLE:
2933 case CONST_VECTOR:
2934 case MATCH_TEST:
2935 case SYMBOL_REF:
2936 case CODE_LABEL:
2937 case PC:
2938 case CC0:
2939 case EQ_ATTR:
2940 case ATTR_FLAG:
2941 return;
2943 default:
2944 break;
2947 /* Compare the elements. If any pair of corresponding elements
2948 fail to match, return 0 for the whole things. */
2950 fmt = GET_RTX_FORMAT (code);
2951 for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
2953 switch (fmt[i])
2955 case 'V':
2956 case 'E':
2957 for (j = 0; j < XVECLEN (x, i); j++)
2958 clear_struct_flag (XVECEXP (x, i, j));
2959 break;
2961 case 'e':
2962 clear_struct_flag (XEXP (x, i));
2963 break;
2968 /* Add attribute value NAME to the beginning of ATTR's list. */
2970 static void
2971 add_attr_value (struct attr_desc *attr, const char *name)
2973 struct attr_value *av;
2975 av = oballoc (struct attr_value);
2976 av->value = attr_rtx (CONST_STRING, name);
2977 av->next = attr->first_value;
2978 attr->first_value = av;
2979 av->first_insn = NULL;
2980 av->num_insns = 0;
2981 av->has_asm_insn = 0;
2984 /* Create table entries for DEFINE_ATTR or DEFINE_ENUM_ATTR. */
2986 static void
2987 gen_attr (rtx exp, int lineno)
2989 struct enum_type *et;
2990 struct enum_value *ev;
2991 struct attr_desc *attr;
2992 const char *name_ptr;
2993 char *p;
2995 /* Make a new attribute structure. Check for duplicate by looking at
2996 attr->default_val, since it is initialized by this routine. */
2997 attr = find_attr (&XSTR (exp, 0), 1);
2998 if (attr->default_val)
3000 error_with_line (lineno, "duplicate definition for attribute %s",
3001 attr->name);
3002 message_with_line (attr->lineno, "previous definition");
3003 return;
3005 attr->lineno = lineno;
3007 if (GET_CODE (exp) == DEFINE_ENUM_ATTR)
3009 attr->enum_name = XSTR (exp, 1);
3010 et = lookup_enum_type (XSTR (exp, 1));
3011 if (!et || !et->md_p)
3012 error_with_line (lineno, "No define_enum called `%s' defined",
3013 attr->name);
3014 if (et)
3015 for (ev = et->values; ev; ev = ev->next)
3016 add_attr_value (attr, ev->name);
3018 else if (*XSTR (exp, 1) == '\0')
3019 attr->is_numeric = 1;
3020 else
3022 name_ptr = XSTR (exp, 1);
3023 while ((p = next_comma_elt (&name_ptr)) != NULL)
3024 add_attr_value (attr, p);
3027 if (GET_CODE (XEXP (exp, 2)) == CONST)
3029 attr->is_const = 1;
3030 if (attr->is_numeric)
3031 error_with_line (lineno,
3032 "constant attributes may not take numeric values");
3034 /* Get rid of the CONST node. It is allowed only at top-level. */
3035 XEXP (exp, 2) = XEXP (XEXP (exp, 2), 0);
3038 if (! strcmp_check (attr->name, length_str) && ! attr->is_numeric)
3039 error_with_line (lineno, "`length' attribute must take numeric values");
3041 /* Set up the default value. */
3042 XEXP (exp, 2) = check_attr_value (XEXP (exp, 2), attr);
3043 attr->default_val = get_attr_value (XEXP (exp, 2), attr, -2);
3046 /* Given a pattern for DEFINE_PEEPHOLE or DEFINE_INSN, return the number of
3047 alternatives in the constraints. Assume all MATCH_OPERANDs have the same
3048 number of alternatives as this should be checked elsewhere. */
3050 static int
3051 count_alternatives (rtx exp)
3053 int i, j, n;
3054 const char *fmt;
3056 if (GET_CODE (exp) == MATCH_OPERAND)
3057 return n_comma_elts (XSTR (exp, 2));
3059 for (i = 0, fmt = GET_RTX_FORMAT (GET_CODE (exp));
3060 i < GET_RTX_LENGTH (GET_CODE (exp)); i++)
3061 switch (*fmt++)
3063 case 'e':
3064 case 'u':
3065 n = count_alternatives (XEXP (exp, i));
3066 if (n)
3067 return n;
3068 break;
3070 case 'E':
3071 case 'V':
3072 if (XVEC (exp, i) != NULL)
3073 for (j = 0; j < XVECLEN (exp, i); j++)
3075 n = count_alternatives (XVECEXP (exp, i, j));
3076 if (n)
3077 return n;
3081 return 0;
3084 /* Returns nonzero if the given expression contains an EQ_ATTR with the
3085 `alternative' attribute. */
3087 static int
3088 compares_alternatives_p (rtx exp)
3090 int i, j;
3091 const char *fmt;
3093 if (GET_CODE (exp) == EQ_ATTR && XSTR (exp, 0) == alternative_name)
3094 return 1;
3096 for (i = 0, fmt = GET_RTX_FORMAT (GET_CODE (exp));
3097 i < GET_RTX_LENGTH (GET_CODE (exp)); i++)
3098 switch (*fmt++)
3100 case 'e':
3101 case 'u':
3102 if (compares_alternatives_p (XEXP (exp, i)))
3103 return 1;
3104 break;
3106 case 'E':
3107 for (j = 0; j < XVECLEN (exp, i); j++)
3108 if (compares_alternatives_p (XVECEXP (exp, i, j)))
3109 return 1;
3110 break;
3113 return 0;
3116 /* Process DEFINE_PEEPHOLE, DEFINE_INSN, and DEFINE_ASM_ATTRIBUTES. */
3118 static void
3119 gen_insn (rtx exp, int lineno)
3121 struct insn_def *id;
3123 id = oballoc (struct insn_def);
3124 id->next = defs;
3125 defs = id;
3126 id->def = exp;
3127 id->lineno = lineno;
3129 switch (GET_CODE (exp))
3131 case DEFINE_INSN:
3132 id->insn_code = insn_code_number;
3133 id->insn_index = insn_index_number;
3134 id->num_alternatives = count_alternatives (exp);
3135 if (id->num_alternatives == 0)
3136 id->num_alternatives = 1;
3137 id->vec_idx = 4;
3138 break;
3140 case DEFINE_PEEPHOLE:
3141 id->insn_code = insn_code_number;
3142 id->insn_index = insn_index_number;
3143 id->num_alternatives = count_alternatives (exp);
3144 if (id->num_alternatives == 0)
3145 id->num_alternatives = 1;
3146 id->vec_idx = 3;
3147 break;
3149 case DEFINE_ASM_ATTRIBUTES:
3150 id->insn_code = -1;
3151 id->insn_index = -1;
3152 id->num_alternatives = 1;
3153 id->vec_idx = 0;
3154 got_define_asm_attributes = 1;
3155 break;
3157 default:
3158 gcc_unreachable ();
3162 /* Process a DEFINE_DELAY. Validate the vector length, check if annul
3163 true or annul false is specified, and make a `struct delay_desc'. */
3165 static void
3166 gen_delay (rtx def, int lineno)
3168 struct delay_desc *delay;
3169 int i;
3171 if (XVECLEN (def, 1) % 3 != 0)
3173 error_with_line (lineno,
3174 "number of elements in DEFINE_DELAY must"
3175 " be multiple of three");
3176 return;
3179 for (i = 0; i < XVECLEN (def, 1); i += 3)
3181 if (XVECEXP (def, 1, i + 1))
3182 have_annul_true = 1;
3183 if (XVECEXP (def, 1, i + 2))
3184 have_annul_false = 1;
3187 delay = oballoc (struct delay_desc);
3188 delay->def = def;
3189 delay->num = ++num_delays;
3190 delay->next = delays;
3191 delay->lineno = lineno;
3192 delays = delay;
3195 /* Names of attributes that could be possibly cached. */
3196 static const char *cached_attrs[32];
3197 /* Number of such attributes. */
3198 static int cached_attr_count;
3199 /* Bitmasks of possibly cached attributes. */
3200 static unsigned int attrs_seen_once, attrs_seen_more_than_once;
3201 static unsigned int attrs_to_cache;
3202 static unsigned int attrs_cached_inside, attrs_cached_after;
3204 /* Finds non-const attributes that could be possibly cached.
3205 When create is TRUE, fills in cached_attrs array.
3206 Computes ATTRS_SEEN_ONCE and ATTRS_SEEN_MORE_THAN_ONCE
3207 bitmasks. */
3209 static void
3210 find_attrs_to_cache (rtx exp, bool create)
3212 int i;
3213 const char *name;
3214 struct attr_desc *attr;
3216 if (exp == NULL)
3217 return;
3219 switch (GET_CODE (exp))
3221 case NOT:
3222 if (GET_CODE (XEXP (exp, 0)) == EQ_ATTR)
3223 find_attrs_to_cache (XEXP (exp, 0), create);
3224 return;
3226 case EQ_ATTR:
3227 name = XSTR (exp, 0);
3228 if (name == alternative_name)
3229 return;
3230 for (i = 0; i < cached_attr_count; i++)
3231 if (name == cached_attrs[i])
3233 if ((attrs_seen_once & (1U << i)) != 0)
3234 attrs_seen_more_than_once |= (1U << i);
3235 else
3236 attrs_seen_once |= (1U << i);
3237 return;
3239 if (!create)
3240 return;
3241 attr = find_attr (&name, 0);
3242 gcc_assert (attr);
3243 if (attr->is_const)
3244 return;
3245 if (cached_attr_count == 32)
3246 return;
3247 cached_attrs[cached_attr_count] = XSTR (exp, 0);
3248 attrs_seen_once |= (1U << cached_attr_count);
3249 cached_attr_count++;
3250 return;
3252 case AND:
3253 case IOR:
3254 find_attrs_to_cache (XEXP (exp, 0), create);
3255 find_attrs_to_cache (XEXP (exp, 1), create);
3256 return;
3258 case COND:
3259 for (i = 0; i < XVECLEN (exp, 0); i += 2)
3260 find_attrs_to_cache (XVECEXP (exp, 0, i), create);
3261 return;
3263 default:
3264 return;
3268 /* Given a piece of RTX, print a C expression to test its truth value to OUTF.
3269 We use AND and IOR both for logical and bit-wise operations, so
3270 interpret them as logical unless they are inside a comparison expression. */
3272 /* Interpret AND/IOR as bit-wise operations instead of logical. */
3273 #define FLG_BITWISE 1
3274 /* Set if cached attribute will be known initialized in else block after
3275 this condition. This is true for LHS of toplevel && and || and
3276 even for RHS of ||, but not for RHS of &&. */
3277 #define FLG_AFTER 2
3278 /* Set if cached attribute will be known initialized in then block after
3279 this condition. This is true for LHS of toplevel && and || and
3280 even for RHS of &&, but not for RHS of ||. */
3281 #define FLG_INSIDE 4
3282 /* Cleared when an operand of &&. */
3283 #define FLG_OUTSIDE_AND 8
3285 static unsigned int
3286 write_test_expr (FILE *outf, rtx exp, unsigned int attrs_cached, int flags)
3288 int comparison_operator = 0;
3289 RTX_CODE code;
3290 struct attr_desc *attr;
3292 /* In order not to worry about operator precedence, surround our part of
3293 the expression with parentheses. */
3295 fprintf (outf, "(");
3296 code = GET_CODE (exp);
3297 switch (code)
3299 /* Binary operators. */
3300 case GEU: case GTU:
3301 case LEU: case LTU:
3302 fprintf (outf, "(unsigned) ");
3303 /* Fall through. */
3305 case EQ: case NE:
3306 case GE: case GT:
3307 case LE: case LT:
3308 comparison_operator = FLG_BITWISE;
3310 case PLUS: case MINUS: case MULT: case DIV: case MOD:
3311 case AND: case IOR: case XOR:
3312 case ASHIFT: case LSHIFTRT: case ASHIFTRT:
3313 if ((code != AND && code != IOR) || (flags & FLG_BITWISE))
3315 flags &= ~(FLG_AFTER | FLG_INSIDE | FLG_OUTSIDE_AND);
3316 write_test_expr (outf, XEXP (exp, 0), attrs_cached,
3317 flags | comparison_operator);
3319 else
3321 if (code == AND)
3322 flags &= ~FLG_OUTSIDE_AND;
3323 if (GET_CODE (XEXP (exp, 0)) == code
3324 || GET_CODE (XEXP (exp, 0)) == EQ_ATTR
3325 || (GET_CODE (XEXP (exp, 0)) == NOT
3326 && GET_CODE (XEXP (XEXP (exp, 0), 0)) == EQ_ATTR))
3327 attrs_cached
3328 = write_test_expr (outf, XEXP (exp, 0), attrs_cached, flags);
3329 else
3330 write_test_expr (outf, XEXP (exp, 0), attrs_cached, flags);
3332 switch (code)
3334 case EQ:
3335 fprintf (outf, " == ");
3336 break;
3337 case NE:
3338 fprintf (outf, " != ");
3339 break;
3340 case GE:
3341 fprintf (outf, " >= ");
3342 break;
3343 case GT:
3344 fprintf (outf, " > ");
3345 break;
3346 case GEU:
3347 fprintf (outf, " >= (unsigned) ");
3348 break;
3349 case GTU:
3350 fprintf (outf, " > (unsigned) ");
3351 break;
3352 case LE:
3353 fprintf (outf, " <= ");
3354 break;
3355 case LT:
3356 fprintf (outf, " < ");
3357 break;
3358 case LEU:
3359 fprintf (outf, " <= (unsigned) ");
3360 break;
3361 case LTU:
3362 fprintf (outf, " < (unsigned) ");
3363 break;
3364 case PLUS:
3365 fprintf (outf, " + ");
3366 break;
3367 case MINUS:
3368 fprintf (outf, " - ");
3369 break;
3370 case MULT:
3371 fprintf (outf, " * ");
3372 break;
3373 case DIV:
3374 fprintf (outf, " / ");
3375 break;
3376 case MOD:
3377 fprintf (outf, " %% ");
3378 break;
3379 case AND:
3380 if (flags & FLG_BITWISE)
3381 fprintf (outf, " & ");
3382 else
3383 fprintf (outf, " && ");
3384 break;
3385 case IOR:
3386 if (flags & FLG_BITWISE)
3387 fprintf (outf, " | ");
3388 else
3389 fprintf (outf, " || ");
3390 break;
3391 case XOR:
3392 fprintf (outf, " ^ ");
3393 break;
3394 case ASHIFT:
3395 fprintf (outf, " << ");
3396 break;
3397 case LSHIFTRT:
3398 case ASHIFTRT:
3399 fprintf (outf, " >> ");
3400 break;
3401 default:
3402 gcc_unreachable ();
3405 if (code == AND)
3407 /* For if (something && (cached_x = get_attr_x (insn)) == X)
3408 cached_x is only known to be initialized in then block. */
3409 flags &= ~FLG_AFTER;
3411 else if (code == IOR)
3413 if (flags & FLG_OUTSIDE_AND)
3414 /* For if (something || (cached_x = get_attr_x (insn)) == X)
3415 cached_x is only known to be initialized in else block
3416 and else if conditions. */
3417 flags &= ~FLG_INSIDE;
3418 else
3419 /* For if ((something || (cached_x = get_attr_x (insn)) == X)
3420 && something_else)
3421 cached_x is not know to be initialized anywhere. */
3422 flags &= ~(FLG_AFTER | FLG_INSIDE);
3424 if ((code == AND || code == IOR)
3425 && (GET_CODE (XEXP (exp, 1)) == code
3426 || GET_CODE (XEXP (exp, 1)) == EQ_ATTR
3427 || (GET_CODE (XEXP (exp, 1)) == NOT
3428 && GET_CODE (XEXP (XEXP (exp, 1), 0)) == EQ_ATTR)))
3429 attrs_cached
3430 = write_test_expr (outf, XEXP (exp, 1), attrs_cached, flags);
3431 else
3432 write_test_expr (outf, XEXP (exp, 1), attrs_cached,
3433 flags | comparison_operator);
3434 break;
3436 case NOT:
3437 /* Special-case (not (eq_attrq "alternative" "x")) */
3438 if (! (flags & FLG_BITWISE) && GET_CODE (XEXP (exp, 0)) == EQ_ATTR)
3440 if (XSTR (XEXP (exp, 0), 0) == alternative_name)
3442 fprintf (outf, "which_alternative != %s",
3443 XSTR (XEXP (exp, 0), 1));
3444 break;
3447 fprintf (outf, "! ");
3448 attrs_cached =
3449 write_test_expr (outf, XEXP (exp, 0), attrs_cached, flags);
3450 break;
3453 /* Otherwise, fall through to normal unary operator. */
3455 /* Unary operators. */
3456 case ABS: case NEG:
3457 switch (code)
3459 case NOT:
3460 if (flags & FLG_BITWISE)
3461 fprintf (outf, "~ ");
3462 else
3463 fprintf (outf, "! ");
3464 break;
3465 case ABS:
3466 fprintf (outf, "abs ");
3467 break;
3468 case NEG:
3469 fprintf (outf, "-");
3470 break;
3471 default:
3472 gcc_unreachable ();
3475 flags &= ~(FLG_AFTER | FLG_INSIDE | FLG_OUTSIDE_AND);
3476 write_test_expr (outf, XEXP (exp, 0), attrs_cached, flags);
3477 break;
3479 case EQ_ATTR_ALT:
3481 int set = XINT (exp, 0), bit = 0;
3483 if (flags & FLG_BITWISE)
3484 fatal ("EQ_ATTR_ALT not valid inside comparison");
3486 if (!set)
3487 fatal ("Empty EQ_ATTR_ALT should be optimized out");
3489 if (!(set & (set - 1)))
3491 if (!(set & 0xffff))
3493 bit += 16;
3494 set >>= 16;
3496 if (!(set & 0xff))
3498 bit += 8;
3499 set >>= 8;
3501 if (!(set & 0xf))
3503 bit += 4;
3504 set >>= 4;
3506 if (!(set & 0x3))
3508 bit += 2;
3509 set >>= 2;
3511 if (!(set & 1))
3512 bit++;
3514 fprintf (outf, "which_alternative %s= %d",
3515 XINT (exp, 1) ? "!" : "=", bit);
3517 else
3519 fprintf (outf, "%s((1 << which_alternative) & %#x)",
3520 XINT (exp, 1) ? "!" : "", set);
3523 break;
3525 /* Comparison test of an attribute with a value. Most of these will
3526 have been removed by optimization. Handle "alternative"
3527 specially and give error if EQ_ATTR present inside a comparison. */
3528 case EQ_ATTR:
3529 if (flags & FLG_BITWISE)
3530 fatal ("EQ_ATTR not valid inside comparison");
3532 if (XSTR (exp, 0) == alternative_name)
3534 fprintf (outf, "which_alternative == %s", XSTR (exp, 1));
3535 break;
3538 attr = find_attr (&XSTR (exp, 0), 0);
3539 gcc_assert (attr);
3541 /* Now is the time to expand the value of a constant attribute. */
3542 if (attr->is_const)
3544 write_test_expr (outf,
3545 evaluate_eq_attr (exp, attr,
3546 attr->default_val->value,
3547 -2, -2),
3548 attrs_cached, 0);
3550 else
3552 int i;
3553 for (i = 0; i < cached_attr_count; i++)
3554 if (attr->name == cached_attrs[i])
3555 break;
3556 if (i < cached_attr_count && (attrs_cached & (1U << i)) != 0)
3557 fprintf (outf, "cached_%s", attr->name);
3558 else if (i < cached_attr_count && (attrs_to_cache & (1U << i)) != 0)
3560 fprintf (outf, "(cached_%s = get_attr_%s (insn))",
3561 attr->name, attr->name);
3562 if (flags & FLG_AFTER)
3563 attrs_cached_after |= (1U << i);
3564 if (flags & FLG_INSIDE)
3565 attrs_cached_inside |= (1U << i);
3566 attrs_cached |= (1U << i);
3568 else
3569 fprintf (outf, "get_attr_%s (insn)", attr->name);
3570 fprintf (outf, " == ");
3571 write_attr_valueq (outf, attr, XSTR (exp, 1));
3573 break;
3575 /* Comparison test of flags for define_delays. */
3576 case ATTR_FLAG:
3577 if (flags & FLG_BITWISE)
3578 fatal ("ATTR_FLAG not valid inside comparison");
3579 fprintf (outf, "(flags & ATTR_FLAG_%s) != 0", XSTR (exp, 0));
3580 break;
3582 /* See if an operand matches a predicate. */
3583 case MATCH_OPERAND:
3584 /* If only a mode is given, just ensure the mode matches the operand.
3585 If neither a mode nor predicate is given, error. */
3586 if (XSTR (exp, 1) == NULL || *XSTR (exp, 1) == '\0')
3588 if (GET_MODE (exp) == VOIDmode)
3589 fatal ("null MATCH_OPERAND specified as test");
3590 else
3591 fprintf (outf, "GET_MODE (operands[%d]) == %smode",
3592 XINT (exp, 0), GET_MODE_NAME (GET_MODE (exp)));
3594 else
3595 fprintf (outf, "%s (operands[%d], %smode)",
3596 XSTR (exp, 1), XINT (exp, 0), GET_MODE_NAME (GET_MODE (exp)));
3597 break;
3599 /* Constant integer. */
3600 case CONST_INT:
3601 fprintf (outf, HOST_WIDE_INT_PRINT_DEC, XWINT (exp, 0));
3602 break;
3604 case MATCH_TEST:
3605 fprint_c_condition (outf, XSTR (exp, 0));
3606 if (flags & FLG_BITWISE)
3607 fprintf (outf, " != 0");
3608 break;
3610 /* A random C expression. */
3611 case SYMBOL_REF:
3612 fprint_c_condition (outf, XSTR (exp, 0));
3613 break;
3615 /* The address of the branch target. */
3616 case MATCH_DUP:
3617 fprintf (outf,
3618 "INSN_ADDRESSES_SET_P () ? INSN_ADDRESSES (INSN_UID (GET_CODE (operands[%d]) == LABEL_REF ? XEXP (operands[%d], 0) : operands[%d])) : 0",
3619 XINT (exp, 0), XINT (exp, 0), XINT (exp, 0));
3620 break;
3622 case PC:
3623 /* The address of the current insn. We implement this actually as the
3624 address of the current insn for backward branches, but the last
3625 address of the next insn for forward branches, and both with
3626 adjustments that account for the worst-case possible stretching of
3627 intervening alignments between this insn and its destination. */
3628 fprintf (outf, "insn_current_reference_address (insn)");
3629 break;
3631 case CONST_STRING:
3632 fprintf (outf, "%s", XSTR (exp, 0));
3633 break;
3635 case IF_THEN_ELSE:
3636 write_test_expr (outf, XEXP (exp, 0), attrs_cached, 0);
3637 fprintf (outf, " ? ");
3638 write_test_expr (outf, XEXP (exp, 1), attrs_cached, FLG_BITWISE);
3639 fprintf (outf, " : ");
3640 write_test_expr (outf, XEXP (exp, 2), attrs_cached, FLG_BITWISE);
3641 break;
3643 default:
3644 fatal ("bad RTX code `%s' in attribute calculation\n",
3645 GET_RTX_NAME (code));
3648 fprintf (outf, ")");
3649 return attrs_cached;
3652 /* Given an attribute value, return the maximum CONST_STRING argument
3653 encountered. Set *UNKNOWNP and return INT_MAX if the value is unknown. */
3655 static int
3656 max_attr_value (rtx exp, int *unknownp)
3658 int current_max;
3659 int i, n;
3661 switch (GET_CODE (exp))
3663 case CONST_STRING:
3664 current_max = atoi (XSTR (exp, 0));
3665 break;
3667 case COND:
3668 current_max = max_attr_value (XEXP (exp, 1), unknownp);
3669 for (i = 0; i < XVECLEN (exp, 0); i += 2)
3671 n = max_attr_value (XVECEXP (exp, 0, i + 1), unknownp);
3672 if (n > current_max)
3673 current_max = n;
3675 break;
3677 case IF_THEN_ELSE:
3678 current_max = max_attr_value (XEXP (exp, 1), unknownp);
3679 n = max_attr_value (XEXP (exp, 2), unknownp);
3680 if (n > current_max)
3681 current_max = n;
3682 break;
3684 default:
3685 *unknownp = 1;
3686 current_max = INT_MAX;
3687 break;
3690 return current_max;
3693 /* Given an attribute value, return the minimum CONST_STRING argument
3694 encountered. Set *UNKNOWNP and return 0 if the value is unknown. */
3696 static int
3697 min_attr_value (rtx exp, int *unknownp)
3699 int current_min;
3700 int i, n;
3702 switch (GET_CODE (exp))
3704 case CONST_STRING:
3705 current_min = atoi (XSTR (exp, 0));
3706 break;
3708 case COND:
3709 current_min = min_attr_value (XEXP (exp, 1), unknownp);
3710 for (i = 0; i < XVECLEN (exp, 0); i += 2)
3712 n = min_attr_value (XVECEXP (exp, 0, i + 1), unknownp);
3713 if (n < current_min)
3714 current_min = n;
3716 break;
3718 case IF_THEN_ELSE:
3719 current_min = min_attr_value (XEXP (exp, 1), unknownp);
3720 n = min_attr_value (XEXP (exp, 2), unknownp);
3721 if (n < current_min)
3722 current_min = n;
3723 break;
3725 default:
3726 *unknownp = 1;
3727 current_min = INT_MAX;
3728 break;
3731 return current_min;
3734 /* Given an attribute value, return the result of ORing together all
3735 CONST_STRING arguments encountered. Set *UNKNOWNP and return -1
3736 if the numeric value is not known. */
3738 static int
3739 or_attr_value (rtx exp, int *unknownp)
3741 int current_or;
3742 int i;
3744 switch (GET_CODE (exp))
3746 case CONST_STRING:
3747 current_or = atoi (XSTR (exp, 0));
3748 break;
3750 case COND:
3751 current_or = or_attr_value (XEXP (exp, 1), unknownp);
3752 for (i = 0; i < XVECLEN (exp, 0); i += 2)
3753 current_or |= or_attr_value (XVECEXP (exp, 0, i + 1), unknownp);
3754 break;
3756 case IF_THEN_ELSE:
3757 current_or = or_attr_value (XEXP (exp, 1), unknownp);
3758 current_or |= or_attr_value (XEXP (exp, 2), unknownp);
3759 break;
3761 default:
3762 *unknownp = 1;
3763 current_or = -1;
3764 break;
3767 return current_or;
3770 /* Scan an attribute value, possibly a conditional, and record what actions
3771 will be required to do any conditional tests in it.
3773 Specifically, set
3774 `must_extract' if we need to extract the insn operands
3775 `must_constrain' if we must compute `which_alternative'
3776 `address_used' if an address expression was used
3777 `length_used' if an (eq_attr "length" ...) was used
3780 static void
3781 walk_attr_value (rtx exp)
3783 int i, j;
3784 const char *fmt;
3785 RTX_CODE code;
3787 if (exp == NULL)
3788 return;
3790 code = GET_CODE (exp);
3791 switch (code)
3793 case SYMBOL_REF:
3794 if (! ATTR_IND_SIMPLIFIED_P (exp))
3795 /* Since this is an arbitrary expression, it can look at anything.
3796 However, constant expressions do not depend on any particular
3797 insn. */
3798 must_extract = must_constrain = 1;
3799 return;
3801 case MATCH_OPERAND:
3802 must_extract = 1;
3803 return;
3805 case MATCH_TEST:
3806 case EQ_ATTR_ALT:
3807 must_extract = must_constrain = 1;
3808 break;
3810 case EQ_ATTR:
3811 if (XSTR (exp, 0) == alternative_name)
3812 must_extract = must_constrain = 1;
3813 else if (strcmp_check (XSTR (exp, 0), length_str) == 0)
3814 length_used = 1;
3815 return;
3817 case MATCH_DUP:
3818 must_extract = 1;
3819 address_used = 1;
3820 return;
3822 case PC:
3823 address_used = 1;
3824 return;
3826 case ATTR_FLAG:
3827 return;
3829 default:
3830 break;
3833 for (i = 0, fmt = GET_RTX_FORMAT (code); i < GET_RTX_LENGTH (code); i++)
3834 switch (*fmt++)
3836 case 'e':
3837 case 'u':
3838 walk_attr_value (XEXP (exp, i));
3839 break;
3841 case 'E':
3842 if (XVEC (exp, i) != NULL)
3843 for (j = 0; j < XVECLEN (exp, i); j++)
3844 walk_attr_value (XVECEXP (exp, i, j));
3845 break;
3849 /* Write out a function to obtain the attribute for a given INSN. */
3851 static void
3852 write_attr_get (FILE *outf, struct attr_desc *attr)
3854 struct attr_value *av, *common_av;
3855 int i, j;
3857 /* Find the most used attribute value. Handle that as the `default' of the
3858 switch we will generate. */
3859 common_av = find_most_used (attr);
3861 /* Write out start of function, then all values with explicit `case' lines,
3862 then a `default', then the value with the most uses. */
3863 if (attr->enum_name)
3864 fprintf (outf, "enum %s\n", attr->enum_name);
3865 else if (!attr->is_numeric)
3866 fprintf (outf, "enum attr_%s\n", attr->name);
3867 else
3868 fprintf (outf, "int\n");
3870 /* If the attribute name starts with a star, the remainder is the name of
3871 the subroutine to use, instead of `get_attr_...'. */
3872 if (attr->name[0] == '*')
3873 fprintf (outf, "%s (rtx insn ATTRIBUTE_UNUSED)\n", &attr->name[1]);
3874 else if (attr->is_const == 0)
3875 fprintf (outf, "get_attr_%s (rtx insn ATTRIBUTE_UNUSED)\n", attr->name);
3876 else
3878 fprintf (outf, "get_attr_%s (void)\n", attr->name);
3879 fprintf (outf, "{\n");
3881 for (av = attr->first_value; av; av = av->next)
3882 if (av->num_insns == 1)
3883 write_attr_set (outf, attr, 2, av->value, "return", ";",
3884 true_rtx, av->first_insn->def->insn_code,
3885 av->first_insn->def->insn_index, 0);
3886 else if (av->num_insns != 0)
3887 write_attr_set (outf, attr, 2, av->value, "return", ";",
3888 true_rtx, -2, 0, 0);
3890 fprintf (outf, "}\n\n");
3891 return;
3894 fprintf (outf, "{\n");
3896 /* Find attributes that are worth caching in the conditions. */
3897 cached_attr_count = 0;
3898 attrs_seen_more_than_once = 0;
3899 for (av = attr->first_value; av; av = av->next)
3901 attrs_seen_once = 0;
3902 find_attrs_to_cache (av->value, true);
3904 /* Remove those that aren't worth caching from the array. */
3905 for (i = 0, j = 0; i < cached_attr_count; i++)
3906 if ((attrs_seen_more_than_once & (1U << i)) != 0)
3908 const char *name = cached_attrs[i];
3909 struct attr_desc *cached_attr;
3910 if (i != j)
3911 cached_attrs[j] = name;
3912 cached_attr = find_attr (&name, 0);
3913 gcc_assert (cached_attr && cached_attr->is_const == 0);
3914 if (cached_attr->enum_name)
3915 fprintf (outf, " enum %s", cached_attr->enum_name);
3916 else if (!cached_attr->is_numeric)
3917 fprintf (outf, " enum attr_%s", cached_attr->name);
3918 else
3919 fprintf (outf, " int");
3920 fprintf (outf, " cached_%s ATTRIBUTE_UNUSED;\n", name);
3921 j++;
3923 cached_attr_count = j;
3924 if (cached_attr_count)
3925 fprintf (outf, "\n");
3927 fprintf (outf, " switch (recog_memoized (insn))\n");
3928 fprintf (outf, " {\n");
3930 for (av = attr->first_value; av; av = av->next)
3931 if (av != common_av)
3932 write_attr_case (outf, attr, av, 1, "return", ";", 4, true_rtx);
3934 write_attr_case (outf, attr, common_av, 0, "return", ";", 4, true_rtx);
3935 fprintf (outf, " }\n}\n\n");
3936 cached_attr_count = 0;
3939 /* Given an AND tree of known true terms (because we are inside an `if' with
3940 that as the condition or are in an `else' clause) and an expression,
3941 replace any known true terms with TRUE. Use `simplify_and_tree' to do
3942 the bulk of the work. */
3944 static rtx
3945 eliminate_known_true (rtx known_true, rtx exp, int insn_code, int insn_index)
3947 rtx term;
3949 known_true = SIMPLIFY_TEST_EXP (known_true, insn_code, insn_index);
3951 if (GET_CODE (known_true) == AND)
3953 exp = eliminate_known_true (XEXP (known_true, 0), exp,
3954 insn_code, insn_index);
3955 exp = eliminate_known_true (XEXP (known_true, 1), exp,
3956 insn_code, insn_index);
3958 else
3960 term = known_true;
3961 exp = simplify_and_tree (exp, &term, insn_code, insn_index);
3964 return exp;
3967 /* Write out a series of tests and assignment statements to perform tests and
3968 sets of an attribute value. We are passed an indentation amount and prefix
3969 and suffix strings to write around each attribute value (e.g., "return"
3970 and ";"). */
3972 static void
3973 write_attr_set (FILE *outf, struct attr_desc *attr, int indent, rtx value,
3974 const char *prefix, const char *suffix, rtx known_true,
3975 int insn_code, int insn_index, unsigned int attrs_cached)
3977 if (GET_CODE (value) == COND)
3979 /* Assume the default value will be the default of the COND unless we
3980 find an always true expression. */
3981 rtx default_val = XEXP (value, 1);
3982 rtx our_known_true = known_true;
3983 rtx newexp;
3984 int first_if = 1;
3985 int i;
3987 if (cached_attr_count)
3989 attrs_seen_once = 0;
3990 attrs_seen_more_than_once = 0;
3991 for (i = 0; i < XVECLEN (value, 0); i += 2)
3992 find_attrs_to_cache (XVECEXP (value, 0, i), false);
3993 attrs_to_cache |= attrs_seen_more_than_once;
3996 for (i = 0; i < XVECLEN (value, 0); i += 2)
3998 rtx testexp;
3999 rtx inner_true;
4001 testexp = eliminate_known_true (our_known_true,
4002 XVECEXP (value, 0, i),
4003 insn_code, insn_index);
4004 newexp = attr_rtx (NOT, testexp);
4005 newexp = insert_right_side (AND, our_known_true, newexp,
4006 insn_code, insn_index);
4008 /* If the test expression is always true or if the next `known_true'
4009 expression is always false, this is the last case, so break
4010 out and let this value be the `else' case. */
4011 if (testexp == true_rtx || newexp == false_rtx)
4013 default_val = XVECEXP (value, 0, i + 1);
4014 break;
4017 /* Compute the expression to pass to our recursive call as being
4018 known true. */
4019 inner_true = insert_right_side (AND, our_known_true,
4020 testexp, insn_code, insn_index);
4022 /* If this is always false, skip it. */
4023 if (inner_true == false_rtx)
4024 continue;
4026 attrs_cached_inside = attrs_cached;
4027 attrs_cached_after = attrs_cached;
4028 write_indent (outf, indent);
4029 fprintf (outf, "%sif ", first_if ? "" : "else ");
4030 first_if = 0;
4031 write_test_expr (outf, testexp, attrs_cached,
4032 (FLG_AFTER | FLG_INSIDE | FLG_OUTSIDE_AND));
4033 attrs_cached = attrs_cached_after;
4034 fprintf (outf, "\n");
4035 write_indent (outf, indent + 2);
4036 fprintf (outf, "{\n");
4038 write_attr_set (outf, attr, indent + 4,
4039 XVECEXP (value, 0, i + 1), prefix, suffix,
4040 inner_true, insn_code, insn_index,
4041 attrs_cached_inside);
4042 write_indent (outf, indent + 2);
4043 fprintf (outf, "}\n");
4044 our_known_true = newexp;
4047 if (! first_if)
4049 write_indent (outf, indent);
4050 fprintf (outf, "else\n");
4051 write_indent (outf, indent + 2);
4052 fprintf (outf, "{\n");
4055 write_attr_set (outf, attr, first_if ? indent : indent + 4, default_val,
4056 prefix, suffix, our_known_true, insn_code, insn_index,
4057 attrs_cached);
4059 if (! first_if)
4061 write_indent (outf, indent + 2);
4062 fprintf (outf, "}\n");
4065 else
4067 write_indent (outf, indent);
4068 fprintf (outf, "%s ", prefix);
4069 write_attr_value (outf, attr, value);
4070 fprintf (outf, "%s\n", suffix);
4074 /* Write a series of case statements for every instruction in list IE.
4075 INDENT is the amount of indentation to write before each case. */
4077 static void
4078 write_insn_cases (FILE *outf, struct insn_ent *ie, int indent)
4080 for (; ie != 0; ie = ie->next)
4081 if (ie->def->insn_code != -1)
4083 write_indent (outf, indent);
4084 if (GET_CODE (ie->def->def) == DEFINE_PEEPHOLE)
4085 fprintf (outf, "case %d: /* define_peephole, line %d */\n",
4086 ie->def->insn_code, ie->def->lineno);
4087 else
4088 fprintf (outf, "case %d: /* %s */\n",
4089 ie->def->insn_code, XSTR (ie->def->def, 0));
4093 /* Write out the computation for one attribute value. */
4095 static void
4096 write_attr_case (FILE *outf, struct attr_desc *attr, struct attr_value *av,
4097 int write_case_lines, const char *prefix, const char *suffix,
4098 int indent, rtx known_true)
4100 if (av->num_insns == 0)
4101 return;
4103 if (av->has_asm_insn)
4105 write_indent (outf, indent);
4106 fprintf (outf, "case -1:\n");
4107 write_indent (outf, indent + 2);
4108 fprintf (outf, "if (GET_CODE (PATTERN (insn)) != ASM_INPUT\n");
4109 write_indent (outf, indent + 2);
4110 fprintf (outf, " && asm_noperands (PATTERN (insn)) < 0)\n");
4111 write_indent (outf, indent + 2);
4112 fprintf (outf, " fatal_insn_not_found (insn);\n");
4115 if (write_case_lines)
4116 write_insn_cases (outf, av->first_insn, indent);
4117 else
4119 write_indent (outf, indent);
4120 fprintf (outf, "default:\n");
4123 /* See what we have to do to output this value. */
4124 must_extract = must_constrain = address_used = 0;
4125 walk_attr_value (av->value);
4127 if (must_constrain)
4129 write_indent (outf, indent + 2);
4130 fprintf (outf, "extract_constrain_insn_cached (insn);\n");
4132 else if (must_extract)
4134 write_indent (outf, indent + 2);
4135 fprintf (outf, "extract_insn_cached (insn);\n");
4138 attrs_to_cache = 0;
4139 if (av->num_insns == 1)
4140 write_attr_set (outf, attr, indent + 2, av->value, prefix, suffix,
4141 known_true, av->first_insn->def->insn_code,
4142 av->first_insn->def->insn_index, 0);
4143 else
4144 write_attr_set (outf, attr, indent + 2, av->value, prefix, suffix,
4145 known_true, -2, 0, 0);
4147 if (strncmp (prefix, "return", 6))
4149 write_indent (outf, indent + 2);
4150 fprintf (outf, "break;\n");
4152 fprintf (outf, "\n");
4155 /* Utilities to write in various forms. */
4157 static void
4158 write_attr_valueq (FILE *outf, struct attr_desc *attr, const char *s)
4160 if (attr->is_numeric)
4162 int num = atoi (s);
4164 fprintf (outf, "%d", num);
4166 if (num > 9 || num < 0)
4167 fprintf (outf, " /* %#x */", num);
4169 else
4171 write_upcase (outf, attr->enum_name ? attr->enum_name : attr->name);
4172 fprintf (outf, "_");
4173 write_upcase (outf, s);
4177 static void
4178 write_attr_value (FILE *outf, struct attr_desc *attr, rtx value)
4180 int op;
4182 switch (GET_CODE (value))
4184 case CONST_STRING:
4185 write_attr_valueq (outf, attr, XSTR (value, 0));
4186 break;
4188 case CONST_INT:
4189 fprintf (outf, HOST_WIDE_INT_PRINT_DEC, INTVAL (value));
4190 break;
4192 case SYMBOL_REF:
4193 fprint_c_condition (outf, XSTR (value, 0));
4194 break;
4196 case ATTR:
4198 struct attr_desc *attr2 = find_attr (&XSTR (value, 0), 0);
4199 if (attr->enum_name)
4200 fprintf (outf, "(enum %s)", attr->enum_name);
4201 else if (!attr->is_numeric)
4202 fprintf (outf, "(enum attr_%s)", attr->name);
4203 else if (!attr2->is_numeric)
4204 fprintf (outf, "(int)");
4206 fprintf (outf, "get_attr_%s (%s)", attr2->name,
4207 (attr2->is_const ? "" : "insn"));
4209 break;
4211 case PLUS:
4212 op = '+';
4213 goto do_operator;
4214 case MINUS:
4215 op = '-';
4216 goto do_operator;
4217 case MULT:
4218 op = '*';
4219 goto do_operator;
4220 case DIV:
4221 op = '/';
4222 goto do_operator;
4223 case MOD:
4224 op = '%';
4225 goto do_operator;
4227 do_operator:
4228 write_attr_value (outf, attr, XEXP (value, 0));
4229 fputc (' ', outf);
4230 fputc (op, outf);
4231 fputc (' ', outf);
4232 write_attr_value (outf, attr, XEXP (value, 1));
4233 break;
4235 default:
4236 gcc_unreachable ();
4240 static void
4241 write_upcase (FILE *outf, const char *str)
4243 while (*str)
4245 /* The argument of TOUPPER should not have side effects. */
4246 fputc (TOUPPER(*str), outf);
4247 str++;
4251 static void
4252 write_indent (FILE *outf, int indent)
4254 for (; indent > 8; indent -= 8)
4255 fprintf (outf, "\t");
4257 for (; indent; indent--)
4258 fprintf (outf, " ");
4261 /* Write a subroutine that is given an insn that requires a delay slot, a
4262 delay slot ordinal, and a candidate insn. It returns nonzero if the
4263 candidate can be placed in the specified delay slot of the insn.
4265 We can write as many as three subroutines. `eligible_for_delay'
4266 handles normal delay slots, `eligible_for_annul_true' indicates that
4267 the specified insn can be annulled if the branch is true, and likewise
4268 for `eligible_for_annul_false'.
4270 KIND is a string distinguishing these three cases ("delay", "annul_true",
4271 or "annul_false"). */
4273 static void
4274 write_eligible_delay (FILE *outf, const char *kind)
4276 struct delay_desc *delay;
4277 int max_slots;
4278 char str[50];
4279 const char *pstr;
4280 struct attr_desc *attr;
4281 struct attr_value *av, *common_av;
4282 int i;
4284 /* Compute the maximum number of delay slots required. We use the delay
4285 ordinal times this number plus one, plus the slot number as an index into
4286 the appropriate predicate to test. */
4288 for (delay = delays, max_slots = 0; delay; delay = delay->next)
4289 if (XVECLEN (delay->def, 1) / 3 > max_slots)
4290 max_slots = XVECLEN (delay->def, 1) / 3;
4292 /* Write function prelude. */
4294 fprintf (outf, "int\n");
4295 fprintf (outf, "eligible_for_%s (rtx delay_insn ATTRIBUTE_UNUSED, int slot, \n"
4296 " rtx candidate_insn, int flags ATTRIBUTE_UNUSED)\n",
4297 kind);
4298 fprintf (outf, "{\n");
4299 fprintf (outf, " rtx insn;\n");
4300 fprintf (outf, "\n");
4301 fprintf (outf, " gcc_assert (slot < %d);\n", max_slots);
4302 fprintf (outf, "\n");
4303 /* Allow dbr_schedule to pass labels, etc. This can happen if try_split
4304 converts a compound instruction into a loop. */
4305 fprintf (outf, " if (!INSN_P (candidate_insn))\n");
4306 fprintf (outf, " return 0;\n");
4307 fprintf (outf, "\n");
4309 /* If more than one delay type, find out which type the delay insn is. */
4311 if (num_delays > 1)
4313 attr = find_attr (&delay_type_str, 0);
4314 gcc_assert (attr);
4315 common_av = find_most_used (attr);
4317 fprintf (outf, " insn = delay_insn;\n");
4318 fprintf (outf, " switch (recog_memoized (insn))\n");
4319 fprintf (outf, " {\n");
4321 sprintf (str, " * %d;\n break;", max_slots);
4322 for (av = attr->first_value; av; av = av->next)
4323 if (av != common_av)
4324 write_attr_case (outf, attr, av, 1, "slot +=", str, 4, true_rtx);
4326 write_attr_case (outf, attr, common_av, 0, "slot +=", str, 4, true_rtx);
4327 fprintf (outf, " }\n\n");
4329 /* Ensure matched. Otherwise, shouldn't have been called. */
4330 fprintf (outf, " gcc_assert (slot >= %d);\n\n", max_slots);
4333 /* If just one type of delay slot, write simple switch. */
4334 if (num_delays == 1 && max_slots == 1)
4336 fprintf (outf, " insn = candidate_insn;\n");
4337 fprintf (outf, " switch (recog_memoized (insn))\n");
4338 fprintf (outf, " {\n");
4340 attr = find_attr (&delay_1_0_str, 0);
4341 gcc_assert (attr);
4342 common_av = find_most_used (attr);
4344 for (av = attr->first_value; av; av = av->next)
4345 if (av != common_av)
4346 write_attr_case (outf, attr, av, 1, "return", ";", 4, true_rtx);
4348 write_attr_case (outf, attr, common_av, 0, "return", ";", 4, true_rtx);
4349 fprintf (outf, " }\n");
4352 else
4354 /* Write a nested CASE. The first indicates which condition we need to
4355 test, and the inner CASE tests the condition. */
4356 fprintf (outf, " insn = candidate_insn;\n");
4357 fprintf (outf, " switch (slot)\n");
4358 fprintf (outf, " {\n");
4360 for (delay = delays; delay; delay = delay->next)
4361 for (i = 0; i < XVECLEN (delay->def, 1); i += 3)
4363 fprintf (outf, " case %d:\n",
4364 (i / 3) + (num_delays == 1 ? 0 : delay->num * max_slots));
4365 fprintf (outf, " switch (recog_memoized (insn))\n");
4366 fprintf (outf, "\t{\n");
4368 sprintf (str, "*%s_%d_%d", kind, delay->num, i / 3);
4369 pstr = str;
4370 attr = find_attr (&pstr, 0);
4371 gcc_assert (attr);
4372 common_av = find_most_used (attr);
4374 for (av = attr->first_value; av; av = av->next)
4375 if (av != common_av)
4376 write_attr_case (outf, attr, av, 1, "return", ";", 8, true_rtx);
4378 write_attr_case (outf, attr, common_av, 0, "return", ";", 8, true_rtx);
4379 fprintf (outf, " }\n");
4382 fprintf (outf, " default:\n");
4383 fprintf (outf, " gcc_unreachable ();\n");
4384 fprintf (outf, " }\n");
4387 fprintf (outf, "}\n\n");
4390 /* This page contains miscellaneous utility routines. */
4392 /* Given a pointer to a (char *), return a malloc'ed string containing the
4393 next comma-separated element. Advance the pointer to after the string
4394 scanned, or the end-of-string. Return NULL if at end of string. */
4396 static char *
4397 next_comma_elt (const char **pstr)
4399 const char *start;
4401 start = scan_comma_elt (pstr);
4403 if (start == NULL)
4404 return NULL;
4406 return attr_string (start, *pstr - start);
4409 /* Return a `struct attr_desc' pointer for a given named attribute. If CREATE
4410 is nonzero, build a new attribute, if one does not exist. *NAME_P is
4411 replaced by a pointer to a canonical copy of the string. */
4413 static struct attr_desc *
4414 find_attr (const char **name_p, int create)
4416 struct attr_desc *attr;
4417 int index;
4418 const char *name = *name_p;
4420 /* Before we resort to using `strcmp', see if the string address matches
4421 anywhere. In most cases, it should have been canonicalized to do so. */
4422 if (name == alternative_name)
4423 return NULL;
4425 index = name[0] & (MAX_ATTRS_INDEX - 1);
4426 for (attr = attrs[index]; attr; attr = attr->next)
4427 if (name == attr->name)
4428 return attr;
4430 /* Otherwise, do it the slow way. */
4431 for (attr = attrs[index]; attr; attr = attr->next)
4432 if (name[0] == attr->name[0] && ! strcmp (name, attr->name))
4434 *name_p = attr->name;
4435 return attr;
4438 if (! create)
4439 return NULL;
4441 attr = oballoc (struct attr_desc);
4442 attr->name = DEF_ATTR_STRING (name);
4443 attr->enum_name = 0;
4444 attr->first_value = attr->default_val = NULL;
4445 attr->is_numeric = attr->is_const = attr->is_special = 0;
4446 attr->next = attrs[index];
4447 attrs[index] = attr;
4449 *name_p = attr->name;
4451 return attr;
4454 /* Create internal attribute with the given default value. */
4456 static void
4457 make_internal_attr (const char *name, rtx value, int special)
4459 struct attr_desc *attr;
4461 attr = find_attr (&name, 1);
4462 gcc_assert (!attr->default_val);
4464 attr->is_numeric = 1;
4465 attr->is_const = 0;
4466 attr->is_special = (special & ATTR_SPECIAL) != 0;
4467 attr->default_val = get_attr_value (value, attr, -2);
4470 /* Find the most used value of an attribute. */
4472 static struct attr_value *
4473 find_most_used (struct attr_desc *attr)
4475 struct attr_value *av;
4476 struct attr_value *most_used;
4477 int nuses;
4479 most_used = NULL;
4480 nuses = -1;
4482 for (av = attr->first_value; av; av = av->next)
4483 if (av->num_insns > nuses)
4484 nuses = av->num_insns, most_used = av;
4486 return most_used;
4489 /* Return (attr_value "n") */
4491 static rtx
4492 make_numeric_value (int n)
4494 static rtx int_values[20];
4495 rtx exp;
4496 char *p;
4498 gcc_assert (n >= 0);
4500 if (n < 20 && int_values[n])
4501 return int_values[n];
4503 p = attr_printf (MAX_DIGITS, "%d", n);
4504 exp = attr_rtx (CONST_STRING, p);
4506 if (n < 20)
4507 int_values[n] = exp;
4509 return exp;
4512 static rtx
4513 copy_rtx_unchanging (rtx orig)
4515 if (ATTR_IND_SIMPLIFIED_P (orig) || ATTR_CURR_SIMPLIFIED_P (orig))
4516 return orig;
4518 ATTR_CURR_SIMPLIFIED_P (orig) = 1;
4519 return orig;
4522 /* Determine if an insn has a constant number of delay slots, i.e., the
4523 number of delay slots is not a function of the length of the insn. */
4525 static void
4526 write_const_num_delay_slots (FILE *outf)
4528 struct attr_desc *attr = find_attr (&num_delay_slots_str, 0);
4529 struct attr_value *av;
4531 if (attr)
4533 fprintf (outf, "int\nconst_num_delay_slots (rtx insn)\n");
4534 fprintf (outf, "{\n");
4535 fprintf (outf, " switch (recog_memoized (insn))\n");
4536 fprintf (outf, " {\n");
4538 for (av = attr->first_value; av; av = av->next)
4540 length_used = 0;
4541 walk_attr_value (av->value);
4542 if (length_used)
4543 write_insn_cases (outf, av->first_insn, 4);
4546 fprintf (outf, " default:\n");
4547 fprintf (outf, " return 1;\n");
4548 fprintf (outf, " }\n}\n\n");
4552 /* Synthetic attributes used by insn-automata.c and the scheduler.
4553 These are primarily concerned with (define_insn_reservation)
4554 patterns. */
4556 struct insn_reserv
4558 struct insn_reserv *next;
4560 const char *name;
4561 int default_latency;
4562 rtx condexp;
4564 /* Sequence number of this insn. */
4565 int insn_num;
4567 /* Whether a (define_bypass) construct names this insn in its
4568 output list. */
4569 bool bypassed;
4572 static struct insn_reserv *all_insn_reservs = 0;
4573 static struct insn_reserv **last_insn_reserv_p = &all_insn_reservs;
4574 static size_t n_insn_reservs;
4576 /* Store information from a DEFINE_INSN_RESERVATION for future
4577 attribute generation. */
4578 static void
4579 gen_insn_reserv (rtx def)
4581 struct insn_reserv *decl = oballoc (struct insn_reserv);
4583 decl->name = DEF_ATTR_STRING (XSTR (def, 0));
4584 decl->default_latency = XINT (def, 1);
4585 decl->condexp = check_attr_test (XEXP (def, 2), 0, 0);
4586 decl->insn_num = n_insn_reservs;
4587 decl->bypassed = false;
4588 decl->next = 0;
4590 *last_insn_reserv_p = decl;
4591 last_insn_reserv_p = &decl->next;
4592 n_insn_reservs++;
4595 /* Store information from a DEFINE_BYPASS for future attribute
4596 generation. The only thing we care about is the list of output
4597 insns, which will later be used to tag reservation structures with
4598 a 'bypassed' bit. */
4600 struct bypass_list
4602 struct bypass_list *next;
4603 const char *pattern;
4606 static struct bypass_list *all_bypasses;
4607 static size_t n_bypasses;
4609 static void
4610 gen_bypass_1 (const char *s, size_t len)
4612 struct bypass_list *b;
4614 if (len == 0)
4615 return;
4617 s = attr_string (s, len);
4618 for (b = all_bypasses; b; b = b->next)
4619 if (s == b->pattern)
4620 return; /* already got that one */
4622 b = oballoc (struct bypass_list);
4623 b->pattern = s;
4624 b->next = all_bypasses;
4625 all_bypasses = b;
4626 n_bypasses++;
4629 static void
4630 gen_bypass (rtx def)
4632 const char *p, *base;
4634 for (p = base = XSTR (def, 1); *p; p++)
4635 if (*p == ',')
4637 gen_bypass_1 (base, p - base);
4639 p++;
4640 while (ISSPACE (*p));
4641 base = p;
4643 gen_bypass_1 (base, p - base);
4646 /* Find and mark all of the bypassed insns. */
4647 static void
4648 process_bypasses (void)
4650 struct bypass_list *b;
4651 struct insn_reserv *r;
4653 /* The reservation list is likely to be much longer than the bypass
4654 list. */
4655 for (r = all_insn_reservs; r; r = r->next)
4656 for (b = all_bypasses; b; b = b->next)
4657 if (fnmatch (b->pattern, r->name, 0) == 0)
4658 r->bypassed = true;
4661 /* Check that attribute NAME is used in define_insn_reservation condition
4662 EXP. Return true if it is. */
4663 static bool
4664 check_tune_attr (const char *name, rtx exp)
4666 switch (GET_CODE (exp))
4668 case AND:
4669 if (check_tune_attr (name, XEXP (exp, 0)))
4670 return true;
4671 return check_tune_attr (name, XEXP (exp, 1));
4673 case IOR:
4674 return (check_tune_attr (name, XEXP (exp, 0))
4675 && check_tune_attr (name, XEXP (exp, 1)));
4677 case EQ_ATTR:
4678 return XSTR (exp, 0) == name;
4680 default:
4681 return false;
4685 /* Try to find a const attribute (usually cpu or tune) that is used
4686 in all define_insn_reservation conditions. */
4687 static struct attr_desc *
4688 find_tune_attr (rtx exp)
4690 struct attr_desc *attr;
4692 switch (GET_CODE (exp))
4694 case AND:
4695 case IOR:
4696 attr = find_tune_attr (XEXP (exp, 0));
4697 if (attr)
4698 return attr;
4699 return find_tune_attr (XEXP (exp, 1));
4701 case EQ_ATTR:
4702 if (XSTR (exp, 0) == alternative_name)
4703 return NULL;
4705 attr = find_attr (&XSTR (exp, 0), 0);
4706 gcc_assert (attr);
4708 if (attr->is_const && !attr->is_special)
4710 struct insn_reserv *decl;
4712 for (decl = all_insn_reservs; decl; decl = decl->next)
4713 if (! check_tune_attr (attr->name, decl->condexp))
4714 return NULL;
4715 return attr;
4717 return NULL;
4719 default:
4720 return NULL;
4724 /* Create all of the attributes that describe automaton properties.
4725 Write the DFA and latency function prototypes to the files that
4726 need to have them, and write the init_sched_attrs(). */
4728 static void
4729 make_automaton_attrs (void)
4731 int i;
4732 struct insn_reserv *decl;
4733 rtx code_exp, lats_exp, byps_exp;
4734 struct attr_desc *tune_attr;
4736 if (n_insn_reservs == 0)
4737 return;
4739 tune_attr = find_tune_attr (all_insn_reservs->condexp);
4740 if (tune_attr != NULL)
4742 rtx *condexps = XNEWVEC (rtx, n_insn_reservs * 3);
4743 struct attr_value *val;
4744 bool first = true;
4746 gcc_assert (tune_attr->is_const
4747 && !tune_attr->is_special
4748 && !tune_attr->is_numeric);
4750 /* Write the prototypes for all DFA functions. */
4751 for (val = tune_attr->first_value; val; val = val->next)
4753 if (val == tune_attr->default_val)
4754 continue;
4755 gcc_assert (GET_CODE (val->value) == CONST_STRING);
4756 fprintf (dfa_file,
4757 "extern int internal_dfa_insn_code_%s (rtx);\n",
4758 XSTR (val->value, 0));
4760 fprintf (dfa_file, "\n");
4762 /* Write the prototypes for all latency functions. */
4763 for (val = tune_attr->first_value; val; val = val->next)
4765 if (val == tune_attr->default_val)
4766 continue;
4767 gcc_assert (GET_CODE (val->value) == CONST_STRING);
4768 fprintf (latency_file,
4769 "extern int insn_default_latency_%s (rtx);\n",
4770 XSTR (val->value, 0));
4772 fprintf (latency_file, "\n");
4774 /* Write the prototypes for all automaton functions. */
4775 for (val = tune_attr->first_value; val; val = val->next)
4777 if (val == tune_attr->default_val)
4778 continue;
4779 gcc_assert (GET_CODE (val->value) == CONST_STRING);
4780 fprintf (attr_file,
4781 "extern int internal_dfa_insn_code_%s (rtx);\n"
4782 "extern int insn_default_latency_%s (rtx);\n",
4783 XSTR (val->value, 0), XSTR (val->value, 0));
4785 fprintf (attr_file, "\n");
4786 fprintf (attr_file, "int (*internal_dfa_insn_code) (rtx);\n");
4787 fprintf (attr_file, "int (*insn_default_latency) (rtx);\n");
4788 fprintf (attr_file, "\n");
4789 fprintf (attr_file, "void\n");
4790 fprintf (attr_file, "init_sched_attrs (void)\n");
4791 fprintf (attr_file, "{\n");
4793 for (val = tune_attr->first_value; val; val = val->next)
4795 int j;
4796 char *name;
4797 rtx test = attr_rtx (EQ_ATTR, tune_attr->name, XSTR (val->value, 0));
4799 if (val == tune_attr->default_val)
4800 continue;
4801 for (decl = all_insn_reservs, i = 0;
4802 decl;
4803 decl = decl->next)
4805 rtx ctest = test;
4806 rtx condexp
4807 = simplify_and_tree (decl->condexp, &ctest, -2, 0);
4808 if (condexp == false_rtx)
4809 continue;
4810 if (condexp == true_rtx)
4811 break;
4812 condexps[i] = condexp;
4813 condexps[i + 1] = make_numeric_value (decl->insn_num);
4814 condexps[i + 2] = make_numeric_value (decl->default_latency);
4815 i += 3;
4818 code_exp = rtx_alloc (COND);
4819 lats_exp = rtx_alloc (COND);
4821 j = i / 3 * 2;
4822 XVEC (code_exp, 0) = rtvec_alloc (j);
4823 XVEC (lats_exp, 0) = rtvec_alloc (j);
4825 if (decl)
4827 XEXP (code_exp, 1) = make_numeric_value (decl->insn_num);
4828 XEXP (lats_exp, 1) = make_numeric_value (decl->default_latency);
4830 else
4832 XEXP (code_exp, 1) = make_numeric_value (n_insn_reservs + 1);
4833 XEXP (lats_exp, 1) = make_numeric_value (0);
4836 while (i > 0)
4838 i -= 3;
4839 j -= 2;
4840 XVECEXP (code_exp, 0, j) = condexps[i];
4841 XVECEXP (lats_exp, 0, j) = condexps[i];
4843 XVECEXP (code_exp, 0, j + 1) = condexps[i + 1];
4844 XVECEXP (lats_exp, 0, j + 1) = condexps[i + 2];
4847 name = XNEWVEC (char,
4848 sizeof ("*internal_dfa_insn_code_")
4849 + strlen (XSTR (val->value, 0)));
4850 strcpy (name, "*internal_dfa_insn_code_");
4851 strcat (name, XSTR (val->value, 0));
4852 make_internal_attr (name, code_exp, ATTR_NONE);
4853 strcpy (name, "*insn_default_latency_");
4854 strcat (name, XSTR (val->value, 0));
4855 make_internal_attr (name, lats_exp, ATTR_NONE);
4856 XDELETEVEC (name);
4858 if (first)
4860 fprintf (attr_file, " if (");
4861 first = false;
4863 else
4864 fprintf (attr_file, " else if (");
4865 write_test_expr (attr_file, test, 0, 0);
4866 fprintf (attr_file, ")\n");
4867 fprintf (attr_file, " {\n");
4868 fprintf (attr_file, " internal_dfa_insn_code\n");
4869 fprintf (attr_file, " = internal_dfa_insn_code_%s;\n",
4870 XSTR (val->value, 0));
4871 fprintf (attr_file, " insn_default_latency\n");
4872 fprintf (attr_file, " = insn_default_latency_%s;\n",
4873 XSTR (val->value, 0));
4874 fprintf (attr_file, " }\n");
4877 fprintf (attr_file, " else\n");
4878 fprintf (attr_file, " gcc_unreachable ();\n");
4879 fprintf (attr_file, "}\n");
4880 fprintf (attr_file, "\n");
4882 XDELETEVEC (condexps);
4884 else
4886 code_exp = rtx_alloc (COND);
4887 lats_exp = rtx_alloc (COND);
4889 XVEC (code_exp, 0) = rtvec_alloc (n_insn_reservs * 2);
4890 XVEC (lats_exp, 0) = rtvec_alloc (n_insn_reservs * 2);
4892 XEXP (code_exp, 1) = make_numeric_value (n_insn_reservs + 1);
4893 XEXP (lats_exp, 1) = make_numeric_value (0);
4895 for (decl = all_insn_reservs, i = 0;
4896 decl;
4897 decl = decl->next, i += 2)
4899 XVECEXP (code_exp, 0, i) = decl->condexp;
4900 XVECEXP (lats_exp, 0, i) = decl->condexp;
4902 XVECEXP (code_exp, 0, i+1) = make_numeric_value (decl->insn_num);
4903 XVECEXP (lats_exp, 0, i+1)
4904 = make_numeric_value (decl->default_latency);
4906 make_internal_attr ("*internal_dfa_insn_code", code_exp, ATTR_NONE);
4907 make_internal_attr ("*insn_default_latency", lats_exp, ATTR_NONE);
4910 if (n_bypasses == 0)
4911 byps_exp = make_numeric_value (0);
4912 else
4914 process_bypasses ();
4916 byps_exp = rtx_alloc (COND);
4917 XVEC (byps_exp, 0) = rtvec_alloc (n_bypasses * 2);
4918 XEXP (byps_exp, 1) = make_numeric_value (0);
4919 for (decl = all_insn_reservs, i = 0;
4920 decl;
4921 decl = decl->next)
4922 if (decl->bypassed)
4924 XVECEXP (byps_exp, 0, i) = decl->condexp;
4925 XVECEXP (byps_exp, 0, i+1) = make_numeric_value (1);
4926 i += 2;
4930 make_internal_attr ("*bypass_p", byps_exp, ATTR_NONE);
4933 static void
4934 write_header (FILE *outf)
4936 fprintf (outf, "/* Generated automatically by the program `genattrtab'\n"
4937 " from the machine description file `md'. */\n\n");
4939 fprintf (outf, "#include \"config.h\"\n");
4940 fprintf (outf, "#include \"system.h\"\n");
4941 fprintf (outf, "#include \"coretypes.h\"\n");
4942 fprintf (outf, "#include \"tm.h\"\n");
4943 fprintf (outf, "#include \"rtl.h\"\n");
4944 fprintf (outf, "#include \"insn-attr.h\"\n");
4945 fprintf (outf, "#include \"tm_p.h\"\n");
4946 fprintf (outf, "#include \"insn-config.h\"\n");
4947 fprintf (outf, "#include \"recog.h\"\n");
4948 fprintf (outf, "#include \"regs.h\"\n");
4949 fprintf (outf, "#include \"real.h\"\n");
4950 fprintf (outf, "#include \"output.h\"\n");
4951 fprintf (outf, "#include \"toplev.h\"\n");
4952 fprintf (outf, "#include \"flags.h\"\n");
4953 fprintf (outf, "#include \"function.h\"\n");
4954 fprintf (outf, "\n");
4955 fprintf (outf, "#define operands recog_data.operand\n\n");
4958 static FILE *
4959 open_outfile (const char *file_name)
4961 FILE *outf;
4962 outf = fopen (file_name, "w");
4963 if (! outf)
4964 fatal ("cannot open file %s: %s", file_name, xstrerror (errno));
4965 write_header (outf);
4966 return outf;
4969 static bool
4970 handle_arg (const char *arg)
4972 switch (arg[1])
4974 case 'A':
4975 attr_file_name = &arg[2];
4976 return true;
4977 case 'D':
4978 dfa_file_name = &arg[2];
4979 return true;
4980 case 'L':
4981 latency_file_name = &arg[2];
4982 return true;
4983 default:
4984 return false;
4989 main (int argc, char **argv)
4991 rtx desc;
4992 struct attr_desc *attr;
4993 struct insn_def *id;
4994 rtx tem;
4995 int i;
4997 progname = "genattrtab";
4999 if (!init_rtx_reader_args_cb (argc, argv, handle_arg))
5000 return FATAL_EXIT_CODE;
5002 attr_file = open_outfile (attr_file_name);
5003 dfa_file = open_outfile (dfa_file_name);
5004 latency_file = open_outfile (latency_file_name);
5006 obstack_init (hash_obstack);
5007 obstack_init (temp_obstack);
5009 /* Set up true and false rtx's */
5010 true_rtx = rtx_alloc (CONST_INT);
5011 XWINT (true_rtx, 0) = 1;
5012 false_rtx = rtx_alloc (CONST_INT);
5013 XWINT (false_rtx, 0) = 0;
5014 ATTR_IND_SIMPLIFIED_P (true_rtx) = ATTR_IND_SIMPLIFIED_P (false_rtx) = 1;
5015 ATTR_PERMANENT_P (true_rtx) = ATTR_PERMANENT_P (false_rtx) = 1;
5017 alternative_name = DEF_ATTR_STRING ("alternative");
5018 length_str = DEF_ATTR_STRING ("length");
5019 delay_type_str = DEF_ATTR_STRING ("*delay_type");
5020 delay_1_0_str = DEF_ATTR_STRING ("*delay_1_0");
5021 num_delay_slots_str = DEF_ATTR_STRING ("*num_delay_slots");
5023 /* Read the machine description. */
5025 while (1)
5027 int lineno;
5029 desc = read_md_rtx (&lineno, &insn_code_number);
5030 if (desc == NULL)
5031 break;
5033 switch (GET_CODE (desc))
5035 case DEFINE_INSN:
5036 case DEFINE_PEEPHOLE:
5037 case DEFINE_ASM_ATTRIBUTES:
5038 gen_insn (desc, lineno);
5039 break;
5041 case DEFINE_ATTR:
5042 case DEFINE_ENUM_ATTR:
5043 gen_attr (desc, lineno);
5044 break;
5046 case DEFINE_DELAY:
5047 gen_delay (desc, lineno);
5048 break;
5050 case DEFINE_INSN_RESERVATION:
5051 gen_insn_reserv (desc);
5052 break;
5054 case DEFINE_BYPASS:
5055 gen_bypass (desc);
5056 break;
5058 default:
5059 break;
5061 if (GET_CODE (desc) != DEFINE_ASM_ATTRIBUTES)
5062 insn_index_number++;
5065 if (have_error)
5066 return FATAL_EXIT_CODE;
5068 insn_code_number++;
5070 /* If we didn't have a DEFINE_ASM_ATTRIBUTES, make a null one. */
5071 if (! got_define_asm_attributes)
5073 tem = rtx_alloc (DEFINE_ASM_ATTRIBUTES);
5074 XVEC (tem, 0) = rtvec_alloc (0);
5075 gen_insn (tem, 0);
5078 /* Expand DEFINE_DELAY information into new attribute. */
5079 if (num_delays)
5080 expand_delays ();
5082 /* Make `insn_alternatives'. */
5083 insn_alternatives = oballocvec (int, insn_code_number);
5084 for (id = defs; id; id = id->next)
5085 if (id->insn_code >= 0)
5086 insn_alternatives[id->insn_code] = (1 << id->num_alternatives) - 1;
5088 /* Make `insn_n_alternatives'. */
5089 insn_n_alternatives = oballocvec (int, insn_code_number);
5090 for (id = defs; id; id = id->next)
5091 if (id->insn_code >= 0)
5092 insn_n_alternatives[id->insn_code] = id->num_alternatives;
5094 /* Construct extra attributes for automata. */
5095 make_automaton_attrs ();
5097 /* Prepare to write out attribute subroutines by checking everything stored
5098 away and building the attribute cases. */
5100 check_defs ();
5102 for (i = 0; i < MAX_ATTRS_INDEX; i++)
5103 for (attr = attrs[i]; attr; attr = attr->next)
5104 attr->default_val->value
5105 = check_attr_value (attr->default_val->value, attr);
5107 if (have_error)
5108 return FATAL_EXIT_CODE;
5110 for (i = 0; i < MAX_ATTRS_INDEX; i++)
5111 for (attr = attrs[i]; attr; attr = attr->next)
5112 fill_attr (attr);
5114 /* Construct extra attributes for `length'. */
5115 make_length_attrs ();
5117 /* Perform any possible optimizations to speed up compilation. */
5118 optimize_attrs ();
5120 /* Now write out all the `gen_attr_...' routines. Do these before the
5121 special routines so that they get defined before they are used. */
5123 for (i = 0; i < MAX_ATTRS_INDEX; i++)
5124 for (attr = attrs[i]; attr; attr = attr->next)
5126 FILE *outf;
5128 #define IS_ATTR_GROUP(X) (!strncmp(attr->name,X,strlen(X)))
5129 if (IS_ATTR_GROUP ("*internal_dfa_insn_code"))
5130 outf = dfa_file;
5131 else if (IS_ATTR_GROUP ("*insn_default_latency"))
5132 outf = latency_file;
5133 else
5134 outf = attr_file;
5135 #undef IS_ATTR_GROUP
5137 if (! attr->is_special && ! attr->is_const)
5138 write_attr_get (outf, attr);
5141 /* Write out delay eligibility information, if DEFINE_DELAY present.
5142 (The function to compute the number of delay slots will be written
5143 below.) */
5144 if (num_delays)
5146 write_eligible_delay (attr_file, "delay");
5147 if (have_annul_true)
5148 write_eligible_delay (attr_file, "annul_true");
5149 if (have_annul_false)
5150 write_eligible_delay (attr_file, "annul_false");
5153 /* Write out constant delay slot info. */
5154 write_const_num_delay_slots (attr_file);
5156 write_length_unit_log (attr_file);
5158 if (fclose (attr_file) != 0)
5159 fatal ("cannot close file %s: %s", attr_file_name, xstrerror (errno));
5160 if (fclose (dfa_file) != 0)
5161 fatal ("cannot close file %s: %s", dfa_file_name, xstrerror (errno));
5162 if (fclose (latency_file) != 0)
5163 fatal ("cannot close file %s: %s", latency_file_name, xstrerror (errno));
5165 return SUCCESS_EXIT_CODE;