Mercurial > hg > CbC > CbC_gcc
comparison gcc/genattr.c @ 67:f6334be47118
update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
author | nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp> |
---|---|
date | Tue, 22 Mar 2011 17:18:12 +0900 |
parents | 77e2b8dfacca |
children | 04ced10e8804 |
comparison
equal
deleted
inserted
replaced
65:65488c3d617d | 67:f6334be47118 |
---|---|
1 /* Generate attribute information (insn-attr.h) from machine description. | 1 /* Generate attribute information (insn-attr.h) from machine description. |
2 Copyright (C) 1991, 1994, 1996, 1998, 1999, 2000, 2003, 2004, 2007, 2008 | 2 Copyright (C) 1991, 1994, 1996, 1998, 1999, 2000, 2003, 2004, 2007, 2008, |
3 Free Software Foundation, Inc. | 3 2010 Free Software Foundation, Inc. |
4 Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu) | 4 Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu) |
5 | 5 |
6 This file is part of GCC. | 6 This file is part of GCC. |
7 | 7 |
8 GCC is free software; you can redistribute it and/or modify it under | 8 GCC is free software; you can redistribute it and/or modify it under |
24 #include "system.h" | 24 #include "system.h" |
25 #include "coretypes.h" | 25 #include "coretypes.h" |
26 #include "tm.h" | 26 #include "tm.h" |
27 #include "rtl.h" | 27 #include "rtl.h" |
28 #include "errors.h" | 28 #include "errors.h" |
29 #include "read-md.h" | |
29 #include "gensupport.h" | 30 #include "gensupport.h" |
30 | 31 |
31 | 32 |
32 static void write_upcase (const char *); | 33 static void write_upcase (const char *); |
33 static void gen_attr (rtx); | 34 static void gen_attr (rtx); |
37 { | 38 { |
38 for (; *str; str++) | 39 for (; *str; str++) |
39 putchar (TOUPPER(*str)); | 40 putchar (TOUPPER(*str)); |
40 } | 41 } |
41 | 42 |
43 static VEC (rtx, heap) *const_attrs, *reservations; | |
44 | |
45 | |
42 static void | 46 static void |
43 gen_attr (rtx attr) | 47 gen_attr (rtx attr) |
44 { | 48 { |
45 const char *p, *tag; | 49 const char *p, *tag; |
46 int is_const = GET_CODE (XEXP (attr, 2)) == CONST; | 50 int is_const = GET_CODE (XEXP (attr, 2)) == CONST; |
47 | 51 |
52 if (is_const) | |
53 VEC_safe_push (rtx, heap, const_attrs, attr); | |
54 | |
48 printf ("#define HAVE_ATTR_%s\n", XSTR (attr, 0)); | 55 printf ("#define HAVE_ATTR_%s\n", XSTR (attr, 0)); |
49 | 56 |
50 /* If numeric attribute, don't need to write an enum. */ | 57 /* If numeric attribute, don't need to write an enum. */ |
51 p = XSTR (attr, 1); | 58 if (GET_CODE (attr) == DEFINE_ENUM_ATTR) |
52 if (*p == '\0') | 59 printf ("extern enum %s get_attr_%s (%s);\n\n", |
53 printf ("extern int get_attr_%s (%s);\n", XSTR (attr, 0), | 60 XSTR (attr, 1), XSTR (attr, 0), (is_const ? "void" : "rtx")); |
54 (is_const ? "void" : "rtx")); | |
55 else | 61 else |
56 { | 62 { |
57 printf ("enum attr_%s {", XSTR (attr, 0)); | 63 p = XSTR (attr, 1); |
58 | 64 if (*p == '\0') |
59 while ((tag = scan_comma_elt (&p)) != 0) | 65 printf ("extern int get_attr_%s (%s);\n", XSTR (attr, 0), |
66 (is_const ? "void" : "rtx")); | |
67 else | |
60 { | 68 { |
61 write_upcase (XSTR (attr, 0)); | 69 printf ("enum attr_%s {", XSTR (attr, 0)); |
62 putchar ('_'); | 70 |
63 while (tag != p) | 71 while ((tag = scan_comma_elt (&p)) != 0) |
64 putchar (TOUPPER (*tag++)); | 72 { |
65 if (*p == ',') | 73 write_upcase (XSTR (attr, 0)); |
66 fputs (", ", stdout); | 74 putchar ('_'); |
75 while (tag != p) | |
76 putchar (TOUPPER (*tag++)); | |
77 if (*p == ',') | |
78 fputs (", ", stdout); | |
79 } | |
80 fputs ("};\n", stdout); | |
81 | |
82 printf ("extern enum attr_%s get_attr_%s (%s);\n\n", | |
83 XSTR (attr, 0), XSTR (attr, 0), (is_const ? "void" : "rtx")); | |
67 } | 84 } |
68 | |
69 fputs ("};\n", stdout); | |
70 printf ("extern enum attr_%s get_attr_%s (%s);\n\n", | |
71 XSTR (attr, 0), XSTR (attr, 0), (is_const ? "void" : "rtx")); | |
72 } | 85 } |
73 | 86 |
74 /* If `length' attribute, write additional function definitions and define | 87 /* If `length' attribute, write additional function definitions and define |
75 variables used by `insn_current_length'. */ | 88 variables used by `insn_current_length'. */ |
76 if (! strcmp (XSTR (attr, 0), "length")) | 89 if (! strcmp (XSTR (attr, 0), "length")) |
83 extern int insn_current_length (rtx);\n\n\ | 96 extern int insn_current_length (rtx);\n\n\ |
84 #include \"insn-addr.h\"\n"); | 97 #include \"insn-addr.h\"\n"); |
85 } | 98 } |
86 } | 99 } |
87 | 100 |
101 /* Check that attribute NAME is used in define_insn_reservation condition | |
102 EXP. Return true if it is. */ | |
103 static bool | |
104 check_tune_attr (const char *name, rtx exp) | |
105 { | |
106 switch (GET_CODE (exp)) | |
107 { | |
108 case AND: | |
109 if (check_tune_attr (name, XEXP (exp, 0))) | |
110 return true; | |
111 return check_tune_attr (name, XEXP (exp, 1)); | |
112 | |
113 case IOR: | |
114 return (check_tune_attr (name, XEXP (exp, 0)) | |
115 && check_tune_attr (name, XEXP (exp, 1))); | |
116 | |
117 case EQ_ATTR: | |
118 return strcmp (XSTR (exp, 0), name) == 0; | |
119 | |
120 default: | |
121 return false; | |
122 } | |
123 } | |
124 | |
125 /* Try to find a const attribute (usually cpu or tune) that is used | |
126 in all define_insn_reservation conditions. */ | |
127 static bool | |
128 find_tune_attr (rtx exp) | |
129 { | |
130 unsigned int i; | |
131 rtx attr; | |
132 | |
133 switch (GET_CODE (exp)) | |
134 { | |
135 case AND: | |
136 case IOR: | |
137 if (find_tune_attr (XEXP (exp, 0))) | |
138 return true; | |
139 return find_tune_attr (XEXP (exp, 1)); | |
140 | |
141 case EQ_ATTR: | |
142 if (strcmp (XSTR (exp, 0), "alternative") == 0) | |
143 return false; | |
144 | |
145 FOR_EACH_VEC_ELT (rtx, const_attrs, i, attr) | |
146 if (strcmp (XSTR (attr, 0), XSTR (exp, 0)) == 0) | |
147 { | |
148 unsigned int j; | |
149 rtx resv; | |
150 | |
151 FOR_EACH_VEC_ELT (rtx, reservations, j, resv) | |
152 if (! check_tune_attr (XSTR (attr, 0), XEXP (resv, 2))) | |
153 return false; | |
154 return true; | |
155 } | |
156 return false; | |
157 | |
158 default: | |
159 return false; | |
160 } | |
161 } | |
162 | |
88 int | 163 int |
89 main (int argc, char **argv) | 164 main (int argc, char **argv) |
90 { | 165 { |
91 rtx desc; | 166 rtx desc; |
92 int have_delay = 0; | 167 int have_delay = 0; |
95 int num_insn_reservations = 0; | 170 int num_insn_reservations = 0; |
96 int i; | 171 int i; |
97 | 172 |
98 progname = "genattr"; | 173 progname = "genattr"; |
99 | 174 |
100 if (init_md_reader_args (argc, argv) != SUCCESS_EXIT_CODE) | 175 if (!init_rtx_reader_args (argc, argv)) |
101 return (FATAL_EXIT_CODE); | 176 return (FATAL_EXIT_CODE); |
102 | 177 |
103 puts ("/* Generated automatically by the program `genattr'"); | 178 puts ("/* Generated automatically by the program `genattr'"); |
104 puts (" from the machine description file `md'. */\n"); | 179 puts (" from the machine description file `md'. */\n"); |
105 puts ("#ifndef GCC_INSN_ATTR_H"); | 180 puts ("#ifndef GCC_INSN_ATTR_H"); |
119 | 194 |
120 desc = read_md_rtx (&line_no, &insn_code_number); | 195 desc = read_md_rtx (&line_no, &insn_code_number); |
121 if (desc == NULL) | 196 if (desc == NULL) |
122 break; | 197 break; |
123 | 198 |
124 if (GET_CODE (desc) == DEFINE_ATTR) | 199 if (GET_CODE (desc) == DEFINE_ATTR |
200 || GET_CODE (desc) == DEFINE_ENUM_ATTR) | |
125 gen_attr (desc); | 201 gen_attr (desc); |
126 | 202 |
127 else if (GET_CODE (desc) == DEFINE_DELAY) | 203 else if (GET_CODE (desc) == DEFINE_DELAY) |
128 { | 204 { |
129 if (! have_delay) | 205 if (! have_delay) |
152 } | 228 } |
153 } | 229 } |
154 } | 230 } |
155 | 231 |
156 else if (GET_CODE (desc) == DEFINE_INSN_RESERVATION) | 232 else if (GET_CODE (desc) == DEFINE_INSN_RESERVATION) |
157 num_insn_reservations++; | 233 { |
234 num_insn_reservations++; | |
235 VEC_safe_push (rtx, heap, reservations, desc); | |
236 } | |
158 } | 237 } |
159 | 238 |
160 if (num_insn_reservations > 0) | 239 if (num_insn_reservations > 0) |
161 { | 240 { |
241 bool has_tune_attr | |
242 = find_tune_attr (XEXP (VEC_index (rtx, reservations, 0), 2)); | |
162 /* Output interface for pipeline hazards recognition based on | 243 /* Output interface for pipeline hazards recognition based on |
163 DFA (deterministic finite state automata. */ | 244 DFA (deterministic finite state automata. */ |
164 printf ("\n#define INSN_SCHEDULING\n"); | 245 printf ("\n#define INSN_SCHEDULING\n"); |
165 printf ("\n/* DFA based pipeline interface. */"); | 246 printf ("\n/* DFA based pipeline interface. */"); |
166 printf ("\n#ifndef AUTOMATON_ALTS\n"); | 247 printf ("\n#ifndef AUTOMATON_ALTS\n"); |
171 printf ("#endif\n\n"); | 252 printf ("#endif\n\n"); |
172 printf ("#ifndef CPU_UNITS_QUERY\n"); | 253 printf ("#ifndef CPU_UNITS_QUERY\n"); |
173 printf ("#define CPU_UNITS_QUERY 0\n"); | 254 printf ("#define CPU_UNITS_QUERY 0\n"); |
174 printf ("#endif\n\n"); | 255 printf ("#endif\n\n"); |
175 /* Interface itself: */ | 256 /* Interface itself: */ |
176 printf ("/* Internal insn code number used by automata. */\n"); | 257 if (has_tune_attr) |
177 printf ("extern int internal_dfa_insn_code (rtx);\n\n"); | 258 { |
178 printf ("/* Insn latency time defined in define_insn_reservation. */\n"); | 259 printf ("/* Initialize fn pointers for internal_dfa_insn_code\n"); |
179 printf ("extern int insn_default_latency (rtx);\n\n"); | 260 printf (" and insn_default_latency. */\n"); |
261 printf ("extern void init_sched_attrs (void);\n\n"); | |
262 printf ("/* Internal insn code number used by automata. */\n"); | |
263 printf ("extern int (*internal_dfa_insn_code) (rtx);\n\n"); | |
264 printf ("/* Insn latency time defined in define_insn_reservation. */\n"); | |
265 printf ("extern int (*insn_default_latency) (rtx);\n\n"); | |
266 } | |
267 else | |
268 { | |
269 printf ("#define init_sched_attrs() do { } while (0)\n\n"); | |
270 printf ("/* Internal insn code number used by automata. */\n"); | |
271 printf ("extern int internal_dfa_insn_code (rtx);\n\n"); | |
272 printf ("/* Insn latency time defined in define_insn_reservation. */\n"); | |
273 printf ("extern int insn_default_latency (rtx);\n\n"); | |
274 } | |
180 printf ("/* Return nonzero if there is a bypass for given insn\n"); | 275 printf ("/* Return nonzero if there is a bypass for given insn\n"); |
181 printf (" which is a data producer. */\n"); | 276 printf (" which is a data producer. */\n"); |
182 printf ("extern int bypass_p (rtx);\n\n"); | 277 printf ("extern int bypass_p (rtx);\n\n"); |
183 printf ("/* Insn latency time on data consumed by the 2nd insn.\n"); | 278 printf ("/* Insn latency time on data consumed by the 2nd insn.\n"); |
184 printf (" Use the function if bypass_p returns nonzero for\n"); | 279 printf (" Use the function if bypass_p returns nonzero for\n"); |