1 /* Process source files and output type information.
2 Copyright (C) 2002, 2003, 2004 Free Software Foundation, Inc.
4 This file is part of GCC.
6 GCC is free software; you can redistribute it and/or modify it under
7 the terms of the GNU General Public License as published by the Free
8 Software Foundation; either version 2, or (at your option) any later
11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 You should have received a copy of the GNU General Public License
17 along with GCC; see the file COPYING. If not, write to the Free
18 Software Foundation, 59 Temple Place - Suite 330, Boston, MA
23 #include "coretypes.h"
32 /* Nonzero iff an error has occurred. */
33 static int hit_error = 0;
35 static void gen_rtx_next (void);
36 static void write_rtx_next (void);
37 static void open_base_files (void);
38 static void close_output_files (void);
40 /* Report an error at POS, printing MSG. */
43 error_at_line (struct fileloc *pos, const char *msg, ...)
49 fprintf (stderr, "%s:%d: ", pos->file, pos->line);
50 vfprintf (stderr, msg, ap);
57 /* vasprintf, but produces fatal message on out-of-memory. */
59 xvasprintf (char **result, const char *format, va_list args)
61 int ret = vasprintf (result, format, args);
62 if (*result == NULL || ret < 0)
64 fputs ("gengtype: out of memory", stderr);
70 /* Wrapper for xvasprintf. */
72 xasprintf (const char *format, ...)
77 va_start (ap, format);
78 xvasprintf (&result, format, ap);
83 /* The one and only TYPE_STRING. */
85 struct type string_type = {
86 TYPE_STRING, NULL, NULL, GC_USED, {0}
89 /* Lists of various things. */
91 static pair_p typedefs;
92 static type_p structures;
93 static type_p param_structs;
94 static pair_p variables;
96 static void do_scalar_typedef (const char *, struct fileloc *);
97 static type_p find_param_structure
98 (type_p t, type_p param[NUM_PARAM]);
99 static type_p adjust_field_tree_exp (type_p t, options_p opt);
100 static type_p adjust_field_rtx_def (type_p t, options_p opt);
102 /* Define S as a typedef to T at POS. */
105 do_typedef (const char *s, type_p t, struct fileloc *pos)
109 for (p = typedefs; p != NULL; p = p->next)
110 if (strcmp (p->name, s) == 0)
114 error_at_line (pos, "type `%s' previously defined", s);
115 error_at_line (&p->line, "previously defined here");
120 p = xmalloc (sizeof (struct pair));
128 /* Define S as a typename of a scalar. */
131 do_scalar_typedef (const char *s, struct fileloc *pos)
133 do_typedef (s, create_scalar_type (s, strlen (s)), pos);
136 /* Return the type previously defined for S. Use POS to report errors. */
139 resolve_typedef (const char *s, struct fileloc *pos)
142 for (p = typedefs; p != NULL; p = p->next)
143 if (strcmp (p->name, s) == 0)
145 error_at_line (pos, "unidentified type `%s'", s);
146 return create_scalar_type ("char", 4);
149 /* Create a new structure with tag NAME (or a union iff ISUNION is nonzero),
150 at POS with fields FIELDS and options O. */
153 new_structure (const char *name, int isunion, struct fileloc *pos,
154 pair_p fields, options_p o)
158 lang_bitmap bitmap = get_base_file_bitmap (pos->file);
160 for (si = structures; si != NULL; si = si->next)
161 if (strcmp (name, si->u.s.tag) == 0
162 && UNION_P (si) == isunion)
165 if (si->kind == TYPE_LANG_STRUCT)
169 for (si = ls->u.s.lang_struct; si != NULL; si = si->next)
170 if (si->u.s.bitmap == bitmap)
173 else if (si->u.s.line.file != NULL && si->u.s.bitmap != bitmap)
176 si = xcalloc (1, sizeof (struct type));
177 memcpy (si, ls, sizeof (struct type));
178 ls->kind = TYPE_LANG_STRUCT;
179 ls->u.s.lang_struct = si;
180 ls->u.s.fields = NULL;
182 si->pointer_to = NULL;
183 si->u.s.lang_struct = ls;
188 if (ls != NULL && s == NULL)
190 s = xcalloc (1, sizeof (struct type));
191 s->next = ls->u.s.lang_struct;
192 ls->u.s.lang_struct = s;
193 s->u.s.lang_struct = ls;
200 s = xcalloc (1, sizeof (struct type));
201 s->next = structures;
205 if (s->u.s.line.file != NULL
206 || (s->u.s.lang_struct && (s->u.s.lang_struct->u.s.bitmap & bitmap)))
208 error_at_line (pos, "duplicate structure definition");
209 error_at_line (&s->u.s.line, "previous definition here");
212 s->kind = isunion ? TYPE_UNION : TYPE_STRUCT;
215 s->u.s.fields = fields;
217 s->u.s.bitmap = bitmap;
218 if (s->u.s.lang_struct)
219 s->u.s.lang_struct->u.s.bitmap |= bitmap;
222 /* Return the previously-defined structure with tag NAME (or a union
223 iff ISUNION is nonzero), or a new empty structure or union if none
224 was defined previously. */
227 find_structure (const char *name, int isunion)
231 for (s = structures; s != NULL; s = s->next)
232 if (strcmp (name, s->u.s.tag) == 0
233 && UNION_P (s) == isunion)
236 s = xcalloc (1, sizeof (struct type));
237 s->next = structures;
239 s->kind = isunion ? TYPE_UNION : TYPE_STRUCT;
245 /* Return the previously-defined parameterized structure for structure
246 T and parameters PARAM, or a new parameterized empty structure or
247 union if none was defined previously. */
250 find_param_structure (type_p t, type_p param[NUM_PARAM])
254 for (res = param_structs; res; res = res->next)
255 if (res->u.param_struct.stru == t
256 && memcmp (res->u.param_struct.param, param,
257 sizeof (type_p) * NUM_PARAM) == 0)
261 res = xcalloc (1, sizeof (*res));
262 res->kind = TYPE_PARAM_STRUCT;
263 res->next = param_structs;
265 res->u.param_struct.stru = t;
266 memcpy (res->u.param_struct.param, param, sizeof (type_p) * NUM_PARAM);
271 /* Return a scalar type with name NAME. */
274 create_scalar_type (const char *name, size_t name_len)
276 type_p r = xcalloc (1, sizeof (struct type));
277 r->kind = TYPE_SCALAR;
278 r->u.sc = xmemdup (name, name_len, name_len + 1);
282 /* Return a pointer to T. */
285 create_pointer (type_p t)
289 type_p r = xcalloc (1, sizeof (struct type));
290 r->kind = TYPE_POINTER;
294 return t->pointer_to;
297 /* Return an array of length LEN. */
300 create_array (type_p t, const char *len)
304 v = xcalloc (1, sizeof (*v));
305 v->kind = TYPE_ARRAY;
311 /* Return an options structure with name NAME and info INFO. */
313 create_option (const char *name, void *info)
315 options_p o = xmalloc (sizeof (*o));
321 /* Add a variable named S of type T with options O defined at POS,
325 note_variable (const char *s, type_p t, options_p o, struct fileloc *pos)
328 n = xmalloc (sizeof (*n));
337 /* We really don't care how long a CONST_DOUBLE is. */
338 #define CONST_DOUBLE_FORMAT "ww"
339 const char * const rtx_format[NUM_RTX_CODE] = {
340 #define DEF_RTL_EXPR(ENUM, NAME, FORMAT, CLASS) FORMAT ,
345 static int rtx_next_new[NUM_RTX_CODE];
347 /* Generate the contents of the rtx_next array. This really doesn't belong
348 in gengtype at all, but it's needed for adjust_field_rtx_def. */
354 for (i = 0; i < NUM_RTX_CODE; i++)
358 rtx_next_new[i] = -1;
359 if (strncmp (rtx_format[i], "iuu", 3) == 0)
361 else if (i == COND_EXEC || i == SET || i == EXPR_LIST || i == INSN_LIST)
364 for (k = strlen (rtx_format[i]) - 1; k >= 0; k--)
365 if (rtx_format[i][k] == 'e' || rtx_format[i][k] == 'u')
370 /* Write out the contents of the rtx_next array. */
372 write_rtx_next (void)
374 outf_p f = get_output_file_with_visibility (NULL);
377 oprintf (f, "\n/* Used to implement the RTX_NEXT macro. */\n");
378 oprintf (f, "const unsigned char rtx_next[NUM_RTX_CODE] = {\n");
379 for (i = 0; i < NUM_RTX_CODE; i++)
380 if (rtx_next_new[i] == -1)
381 oprintf (f, " 0,\n");
384 " RTX_HDR_SIZE + %d * sizeof (rtunion),\n",
389 /* Handle `special("rtx_def")'. This is a special case for field
390 `fld' of struct rtx_def, which is an array of unions whose values
391 are based in a complex way on the type of RTL. */
394 adjust_field_rtx_def (type_p t, options_p opt ATTRIBUTE_UNUSED)
399 type_p rtx_tp, rtvec_tp, tree_tp, mem_attrs_tp, note_union_tp, scalar_tp;
400 type_p bitmap_tp, basic_block_tp, reg_attrs_tp;
402 static const char * const rtx_name[NUM_RTX_CODE] = {
403 #define DEF_RTL_EXPR(ENUM, NAME, FORMAT, CLASS) NAME ,
408 if (t->kind != TYPE_UNION)
410 error_at_line (&lexer_line,
411 "special `rtx_def' must be applied to a union");
415 nodot = xmalloc (sizeof (*nodot));
420 rtx_tp = create_pointer (find_structure ("rtx_def", 0));
421 rtvec_tp = create_pointer (find_structure ("rtvec_def", 0));
422 tree_tp = create_pointer (find_structure ("tree_node", 1));
423 mem_attrs_tp = create_pointer (find_structure ("mem_attrs", 0));
424 reg_attrs_tp = create_pointer (find_structure ("reg_attrs", 0));
425 bitmap_tp = create_pointer (find_structure ("bitmap_element_def", 0));
426 basic_block_tp = create_pointer (find_structure ("basic_block_def", 0));
427 scalar_tp = create_scalar_type ("rtunion scalar", 14);
430 pair_p note_flds = NULL;
433 for (c = NOTE_INSN_BIAS; c <= NOTE_INSN_MAX; c++)
435 pair_p old_note_flds = note_flds;
437 note_flds = xmalloc (sizeof (*note_flds));
438 note_flds->line.file = __FILE__;
439 note_flds->line.line = __LINE__;
440 note_flds->opt = xmalloc (sizeof (*note_flds->opt));
441 note_flds->opt->next = nodot;
442 note_flds->opt->name = "tag";
443 note_flds->opt->info = xasprintf ("%d", c);
444 note_flds->next = old_note_flds;
448 /* NOTE_INSN_MAX is used as the default field for line
451 note_flds->opt->name = "default";
452 note_flds->name = "rtstr";
453 note_flds->type = &string_type;
456 case NOTE_INSN_BLOCK_BEG:
457 case NOTE_INSN_BLOCK_END:
458 note_flds->name = "rttree";
459 note_flds->type = tree_tp;
462 case NOTE_INSN_EXPECTED_VALUE:
463 case NOTE_INSN_VAR_LOCATION:
464 note_flds->name = "rtx";
465 note_flds->type = rtx_tp;
469 note_flds->name = "rtint";
470 note_flds->type = scalar_tp;
474 new_structure ("rtx_def_note_subunion", 1, &lexer_line, note_flds, NULL);
477 note_union_tp = find_structure ("rtx_def_note_subunion", 1);
479 for (i = 0; i < NUM_RTX_CODE; i++)
481 pair_p old_flds = flds;
482 pair_p subfields = NULL;
483 size_t aindex, nmindex;
487 for (aindex = 0; aindex < strlen (rtx_format[i]); aindex++)
489 pair_p old_subf = subfields;
493 switch (rtx_format[i][aindex])
504 if (i == MEM && aindex == 1)
505 t = mem_attrs_tp, subname = "rtmem";
506 else if (i == JUMP_INSN && aindex == 9)
507 t = rtx_tp, subname = "rtx";
508 else if (i == CODE_LABEL && aindex == 4)
509 t = scalar_tp, subname = "rtint";
510 else if (i == CODE_LABEL && aindex == 5)
511 t = rtx_tp, subname = "rtx";
512 else if (i == LABEL_REF
513 && (aindex == 1 || aindex == 2))
514 t = rtx_tp, subname = "rtx";
515 else if (i == NOTE && aindex == 4)
516 t = note_union_tp, subname = "";
517 else if (i == NOTE && aindex >= 7)
518 t = scalar_tp, subname = "rtint";
519 else if (i == ADDR_DIFF_VEC && aindex == 4)
520 t = scalar_tp, subname = "rtint";
521 else if (i == VALUE && aindex == 0)
522 t = scalar_tp, subname = "rtint";
523 else if (i == REG && aindex == 1)
524 t = scalar_tp, subname = "rtint";
525 else if (i == REG && aindex == 2)
526 t = reg_attrs_tp, subname = "rtreg";
527 else if (i == SCRATCH && aindex == 0)
528 t = scalar_tp, subname = "rtint";
529 else if (i == SYMBOL_REF && aindex == 1)
530 t = scalar_tp, subname = "rtint";
531 else if (i == SYMBOL_REF && aindex == 2)
532 t = tree_tp, subname = "rttree";
533 else if (i == BARRIER && aindex >= 3)
534 t = scalar_tp, subname = "rtint";
537 error_at_line (&lexer_line,
538 "rtx type `%s' has `0' in position %lu, can't handle",
539 rtx_name[i], (unsigned long) aindex);
580 error_at_line (&lexer_line,
581 "rtx type `%s' has `%c' in position %lu, can't handle",
582 rtx_name[i], rtx_format[i][aindex],
583 (unsigned long)aindex);
589 subfields = xmalloc (sizeof (*subfields));
590 subfields->next = old_subf;
592 subfields->name = xasprintf (".fld[%lu].%s", (unsigned long)aindex,
594 subfields->line.file = __FILE__;
595 subfields->line.line = __LINE__;
596 if (t == note_union_tp)
598 subfields->opt = xmalloc (sizeof (*subfields->opt));
599 subfields->opt->next = nodot;
600 subfields->opt->name = "desc";
601 subfields->opt->info = "NOTE_LINE_NUMBER (&%0)";
603 else if (t == basic_block_tp)
605 /* We don't presently GC basic block structures... */
606 subfields->opt = xmalloc (sizeof (*subfields->opt));
607 subfields->opt->next = nodot;
608 subfields->opt->name = "skip";
609 subfields->opt->info = NULL;
612 subfields->opt = nodot;
615 flds = xmalloc (sizeof (*flds));
616 flds->next = old_flds;
618 sname = xasprintf ("rtx_def_%s", rtx_name[i]);
619 new_structure (sname, 0, &lexer_line, subfields, NULL);
620 flds->type = find_structure (sname, 0);
621 flds->line.file = __FILE__;
622 flds->line.line = __LINE__;
623 flds->opt = xmalloc (sizeof (*flds->opt));
624 flds->opt->next = nodot;
625 flds->opt->name = "tag";
626 ftag = xstrdup (rtx_name[i]);
627 for (nmindex = 0; nmindex < strlen (ftag); nmindex++)
628 ftag[nmindex] = TOUPPER (ftag[nmindex]);
629 flds->opt->info = ftag;
632 new_structure ("rtx_def_subunion", 1, &lexer_line, flds, nodot);
633 return find_structure ("rtx_def_subunion", 1);
636 /* Handle `special("tree_exp")'. This is a special case for
637 field `operands' of struct tree_exp, which although it claims to contain
638 pointers to trees, actually sometimes contains pointers to RTL too.
639 Passed T, the old type of the field, and OPT its options. Returns
640 a new type for the field. */
643 adjust_field_tree_exp (type_p t, options_p opt ATTRIBUTE_UNUSED)
648 static const struct {
653 { "SAVE_EXPR", 2, 1 },
654 { "GOTO_SUBROUTINE_EXPR", 0, 2 },
655 { "RTL_EXPR", 0, 2 },
656 { "WITH_CLEANUP_EXPR", 2, 1 },
659 if (t->kind != TYPE_ARRAY)
661 error_at_line (&lexer_line,
662 "special `tree_exp' must be applied to an array");
666 nodot = xmalloc (sizeof (*nodot));
671 flds = xmalloc (sizeof (*flds));
675 flds->line.file = __FILE__;
676 flds->line.line = __LINE__;
677 flds->opt = xmalloc (sizeof (*flds->opt));
678 flds->opt->next = nodot;
679 flds->opt->name = "length";
680 flds->opt->info = "TREE_CODE_LENGTH (TREE_CODE ((tree) &%0))";
682 options_p oldopt = flds->opt;
683 flds->opt = xmalloc (sizeof (*flds->opt));
684 flds->opt->next = oldopt;
685 flds->opt->name = "default";
686 flds->opt->info = "";
689 for (i = 0; i < ARRAY_SIZE (data); i++)
691 pair_p old_flds = flds;
692 pair_p subfields = NULL;
697 r_index < data[i].first_rtl + data[i].num_rtl;
700 pair_p old_subf = subfields;
701 subfields = xmalloc (sizeof (*subfields));
702 subfields->next = old_subf;
703 subfields->name = xasprintf ("[%d]", r_index);
704 if (r_index < data[i].first_rtl)
705 subfields->type = t->u.a.p;
707 subfields->type = create_pointer (find_structure ("rtx_def", 0));
708 subfields->line.file = __FILE__;
709 subfields->line.line = __LINE__;
710 subfields->opt = nodot;
713 flds = xmalloc (sizeof (*flds));
714 flds->next = old_flds;
716 sname = xasprintf ("tree_exp_%s", data[i].name);
717 new_structure (sname, 0, &lexer_line, subfields, NULL);
718 flds->type = find_structure (sname, 0);
719 flds->line.file = __FILE__;
720 flds->line.line = __LINE__;
721 flds->opt = xmalloc (sizeof (*flds->opt));
722 flds->opt->next = nodot;
723 flds->opt->name = "tag";
724 flds->opt->info = data[i].name;
727 new_structure ("tree_exp_subunion", 1, &lexer_line, flds, nodot);
728 return find_structure ("tree_exp_subunion", 1);
731 /* Perform any special processing on a type T, about to become the type
732 of a field. Return the appropriate type for the field.
734 - Converts pointer-to-char, with no length parameter, to TYPE_STRING;
735 - Similarly for arrays of pointer-to-char;
736 - Converts structures for which a parameter is provided to
738 - Handles "special" options.
742 adjust_field_type (type_p t, options_p opt)
745 const int pointer_p = t->kind == TYPE_POINTER;
746 type_p params[NUM_PARAM];
750 for (i = 0; i < NUM_PARAM; i++)
753 for (; opt; opt = opt->next)
754 if (strcmp (opt->name, "length") == 0)
756 else if (strcmp (opt->name, "param_is") == 0
757 || (strncmp (opt->name, "param", 5) == 0
758 && ISDIGIT (opt->name[5])
759 && strcmp (opt->name + 6, "_is") == 0))
761 int num = ISDIGIT (opt->name[5]) ? opt->name[5] - '0' : 0;
763 if (! UNION_OR_STRUCT_P (t)
764 && (t->kind != TYPE_POINTER || ! UNION_OR_STRUCT_P (t->u.p)))
766 error_at_line (&lexer_line,
767 "option `%s' may only be applied to structures or structure pointers",
773 if (params[num] != NULL)
774 error_at_line (&lexer_line, "duplicate `%s' option", opt->name);
775 if (! ISDIGIT (opt->name[5]))
776 params[num] = create_pointer ((type_p) opt->info);
778 params[num] = (type_p) opt->info;
780 else if (strcmp (opt->name, "special") == 0)
782 const char *special_name = (const char *)opt->info;
783 if (strcmp (special_name, "tree_exp") == 0)
784 t = adjust_field_tree_exp (t, opt);
785 else if (strcmp (special_name, "rtx_def") == 0)
786 t = adjust_field_rtx_def (t, opt);
788 error_at_line (&lexer_line, "unknown special `%s'", special_name);
797 realt = find_param_structure (t, params);
798 t = pointer_p ? create_pointer (realt) : realt;
803 && t->u.p->kind == TYPE_SCALAR
804 && (strcmp (t->u.p->u.sc, "char") == 0
805 || strcmp (t->u.p->u.sc, "unsigned char") == 0))
807 if (t->kind == TYPE_ARRAY && t->u.a.p->kind == TYPE_POINTER
808 && t->u.a.p->u.p->kind == TYPE_SCALAR
809 && (strcmp (t->u.a.p->u.p->u.sc, "char") == 0
810 || strcmp (t->u.a.p->u.p->u.sc, "unsigned char") == 0))
811 return create_array (&string_type, t->u.a.len);
816 /* Create a union for YYSTYPE, as yacc would do it, given a fieldlist FIELDS
817 and information about the correspondence between token types and fields
818 in TYPEINFO. POS is used for error messages. */
821 note_yacc_type (options_p o, pair_p fields, pair_p typeinfo,
827 for (p = typeinfo; p; p = p->next)
834 if (p->type == (type_p) 1)
839 for (pp = typeinfo; pp; pp = pp->next)
840 if (pp->type != (type_p) 1
841 && strcmp (pp->opt->info, p->opt->info) == 0)
850 for (m = fields; m; m = m->next)
851 if (strcmp (m->name, p->name) == 0)
855 error_at_line (&p->line,
856 "couldn't match fieldname `%s'", p->name);
867 || p->type == (type_p) 1)
873 new_structure ("yy_union", 1, pos, typeinfo, o);
874 do_typedef ("YYSTYPE", find_structure ("yy_union", 1), pos);
877 static void process_gc_options (options_p, enum gc_used_enum,
878 int *, int *, int *);
879 static void set_gc_used_type (type_p, enum gc_used_enum, type_p *);
880 static void set_gc_used (pair_p);
882 /* Handle OPT for set_gc_used_type. */
885 process_gc_options (options_p opt, enum gc_used_enum level, int *maybe_undef,
886 int *pass_param, int *length)
889 for (o = opt; o; o = o->next)
890 if (strcmp (o->name, "ptr_alias") == 0 && level == GC_POINTED_TO)
891 set_gc_used_type ((type_p) o->info, GC_POINTED_TO, NULL);
892 else if (strcmp (o->name, "maybe_undef") == 0)
894 else if (strcmp (o->name, "use_params") == 0)
896 else if (strcmp (o->name, "length") == 0)
900 /* Set the gc_used field of T to LEVEL, and handle the types it references. */
903 set_gc_used_type (type_p t, enum gc_used_enum level, type_p param[NUM_PARAM])
905 if (t->gc_used >= level)
918 process_gc_options (t->u.s.opt, level, &dummy, &dummy, &dummy);
920 for (f = t->u.s.fields; f; f = f->next)
925 process_gc_options (f->opt, level, &maybe_undef, &pass_param,
928 if (length && f->type->kind == TYPE_POINTER)
929 set_gc_used_type (f->type->u.p, GC_USED, NULL);
930 else if (maybe_undef && f->type->kind == TYPE_POINTER)
931 set_gc_used_type (f->type->u.p, GC_MAYBE_POINTED_TO, NULL);
932 else if (pass_param && f->type->kind == TYPE_POINTER && param)
933 set_gc_used_type (find_param_structure (f->type->u.p, param),
934 GC_POINTED_TO, NULL);
936 set_gc_used_type (f->type, GC_USED, pass_param ? param : NULL);
942 set_gc_used_type (t->u.p, GC_POINTED_TO, NULL);
946 set_gc_used_type (t->u.a.p, GC_USED, param);
949 case TYPE_LANG_STRUCT:
950 for (t = t->u.s.lang_struct; t; t = t->next)
951 set_gc_used_type (t, level, param);
954 case TYPE_PARAM_STRUCT:
957 for (i = 0; i < NUM_PARAM; i++)
958 if (t->u.param_struct.param[i] != 0)
959 set_gc_used_type (t->u.param_struct.param[i], GC_USED, NULL);
961 if (t->u.param_struct.stru->gc_used == GC_POINTED_TO)
962 level = GC_POINTED_TO;
965 t->u.param_struct.stru->gc_used = GC_UNUSED;
966 set_gc_used_type (t->u.param_struct.stru, level,
967 t->u.param_struct.param);
975 /* Set the gc_used fields of all the types pointed to by VARIABLES. */
978 set_gc_used (pair_p variables)
981 for (p = variables; p; p = p->next)
982 set_gc_used_type (p->type, GC_USED, NULL);
985 /* File mapping routines. For each input file, there is one output .c file
986 (but some output files have many input files), and there is one .h file
987 for the whole build. */
989 /* The list of output files. */
990 static outf_p output_files;
992 /* The output header file that is included into pretty much every
994 static outf_p header_file;
996 /* Number of files specified in gtfiles. */
997 #define NUM_GT_FILES (ARRAY_SIZE (all_files) - 1)
999 /* Number of files in the language files array. */
1000 #define NUM_LANG_FILES (ARRAY_SIZE (lang_files) - 1)
1002 /* Length of srcdir name. */
1003 static int srcdir_len = 0;
1005 #define NUM_BASE_FILES (ARRAY_SIZE (lang_dir_names) - 1)
1006 outf_p base_files[NUM_BASE_FILES];
1008 static outf_p create_file (const char *, const char *);
1009 static const char * get_file_basename (const char *);
1011 /* Create and return an outf_p for a new file for NAME, to be called
1015 create_file (const char *name, const char *oname)
1017 static const char *const hdr[] = {
1018 " Copyright (C) 2003 Free Software Foundation, Inc.\n",
1020 "This file is part of GCC.\n",
1022 "GCC is free software; you can redistribute it and/or modify it under\n",
1023 "the terms of the GNU General Public License as published by the Free\n",
1024 "Software Foundation; either version 2, or (at your option) any later\n",
1027 "GCC is distributed in the hope that it will be useful, but WITHOUT ANY\n",
1028 "WARRANTY; without even the implied warranty of MERCHANTABILITY or\n",
1029 "FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License\n",
1030 "for more details.\n",
1032 "You should have received a copy of the GNU General Public License\n",
1033 "along with GCC; see the file COPYING. If not, write to the Free\n",
1034 "Software Foundation, 59 Temple Place - Suite 330, Boston, MA\n",
1035 "02111-1307, USA. */\n",
1037 "/* This file is machine generated. Do not edit. */\n"
1042 f = xcalloc (sizeof (*f), 1);
1043 f->next = output_files;
1047 oprintf (f, "/* Type information for %s.\n", name);
1048 for (i = 0; i < ARRAY_SIZE (hdr); i++)
1049 oprintf (f, "%s", hdr[i]);
1053 /* Print, like fprintf, to O. */
1055 oprintf (outf_p o, const char *format, ...)
1061 va_start (ap, format);
1062 slength = xvasprintf (&s, format, ap);
1064 if (o->bufused + slength > o->buflength)
1066 size_t new_len = o->buflength;
1071 } while (o->bufused + slength >= new_len);
1072 o->buf = xrealloc (o->buf, new_len);
1073 o->buflength = new_len;
1075 memcpy (o->buf + o->bufused, s, slength);
1076 o->bufused += slength;
1081 /* Open the global header file and the language-specific header files. */
1084 open_base_files (void)
1088 header_file = create_file ("GCC", "gtype-desc.h");
1090 for (i = 0; i < NUM_BASE_FILES; i++)
1091 base_files[i] = create_file (lang_dir_names[i],
1092 xasprintf ("gtype-%s.h", lang_dir_names[i]));
1094 /* gtype-desc.c is a little special, so we create it here. */
1096 /* The order of files here matters very much. */
1097 static const char *const ifiles [] = {
1098 "config.h", "system.h", "coretypes.h", "tm.h", "varray.h",
1099 "hashtab.h", "splay-tree.h", "bitmap.h", "tree.h", "rtl.h",
1100 "function.h", "insn-config.h", "expr.h", "hard-reg-set.h",
1101 "basic-block.h", "cselib.h", "insn-addr.h", "optabs.h",
1102 "libfuncs.h", "debug.h", "ggc.h", "cgraph.h",
1103 "tree-alias-type.h", "tree-flow.h", "reload.h",
1106 const char *const *ifp;
1107 outf_p gtype_desc_c;
1109 gtype_desc_c = create_file ("GCC", "gtype-desc.c");
1110 for (ifp = ifiles; *ifp; ifp++)
1111 oprintf (gtype_desc_c, "#include \"%s\"\n", *ifp);
1115 /* Determine the pathname to F relative to $(srcdir). */
1118 get_file_basename (const char *f)
1120 const char *basename;
1123 basename = strrchr (f, '/');
1130 for (i = 1; i < NUM_BASE_FILES; i++)
1136 s1 = basename - strlen (lang_dir_names [i]) - 1;
1137 s2 = lang_dir_names [i];
1140 if (l1 >= l2 && !memcmp (s1, s2, l2))
1143 if ((basename - f - 1) != srcdir_len)
1144 abort (); /* Match is wrong - should be preceded by $srcdir. */
1152 /* Return a bitmap which has bit `1 << BASE_FILE_<lang>' set iff
1153 INPUT_FILE is used by <lang>.
1155 This function should be written to assume that a file _is_ used
1156 if the situation is unclear. If it wrongly assumes a file _is_ used,
1157 a linker error will result. If it wrongly assumes a file _is not_ used,
1158 some GC roots may be missed, which is a much harder-to-debug problem. */
1161 get_base_file_bitmap (const char *input_file)
1163 const char *basename = get_file_basename (input_file);
1164 const char *slashpos = strchr (basename, '/');
1172 for (i = 1; i < NUM_BASE_FILES; i++)
1173 if ((size_t)(slashpos - basename) == strlen (lang_dir_names [i])
1174 && memcmp (basename, lang_dir_names[i], strlen (lang_dir_names[i])) == 0)
1176 /* It's in a language directory, set that language. */
1181 abort (); /* Should have found the language. */
1184 /* If it's in any config-lang.in, then set for the languages
1189 for (j = 0; j < NUM_LANG_FILES; j++)
1191 if (!strcmp(input_file, lang_files[j]))
1193 for (k = 0; k < NUM_BASE_FILES; k++)
1195 if (!strcmp(lang_dir_names[k], langs_for_lang_files[j]))
1201 /* Otherwise, set all languages. */
1203 bitmap = (1 << NUM_BASE_FILES) - 1;
1208 /* An output file, suitable for definitions, that can see declarations
1209 made in INPUT_FILE and is linked into every language that uses
1213 get_output_file_with_visibility (const char *input_file)
1217 const char *basename;
1218 const char *for_name;
1219 const char *output_name;
1221 /* This can happen when we need a file with visibility on a
1222 structure that we've never seen. We have to just hope that it's
1223 globally visible. */
1224 if (input_file == NULL)
1225 input_file = "system.h";
1227 /* Determine the output file name. */
1228 basename = get_file_basename (input_file);
1230 len = strlen (basename);
1231 if ((len > 2 && memcmp (basename+len-2, ".c", 2) == 0)
1232 || (len > 2 && memcmp (basename+len-2, ".y", 2) == 0)
1233 || (len > 3 && memcmp (basename+len-3, ".in", 3) == 0))
1237 output_name = s = xasprintf ("gt-%s", basename);
1238 for (; *s != '.'; s++)
1239 if (! ISALNUM (*s) && *s != '-')
1241 memcpy (s, ".h", sizeof (".h"));
1242 for_name = basename;
1244 else if (strcmp (basename, "c-common.h") == 0)
1245 output_name = "gt-c-common.h", for_name = "c-common.c";
1246 else if (strcmp (basename, "c-tree.h") == 0)
1247 output_name = "gt-c-decl.h", for_name = "c-decl.c";
1252 for (i = 0; i < NUM_BASE_FILES; i++)
1253 if (memcmp (basename, lang_dir_names[i], strlen (lang_dir_names[i])) == 0
1254 && basename[strlen(lang_dir_names[i])] == '/')
1255 return base_files[i];
1257 output_name = "gtype-desc.c";
1261 /* Look through to see if we've ever seen this output filename before. */
1262 for (r = output_files; r; r = r->next)
1263 if (strcmp (r->name, output_name) == 0)
1266 /* If not, create it. */
1267 r = create_file (for_name, output_name);
1272 /* The name of an output file, suitable for definitions, that can see
1273 declarations made in INPUT_FILE and is linked into every language
1274 that uses INPUT_FILE. */
1277 get_output_file_name (const char *input_file)
1279 return get_output_file_with_visibility (input_file)->name;
1282 /* Copy the output to its final destination,
1283 but don't unnecessarily change modification times. */
1286 close_output_files (void)
1290 for (of = output_files; of; of = of->next)
1294 newfile = fopen (of->name, "r");
1295 if (newfile != NULL )
1300 for (i = 0; i < of->bufused; i++)
1303 ch = fgetc (newfile);
1304 if (ch == EOF || ch != (unsigned char) of->buf[i])
1307 no_write_p = i == of->bufused && fgetc (newfile) == EOF;
1314 newfile = fopen (of->name, "w");
1315 if (newfile == NULL)
1317 perror ("opening output file");
1320 if (fwrite (of->buf, 1, of->bufused, newfile) != of->bufused)
1322 perror ("writing output file");
1325 if (fclose (newfile) != 0)
1327 perror ("closing output file");
1340 struct walk_type_data;
1342 /* For scalars and strings, given the item in 'val'.
1343 For structures, given a pointer to the item in 'val'.
1344 For misc. pointers, given the item in 'val'.
1346 typedef void (*process_field_fn)
1347 (type_p f, const struct walk_type_data *p);
1348 typedef void (*func_name_fn)
1349 (type_p s, const struct walk_type_data *p);
1351 /* Parameters for write_types. */
1353 struct write_types_data
1356 const char *param_prefix;
1357 const char *subfield_marker_routine;
1358 const char *marker_routine;
1359 const char *reorder_note_routine;
1360 const char *comment;
1363 static void output_escaped_param (struct walk_type_data *d,
1364 const char *, const char *);
1365 static void output_mangled_typename (outf_p, type_p);
1366 static void walk_type (type_p t, struct walk_type_data *d);
1367 static void write_func_for_structure
1368 (type_p orig_s, type_p s, type_p * param,
1369 const struct write_types_data *wtd);
1370 static void write_types_process_field
1371 (type_p f, const struct walk_type_data *d);
1372 static void write_types (type_p structures,
1373 type_p param_structs,
1374 const struct write_types_data *wtd);
1375 static void write_types_local_process_field
1376 (type_p f, const struct walk_type_data *d);
1377 static void write_local_func_for_structure
1378 (type_p orig_s, type_p s, type_p * param);
1379 static void write_local (type_p structures,
1380 type_p param_structs);
1381 static void write_enum_defn (type_p structures, type_p param_structs);
1382 static int contains_scalar_p (type_p t);
1383 static void put_mangled_filename (outf_p , const char *);
1384 static void finish_root_table (struct flist *flp, const char *pfx,
1385 const char *tname, const char *lastname,
1387 static void write_root (outf_p , pair_p, type_p, const char *, int,
1388 struct fileloc *, const char *);
1389 static void write_array (outf_p f, pair_p v,
1390 const struct write_types_data *wtd);
1391 static void write_roots (pair_p);
1393 /* Parameters for walk_type. */
1395 struct walk_type_data
1397 process_field_fn process_field;
1402 const char *prev_val[4];
1405 struct fileloc *line;
1410 const char *reorder_fn;
1414 /* Print a mangled name representing T to OF. */
1417 output_mangled_typename (outf_p of, type_p t)
1421 else switch (t->kind)
1425 output_mangled_typename (of, t->u.p);
1435 case TYPE_LANG_STRUCT:
1436 oprintf (of, "%lu%s", (unsigned long) strlen (t->u.s.tag), t->u.s.tag);
1438 case TYPE_PARAM_STRUCT:
1441 for (i = 0; i < NUM_PARAM; i++)
1442 if (t->u.param_struct.param[i] != NULL)
1443 output_mangled_typename (of, t->u.param_struct.param[i]);
1444 output_mangled_typename (of, t->u.param_struct.stru);
1452 /* Print PARAM to D->OF processing escapes. D->VAL references the
1453 current object, D->PREV_VAL the object containing the current
1454 object, ONAME is the name of the option and D->LINE is used to
1455 print error messages. */
1458 output_escaped_param (struct walk_type_data *d, const char *param,
1463 for (p = param; *p; p++)
1465 oprintf (d->of, "%c", *p);
1469 oprintf (d->of, "(%s)", d->prev_val[2]);
1472 oprintf (d->of, "(%s)", d->prev_val[0]);
1475 oprintf (d->of, "(%s)", d->prev_val[1]);
1479 const char *pp = d->val + strlen (d->val);
1480 while (pp[-1] == ']')
1483 oprintf (d->of, "%s", pp);
1487 error_at_line (d->line, "`%s' option contains bad escape %c%c",
1492 /* Call D->PROCESS_FIELD for every field (or subfield) of D->VAL,
1493 which is of type T. Write code to D->OF to constrain execution (at
1494 the point that D->PROCESS_FIELD is called) to the appropriate
1495 cases. Call D->PROCESS_FIELD on subobjects before calling it on
1496 pointers to those objects. D->PREV_VAL lists the objects
1497 containing the current object, D->OPT is a list of options to
1498 apply, D->INDENT is the current indentation level, D->LINE is used
1499 to print error messages, D->BITMAP indicates which languages to
1500 print the structure for, and D->PARAM is the current parameter
1501 (from an enclosing param_is option). */
1504 walk_type (type_p t, struct walk_type_data *d)
1506 const char *length = NULL;
1507 const char *desc = NULL;
1508 int maybe_undef_p = 0;
1509 int use_param_num = -1;
1510 int use_params_p = 0;
1512 const struct nested_ptr_data *nested_ptr_d = NULL;
1514 d->needs_cast_p = 0;
1515 for (oo = d->opt; oo; oo = oo->next)
1516 if (strcmp (oo->name, "length") == 0)
1517 length = (const char *)oo->info;
1518 else if (strcmp (oo->name, "maybe_undef") == 0)
1520 else if (strncmp (oo->name, "use_param", 9) == 0
1521 && (oo->name[9] == '\0' || ISDIGIT (oo->name[9])))
1522 use_param_num = oo->name[9] == '\0' ? 0 : oo->name[9] - '0';
1523 else if (strcmp (oo->name, "use_params") == 0)
1525 else if (strcmp (oo->name, "desc") == 0)
1526 desc = (const char *)oo->info;
1527 else if (strcmp (oo->name, "nested_ptr") == 0)
1528 nested_ptr_d = (const struct nested_ptr_data *)oo->info ;
1529 else if (strcmp (oo->name, "dot") == 0)
1531 else if (strcmp (oo->name, "tag") == 0)
1533 else if (strcmp (oo->name, "special") == 0)
1535 else if (strcmp (oo->name, "skip") == 0)
1537 else if (strcmp (oo->name, "default") == 0)
1539 else if (strcmp (oo->name, "descbits") == 0)
1541 else if (strcmp (oo->name, "param_is") == 0)
1543 else if (strncmp (oo->name, "param", 5) == 0
1544 && ISDIGIT (oo->name[5])
1545 && strcmp (oo->name + 6, "_is") == 0)
1547 else if (strcmp (oo->name, "chain_next") == 0)
1549 else if (strcmp (oo->name, "chain_prev") == 0)
1551 else if (strcmp (oo->name, "reorder") == 0)
1554 error_at_line (d->line, "unknown option `%s'\n", oo->name);
1561 int pointer_p = t->kind == TYPE_POINTER;
1565 if (! UNION_OR_STRUCT_P (t))
1566 error_at_line (d->line, "`use_params' option on unimplemented type");
1568 t = find_param_structure (t, d->param);
1570 t = create_pointer (t);
1573 if (use_param_num != -1)
1575 if (d->param != NULL && d->param[use_param_num] != NULL)
1577 type_p nt = d->param[use_param_num];
1579 if (t->kind == TYPE_ARRAY)
1580 nt = create_array (nt, t->u.a.len);
1581 else if (length != NULL && t->kind == TYPE_POINTER)
1582 nt = create_pointer (nt);
1583 d->needs_cast_p = (t->kind != TYPE_POINTER
1584 && (nt->kind == TYPE_POINTER
1585 || nt->kind == TYPE_STRING));
1589 error_at_line (d->line, "no parameter defined for `%s'",
1594 && (t->kind != TYPE_POINTER || ! UNION_OR_STRUCT_P (t->u.p)))
1596 error_at_line (d->line,
1597 "field `%s' has invalid option `maybe_undef_p'\n",
1606 d->process_field (t, d);
1612 && t->u.p->u.s.line.file == NULL)
1614 oprintf (d->of, "%*sif (%s) abort();\n", d->indent, "", d->val);
1620 if (! UNION_OR_STRUCT_P (t->u.p)
1621 && t->u.p->kind != TYPE_PARAM_STRUCT)
1623 error_at_line (d->line,
1624 "field `%s' is pointer to unimplemented type",
1631 const char *oldprevval2 = d->prev_val[2];
1633 if (! UNION_OR_STRUCT_P (nested_ptr_d->type))
1635 error_at_line (d->line,
1636 "field `%s' has invalid "
1637 "option `nested_ptr'\n",
1642 d->prev_val[2] = d->val;
1643 oprintf (d->of, "%*s{\n", d->indent, "");
1645 d->val = xasprintf ("x%d", d->counter++);
1646 oprintf (d->of, "%*s%s %s * %s =\n", d->indent, "",
1647 (nested_ptr_d->type->kind == TYPE_UNION
1648 ? "union" : "struct"),
1649 nested_ptr_d->type->u.s.tag, d->val);
1650 oprintf (d->of, "%*s", d->indent + 2, "");
1651 output_escaped_param (d, nested_ptr_d->convert_from,
1653 oprintf (d->of, ";\n");
1655 d->process_field (nested_ptr_d->type, d);
1657 oprintf (d->of, "%*s%s = ", d->indent, "",
1659 d->prev_val[2] = d->val;
1660 output_escaped_param (d, nested_ptr_d->convert_to,
1662 oprintf (d->of, ";\n");
1665 oprintf (d->of, "%*s}\n", d->indent, "");
1666 d->val = d->prev_val[2];
1667 d->prev_val[2] = oldprevval2;
1670 d->process_field (t->u.p, d);
1674 int loopcounter = d->counter++;
1675 const char *oldval = d->val;
1676 const char *oldprevval3 = d->prev_val[3];
1679 oprintf (d->of, "%*sif (%s != NULL) {\n", d->indent, "", d->val);
1681 oprintf (d->of, "%*ssize_t i%d;\n", d->indent, "", loopcounter);
1682 oprintf (d->of, "%*sfor (i%d = 0; i%d < (size_t)(", d->indent, "",
1683 loopcounter, loopcounter);
1684 output_escaped_param (d, length, "length");
1685 oprintf (d->of, "); i%d++) {\n", loopcounter);
1687 d->val = newval = xasprintf ("%s[i%d]", oldval, loopcounter);
1689 d->prev_val[3] = oldval;
1690 walk_type (t->u.p, d);
1693 d->prev_val[3] = oldprevval3;
1696 oprintf (d->of, "%*s}\n", d->indent, "");
1697 d->process_field(t, d);
1699 oprintf (d->of, "%*s}\n", d->indent, "");
1706 int loopcounter = d->counter++;
1707 const char *oldval = d->val;
1710 /* If it's an array of scalars, we optimize by not generating
1712 if (t->u.a.p->kind == TYPE_SCALAR)
1715 oprintf (d->of, "%*s{\n", d->indent, "");
1717 oprintf (d->of, "%*ssize_t i%d;\n", d->indent, "", loopcounter);
1718 oprintf (d->of, "%*sfor (i%d = 0; i%d < (size_t)(", d->indent, "",
1719 loopcounter, loopcounter);
1721 output_escaped_param (d, length, "length");
1723 oprintf (d->of, "%s", t->u.a.len);
1724 oprintf (d->of, "); i%d++) {\n", loopcounter);
1726 d->val = newval = xasprintf ("%s[i%d]", oldval, loopcounter);
1728 walk_type (t->u.a.p, d);
1733 oprintf (d->of, "%*s}\n", d->indent, "");
1735 oprintf (d->of, "%*s}\n", d->indent, "");
1743 const char *oldval = d->val;
1744 const char *oldprevval1 = d->prev_val[1];
1745 const char *oldprevval2 = d->prev_val[2];
1746 const int union_p = t->kind == TYPE_UNION;
1747 int seen_default_p = 0;
1750 if (! t->u.s.line.file)
1751 error_at_line (d->line, "incomplete structure `%s'", t->u.s.tag);
1753 if ((d->bitmap & t->u.s.bitmap) != d->bitmap)
1755 error_at_line (d->line,
1756 "structure `%s' defined for mismatching languages",
1758 error_at_line (&t->u.s.line, "one structure defined here");
1761 /* Some things may also be defined in the structure's options. */
1762 for (o = t->u.s.opt; o; o = o->next)
1763 if (! desc && strcmp (o->name, "desc") == 0)
1764 desc = (const char *)o->info;
1766 d->prev_val[2] = oldval;
1767 d->prev_val[1] = oldprevval2;
1772 error_at_line (d->line, "missing `desc' option for union `%s'",
1776 oprintf (d->of, "%*sswitch (", d->indent, "");
1777 output_escaped_param (d, desc, "desc");
1778 oprintf (d->of, ")\n");
1780 oprintf (d->of, "%*s{\n", d->indent, "");
1782 for (f = t->u.s.fields; f; f = f->next)
1785 const char *dot = ".";
1786 const char *tagid = NULL;
1789 int use_param_p = 0;
1792 d->reorder_fn = NULL;
1793 for (oo = f->opt; oo; oo = oo->next)
1794 if (strcmp (oo->name, "dot") == 0)
1795 dot = (const char *)oo->info;
1796 else if (strcmp (oo->name, "tag") == 0)
1797 tagid = (const char *)oo->info;
1798 else if (strcmp (oo->name, "skip") == 0)
1800 else if (strcmp (oo->name, "default") == 0)
1802 else if (strcmp (oo->name, "reorder") == 0)
1803 d->reorder_fn = (const char *)oo->info;
1804 else if (strncmp (oo->name, "use_param", 9) == 0
1805 && (oo->name[9] == '\0' || ISDIGIT (oo->name[9])))
1811 if (union_p && tagid)
1813 oprintf (d->of, "%*scase %s:\n", d->indent, "", tagid);
1816 else if (union_p && default_p)
1818 oprintf (d->of, "%*sdefault:\n", d->indent, "");
1822 else if (! union_p && (default_p || tagid))
1823 error_at_line (d->line,
1824 "can't use `%s' outside a union on field `%s'",
1825 default_p ? "default" : "tag", f->name);
1826 else if (union_p && ! (default_p || tagid)
1827 && f->type->kind == TYPE_SCALAR)
1830 "%s:%d: warning: field `%s' is missing `tag' or `default' option\n",
1831 d->line->file, d->line->line, f->name);
1834 else if (union_p && ! (default_p || tagid))
1835 error_at_line (d->line,
1836 "field `%s' is missing `tag' or `default' option",
1840 d->val = newval = xasprintf ("%s%s%s", oldval, dot, f->name);
1843 if (union_p && use_param_p && d->param == NULL)
1844 oprintf (d->of, "%*sabort();\n", d->indent, "");
1846 walk_type (f->type, d);
1852 oprintf (d->of, "%*sbreak;\n", d->indent, "");
1856 d->reorder_fn = NULL;
1859 d->prev_val[1] = oldprevval1;
1860 d->prev_val[2] = oldprevval2;
1862 if (union_p && ! seen_default_p)
1864 oprintf (d->of, "%*sdefault:\n", d->indent, "");
1865 oprintf (d->of, "%*s break;\n", d->indent, "");
1869 oprintf (d->of, "%*s}\n", d->indent, "");
1875 case TYPE_LANG_STRUCT:
1878 for (nt = t->u.s.lang_struct; nt; nt = nt->next)
1879 if ((d->bitmap & nt->u.s.bitmap) == d->bitmap)
1882 error_at_line (d->line, "structure `%s' differs between languages",
1889 case TYPE_PARAM_STRUCT:
1891 type_p *oldparam = d->param;
1893 d->param = t->u.param_struct.param;
1894 walk_type (t->u.param_struct.stru, d);
1895 d->param = oldparam;
1904 /* process_field routine for marking routines. */
1907 write_types_process_field (type_p f, const struct walk_type_data *d)
1909 const struct write_types_data *wtd;
1910 const char *cast = d->needs_cast_p ? "(void *)" : "";
1911 wtd = (const struct write_types_data *) d->cookie;
1916 oprintf (d->of, "%*s%s (%s%s", d->indent, "",
1917 wtd->subfield_marker_routine, cast, d->val);
1918 if (wtd->param_prefix)
1920 oprintf (d->of, ", %s", d->prev_val[3]);
1923 oprintf (d->of, ", gt_%s_", wtd->param_prefix);
1924 output_mangled_typename (d->of, d->orig_s);
1927 oprintf (d->of, ", gt_%sa_%s", wtd->param_prefix, d->prev_val[0]);
1929 oprintf (d->of, ");\n");
1930 if (d->reorder_fn && wtd->reorder_note_routine)
1931 oprintf (d->of, "%*s%s (%s%s, %s, %s);\n", d->indent, "",
1932 wtd->reorder_note_routine, cast, d->val,
1933 d->prev_val[3], d->reorder_fn);
1937 if (wtd->param_prefix == NULL)
1942 case TYPE_LANG_STRUCT:
1943 case TYPE_PARAM_STRUCT:
1944 oprintf (d->of, "%*sgt_%s_", d->indent, "", wtd->prefix);
1945 output_mangled_typename (d->of, f);
1946 oprintf (d->of, " (%s%s);\n", cast, d->val);
1947 if (d->reorder_fn && wtd->reorder_note_routine)
1948 oprintf (d->of, "%*s%s (%s%s, %s%s, %s);\n", d->indent, "",
1949 wtd->reorder_note_routine, cast, d->val, cast, d->val,
1961 /* For S, a structure that's part of ORIG_S, and using parameters
1962 PARAM, write out a routine that:
1963 - Takes a parameter, a void * but actually of type *S
1964 - If SEEN_ROUTINE returns nonzero, calls write_types_process_field on each
1965 field of S or its substructures and (in some cases) things
1966 that are pointed to by S.
1970 write_func_for_structure (type_p orig_s, type_p s, type_p *param,
1971 const struct write_types_data *wtd)
1973 const char *fn = s->u.s.line.file;
1975 const char *chain_next = NULL;
1976 const char *chain_prev = NULL;
1978 struct walk_type_data d;
1980 /* This is a hack, and not the good kind either. */
1981 for (i = NUM_PARAM - 1; i >= 0; i--)
1982 if (param && param[i] && param[i]->kind == TYPE_POINTER
1983 && UNION_OR_STRUCT_P (param[i]->u.p))
1984 fn = param[i]->u.p->u.s.line.file;
1986 memset (&d, 0, sizeof (d));
1987 d.of = get_output_file_with_visibility (fn);
1989 for (opt = s->u.s.opt; opt; opt = opt->next)
1990 if (strcmp (opt->name, "chain_next") == 0)
1991 chain_next = (const char *) opt->info;
1992 else if (strcmp (opt->name, "chain_prev") == 0)
1993 chain_prev = (const char *) opt->info;
1995 if (chain_prev != NULL && chain_next == NULL)
1996 error_at_line (&s->u.s.line, "chain_prev without chain_next");
1998 d.process_field = write_types_process_field;
2002 d.line = &s->u.s.line;
2003 d.bitmap = s->u.s.bitmap;
2005 d.prev_val[0] = "*x";
2006 d.prev_val[1] = "not valid postage"; /* Guarantee an error. */
2007 d.prev_val[3] = "x";
2010 oprintf (d.of, "\n");
2011 oprintf (d.of, "void\n");
2013 oprintf (d.of, "gt_%sx_%s", wtd->prefix, orig_s->u.s.tag);
2016 oprintf (d.of, "gt_%s_", wtd->prefix);
2017 output_mangled_typename (d.of, orig_s);
2019 oprintf (d.of, " (void *x_p)\n");
2020 oprintf (d.of, "{\n");
2021 oprintf (d.of, " %s %s * %sx = (%s %s *)x_p;\n",
2022 s->kind == TYPE_UNION ? "union" : "struct", s->u.s.tag,
2023 chain_next == NULL ? "const " : "",
2024 s->kind == TYPE_UNION ? "union" : "struct", s->u.s.tag);
2025 if (chain_next != NULL)
2026 oprintf (d.of, " %s %s * xlimit = x;\n",
2027 s->kind == TYPE_UNION ? "union" : "struct", s->u.s.tag);
2028 if (chain_next == NULL)
2030 oprintf (d.of, " if (%s (x", wtd->marker_routine);
2031 if (wtd->param_prefix)
2033 oprintf (d.of, ", x, gt_%s_", wtd->param_prefix);
2034 output_mangled_typename (d.of, orig_s);
2036 oprintf (d.of, "))\n");
2040 oprintf (d.of, " while (%s (xlimit", wtd->marker_routine);
2041 if (wtd->param_prefix)
2043 oprintf (d.of, ", xlimit, gt_%s_", wtd->param_prefix);
2044 output_mangled_typename (d.of, orig_s);
2046 oprintf (d.of, "))\n");
2047 oprintf (d.of, " xlimit = (");
2048 d.prev_val[2] = "*xlimit";
2049 output_escaped_param (&d, chain_next, "chain_next");
2050 oprintf (d.of, ");\n");
2051 if (chain_prev != NULL)
2053 oprintf (d.of, " if (x != xlimit)\n");
2054 oprintf (d.of, " for (;;)\n");
2055 oprintf (d.of, " {\n");
2056 oprintf (d.of, " %s %s * const xprev = (",
2057 s->kind == TYPE_UNION ? "union" : "struct", s->u.s.tag);
2059 d.prev_val[2] = "*x";
2060 output_escaped_param (&d, chain_prev, "chain_prev");
2061 oprintf (d.of, ");\n");
2062 oprintf (d.of, " if (xprev == NULL) break;\n");
2063 oprintf (d.of, " x = xprev;\n");
2064 oprintf (d.of, " (void) %s (xprev",
2065 wtd->marker_routine);
2066 if (wtd->param_prefix)
2068 oprintf (d.of, ", xprev, gt_%s_", wtd->param_prefix);
2069 output_mangled_typename (d.of, orig_s);
2071 oprintf (d.of, ");\n");
2072 oprintf (d.of, " }\n");
2074 oprintf (d.of, " while (x != xlimit)\n");
2076 oprintf (d.of, " {\n");
2078 d.prev_val[2] = "*x";
2082 if (chain_next != NULL)
2084 oprintf (d.of, " x = (");
2085 output_escaped_param (&d, chain_next, "chain_next");
2086 oprintf (d.of, ");\n");
2089 oprintf (d.of, " }\n");
2090 oprintf (d.of, "}\n");
2093 /* Write out marker routines for STRUCTURES and PARAM_STRUCTS. */
2096 write_types (type_p structures, type_p param_structs,
2097 const struct write_types_data *wtd)
2101 oprintf (header_file, "\n/* %s*/\n", wtd->comment);
2102 for (s = structures; s; s = s->next)
2103 if (s->gc_used == GC_POINTED_TO
2104 || s->gc_used == GC_MAYBE_POINTED_TO)
2108 if (s->gc_used == GC_MAYBE_POINTED_TO
2109 && s->u.s.line.file == NULL)
2112 oprintf (header_file, "#define gt_%s_", wtd->prefix);
2113 output_mangled_typename (header_file, s);
2114 oprintf (header_file, "(X) do { \\\n");
2115 oprintf (header_file,
2116 " if (X != NULL) gt_%sx_%s (X);\\\n", wtd->prefix,
2118 oprintf (header_file,
2121 for (opt = s->u.s.opt; opt; opt = opt->next)
2122 if (strcmp (opt->name, "ptr_alias") == 0)
2124 type_p t = (type_p) opt->info;
2125 if (t->kind == TYPE_STRUCT
2126 || t->kind == TYPE_UNION
2127 || t->kind == TYPE_LANG_STRUCT)
2128 oprintf (header_file,
2129 "#define gt_%sx_%s gt_%sx_%s\n",
2130 wtd->prefix, s->u.s.tag, wtd->prefix, t->u.s.tag);
2132 error_at_line (&s->u.s.line,
2133 "structure alias is not a structure");
2139 /* Declare the marker procedure only once. */
2140 oprintf (header_file,
2141 "extern void gt_%sx_%s (void *);\n",
2142 wtd->prefix, s->u.s.tag);
2144 if (s->u.s.line.file == NULL)
2146 fprintf (stderr, "warning: structure `%s' used but not defined\n",
2151 if (s->kind == TYPE_LANG_STRUCT)
2154 for (ss = s->u.s.lang_struct; ss; ss = ss->next)
2155 write_func_for_structure (s, ss, NULL, wtd);
2158 write_func_for_structure (s, s, NULL, wtd);
2161 for (s = param_structs; s; s = s->next)
2162 if (s->gc_used == GC_POINTED_TO)
2164 type_p * param = s->u.param_struct.param;
2165 type_p stru = s->u.param_struct.stru;
2167 /* Declare the marker procedure. */
2168 oprintf (header_file, "extern void gt_%s_", wtd->prefix);
2169 output_mangled_typename (header_file, s);
2170 oprintf (header_file, " (void *);\n");
2172 if (stru->u.s.line.file == NULL)
2174 fprintf (stderr, "warning: structure `%s' used but not defined\n",
2179 if (stru->kind == TYPE_LANG_STRUCT)
2182 for (ss = stru->u.s.lang_struct; ss; ss = ss->next)
2183 write_func_for_structure (s, ss, param, wtd);
2186 write_func_for_structure (s, stru, param, wtd);
2190 static const struct write_types_data ggc_wtd =
2192 "ggc_m", NULL, "ggc_mark", "ggc_test_and_set_mark", NULL,
2193 "GC marker procedures. "
2196 static const struct write_types_data pch_wtd =
2198 "pch_n", "pch_p", "gt_pch_note_object", "gt_pch_note_object",
2199 "gt_pch_note_reorder",
2200 "PCH type-walking procedures. "
2203 /* Write out the local pointer-walking routines. */
2205 /* process_field routine for local pointer-walking. */
2208 write_types_local_process_field (type_p f, const struct walk_type_data *d)
2215 case TYPE_LANG_STRUCT:
2216 case TYPE_PARAM_STRUCT:
2218 oprintf (d->of, "%*sif ((void *)(%s) == this_obj)\n", d->indent, "",
2220 oprintf (d->of, "%*s op (&(%s), cookie);\n", d->indent, "", d->val);
2231 /* For S, a structure that's part of ORIG_S, and using parameters
2232 PARAM, write out a routine that:
2233 - Is of type gt_note_pointers
2234 - If calls PROCESS_FIELD on each field of S or its substructures.
2238 write_local_func_for_structure (type_p orig_s, type_p s, type_p *param)
2240 const char *fn = s->u.s.line.file;
2242 struct walk_type_data d;
2244 /* This is a hack, and not the good kind either. */
2245 for (i = NUM_PARAM - 1; i >= 0; i--)
2246 if (param && param[i] && param[i]->kind == TYPE_POINTER
2247 && UNION_OR_STRUCT_P (param[i]->u.p))
2248 fn = param[i]->u.p->u.s.line.file;
2250 memset (&d, 0, sizeof (d));
2251 d.of = get_output_file_with_visibility (fn);
2253 d.process_field = write_types_local_process_field;
2255 d.line = &s->u.s.line;
2256 d.bitmap = s->u.s.bitmap;
2258 d.prev_val[0] = d.prev_val[2] = "*x";
2259 d.prev_val[1] = "not valid postage"; /* Guarantee an error. */
2260 d.prev_val[3] = "x";
2263 oprintf (d.of, "\n");
2264 oprintf (d.of, "void\n");
2265 oprintf (d.of, "gt_pch_p_");
2266 output_mangled_typename (d.of, orig_s);
2267 oprintf (d.of, " (void *this_obj ATTRIBUTE_UNUSED,\n\tvoid *x_p,\n\tgt_pointer_operator op ATTRIBUTE_UNUSED,\n\tvoid *cookie ATTRIBUTE_UNUSED)\n");
2268 oprintf (d.of, "{\n");
2269 oprintf (d.of, " %s %s * const x ATTRIBUTE_UNUSED = (%s %s *)x_p;\n",
2270 s->kind == TYPE_UNION ? "union" : "struct", s->u.s.tag,
2271 s->kind == TYPE_UNION ? "union" : "struct", s->u.s.tag);
2274 oprintf (d.of, "}\n");
2277 /* Write out local marker routines for STRUCTURES and PARAM_STRUCTS. */
2280 write_local (type_p structures, type_p param_structs)
2284 oprintf (header_file, "\n/* Local pointer-walking routines. */\n");
2285 for (s = structures; s; s = s->next)
2286 if (s->gc_used == GC_POINTED_TO
2287 || s->gc_used == GC_MAYBE_POINTED_TO)
2291 if (s->u.s.line.file == NULL)
2294 for (opt = s->u.s.opt; opt; opt = opt->next)
2295 if (strcmp (opt->name, "ptr_alias") == 0)
2297 type_p t = (type_p) opt->info;
2298 if (t->kind == TYPE_STRUCT
2299 || t->kind == TYPE_UNION
2300 || t->kind == TYPE_LANG_STRUCT)
2302 oprintf (header_file, "#define gt_pch_p_");
2303 output_mangled_typename (header_file, s);
2304 oprintf (header_file, " gt_pch_p_");
2305 output_mangled_typename (header_file, t);
2306 oprintf (header_file, "\n");
2309 error_at_line (&s->u.s.line,
2310 "structure alias is not a structure");
2316 /* Declare the marker procedure only once. */
2317 oprintf (header_file, "extern void gt_pch_p_");
2318 output_mangled_typename (header_file, s);
2319 oprintf (header_file,
2320 "\n (void *, void *, gt_pointer_operator, void *);\n");
2322 if (s->kind == TYPE_LANG_STRUCT)
2325 for (ss = s->u.s.lang_struct; ss; ss = ss->next)
2326 write_local_func_for_structure (s, ss, NULL);
2329 write_local_func_for_structure (s, s, NULL);
2332 for (s = param_structs; s; s = s->next)
2333 if (s->gc_used == GC_POINTED_TO)
2335 type_p * param = s->u.param_struct.param;
2336 type_p stru = s->u.param_struct.stru;
2338 /* Declare the marker procedure. */
2339 oprintf (header_file, "extern void gt_pch_p_");
2340 output_mangled_typename (header_file, s);
2341 oprintf (header_file,
2342 "\n (void *, void *, gt_pointer_operator, void *);\n");
2344 if (stru->u.s.line.file == NULL)
2346 fprintf (stderr, "warning: structure `%s' used but not defined\n",
2351 if (stru->kind == TYPE_LANG_STRUCT)
2354 for (ss = stru->u.s.lang_struct; ss; ss = ss->next)
2355 write_local_func_for_structure (s, ss, param);
2358 write_local_func_for_structure (s, stru, param);
2362 /* Write out the 'enum' definition for gt_types_enum. */
2365 write_enum_defn (type_p structures, type_p param_structs)
2369 oprintf (header_file, "\n/* Enumeration of types known. */\n");
2370 oprintf (header_file, "enum gt_types_enum {\n");
2371 for (s = structures; s; s = s->next)
2372 if (s->gc_used == GC_POINTED_TO
2373 || s->gc_used == GC_MAYBE_POINTED_TO)
2375 if (s->gc_used == GC_MAYBE_POINTED_TO
2376 && s->u.s.line.file == NULL)
2379 oprintf (header_file, " gt_ggc_e_");
2380 output_mangled_typename (header_file, s);
2381 oprintf (header_file, ", \n");
2383 for (s = param_structs; s; s = s->next)
2384 if (s->gc_used == GC_POINTED_TO)
2386 oprintf (header_file, " gt_e_");
2387 output_mangled_typename (header_file, s);
2388 oprintf (header_file, ", \n");
2390 oprintf (header_file, " gt_types_enum_last\n");
2391 oprintf (header_file, "};\n");
2394 /* Might T contain any non-pointer elements? */
2397 contains_scalar_p (type_p t)
2405 return contains_scalar_p (t->u.a.p);
2407 /* Could also check for structures that have no non-pointer
2408 fields, but there aren't enough of those to worry about. */
2413 /* Mangle FN and print it to F. */
2416 put_mangled_filename (outf_p f, const char *fn)
2418 const char *name = get_output_file_name (fn);
2419 for (; *name != 0; name++)
2420 if (ISALNUM (*name))
2421 oprintf (f, "%c", *name);
2423 oprintf (f, "%c", '_');
2426 /* Finish off the currently-created root tables in FLP. PFX, TNAME,
2427 LASTNAME, and NAME are all strings to insert in various places in
2428 the resulting code. */
2431 finish_root_table (struct flist *flp, const char *pfx, const char *lastname,
2432 const char *tname, const char *name)
2436 for (fli2 = flp; fli2; fli2 = fli2->next)
2437 if (fli2->started_p)
2439 oprintf (fli2->f, " %s\n", lastname);
2440 oprintf (fli2->f, "};\n\n");
2443 for (fli2 = flp; fli2; fli2 = fli2->next)
2444 if (fli2->started_p)
2446 lang_bitmap bitmap = get_base_file_bitmap (fli2->name);
2449 for (fnum = 0; bitmap != 0; fnum++, bitmap >>= 1)
2452 oprintf (base_files[fnum],
2453 "extern const struct %s gt_%s_",
2455 put_mangled_filename (base_files[fnum], fli2->name);
2456 oprintf (base_files[fnum], "[];\n");
2462 for (fnum = 0; fnum < NUM_BASE_FILES; fnum++)
2463 oprintf (base_files [fnum],
2464 "const struct %s * const %s[] = {\n",
2469 for (fli2 = flp; fli2; fli2 = fli2->next)
2470 if (fli2->started_p)
2472 lang_bitmap bitmap = get_base_file_bitmap (fli2->name);
2475 fli2->started_p = 0;
2477 for (fnum = 0; bitmap != 0; fnum++, bitmap >>= 1)
2480 oprintf (base_files[fnum], " gt_%s_", pfx);
2481 put_mangled_filename (base_files[fnum], fli2->name);
2482 oprintf (base_files[fnum], ",\n");
2488 for (fnum = 0; fnum < NUM_BASE_FILES; fnum++)
2490 oprintf (base_files[fnum], " NULL\n");
2491 oprintf (base_files[fnum], "};\n");
2496 /* Write out to F the table entry and any marker routines needed to
2497 mark NAME as TYPE. The original variable is V, at LINE.
2498 HAS_LENGTH is nonzero iff V was a variable-length array. IF_MARKED
2499 is nonzero iff we are building the root table for hash table caches. */
2502 write_root (outf_p f, pair_p v, type_p type, const char *name, int has_length,
2503 struct fileloc *line, const char *if_marked)
2510 for (fld = type->u.s.fields; fld; fld = fld->next)
2513 const char *desc = NULL;
2516 for (o = fld->opt; o; o = o->next)
2517 if (strcmp (o->name, "skip") == 0)
2519 else if (strcmp (o->name, "desc") == 0)
2520 desc = (const char *)o->info;
2522 error_at_line (line,
2523 "field `%s' of global `%s' has unknown option `%s'",
2524 fld->name, name, o->name);
2528 else if (desc && fld->type->kind == TYPE_UNION)
2530 pair_p validf = NULL;
2533 for (ufld = fld->type->u.s.fields; ufld; ufld = ufld->next)
2535 const char *tag = NULL;
2538 for (oo = ufld->opt; oo; oo = oo->next)
2539 if (strcmp (oo->name, "tag") == 0)
2540 tag = (const char *)oo->info;
2541 if (tag == NULL || strcmp (tag, desc) != 0)
2544 error_at_line (line,
2545 "both `%s.%s.%s' and `%s.%s.%s' have tag `%s'",
2546 name, fld->name, validf->name,
2547 name, fld->name, ufld->name,
2554 newname = xasprintf ("%s.%s.%s",
2555 name, fld->name, validf->name);
2556 write_root (f, v, validf->type, newname, 0, line,
2562 error_at_line (line,
2563 "global `%s.%s' has `desc' option but is not union",
2568 newname = xasprintf ("%s.%s", name, fld->name);
2569 write_root (f, v, fld->type, newname, 0, line, if_marked);
2579 newname = xasprintf ("%s[0]", name);
2580 write_root (f, v, type->u.a.p, newname, has_length, line, if_marked);
2589 oprintf (f, " {\n");
2590 oprintf (f, " &%s,\n", name);
2593 for (ap = v->type; ap->kind == TYPE_ARRAY; ap = ap->u.a.p)
2595 oprintf (f, " * (%s)", ap->u.a.len);
2596 else if (ap == v->type)
2597 oprintf (f, " * ARRAY_SIZE (%s)", v->name);
2599 oprintf (f, " sizeof (%s", v->name);
2600 for (ap = v->type; ap->kind == TYPE_ARRAY; ap = ap->u.a.p)
2602 oprintf (f, "),\n");
2606 if (! has_length && UNION_OR_STRUCT_P (tp))
2608 oprintf (f, " >_ggc_mx_%s,\n", tp->u.s.tag);
2609 oprintf (f, " >_pch_nx_%s", tp->u.s.tag);
2611 else if (! has_length && tp->kind == TYPE_PARAM_STRUCT)
2613 oprintf (f, " >_ggc_m_");
2614 output_mangled_typename (f, tp);
2615 oprintf (f, ",\n >_pch_n_");
2616 output_mangled_typename (f, tp);
2619 && (tp->kind == TYPE_POINTER || UNION_OR_STRUCT_P (tp)))
2621 oprintf (f, " >_ggc_ma_%s,\n", name);
2622 oprintf (f, " >_pch_na_%s", name);
2626 error_at_line (line,
2627 "global `%s' is pointer to unimplemented type",
2631 oprintf (f, ",\n &%s", if_marked);
2632 oprintf (f, "\n },\n");
2638 oprintf (f, " {\n");
2639 oprintf (f, " &%s,\n", name);
2640 oprintf (f, " 1, \n");
2641 oprintf (f, " sizeof (%s),\n", v->name);
2642 oprintf (f, " >_ggc_m_S,\n");
2643 oprintf (f, " (gt_pointer_walker) >_pch_n_S\n");
2644 oprintf (f, " },\n");
2652 error_at_line (line,
2653 "global `%s' is unimplemented type",
2658 /* This generates a routine to walk an array. */
2661 write_array (outf_p f, pair_p v, const struct write_types_data *wtd)
2663 struct walk_type_data d;
2666 memset (&d, 0, sizeof (d));
2672 d.bitmap = get_base_file_bitmap (v->line.file);
2675 d.prev_val[3] = prevval3 = xasprintf ("&%s", v->name);
2677 if (wtd->param_prefix)
2679 oprintf (f, "static void gt_%sa_%s\n", wtd->param_prefix, v->name);
2681 " (void *, void *, gt_pointer_operator, void *);\n");
2682 oprintf (f, "static void gt_%sa_%s (void *this_obj ATTRIBUTE_UNUSED,\n",
2683 wtd->param_prefix, v->name);
2684 oprintf (d.of, " void *x_p ATTRIBUTE_UNUSED,\n");
2685 oprintf (d.of, " gt_pointer_operator op ATTRIBUTE_UNUSED,\n");
2686 oprintf (d.of, " void *cookie ATTRIBUTE_UNUSED)\n");
2687 oprintf (d.of, "{\n");
2688 d.prev_val[0] = d.prev_val[1] = d.prev_val[2] = d.val = v->name;
2689 d.process_field = write_types_local_process_field;
2690 walk_type (v->type, &d);
2691 oprintf (f, "}\n\n");
2695 oprintf (f, "static void gt_%sa_%s (void *);\n",
2696 wtd->prefix, v->name);
2697 oprintf (f, "static void\ngt_%sa_%s (void *x_p ATTRIBUTE_UNUSED)\n",
2698 wtd->prefix, v->name);
2700 d.prev_val[0] = d.prev_val[1] = d.prev_val[2] = d.val = v->name;
2701 d.process_field = write_types_process_field;
2702 walk_type (v->type, &d);
2704 oprintf (f, "}\n\n");
2707 /* Output a table describing the locations and types of VARIABLES. */
2710 write_roots (pair_p variables)
2713 struct flist *flp = NULL;
2715 for (v = variables; v; v = v->next)
2717 outf_p f = get_output_file_with_visibility (v->line.file);
2719 const char *length = NULL;
2720 int deletable_p = 0;
2723 for (o = v->opt; o; o = o->next)
2724 if (strcmp (o->name, "length") == 0)
2725 length = (const char *)o->info;
2726 else if (strcmp (o->name, "deletable") == 0)
2728 else if (strcmp (o->name, "param_is") == 0)
2730 else if (strncmp (o->name, "param", 5) == 0
2731 && ISDIGIT (o->name[5])
2732 && strcmp (o->name + 6, "_is") == 0)
2734 else if (strcmp (o->name, "if_marked") == 0)
2737 error_at_line (&v->line,
2738 "global `%s' has unknown option `%s'",
2741 for (fli = flp; fli; fli = fli->next)
2746 fli = xmalloc (sizeof (*fli));
2750 fli->name = v->line.file;
2753 oprintf (f, "\n/* GC roots. */\n\n");
2758 && v->type->kind == TYPE_POINTER
2759 && (v->type->u.p->kind == TYPE_POINTER
2760 || v->type->u.p->kind == TYPE_STRUCT))
2762 write_array (f, v, &ggc_wtd);
2763 write_array (f, v, &pch_wtd);
2767 for (v = variables; v; v = v->next)
2769 outf_p f = get_output_file_with_visibility (v->line.file);
2775 for (o = v->opt; o; o = o->next)
2776 if (strcmp (o->name, "length") == 0)
2778 else if (strcmp (o->name, "deletable") == 0
2779 || strcmp (o->name, "if_marked") == 0)
2785 for (fli = flp; fli; fli = fli->next)
2788 if (! fli->started_p)
2792 oprintf (f, "const struct ggc_root_tab gt_ggc_r_");
2793 put_mangled_filename (f, v->line.file);
2794 oprintf (f, "[] = {\n");
2797 write_root (f, v, v->type, v->name, length_p, &v->line, NULL);
2800 finish_root_table (flp, "ggc_r", "LAST_GGC_ROOT_TAB", "ggc_root_tab",
2803 for (v = variables; v; v = v->next)
2805 outf_p f = get_output_file_with_visibility (v->line.file);
2810 for (o = v->opt; o; o = o->next)
2811 if (strcmp (o->name, "deletable") == 0)
2813 else if (strcmp (o->name, "if_marked") == 0)
2819 for (fli = flp; fli; fli = fli->next)
2822 if (! fli->started_p)
2826 oprintf (f, "const struct ggc_root_tab gt_ggc_rd_");
2827 put_mangled_filename (f, v->line.file);
2828 oprintf (f, "[] = {\n");
2831 oprintf (f, " { &%s, 1, sizeof (%s), NULL, NULL },\n",
2835 finish_root_table (flp, "ggc_rd", "LAST_GGC_ROOT_TAB", "ggc_root_tab",
2836 "gt_ggc_deletable_rtab");
2838 for (v = variables; v; v = v->next)
2840 outf_p f = get_output_file_with_visibility (v->line.file);
2842 const char *if_marked = NULL;
2846 for (o = v->opt; o; o = o->next)
2847 if (strcmp (o->name, "length") == 0)
2849 else if (strcmp (o->name, "if_marked") == 0)
2850 if_marked = (const char *) o->info;
2852 if (if_marked == NULL)
2855 if (v->type->kind != TYPE_POINTER
2856 || v->type->u.p->kind != TYPE_PARAM_STRUCT
2857 || v->type->u.p->u.param_struct.stru != find_structure ("htab", 0))
2859 error_at_line (&v->line, "if_marked option used but not hash table");
2863 for (fli = flp; fli; fli = fli->next)
2866 if (! fli->started_p)
2870 oprintf (f, "const struct ggc_cache_tab gt_ggc_rc_");
2871 put_mangled_filename (f, v->line.file);
2872 oprintf (f, "[] = {\n");
2875 write_root (f, v, v->type->u.p->u.param_struct.param[0],
2876 v->name, length_p, &v->line, if_marked);
2879 finish_root_table (flp, "ggc_rc", "LAST_GGC_CACHE_TAB", "ggc_cache_tab",
2880 "gt_ggc_cache_rtab");
2882 for (v = variables; v; v = v->next)
2884 outf_p f = get_output_file_with_visibility (v->line.file);
2887 int if_marked_p = 0;
2890 for (o = v->opt; o; o = o->next)
2891 if (strcmp (o->name, "length") == 0)
2893 else if (strcmp (o->name, "if_marked") == 0)
2899 for (fli = flp; fli; fli = fli->next)
2902 if (! fli->started_p)
2906 oprintf (f, "const struct ggc_root_tab gt_pch_rc_");
2907 put_mangled_filename (f, v->line.file);
2908 oprintf (f, "[] = {\n");
2911 write_root (f, v, v->type, v->name, length_p, &v->line, NULL);
2914 finish_root_table (flp, "pch_rc", "LAST_GGC_ROOT_TAB", "ggc_root_tab",
2915 "gt_pch_cache_rtab");
2917 for (v = variables; v; v = v->next)
2919 outf_p f = get_output_file_with_visibility (v->line.file);
2924 for (o = v->opt; o; o = o->next)
2925 if (strcmp (o->name, "deletable") == 0
2926 || strcmp (o->name, "if_marked") == 0)
2932 if (! contains_scalar_p (v->type))
2935 for (fli = flp; fli; fli = fli->next)
2938 if (! fli->started_p)
2942 oprintf (f, "const struct ggc_root_tab gt_pch_rs_");
2943 put_mangled_filename (f, v->line.file);
2944 oprintf (f, "[] = {\n");
2947 oprintf (f, " { &%s, 1, sizeof (%s), NULL, NULL },\n",
2951 finish_root_table (flp, "pch_rs", "LAST_GGC_ROOT_TAB", "ggc_root_tab",
2952 "gt_pch_scalar_rtab");
2956 extern int main (int argc, char **argv);
2958 main(int argc ATTRIBUTE_UNUSED, char **argv ATTRIBUTE_UNUSED)
2961 static struct fileloc pos = { __FILE__, __LINE__ };
2966 srcdir_len = strlen (srcdir);
2968 do_scalar_typedef ("CUMULATIVE_ARGS", &pos);
2969 do_scalar_typedef ("REAL_VALUE_TYPE", &pos);
2970 do_scalar_typedef ("uint8", &pos);
2971 do_scalar_typedef ("jword", &pos);
2972 do_scalar_typedef ("JCF_u2", &pos);
2973 do_scalar_typedef ("void", &pos);
2975 do_typedef ("PTR", create_pointer (resolve_typedef ("void", &pos)), &pos);
2977 do_typedef ("HARD_REG_SET", create_array (
2978 create_scalar_type ("unsigned long", strlen ("unsigned long")),
2981 for (i = 0; i < NUM_GT_FILES; i++)
2984 /* Omit if already seen. */
2985 for (j = 0; j < i; j++)
2987 if (!strcmp (all_files[i], all_files[j]))
2994 parse_file (all_files[i]);
3000 set_gc_used (variables);
3003 write_enum_defn (structures, param_structs);
3004 write_types (structures, param_structs, &ggc_wtd);
3005 write_types (structures, param_structs, &pch_wtd);
3006 write_local (structures, param_structs);
3007 write_roots (variables);
3009 close_output_files ();
3011 return (hit_error != 0);