16. Toolof gengenrtl
16.1. Overview
This tool generates genrtl.h and genrtl.c from rtl.def. The outputfiles give the functions to generate various rtl objects following thedefinitions in the file rtl.def.
340 int
341 main (int argc, char **argv) ingengenrtl.c
342 {
343 find_formats ();
344 genlegend ();
345
346 if (argc == 2 && argv[1][0]== '-' && argv[1][1] == 'h')
347 genheader ();
348 else
349 gencode ();
350
351 if (ferror (stdout) || fflush (stdout) || fclose (stdout))
352 return FATAL_EXIT_CODE;
353
354 return SUCCESS_EXIT_CODE;
355 }
For the format of rtx, the detail is as following.
Ø "*" undefined. cancause a warning message
Ø "0" field is unused(or used in a phase-dependent manner) prints nothing
Ø "i" an integer printsthe integer
Ø "n" like"i", but prints entries from `note_insn_name'
Ø "w" an integer ofwidth HOST_BITS_PER_WIDE_INT prints the integer
Ø "s" a pointer to astring prints the string
Ø "S" like"s", but optional: the containing rtx may end before this operand
Ø "T" like"s", but treated specially by the RTL reader; only found in machinedescription patterns.
Ø "e" a pointer to anrtl expression prints the expression
Ø "E" a pointer to avector that points to a number of rtl expressions prints a list of the rtlexpressions
Ø "V" like"E", but optional: the containing rtx may end before this operand
Ø "u" a pointer toanother insn prints the uid of the insn.
Ø "b" is a pointer to abitmap header.
Ø "B" is a basic blockpointer.
Ø "t" is a treepointer.
165 static void
166 find_formats (void) ingengenrtl.c
167 {
168 unsigned int i;
169
170 for(i = 0; i < NUM_RTX_CODE; i++)
171 {
172 const char **f;
173
174 if (special_format (defs[i].format))
175 continue;
176
177 for(f = formats;*f; f++)
178 if (! strcmp (*f, defs[i].format))
179 break;
180
181 if (*f == 0)
182 *f = defs[i].format;
183 }
184 }
defs at line 174 is defined as following. It is expanded from rtl.def.
36 #defineDEF_RTL_EXPR(ENUM, NAME, FORMAT, CLASS) { #ENUM, NAME, FORMAT },
37
38 static const structrtx_definition defs[] =
39 {
40 #include "rtl.def" /* rtlexpressions are documented here */
41 };
26 struct rtx_definition
27 {
28 const char *constenumname, *const name, *const format;
29 };
130 static int
131 special_format (const char *fmt) ingengenrtl.c
132 {
133 return (strchr (fmt, '*') != 0
134 || strchr (fmt, 'V') != 0
135 || strchr (fmt, 'S') != 0
136 || strchr (fmt, 'n') != 0);
137 }
16.2. Output genrtl.h
Formats except those filtered out by special_format will be saved into format.genrtl.h is produced by genheader.
296 static void
297 genheader (void) ingengenrtl.c
298 {
299 unsigned int i;
300 const char **fmt;
301
302 puts ("#ifndef GCC_GENRTL_H");
303 puts ("#define GCC_GENRTL_H\n");
304
305 for(fmt = formats;*fmt; ++fmt)
306 gendecl (*fmt);
307
308 putchar ('\n');
309
310 for(i = 0; i < NUM_RTX_CODE; i++)
311 if (! special_format (defs[i].format))
312 genmacro (i);
313
314 puts ("\n#endif /* GCC_GENRTL_H */");
315 }
Notice that at line 306 above, formats must pass special_format.gendecl generatesthe declaration of the rtx generation functions.
188 static void
189 gendecl (const char *format) ingengenrtl.c
190 {
191 constchar *p;
192 int i, pos;
193
194 printf ("extern rtxgen_rtx_fmt_%s\t (RTX_CODE, ", format);
195 printf ("enum machine_modemode");
196
197 /* Write each parameter that is needed andstart a new line when the line
198 would overflow. */
199 for (p = format, i = 0, pos = 75; *p !=0; p++)
200 if (*p != '0')
201 {
202 int ourlen = strlen (type_from_format(*p)) + 6 + (i > 9);
203
204 printf (",");
205 if (pos + ourlen > 76)
206 printf ("\n\t\t\t\t "), pos = 39;
207
208 printf (" %sarg%d", type_from_format(*p), i++);
209 pos += ourlen;
210 }
211
212 printf (");\n");
213 }
type_from_format maps the rtx format to the corresponding c types.
61 static const char *
62 type_from_format (int c) ingengenrtl.c
63 {
64 switch (c)
65 {
66 case 'i':
67 return "int ";
68
69 case 'w':
70 return "HOST_WIDE_INT ";
71
72 case 's':
73 return "const char *";
74
75 case 'e': case 'u':
76 return"rtx ";
77
78 case 'E':
79 return "rtvec ";
80 case 'b':
81 return "struct bitmap_head_def*"; /*bitmap - typedef not available */
82 case 't':
83 return "union tree_node*"; /*tree - typedef not available */
84 case 'B':
85 return "struct basic_block_def*"; /*basic block - typedef not available */
86 default:
87 abort ();
88 }
89 }
For DEF_RTL_EXPR definition, ENUM will be output as rtx_code,while creating rtx object during compilation, most of time, rtx_codewill be specified for the object created. So genmacro will output macros for creatingrtx object according to rtx_code.
218 static void
219 genmacro (int idx) ingengenrtl.c
220 {
221 const char *p;
222 int i;
223
224 /* We write a macro that definesgen_rtx_RTLCODE to be an equivalent to
225 gen_rtx_fmt_FORMAT where FORMAT is theRTX_FORMAT of RTLCODE. */
226
227 if (excluded_rtx (idx))
228 /* Don't define a macro for this code. */
229 return;
230
231 printf ("#define gen_rtx_%s%s(MODE",
232 special_rtx (idx)? "raw_" : "", defs[idx].enumname);
233
234 for(p = defs[idx].format,i = 0; *p != 0; p++)
235 if (*p != '0')
236 printf (", ARG%d", i++);
237
238 printf (") \\\n gen_rtx_fmt_%s (%s, (MODE)",
239 defs[idx].format, defs[idx].enumname);
240
241 for(p = defs[idx].format,i = 0; *p != 0; p++)
242 if (*p != '0')
243 printf (", (ARG%d)", i++);
244
245 puts (")");
246 }
The detail of special_rtx is asfollowing.
143 static int
144 special_rtx (int idx) ingengenrtl.c
145 {
146 return (strcmp (defs[idx].enumname,"CONST_INT") == 0
147 || strcmp (defs[idx].enumname,"REG") == 0
148 || strcmp (defs[idx].enumname,"SUBREG") == 0
149 || strcmp (defs[idx].enumname,"MEM") == 0
150 || strcmp (defs[idx].enumname,"CONST_VECTOR") == 0);
151 }
16.3. Output genrtl.c
The definition of functions creating rtx object are produced by gencode.
319 static void
320 gencode (void) ingengenrtl.c
321 {
322 const char **fmt;
323
324 puts ("#include \"config.h\"");
325 puts ("#include \"system.h\"");
326 puts ("#include \"coretypes.h\"");
327 puts ("#include \"tm.h\"");
328 puts ("#include \"obstack.h\"");
329 puts ("#include \"rtl.h\"");
330 puts ("#include \"ggc.h\"\n");
331
332 for(fmt = formats;*fmt != 0; fmt++)
333 gendef (*fmt);
334 }
Only for normal format object, will define the creation functions.
251 static void
252 gendef (const char *format) in gengenrtl.c
253 {
254 const char *p;
255 int i, j;
256
257 /* Start by writing the definition of the functionname and the types
258 of thearguments. */
259
260 printf ("rtx\ngen_rtx_fmt_%s(RTX_CODE code, enum machine_mode mode", format);
261 for(p = format, i = 0; *p != 0; p++)
262 if (*p != '0')
263 printf (",\n\t%sarg%d", type_from_format(*p), i++);
264
265 puts (")");
266
267 /* Now write out the body of the functionitself, which allocates
268 the memory and initializes it. */
269 puts ("{");
270 puts (" rtx rt;");
271 puts (" rt = ggc_alloc_rtx(code);\n");
272
273 puts (" memset (rt, 0,RTX_HDR_SIZE);\n");
274 puts (" PUT_CODE (rt, code);");
275 puts (" PUT_MODE (rt, mode);");
276
277 for(p = format, i = j = 0; *p ; ++p, ++i)
278 if (*p != '0')
279 printf (" %s (rt, %d) =arg%d;\n", accessor_from_format (*p),i, j++);
280 else
281 printf (" X0EXP (rt, %d) =NULL_RTX;\n", i);
282
283 puts ("\n returnrt;\n}\n");
284 }
accessor_from_format maps rtx accessing macros with their formats.
93 static const char *
94 accessor_from_format (int c) in gengenrtl.c
95 {
96 switch (c)
97 {
98 case 'i':
99 return "XINT";
100
101 case 'w':
102 return "XWINT";
103
104 case 's':
105 return "XSTR";
106
107 case 'e': case 'u':
108 return "XEXP";
109
110 case 'E':
111 return "XVEC";
112
113 case 'b':
114 return "XBITMAP";
115
116 case 't':
117 return "XTREE";
118
119 case 'B':
120 return "XBBDEF";
121
122 default:
123 abort ();
124 }
125 }