1 /* Print GENERIC declaration (functions, variables, types) trees coming from
2 the C and C++ front-ends as well as macros in Ada syntax.
3 Copyright (C) 2010-2015 Free Software Foundation, Inc.
4 Adapted from tree-pretty-print.c by Arnaud Charlet <charlet@adacore.com>
6 This file is part of GCC.
8 GCC is free software; you can redistribute it and/or modify it under
9 the terms of the GNU General Public License as published by the Free
10 Software Foundation; either version 3, or (at your option) any later
13 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
14 WARRANTY; without even the implied warranty of MERCHANTABILITY or
15 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
18 You should have received a copy of the GNU General Public License
19 along with GCC; see the file COPYING3. If not see
20 <http://www.gnu.org/licenses/>. */
24 #include "coretypes.h"
29 #include "double-int.h"
37 #include "fold-const.h"
39 #include "c-ada-spec.h"
42 #include "cpp-id-data.h"
45 /* Local functions, macros and variables. */
46 static int dump_generic_ada_node (pretty_printer *, tree, tree, int, int,
48 static int print_ada_declaration (pretty_printer *, tree, tree, int);
49 static void print_ada_struct_decl (pretty_printer *, tree, tree, int, bool);
50 static void dump_sloc (pretty_printer *buffer, tree node);
51 static void print_comment (pretty_printer *, const char *);
52 static void print_generic_ada_decl (pretty_printer *, tree, const char *);
53 static char *get_ada_package (const char *);
54 static void dump_ada_nodes (pretty_printer *, const char *);
55 static void reset_ada_withs (void);
56 static void dump_ada_withs (FILE *);
57 static void dump_ads (const char *, void (*)(const char *),
58 int (*)(tree, cpp_operation));
59 static char *to_ada_name (const char *, int *);
60 static bool separate_class_package (tree);
62 #define INDENT(SPACE) \
63 do { int i; for (i = 0; i<SPACE; i++) pp_space (buffer); } while (0)
67 /* Global hook used to perform C++ queries on nodes. */
68 static int (*cpp_check) (tree, cpp_operation) = NULL;
71 /* Given a cpp MACRO, compute the max length BUFFER_LEN of the macro, as well
72 as max length PARAM_LEN of arguments for fun_like macros, and also set
73 SUPPORTED to 0 if the macro cannot be mapped to an Ada construct. */
76 macro_length (const cpp_macro *macro, int *supported, int *buffer_len,
89 for (i = 0; i < macro->paramc; i++)
91 cpp_hashnode *param = macro->params[i];
93 *param_len += NODE_LEN (param);
95 if (i + 1 < macro->paramc)
97 *param_len += 2; /* ", " */
99 else if (macro->variadic)
105 *param_len += 2; /* ")\0" */
108 for (j = 0; j < macro->count; j++)
110 cpp_token *token = ¯o->exp.tokens[j];
112 if (token->flags & PREV_WHITE)
115 if (token->flags & STRINGIFY_ARG || token->flags & PASTE_LEFT)
121 if (token->type == CPP_MACRO_ARG)
123 NODE_LEN (macro->params[token->val.macro_arg.arg_no - 1]);
125 /* Include enough extra space to handle e.g. special characters. */
126 *buffer_len += (cpp_token_len (token) + 1) * 8;
132 /* Dump into PP a set of MAX_ADA_MACROS MACROS (C/C++) as Ada constants when
136 print_ada_macros (pretty_printer *pp, cpp_hashnode **macros, int max_ada_macros)
138 int j, num_macros = 0, prev_line = -1;
140 for (j = 0; j < max_ada_macros; j++)
142 cpp_hashnode *node = macros[j];
143 const cpp_macro *macro = node->value.macro;
145 int supported = 1, prev_is_one = 0, buffer_len, param_len;
146 int is_string = 0, is_char = 0;
148 unsigned char *s, *params, *buffer, *buf_param, *char_one = NULL;
150 macro_length (macro, &supported, &buffer_len, ¶m_len);
151 s = buffer = XALLOCAVEC (unsigned char, buffer_len);
152 params = buf_param = XALLOCAVEC (unsigned char, param_len);
159 for (i = 0; i < macro->paramc; i++)
161 cpp_hashnode *param = macro->params[i];
163 memcpy (buf_param, NODE_NAME (param), NODE_LEN (param));
164 buf_param += NODE_LEN (param);
166 if (i + 1 < macro->paramc)
171 else if (macro->variadic)
181 for (i = 0; supported && i < macro->count; i++)
183 cpp_token *token = ¯o->exp.tokens[i];
186 if (token->flags & PREV_WHITE)
189 if (token->flags & STRINGIFY_ARG || token->flags & PASTE_LEFT)
199 cpp_hashnode *param =
200 macro->params[token->val.macro_arg.arg_no - 1];
201 memcpy (buffer, NODE_NAME (param), NODE_LEN (param));
202 buffer += NODE_LEN (param);
206 case CPP_EQ_EQ: *buffer++ = '='; break;
207 case CPP_GREATER: *buffer++ = '>'; break;
208 case CPP_LESS: *buffer++ = '<'; break;
209 case CPP_PLUS: *buffer++ = '+'; break;
210 case CPP_MINUS: *buffer++ = '-'; break;
211 case CPP_MULT: *buffer++ = '*'; break;
212 case CPP_DIV: *buffer++ = '/'; break;
213 case CPP_COMMA: *buffer++ = ','; break;
214 case CPP_OPEN_SQUARE:
215 case CPP_OPEN_PAREN: *buffer++ = '('; break;
216 case CPP_CLOSE_SQUARE: /* fallthrough */
217 case CPP_CLOSE_PAREN: *buffer++ = ')'; break;
218 case CPP_DEREF: /* fallthrough */
219 case CPP_SCOPE: /* fallthrough */
220 case CPP_DOT: *buffer++ = '.'; break;
222 case CPP_EQ: *buffer++ = ':'; *buffer++ = '='; break;
223 case CPP_NOT_EQ: *buffer++ = '/'; *buffer++ = '='; break;
224 case CPP_GREATER_EQ: *buffer++ = '>'; *buffer++ = '='; break;
225 case CPP_LESS_EQ: *buffer++ = '<'; *buffer++ = '='; break;
228 *buffer++ = 'n'; *buffer++ = 'o'; *buffer++ = 't'; break;
230 *buffer++ = 'm'; *buffer++ = 'o'; *buffer++ = 'd'; break;
232 *buffer++ = 'a'; *buffer++ = 'n'; *buffer++ = 'd'; break;
234 *buffer++ = 'o'; *buffer++ = 'r'; break;
236 *buffer++ = 'x'; *buffer++ = 'o'; *buffer++ = 'r'; break;
238 strcpy ((char *) buffer, " and then ");
242 strcpy ((char *) buffer, " or else ");
248 is_one = prev_is_one;
251 case CPP_COMMENT: break;
263 if (!macro->fun_like)
266 buffer = cpp_spell_token (parse_in, token, buffer, false);
276 c = cpp_interpret_charconst (parse_in, token,
277 &chars_seen, &ignored);
278 if (c >= 32 && c <= 126)
281 *buffer++ = (char) c;
287 ((char *) buffer, "Character'Val (%d)", (int) c);
288 buffer += chars_seen;
296 /* Replace "1 << N" by "2 ** N" */
323 case CPP_CLOSE_BRACE:
327 case CPP_MINUS_MINUS:
331 case CPP_HEADER_NAME:
334 case CPP_OBJC_STRING:
336 if (!macro->fun_like)
339 buffer = cpp_spell_token (parse_in, token, buffer, false);
343 prev_is_one = is_one;
350 if (macro->fun_like && supported)
352 char *start = (char *) s;
355 pp_string (pp, " -- arg-macro: ");
357 if (*start == '(' && buffer[-1] == ')')
362 pp_string (pp, "function ");
366 pp_string (pp, "procedure ");
369 pp_string (pp, (const char *) NODE_NAME (node));
371 pp_string (pp, (char *) params);
373 pp_string (pp, " -- ");
377 pp_string (pp, "return ");
378 pp_string (pp, start);
382 pp_string (pp, start);
388 expanded_location sloc = expand_location (macro->line);
390 if (sloc.line != prev_line + 1)
394 prev_line = sloc.line;
397 ada_name = to_ada_name ((const char *) NODE_NAME (node), NULL);
398 pp_string (pp, ada_name);
400 pp_string (pp, " : ");
403 pp_string (pp, "aliased constant String");
405 pp_string (pp, "aliased constant Character");
407 pp_string (pp, "constant");
409 pp_string (pp, " := ");
410 pp_string (pp, (char *) s);
413 pp_string (pp, " & ASCII.NUL");
415 pp_string (pp, "; -- ");
416 pp_string (pp, sloc.file);
418 pp_scalar (pp, "%d", sloc.line);
423 pp_string (pp, " -- unsupported macro: ");
424 pp_string (pp, (const char *) cpp_macro_definition (parse_in, node));
433 static const char *source_file;
434 static int max_ada_macros;
436 /* Callback used to count the number of relevant macros from
437 cpp_forall_identifiers. PFILE and V are not used. NODE is the current macro
441 count_ada_macro (cpp_reader *pfile ATTRIBUTE_UNUSED, cpp_hashnode *node,
442 void *v ATTRIBUTE_UNUSED)
444 const cpp_macro *macro = node->value.macro;
446 if (node->type == NT_MACRO && !(node->flags & NODE_BUILTIN)
448 && *NODE_NAME (node) != '_'
449 && LOCATION_FILE (macro->line) == source_file)
455 static int store_ada_macro_index;
457 /* Callback used to store relevant macros from cpp_forall_identifiers.
458 PFILE is not used. NODE is the current macro to store if relevant.
459 MACROS is an array of cpp_hashnode* used to store NODE. */
462 store_ada_macro (cpp_reader *pfile ATTRIBUTE_UNUSED,
463 cpp_hashnode *node, void *macros)
465 const cpp_macro *macro = node->value.macro;
467 if (node->type == NT_MACRO && !(node->flags & NODE_BUILTIN)
469 && *NODE_NAME (node) != '_'
470 && LOCATION_FILE (macro->line) == source_file)
471 ((cpp_hashnode **) macros)[store_ada_macro_index++] = node;
476 /* Callback used to compare (during qsort) macros. NODE1 and NODE2 are the
477 two macro nodes to compare. */
480 compare_macro (const void *node1, const void *node2)
482 typedef const cpp_hashnode *const_hnode;
484 const_hnode n1 = *(const const_hnode *) node1;
485 const_hnode n2 = *(const const_hnode *) node2;
487 return n1->value.macro->line - n2->value.macro->line;
490 /* Dump in PP all relevant macros appearing in FILE. */
493 dump_ada_macros (pretty_printer *pp, const char* file)
495 cpp_hashnode **macros;
497 /* Initialize file-scope variables. */
499 store_ada_macro_index = 0;
502 /* Count all potentially relevant macros, and then sort them by sloc. */
503 cpp_forall_identifiers (parse_in, count_ada_macro, NULL);
504 macros = XALLOCAVEC (cpp_hashnode *, max_ada_macros);
505 cpp_forall_identifiers (parse_in, store_ada_macro, macros);
506 qsort (macros, max_ada_macros, sizeof (cpp_hashnode *), compare_macro);
508 print_ada_macros (pp, macros, max_ada_macros);
511 /* Current source file being handled. */
513 static const char *source_file_base;
515 /* Compare the declaration (DECL) of struct-like types based on the sloc of
516 their last field (if LAST is true), so that more nested types collate before
518 If ORIG_TYPE is true, also consider struct with a DECL_ORIGINAL_TYPE. */
521 decl_sloc_common (const_tree decl, bool last, bool orig_type)
523 tree type = TREE_TYPE (decl);
525 if (TREE_CODE (decl) == TYPE_DECL
526 && (orig_type || !DECL_ORIGINAL_TYPE (decl))
527 && RECORD_OR_UNION_TYPE_P (type)
528 && TYPE_FIELDS (type))
530 tree f = TYPE_FIELDS (type);
533 while (TREE_CHAIN (f))
536 return DECL_SOURCE_LOCATION (f);
539 return DECL_SOURCE_LOCATION (decl);
542 /* Return sloc of DECL, using sloc of last field if LAST is true. */
545 decl_sloc (const_tree decl, bool last)
547 return decl_sloc_common (decl, last, false);
550 /* Compare two locations LHS and RHS. */
553 compare_location (location_t lhs, location_t rhs)
555 expanded_location xlhs = expand_location (lhs);
556 expanded_location xrhs = expand_location (rhs);
558 if (xlhs.file != xrhs.file)
559 return filename_cmp (xlhs.file, xrhs.file);
561 if (xlhs.line != xrhs.line)
562 return xlhs.line - xrhs.line;
564 if (xlhs.column != xrhs.column)
565 return xlhs.column - xrhs.column;
570 /* Compare two declarations (LP and RP) by their source location. */
573 compare_node (const void *lp, const void *rp)
575 const_tree lhs = *((const tree *) lp);
576 const_tree rhs = *((const tree *) rp);
578 return compare_location (decl_sloc (lhs, true), decl_sloc (rhs, true));
581 /* Compare two comments (LP and RP) by their source location. */
584 compare_comment (const void *lp, const void *rp)
586 const cpp_comment *lhs = (const cpp_comment *) lp;
587 const cpp_comment *rhs = (const cpp_comment *) rp;
589 return compare_location (lhs->sloc, rhs->sloc);
592 static tree *to_dump = NULL;
593 static int to_dump_count = 0;
595 /* Collect a list of declarations from T relevant to SOURCE_FILE to be dumped
596 by a subsequent call to dump_ada_nodes. */
599 collect_ada_nodes (tree t, const char *source_file)
602 int i = to_dump_count;
604 /* Count the likely relevant nodes. */
605 for (n = t; n; n = TREE_CHAIN (n))
606 if (!DECL_IS_BUILTIN (n)
607 && LOCATION_FILE (decl_sloc (n, false)) == source_file)
610 /* Allocate sufficient storage for all nodes. */
611 to_dump = XRESIZEVEC (tree, to_dump, to_dump_count);
613 /* Store the relevant nodes. */
614 for (n = t; n; n = TREE_CHAIN (n))
615 if (!DECL_IS_BUILTIN (n)
616 && LOCATION_FILE (decl_sloc (n, false)) == source_file)
620 /* Call back for walk_tree to clear the TREE_VISITED flag of TP. */
623 unmark_visited_r (tree *tp, int *walk_subtrees ATTRIBUTE_UNUSED,
624 void *data ATTRIBUTE_UNUSED)
626 if (TREE_VISITED (*tp))
627 TREE_VISITED (*tp) = 0;
634 /* Dump nodes into PP relevant to SOURCE_FILE, as collected by previous calls
635 to collect_ada_nodes. */
638 dump_ada_nodes (pretty_printer *pp, const char *source_file)
641 cpp_comment_table *comments;
643 /* Sort the table of declarations to dump by sloc. */
644 qsort (to_dump, to_dump_count, sizeof (tree), compare_node);
646 /* Fetch the table of comments. */
647 comments = cpp_get_comments (parse_in);
649 /* Sort the comments table by sloc. */
650 if (comments->count > 1)
651 qsort (comments->entries, comments->count, sizeof (cpp_comment),
654 /* Interleave comments and declarations in line number order. */
658 /* Advance j until comment j is in this file. */
659 while (j != comments->count
660 && LOCATION_FILE (comments->entries[j].sloc) != source_file)
663 /* Advance j until comment j is not a duplicate. */
664 while (j < comments->count - 1
665 && !compare_comment (&comments->entries[j],
666 &comments->entries[j + 1]))
669 /* Write decls until decl i collates after comment j. */
670 while (i != to_dump_count)
672 if (j == comments->count
673 || LOCATION_LINE (decl_sloc (to_dump[i], false))
674 < LOCATION_LINE (comments->entries[j].sloc))
675 print_generic_ada_decl (pp, to_dump[i++], source_file);
680 /* Write comment j, if there is one. */
681 if (j != comments->count)
682 print_comment (pp, comments->entries[j++].comment);
684 } while (i != to_dump_count || j != comments->count);
686 /* Clear the TREE_VISITED flag over each subtree we've dumped. */
687 for (i = 0; i < to_dump_count; i++)
688 walk_tree (&to_dump[i], unmark_visited_r, NULL, NULL);
690 /* Finalize the to_dump table. */
699 /* Print a COMMENT to the output stream PP. */
702 print_comment (pretty_printer *pp, const char *comment)
704 int len = strlen (comment);
705 char *str = XALLOCAVEC (char, len + 1);
707 bool extra_newline = false;
709 memcpy (str, comment, len + 1);
711 /* Trim C/C++ comment indicators. */
712 if (str[len - 2] == '*' && str[len - 1] == '/')
719 tok = strtok (str, "\n");
721 pp_string (pp, " --");
724 tok = strtok (NULL, "\n");
726 /* Leave a blank line after multi-line comments. */
728 extra_newline = true;
735 /* Print declaration DECL to PP in Ada syntax. The current source file being
736 handled is SOURCE_FILE. */
739 print_generic_ada_decl (pretty_printer *pp, tree decl, const char *source_file)
741 source_file_base = source_file;
743 if (print_ada_declaration (pp, decl, 0, INDENT_INCR))
750 /* Dump a newline and indent BUFFER by SPC chars. */
753 newline_and_indent (pretty_printer *buffer, int spc)
759 struct with { char *s; const char *in_file; int limited; };
760 static struct with *withs = NULL;
761 static int withs_max = 4096;
762 static int with_len = 0;
764 /* Record a "with" clause on package S (a limited with if LIMITED_ACCESS is
765 true), if not already done. */
768 append_withs (const char *s, int limited_access)
773 withs = XNEWVEC (struct with, withs_max);
775 if (with_len == withs_max)
778 withs = XRESIZEVEC (struct with, withs, withs_max);
781 for (i = 0; i < with_len; i++)
782 if (!strcmp (s, withs[i].s)
783 && source_file_base == withs[i].in_file)
785 withs[i].limited &= limited_access;
789 withs[with_len].s = xstrdup (s);
790 withs[with_len].in_file = source_file_base;
791 withs[with_len].limited = limited_access;
795 /* Reset "with" clauses. */
798 reset_ada_withs (void)
805 for (i = 0; i < with_len; i++)
813 /* Dump "with" clauses in F. */
816 dump_ada_withs (FILE *f)
820 fprintf (f, "with Interfaces.C; use Interfaces.C;\n");
822 for (i = 0; i < with_len; i++)
824 (f, "%swith %s;\n", withs[i].limited ? "limited " : "", withs[i].s);
827 /* Return suitable Ada package name from FILE. */
830 get_ada_package (const char *file)
838 s = strstr (file, "/include/");
842 base = lbasename (file);
844 if (ada_specs_parent == NULL)
847 plen = strlen (ada_specs_parent) + 1;
849 res = XNEWVEC (char, plen + strlen (base) + 1);
850 if (ada_specs_parent != NULL) {
851 strcpy (res, ada_specs_parent);
855 for (i = plen; *base; base++, i++)
867 res[i] = (i == 0 || res[i - 1] == '.' || res[i - 1] == '_') ? 'u' : '_';
879 static const char *ada_reserved[] = {
880 "abort", "abs", "abstract", "accept", "access", "aliased", "all", "and",
881 "array", "at", "begin", "body", "case", "constant", "declare", "delay",
882 "delta", "digits", "do", "else", "elsif", "end", "entry", "exception",
883 "exit", "for", "function", "generic", "goto", "if", "in", "interface", "is",
884 "limited", "loop", "mod", "new", "not", "null", "others", "out", "of", "or",
885 "overriding", "package", "pragma", "private", "procedure", "protected",
886 "raise", "range", "record", "rem", "renames", "requeue", "return", "reverse",
887 "select", "separate", "subtype", "synchronized", "tagged", "task",
888 "terminate", "then", "type", "until", "use", "when", "while", "with", "xor",
891 /* ??? would be nice to specify this list via a config file, so that users
892 can create their own dictionary of conflicts. */
893 static const char *c_duplicates[] = {
894 /* system will cause troubles with System.Address. */
897 /* The following values have other definitions with same name/other
903 "rl_readline_version",
909 /* Return a declaration tree corresponding to TYPE. */
912 get_underlying_decl (tree type)
914 tree decl = NULL_TREE;
916 if (type == NULL_TREE)
919 /* type is a declaration. */
923 /* type is a typedef. */
924 if (TYPE_P (type) && TYPE_NAME (type) && DECL_P (TYPE_NAME (type)))
925 decl = TYPE_NAME (type);
927 /* TYPE_STUB_DECL has been set for type. */
928 if (TYPE_P (type) && TYPE_STUB_DECL (type) &&
929 DECL_P (TYPE_STUB_DECL (type)))
930 decl = TYPE_STUB_DECL (type);
935 /* Return whether TYPE has static fields. */
938 has_static_fields (const_tree type)
942 if (!type || !RECORD_OR_UNION_TYPE_P (type))
945 for (tmp = TYPE_FIELDS (type); tmp; tmp = TREE_CHAIN (tmp))
946 if (DECL_NAME (tmp) && TREE_STATIC (tmp))
952 /* Return whether TYPE corresponds to an Ada tagged type (has a dispatch
956 is_tagged_type (const_tree type)
960 if (!type || !RECORD_OR_UNION_TYPE_P (type))
963 for (tmp = TYPE_METHODS (type); tmp; tmp = TREE_CHAIN (tmp))
964 if (DECL_VINDEX (tmp))
970 /* Return whether TYPE has non-trivial methods, i.e. methods that do something
971 for the objects of TYPE. In C++, all classes have implicit special methods,
972 e.g. constructors and destructors, but they can be trivial if the type is
973 sufficiently simple. */
976 has_nontrivial_methods (tree type)
980 if (!type || !RECORD_OR_UNION_TYPE_P (type))
983 /* Only C++ types can have methods. */
987 /* A non-trivial type has non-trivial special methods. */
988 if (!cpp_check (type, IS_TRIVIAL))
991 /* If there are user-defined methods, they are deemed non-trivial. */
992 for (tmp = TYPE_METHODS (type); tmp; tmp = TREE_CHAIN (tmp))
993 if (!DECL_ARTIFICIAL (tmp))
999 /* Generate a legal Ada name from a C NAME, returning a malloc'd string.
1000 SPACE_FOUND, if not NULL, is used to indicate whether a space was found in
1004 to_ada_name (const char *name, int *space_found)
1007 int len = strlen (name);
1010 char *s = XNEWVEC (char, len * 2 + 5);
1014 *space_found = false;
1016 /* Add trailing "c_" if name is an Ada reserved word. */
1017 for (names = ada_reserved; *names; names++)
1018 if (!strcasecmp (name, *names))
1027 /* Add trailing "c_" if name is an potential case sensitive duplicate. */
1028 for (names = c_duplicates; *names; names++)
1029 if (!strcmp (name, *names))
1037 for (j = 0; name[j] == '_'; j++)
1042 else if (*name == '.' || *name == '$')
1052 /* Replace unsuitable characters for Ada identifiers. */
1054 for (; j < len; j++)
1059 *space_found = true;
1063 /* ??? missing some C++ operators. */
1067 if (name[j + 1] == '=')
1082 if (name[j + 1] == '=')
1100 s[len2++] = name[j] == '&' ? 'a' : name[j] == '|' ? 'o' : 'x';
1102 if (name[j + 1] == '=')
1115 if (s[len2 - 1] != '_')
1118 switch (name[j + 1]) {
1121 switch (name[j - 1]) {
1122 case '+': s[len2++] = 'p'; break; /* + */
1123 case '-': s[len2++] = 'm'; break; /* - */
1124 case '*': s[len2++] = 't'; break; /* * */
1125 case '/': s[len2++] = 'd'; break; /* / */
1131 switch (name[j - 1]) {
1132 case '+': s[len2++] = 'p'; break; /* += */
1133 case '-': s[len2++] = 'm'; break; /* -= */
1134 case '*': s[len2++] = 't'; break; /* *= */
1135 case '/': s[len2++] = 'd'; break; /* /= */
1169 c = name[j] == '<' ? 'l' : 'g';
1172 switch (name[j + 1]) {
1198 if (len2 && s[len2 - 1] == '_')
1203 s[len2++] = name[j];
1206 if (s[len2 - 1] == '_')
1214 /* Return true if DECL refers to a C++ class type for which a
1215 separate enclosing package has been or should be generated. */
1218 separate_class_package (tree decl)
1220 tree type = TREE_TYPE (decl);
1221 return has_nontrivial_methods (type) || has_static_fields (type);
1224 static bool package_prefix = true;
1226 /* Dump in BUFFER the name of an identifier NODE of type TYPE, following Ada
1227 syntax. LIMITED_ACCESS indicates whether NODE can be accessed via a limited
1228 'with' clause rather than a regular 'with' clause. */
1231 pp_ada_tree_identifier (pretty_printer *buffer, tree node, tree type,
1234 const char *name = IDENTIFIER_POINTER (node);
1235 int space_found = false;
1236 char *s = to_ada_name (name, &space_found);
1239 /* If the entity is a type and comes from another file, generate "package"
1241 decl = get_underlying_decl (type);
1245 expanded_location xloc = expand_location (decl_sloc (decl, false));
1247 if (xloc.file && xloc.line)
1249 if (xloc.file != source_file_base)
1251 switch (TREE_CODE (type))
1256 case FIXED_POINT_TYPE:
1258 case REFERENCE_TYPE:
1263 case QUAL_UNION_TYPE:
1267 char *s1 = get_ada_package (xloc.file);
1268 append_withs (s1, limited_access);
1269 pp_string (buffer, s1);
1278 /* Generate the additional package prefix for C++ classes. */
1279 if (separate_class_package (decl))
1281 pp_string (buffer, "Class_");
1282 pp_string (buffer, s);
1290 if (!strcmp (s, "short_int"))
1291 pp_string (buffer, "short");
1292 else if (!strcmp (s, "short_unsigned_int"))
1293 pp_string (buffer, "unsigned_short");
1294 else if (!strcmp (s, "unsigned_int"))
1295 pp_string (buffer, "unsigned");
1296 else if (!strcmp (s, "long_int"))
1297 pp_string (buffer, "long");
1298 else if (!strcmp (s, "long_unsigned_int"))
1299 pp_string (buffer, "unsigned_long");
1300 else if (!strcmp (s, "long_long_int"))
1301 pp_string (buffer, "Long_Long_Integer");
1302 else if (!strcmp (s, "long_long_unsigned_int"))
1306 append_withs ("Interfaces.C.Extensions", false);
1307 pp_string (buffer, "Extensions.unsigned_long_long");
1310 pp_string (buffer, "unsigned_long_long");
1313 pp_string(buffer, s);
1315 if (!strcmp (s, "bool"))
1319 append_withs ("Interfaces.C.Extensions", false);
1320 pp_string (buffer, "Extensions.bool");
1323 pp_string (buffer, "bool");
1326 pp_string(buffer, s);
1331 /* Dump in BUFFER the assembly name of T. */
1334 pp_asm_name (pretty_printer *buffer, tree t)
1336 tree name = DECL_ASSEMBLER_NAME (t);
1337 char *ada_name = XALLOCAVEC (char, IDENTIFIER_LENGTH (name) + 1), *s;
1338 const char *ident = IDENTIFIER_POINTER (name);
1340 for (s = ada_name; *ident; ident++)
1344 else if (*ident != '*')
1349 pp_string (buffer, ada_name);
1352 /* Dump in BUFFER the name of a DECL node if set, following Ada syntax.
1353 LIMITED_ACCESS indicates whether NODE can be accessed via a limited
1354 'with' clause rather than a regular 'with' clause. */
1357 dump_ada_decl_name (pretty_printer *buffer, tree decl, int limited_access)
1359 if (DECL_NAME (decl))
1360 pp_ada_tree_identifier (buffer, DECL_NAME (decl), decl, limited_access);
1363 tree type_name = TYPE_NAME (TREE_TYPE (decl));
1367 pp_string (buffer, "anon");
1368 if (TREE_CODE (decl) == FIELD_DECL)
1369 pp_scalar (buffer, "%d", DECL_UID (decl));
1371 pp_scalar (buffer, "%d", TYPE_UID (TREE_TYPE (decl)));
1373 else if (TREE_CODE (type_name) == IDENTIFIER_NODE)
1374 pp_ada_tree_identifier (buffer, type_name, decl, limited_access);
1378 /* Dump in BUFFER a name based on both T1 and T2, followed by S. */
1381 dump_ada_double_name (pretty_printer *buffer, tree t1, tree t2, const char *s)
1384 pp_ada_tree_identifier (buffer, DECL_NAME (t1), t1, false);
1387 pp_string (buffer, "anon");
1388 pp_scalar (buffer, "%d", TYPE_UID (TREE_TYPE (t1)));
1391 pp_underscore (buffer);
1394 pp_ada_tree_identifier (buffer, DECL_NAME (t2), t2, false);
1397 pp_string (buffer, "anon");
1398 pp_scalar (buffer, "%d", TYPE_UID (TREE_TYPE (t2)));
1401 pp_string (buffer, s);
1404 /* Dump in BUFFER pragma Import C/CPP on a given node T. */
1407 dump_ada_import (pretty_printer *buffer, tree t)
1409 const char *name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (t));
1410 int is_stdcall = TREE_CODE (t) == FUNCTION_DECL &&
1411 lookup_attribute ("stdcall", TYPE_ATTRIBUTES (TREE_TYPE (t)));
1414 pp_string (buffer, "pragma Import (Stdcall, ");
1415 else if (name[0] == '_' && name[1] == 'Z')
1416 pp_string (buffer, "pragma Import (CPP, ");
1418 pp_string (buffer, "pragma Import (C, ");
1420 dump_ada_decl_name (buffer, t, false);
1421 pp_string (buffer, ", \"");
1424 pp_string (buffer, IDENTIFIER_POINTER (DECL_NAME (t)));
1426 pp_asm_name (buffer, t);
1428 pp_string (buffer, "\");");
1431 /* Check whether T and its type have different names, and append "the_"
1432 otherwise in BUFFER. */
1435 check_name (pretty_printer *buffer, tree t)
1438 tree tmp = TREE_TYPE (t);
1440 while (TREE_CODE (tmp) == POINTER_TYPE && !TYPE_NAME (tmp))
1441 tmp = TREE_TYPE (tmp);
1443 if (TREE_CODE (tmp) != FUNCTION_TYPE)
1445 if (TREE_CODE (tmp) == IDENTIFIER_NODE)
1446 s = IDENTIFIER_POINTER (tmp);
1447 else if (!TYPE_NAME (tmp))
1449 else if (TREE_CODE (TYPE_NAME (tmp)) == IDENTIFIER_NODE)
1450 s = IDENTIFIER_POINTER (TYPE_NAME (tmp));
1452 s = IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (tmp)));
1454 if (!strcasecmp (IDENTIFIER_POINTER (DECL_NAME (t)), s))
1455 pp_string (buffer, "the_");
1459 /* Dump in BUFFER a function declaration FUNC with Ada syntax.
1460 IS_METHOD indicates whether FUNC is a C++ method.
1461 IS_CONSTRUCTOR whether FUNC is a C++ constructor.
1462 IS_DESTRUCTOR whether FUNC is a C++ destructor.
1463 SPC is the current indentation level. */
1466 dump_ada_function_declaration (pretty_printer *buffer, tree func,
1467 int is_method, int is_constructor,
1468 int is_destructor, int spc)
1471 const tree node = TREE_TYPE (func);
1473 int num = 0, num_args = 0, have_args = true, have_ellipsis = false;
1475 /* Compute number of arguments. */
1476 arg = TYPE_ARG_TYPES (node);
1480 while (TREE_CHAIN (arg) && arg != error_mark_node)
1483 arg = TREE_CHAIN (arg);
1486 if (TREE_CODE (TREE_VALUE (arg)) != VOID_TYPE)
1489 have_ellipsis = true;
1500 newline_and_indent (buffer, spc + 1);
1505 pp_left_paren (buffer);
1508 if (TREE_CODE (func) == FUNCTION_DECL)
1509 arg = DECL_ARGUMENTS (func);
1513 if (arg == NULL_TREE)
1516 arg = TYPE_ARG_TYPES (node);
1518 if (arg && TREE_CODE (TREE_VALUE (arg)) == VOID_TYPE)
1523 arg = TREE_CHAIN (arg);
1525 /* Print the argument names (if available) & types. */
1527 for (num = 1; num <= num_args; num++)
1531 if (DECL_NAME (arg))
1533 check_name (buffer, arg);
1534 pp_ada_tree_identifier (buffer, DECL_NAME (arg), 0, false);
1535 pp_string (buffer, " : ");
1539 sprintf (buf, "arg%d : ", num);
1540 pp_string (buffer, buf);
1543 dump_generic_ada_node (buffer, TREE_TYPE (arg), node, spc, 0, true);
1547 sprintf (buf, "arg%d : ", num);
1548 pp_string (buffer, buf);
1549 dump_generic_ada_node (buffer, TREE_VALUE (arg), node, spc, 0, true);
1552 if (TREE_TYPE (arg) && TREE_TYPE (TREE_TYPE (arg))
1553 && is_tagged_type (TREE_TYPE (TREE_TYPE (arg))))
1556 || (num != 1 || (!DECL_VINDEX (func) && !is_constructor)))
1557 pp_string (buffer, "'Class");
1560 arg = TREE_CHAIN (arg);
1564 pp_semicolon (buffer);
1567 newline_and_indent (buffer, spc + INDENT_INCR);
1575 pp_string (buffer, " -- , ...");
1576 newline_and_indent (buffer, spc + INDENT_INCR);
1580 pp_right_paren (buffer);
1584 /* Dump in BUFFER all the domains associated with an array NODE,
1585 using Ada syntax. SPC is the current indentation level. */
1588 dump_ada_array_domains (pretty_printer *buffer, tree node, int spc)
1591 pp_left_paren (buffer);
1593 for (; TREE_CODE (node) == ARRAY_TYPE; node = TREE_TYPE (node))
1595 tree domain = TYPE_DOMAIN (node);
1599 tree min = TYPE_MIN_VALUE (domain);
1600 tree max = TYPE_MAX_VALUE (domain);
1603 pp_string (buffer, ", ");
1607 dump_generic_ada_node (buffer, min, NULL_TREE, spc, 0, true);
1608 pp_string (buffer, " .. ");
1610 /* If the upper bound is zero, gcc may generate a NULL_TREE
1611 for TYPE_MAX_VALUE rather than an integer_cst. */
1613 dump_generic_ada_node (buffer, max, NULL_TREE, spc, 0, true);
1615 pp_string (buffer, "0");
1618 pp_string (buffer, "size_t");
1620 pp_right_paren (buffer);
1623 /* Dump in BUFFER file:line information related to NODE. */
1626 dump_sloc (pretty_printer *buffer, tree node)
1628 expanded_location xloc;
1632 if (TREE_CODE_CLASS (TREE_CODE (node)) == tcc_declaration)
1633 xloc = expand_location (DECL_SOURCE_LOCATION (node));
1634 else if (EXPR_HAS_LOCATION (node))
1635 xloc = expand_location (EXPR_LOCATION (node));
1639 pp_string (buffer, xloc.file);
1641 pp_decimal_int (buffer, xloc.line);
1645 /* Return true if T designates a one dimension array of "char". */
1648 is_char_array (tree t)
1653 /* Retrieve array's type. */
1655 while (TREE_CODE (TREE_TYPE (tmp)) == ARRAY_TYPE)
1658 tmp = TREE_TYPE (tmp);
1661 tmp = TREE_TYPE (tmp);
1662 return num_dim == 1 && TREE_CODE (tmp) == INTEGER_TYPE
1663 && !strcmp (IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (tmp))), "char");
1666 /* Dump in BUFFER an array type T in Ada syntax. Assume that the "type"
1667 keyword and name have already been printed. SPC is the indentation
1671 dump_ada_array_type (pretty_printer *buffer, tree t, int spc)
1674 bool char_array = is_char_array (t);
1676 /* Special case char arrays. */
1679 pp_string (buffer, "Interfaces.C.char_array ");
1682 pp_string (buffer, "array ");
1684 /* Print the dimensions. */
1685 dump_ada_array_domains (buffer, TREE_TYPE (t), spc);
1687 /* Retrieve array's type. */
1688 tmp = TREE_TYPE (t);
1689 while (TREE_CODE (TREE_TYPE (tmp)) == ARRAY_TYPE)
1690 tmp = TREE_TYPE (tmp);
1692 /* Print array's type. */
1695 pp_string (buffer, " of ");
1697 if (TREE_CODE (TREE_TYPE (tmp)) != POINTER_TYPE)
1698 pp_string (buffer, "aliased ");
1700 dump_generic_ada_node
1701 (buffer, TREE_TYPE (tmp), TREE_TYPE (t), spc, false, true);
1705 /* Dump in BUFFER type names associated with a template, each prepended with
1706 '_'. TYPES is the TREE_PURPOSE of a DECL_TEMPLATE_INSTANTIATIONS. SPC is
1707 the indentation level. */
1710 dump_template_types (pretty_printer *buffer, tree types, int spc)
1713 size_t len = TREE_VEC_LENGTH (types);
1715 for (i = 0; i < len; i++)
1717 tree elem = TREE_VEC_ELT (types, i);
1718 pp_underscore (buffer);
1719 if (!dump_generic_ada_node (buffer, elem, 0, spc, false, true))
1721 pp_string (buffer, "unknown");
1722 pp_scalar (buffer, "%lu", (unsigned long) TREE_HASH (elem));
1727 /* Dump in BUFFER the contents of all class instantiations associated with
1728 a given template T. SPC is the indentation level. */
1731 dump_ada_template (pretty_printer *buffer, tree t, int spc)
1733 /* DECL_VINDEX is DECL_TEMPLATE_INSTANTIATIONS in this context. */
1734 tree inst = DECL_VINDEX (t);
1735 /* DECL_RESULT_FLD is DECL_TEMPLATE_RESULT in this context. */
1736 tree result = DECL_RESULT_FLD (t);
1739 /* Don't look at template declarations declaring something coming from
1740 another file. This can occur for template friend declarations. */
1741 if (LOCATION_FILE (decl_sloc (result, false))
1742 != LOCATION_FILE (decl_sloc (t, false)))
1745 while (inst && inst != error_mark_node)
1747 tree types = TREE_PURPOSE (inst);
1748 tree instance = TREE_VALUE (inst);
1750 if (TREE_VEC_LENGTH (types) == 0)
1753 if (!TYPE_P (instance) || !TYPE_METHODS (instance))
1758 pp_string (buffer, "package ");
1759 package_prefix = false;
1760 dump_generic_ada_node (buffer, instance, t, spc, false, true);
1761 dump_template_types (buffer, types, spc);
1762 pp_string (buffer, " is");
1764 newline_and_indent (buffer, spc);
1766 TREE_VISITED (get_underlying_decl (instance)) = 1;
1767 pp_string (buffer, "type ");
1768 dump_generic_ada_node (buffer, instance, t, spc, false, true);
1769 package_prefix = true;
1771 if (is_tagged_type (instance))
1772 pp_string (buffer, " is tagged limited ");
1774 pp_string (buffer, " is limited ");
1776 dump_generic_ada_node (buffer, instance, t, spc, false, false);
1777 pp_newline (buffer);
1779 newline_and_indent (buffer, spc);
1781 pp_string (buffer, "end;");
1782 newline_and_indent (buffer, spc);
1783 pp_string (buffer, "use ");
1784 package_prefix = false;
1785 dump_generic_ada_node (buffer, instance, t, spc, false, true);
1786 dump_template_types (buffer, types, spc);
1787 package_prefix = true;
1788 pp_semicolon (buffer);
1789 pp_newline (buffer);
1790 pp_newline (buffer);
1792 inst = TREE_CHAIN (inst);
1795 return num_inst > 0;
1798 /* Return true if NODE is a simple enum types, that can be mapped to an
1799 Ada enum type directly. */
1802 is_simple_enum (tree node)
1804 HOST_WIDE_INT count = 0;
1807 for (value = TYPE_VALUES (node); value; value = TREE_CHAIN (value))
1809 tree int_val = TREE_VALUE (value);
1811 if (TREE_CODE (int_val) != INTEGER_CST)
1812 int_val = DECL_INITIAL (int_val);
1814 if (!tree_fits_shwi_p (int_val))
1816 else if (tree_to_shwi (int_val) != count)
1825 static bool in_function = true;
1826 static bool bitfield_used = false;
1828 /* Recursively dump in BUFFER Ada declarations corresponding to NODE of type
1829 TYPE. SPC is the indentation level. LIMITED_ACCESS indicates whether NODE
1830 can be referenced via a "limited with" clause. NAME_ONLY indicates whether
1831 we should only dump the name of NODE, instead of its full declaration. */
1834 dump_generic_ada_node (pretty_printer *buffer, tree node, tree type, int spc,
1835 int limited_access, bool name_only)
1837 if (node == NULL_TREE)
1840 switch (TREE_CODE (node))
1843 pp_string (buffer, "<<< error >>>");
1846 case IDENTIFIER_NODE:
1847 pp_ada_tree_identifier (buffer, node, type, limited_access);
1851 pp_string (buffer, "--- unexpected node: TREE_LIST");
1855 dump_generic_ada_node
1856 (buffer, BINFO_TYPE (node), type, spc, limited_access, name_only);
1859 pp_string (buffer, "--- unexpected node: TREE_VEC");
1865 append_withs ("System", false);
1866 pp_string (buffer, "System.Address");
1869 pp_string (buffer, "address");
1873 pp_string (buffer, "<vector>");
1877 pp_string (buffer, "<complex>");
1882 dump_generic_ada_node
1883 (buffer, TYPE_NAME (node), node, spc, 0, true);
1886 tree value = TYPE_VALUES (node);
1888 if (is_simple_enum (node))
1892 newline_and_indent (buffer, spc - 1);
1893 pp_left_paren (buffer);
1894 for (; value; value = TREE_CHAIN (value))
1901 newline_and_indent (buffer, spc);
1904 pp_ada_tree_identifier
1905 (buffer, TREE_PURPOSE (value), node, false);
1907 pp_string (buffer, ");");
1909 newline_and_indent (buffer, spc);
1910 pp_string (buffer, "pragma Convention (C, ");
1911 dump_generic_ada_node
1912 (buffer, DECL_NAME (type) ? type : TYPE_NAME (node), type,
1914 pp_right_paren (buffer);
1918 pp_string (buffer, "unsigned");
1919 for (; value; value = TREE_CHAIN (value))
1921 pp_semicolon (buffer);
1922 newline_and_indent (buffer, spc);
1924 pp_ada_tree_identifier
1925 (buffer, TREE_PURPOSE (value), node, false);
1926 pp_string (buffer, " : constant ");
1928 dump_generic_ada_node
1929 (buffer, DECL_NAME (type) ? type : TYPE_NAME (node), type,
1932 pp_string (buffer, " := ");
1933 dump_generic_ada_node
1935 TREE_CODE (TREE_VALUE (value)) == INTEGER_CST ?
1936 TREE_VALUE (value) : DECL_INITIAL (TREE_VALUE (value)),
1937 node, spc, false, true);
1945 case FIXED_POINT_TYPE:
1948 enum tree_code_class tclass;
1950 tclass = TREE_CODE_CLASS (TREE_CODE (node));
1952 if (tclass == tcc_declaration)
1954 if (DECL_NAME (node))
1955 pp_ada_tree_identifier
1956 (buffer, DECL_NAME (node), 0, limited_access);
1958 pp_string (buffer, "<unnamed type decl>");
1960 else if (tclass == tcc_type)
1962 if (TYPE_NAME (node))
1964 if (TREE_CODE (TYPE_NAME (node)) == IDENTIFIER_NODE)
1965 pp_ada_tree_identifier (buffer, TYPE_NAME (node),
1966 node, limited_access);
1967 else if (TREE_CODE (TYPE_NAME (node)) == TYPE_DECL
1968 && DECL_NAME (TYPE_NAME (node)))
1969 dump_ada_decl_name (buffer, TYPE_NAME (node), limited_access);
1971 pp_string (buffer, "<unnamed type>");
1973 else if (TREE_CODE (node) == INTEGER_TYPE)
1975 append_withs ("Interfaces.C.Extensions", false);
1976 bitfield_used = true;
1978 if (TYPE_PRECISION (node) == 1)
1979 pp_string (buffer, "Extensions.Unsigned_1");
1982 pp_string (buffer, (TYPE_UNSIGNED (node)
1983 ? "Extensions.Unsigned_"
1984 : "Extensions.Signed_"));
1985 pp_decimal_int (buffer, TYPE_PRECISION (node));
1989 pp_string (buffer, "<unnamed type>");
1995 case REFERENCE_TYPE:
1996 if (name_only && TYPE_NAME (node))
1997 dump_generic_ada_node
1998 (buffer, TYPE_NAME (node), node, spc, limited_access, true);
2000 else if (TREE_CODE (TREE_TYPE (node)) == FUNCTION_TYPE)
2002 tree fnode = TREE_TYPE (node);
2004 bool prev_in_function = in_function;
2006 if (VOID_TYPE_P (TREE_TYPE (fnode)))
2008 is_function = false;
2009 pp_string (buffer, "access procedure");
2014 pp_string (buffer, "access function");
2017 in_function = is_function;
2018 dump_ada_function_declaration
2019 (buffer, node, false, false, false, spc + INDENT_INCR);
2020 in_function = prev_in_function;
2024 pp_string (buffer, " return ");
2025 dump_generic_ada_node
2026 (buffer, TREE_TYPE (fnode), type, spc, 0, true);
2029 /* If we are dumping the full type, it means we are part of a
2030 type definition and need also a Convention C pragma. */
2033 pp_semicolon (buffer);
2034 newline_and_indent (buffer, spc);
2035 pp_string (buffer, "pragma Convention (C, ");
2036 dump_generic_ada_node
2037 (buffer, type, 0, spc, false, true);
2038 pp_right_paren (buffer);
2043 int is_access = false;
2044 unsigned int quals = TYPE_QUALS (TREE_TYPE (node));
2046 if (VOID_TYPE_P (TREE_TYPE (node)))
2049 pp_string (buffer, "new ");
2052 append_withs ("System", false);
2053 pp_string (buffer, "System.Address");
2056 pp_string (buffer, "address");
2060 if (TREE_CODE (node) == POINTER_TYPE
2061 && TREE_CODE (TREE_TYPE (node)) == INTEGER_TYPE
2063 (IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME
2064 (TREE_TYPE (node)))), "char"))
2067 pp_string (buffer, "new ");
2071 pp_string (buffer, "Interfaces.C.Strings.chars_ptr");
2072 append_withs ("Interfaces.C.Strings", false);
2075 pp_string (buffer, "chars_ptr");
2079 /* For now, handle all access-to-access or
2080 access-to-unknown-structs as opaque system.address. */
2082 tree type_name = TYPE_NAME (TREE_TYPE (node));
2083 const_tree typ2 = !type ||
2084 DECL_P (type) ? type : TYPE_NAME (type);
2085 const_tree underlying_type =
2086 get_underlying_decl (TREE_TYPE (node));
2088 if (TREE_CODE (TREE_TYPE (node)) == POINTER_TYPE
2089 /* Pointer to pointer. */
2091 || (RECORD_OR_UNION_TYPE_P (TREE_TYPE (node))
2092 && (!underlying_type
2093 || !TYPE_FIELDS (TREE_TYPE (underlying_type))))
2094 /* Pointer to opaque structure. */
2096 || underlying_type == NULL_TREE
2098 && !TREE_VISITED (underlying_type)
2099 && !TREE_VISITED (type_name)
2100 && !is_tagged_type (TREE_TYPE (node))
2101 && DECL_SOURCE_FILE (underlying_type)
2102 == source_file_base)
2103 || (type_name && typ2
2104 && DECL_P (underlying_type)
2106 && decl_sloc (underlying_type, true)
2107 > decl_sloc (typ2, true)
2108 && DECL_SOURCE_FILE (underlying_type)
2109 == DECL_SOURCE_FILE (typ2)))
2113 append_withs ("System", false);
2115 pp_string (buffer, "new ");
2116 pp_string (buffer, "System.Address");
2119 pp_string (buffer, "address");
2123 if (!package_prefix)
2124 pp_string (buffer, "access");
2125 else if (AGGREGATE_TYPE_P (TREE_TYPE (node)))
2127 if (!type || TREE_CODE (type) != FUNCTION_DECL)
2129 pp_string (buffer, "access ");
2132 if (quals & TYPE_QUAL_CONST)
2133 pp_string (buffer, "constant ");
2134 else if (!name_only)
2135 pp_string (buffer, "all ");
2137 else if (quals & TYPE_QUAL_CONST)
2138 pp_string (buffer, "in ");
2139 else if (in_function)
2142 pp_string (buffer, "access ");
2147 pp_string (buffer, "access ");
2148 /* ??? should be configurable: access or in out. */
2154 pp_string (buffer, "access ");
2157 pp_string (buffer, "all ");
2160 if (RECORD_OR_UNION_TYPE_P (TREE_TYPE (node))
2161 && type_name != NULL_TREE)
2162 dump_generic_ada_node
2164 TREE_TYPE (node), spc, is_access, true);
2166 dump_generic_ada_node
2167 (buffer, TREE_TYPE (node), TREE_TYPE (node),
2176 dump_generic_ada_node
2177 (buffer, TYPE_NAME (node), node, spc, limited_access, true);
2179 dump_ada_array_type (buffer, node, spc);
2184 case QUAL_UNION_TYPE:
2187 if (TYPE_NAME (node))
2188 dump_generic_ada_node
2189 (buffer, TYPE_NAME (node), node, spc, limited_access, true);
2192 pp_string (buffer, "anon_");
2193 pp_scalar (buffer, "%d", TYPE_UID (node));
2197 print_ada_struct_decl (buffer, node, type, spc, true);
2201 /* We treat the upper half of the sizetype range as negative. This
2202 is consistent with the internal treatment and makes it possible
2203 to generate the (0 .. -1) range for flexible array members. */
2204 if (TREE_TYPE (node) == sizetype)
2205 node = fold_convert (ssizetype, node);
2206 if (tree_fits_shwi_p (node))
2207 pp_wide_integer (buffer, tree_to_shwi (node));
2208 else if (tree_fits_uhwi_p (node))
2209 pp_unsigned_wide_integer (buffer, tree_to_uhwi (node));
2212 wide_int val = node;
2214 if (wi::neg_p (val))
2219 sprintf (pp_buffer (buffer)->digit_buffer,
2220 "16#%" HOST_WIDE_INT_PRINT "x",
2221 val.elt (val.get_len () - 1));
2222 for (i = val.get_len () - 2; i >= 0; i--)
2223 sprintf (pp_buffer (buffer)->digit_buffer,
2224 HOST_WIDE_INT_PRINT_PADDED_HEX, val.elt (i));
2225 pp_string (buffer, pp_buffer (buffer)->digit_buffer);
2238 dump_ada_decl_name (buffer, node, limited_access);
2242 if (DECL_IS_BUILTIN (node))
2244 /* Don't print the declaration of built-in types. */
2248 /* If we're in the middle of a declaration, defaults to
2252 append_withs ("System", false);
2253 pp_string (buffer, "System.Address");
2256 pp_string (buffer, "address");
2262 dump_ada_decl_name (buffer, node, limited_access);
2265 if (is_tagged_type (TREE_TYPE (node)))
2267 tree tmp = TYPE_FIELDS (TREE_TYPE (node));
2270 /* Look for ancestors. */
2271 for (; tmp; tmp = TREE_CHAIN (tmp))
2273 if (!DECL_NAME (tmp) && is_tagged_type (TREE_TYPE (tmp)))
2277 pp_string (buffer, "limited new ");
2281 pp_string (buffer, " and ");
2284 (buffer, TYPE_NAME (TREE_TYPE (tmp)), false);
2288 pp_string (buffer, first ? "tagged limited " : " with ");
2290 else if (has_nontrivial_methods (TREE_TYPE (node)))
2291 pp_string (buffer, "limited ");
2293 dump_generic_ada_node
2294 (buffer, TREE_TYPE (node), type, spc, false, false);
2301 case NAMESPACE_DECL:
2302 dump_ada_decl_name (buffer, node, false);
2306 /* Ignore other nodes (e.g. expressions). */
2313 /* Dump in BUFFER NODE's methods. SPC is the indentation level. Return 1 if
2314 methods were printed, 0 otherwise. */
2317 print_ada_methods (pretty_printer *buffer, tree node, int spc)
2322 if (!has_nontrivial_methods (node))
2325 pp_semicolon (buffer);
2327 for (tmp = TYPE_METHODS (node); tmp; tmp = TREE_CHAIN (tmp))
2331 pp_newline (buffer);
2332 pp_newline (buffer);
2334 res = print_ada_declaration (buffer, tmp, node, spc);
2340 /* Dump in BUFFER anonymous types nested inside T's definition.
2341 PARENT is the parent node of T.
2342 FORWARD indicates whether a forward declaration of T should be generated.
2343 SPC is the indentation level. */
2346 dump_nested_types (pretty_printer *buffer, tree t, tree parent, bool forward,
2349 tree field, outer, decl;
2351 /* Avoid recursing over the same tree. */
2352 if (TREE_VISITED (t))
2355 /* Find possible anonymous arrays/unions/structs recursively. */
2357 outer = TREE_TYPE (t);
2359 if (outer == NULL_TREE)
2364 pp_string (buffer, "type ");
2365 dump_generic_ada_node (buffer, t, t, spc, false, true);
2366 pp_semicolon (buffer);
2367 newline_and_indent (buffer, spc);
2368 TREE_VISITED (t) = 1;
2371 field = TYPE_FIELDS (outer);
2374 if ((TREE_TYPE (field) != outer
2375 || (TREE_CODE (TREE_TYPE (field)) == POINTER_TYPE
2376 && TREE_TYPE (TREE_TYPE (field)) != outer))
2377 && (!TYPE_NAME (TREE_TYPE (field))
2378 || (TREE_CODE (field) == TYPE_DECL
2379 && DECL_NAME (field) != DECL_NAME (t)
2380 && TYPE_NAME (TREE_TYPE (field)) != TYPE_NAME (outer))))
2382 switch (TREE_CODE (TREE_TYPE (field)))
2385 decl = TREE_TYPE (TREE_TYPE (field));
2387 if (TREE_CODE (decl) == FUNCTION_TYPE)
2388 for (decl = TREE_TYPE (decl);
2389 decl && TREE_CODE (decl) == POINTER_TYPE;
2390 decl = TREE_TYPE (decl))
2393 decl = get_underlying_decl (decl);
2397 && decl_sloc (decl, true) > decl_sloc (t, true)
2398 && DECL_SOURCE_FILE (decl) == DECL_SOURCE_FILE (t)
2399 && !TREE_VISITED (decl)
2400 && !DECL_IS_BUILTIN (decl)
2401 && (!RECORD_OR_UNION_TYPE_P (TREE_TYPE (decl))
2402 || TYPE_FIELDS (TREE_TYPE (decl))))
2404 /* Generate forward declaration. */
2406 pp_string (buffer, "type ");
2407 dump_generic_ada_node (buffer, decl, 0, spc, false, true);
2408 pp_semicolon (buffer);
2409 newline_and_indent (buffer, spc);
2411 /* Ensure we do not generate duplicate forward
2412 declarations for this type. */
2413 TREE_VISITED (decl) = 1;
2418 /* Special case char arrays. */
2419 if (is_char_array (field))
2420 pp_string (buffer, "sub");
2422 pp_string (buffer, "type ");
2423 dump_ada_double_name (buffer, parent, field, "_array is ");
2424 dump_ada_array_type (buffer, field, spc);
2425 pp_semicolon (buffer);
2426 newline_and_indent (buffer, spc);
2430 TREE_VISITED (t) = 1;
2431 dump_nested_types (buffer, field, t, false, spc);
2433 pp_string (buffer, "type ");
2435 if (TYPE_NAME (TREE_TYPE (field)))
2437 dump_generic_ada_node
2438 (buffer, TYPE_NAME (TREE_TYPE (field)), 0, spc, false,
2440 pp_string (buffer, " (discr : unsigned := 0) is ");
2441 print_ada_struct_decl
2442 (buffer, TREE_TYPE (field), t, spc, false);
2444 pp_string (buffer, "pragma Convention (C_Pass_By_Copy, ");
2445 dump_generic_ada_node
2446 (buffer, TREE_TYPE (field), 0, spc, false, true);
2447 pp_string (buffer, ");");
2448 newline_and_indent (buffer, spc);
2450 pp_string (buffer, "pragma Unchecked_Union (");
2451 dump_generic_ada_node
2452 (buffer, TREE_TYPE (field), 0, spc, false, true);
2453 pp_string (buffer, ");");
2457 dump_ada_double_name
2458 (buffer, parent, field,
2459 "_union (discr : unsigned := 0) is ");
2460 print_ada_struct_decl
2461 (buffer, TREE_TYPE (field), t, spc, false);
2462 pp_string (buffer, "pragma Convention (C_Pass_By_Copy, ");
2463 dump_ada_double_name (buffer, parent, field, "_union);");
2464 newline_and_indent (buffer, spc);
2466 pp_string (buffer, "pragma Unchecked_Union (");
2467 dump_ada_double_name (buffer, parent, field, "_union);");
2470 newline_and_indent (buffer, spc);
2474 if (TYPE_NAME (TREE_TYPE (t)) && !TREE_VISITED (t))
2476 pp_string (buffer, "type ");
2477 dump_generic_ada_node
2478 (buffer, t, parent, spc, false, true);
2479 pp_semicolon (buffer);
2480 newline_and_indent (buffer, spc);
2483 TREE_VISITED (t) = 1;
2484 dump_nested_types (buffer, field, t, false, spc);
2485 pp_string (buffer, "type ");
2487 if (TYPE_NAME (TREE_TYPE (field)))
2489 dump_generic_ada_node
2490 (buffer, TREE_TYPE (field), 0, spc, false, true);
2491 pp_string (buffer, " is ");
2492 print_ada_struct_decl
2493 (buffer, TREE_TYPE (field), t, spc, false);
2494 pp_string (buffer, "pragma Convention (C_Pass_By_Copy, ");
2495 dump_generic_ada_node
2496 (buffer, TREE_TYPE (field), 0, spc, false, true);
2497 pp_string (buffer, ");");
2501 dump_ada_double_name
2502 (buffer, parent, field, "_struct is ");
2503 print_ada_struct_decl
2504 (buffer, TREE_TYPE (field), t, spc, false);
2505 pp_string (buffer, "pragma Convention (C_Pass_By_Copy, ");
2506 dump_ada_double_name (buffer, parent, field, "_struct);");
2509 newline_and_indent (buffer, spc);
2516 field = TREE_CHAIN (field);
2519 TREE_VISITED (t) = 1;
2522 /* Dump in BUFFER constructor spec corresponding to T. */
2525 print_constructor (pretty_printer *buffer, tree t)
2527 tree decl_name = DECL_NAME (DECL_ORIGIN (t));
2529 pp_string (buffer, "New_");
2530 pp_ada_tree_identifier (buffer, decl_name, t, false);
2533 /* Dump in BUFFER destructor spec corresponding to T. */
2536 print_destructor (pretty_printer *buffer, tree t)
2538 tree decl_name = DECL_NAME (DECL_ORIGIN (t));
2539 const char *s = IDENTIFIER_POINTER (decl_name);
2543 for (s += 2; *s != ' '; s++)
2544 pp_character (buffer, *s);
2548 pp_string (buffer, "Delete_");
2549 pp_ada_tree_identifier (buffer, decl_name, t, false);
2553 /* Return the name of type T. */
2558 tree n = TYPE_NAME (t);
2560 if (TREE_CODE (n) == IDENTIFIER_NODE)
2561 return IDENTIFIER_POINTER (n);
2563 return IDENTIFIER_POINTER (DECL_NAME (n));
2566 /* Print in BUFFER the declaration of a variable T of type TYPE in Ada syntax.
2567 SPC is the indentation level. Return 1 if a declaration was printed,
2571 print_ada_declaration (pretty_printer *buffer, tree t, tree type, int spc)
2573 int is_var = 0, need_indent = 0;
2574 int is_class = false;
2575 tree name = TYPE_NAME (TREE_TYPE (t));
2576 tree decl_name = DECL_NAME (t);
2577 tree orig = NULL_TREE;
2579 if (cpp_check && cpp_check (t, IS_TEMPLATE))
2580 return dump_ada_template (buffer, t, spc);
2582 if (TREE_CODE (t) == CONST_DECL && TREE_CODE (TREE_TYPE (t)) == ENUMERAL_TYPE)
2583 /* Skip enumeral values: will be handled as part of the type itself. */
2586 if (TREE_CODE (t) == TYPE_DECL)
2588 orig = DECL_ORIGINAL_TYPE (t);
2590 if (orig && TYPE_STUB_DECL (orig))
2592 tree stub = TYPE_STUB_DECL (orig);
2593 tree typ = TREE_TYPE (stub);
2595 if (TYPE_NAME (typ))
2597 /* If types have same representation, and same name (ignoring
2598 casing), then ignore the second type. */
2599 if (type_name (typ) == type_name (TREE_TYPE (t))
2600 || !strcasecmp (type_name (typ), type_name (TREE_TYPE (t))))
2605 if (RECORD_OR_UNION_TYPE_P (typ) && !TYPE_FIELDS (typ))
2607 pp_string (buffer, "-- skipped empty struct ");
2608 dump_generic_ada_node (buffer, t, type, spc, false, true);
2612 if (!TREE_VISITED (stub)
2613 && DECL_SOURCE_FILE (stub) == source_file_base)
2614 dump_nested_types (buffer, stub, stub, true, spc);
2616 pp_string (buffer, "subtype ");
2617 dump_generic_ada_node (buffer, t, type, spc, false, true);
2618 pp_string (buffer, " is ");
2619 dump_generic_ada_node (buffer, typ, type, spc, false, true);
2620 pp_semicolon (buffer);
2626 /* Skip unnamed or anonymous structs/unions/enum types. */
2627 if (!orig && !decl_name && !name)
2632 if (cpp_check || TREE_CODE (TREE_TYPE (t)) == ENUMERAL_TYPE)
2635 if (RECORD_OR_UNION_TYPE_P (TREE_TYPE (t)))
2637 /* Search next items until finding a named type decl. */
2638 sloc = decl_sloc_common (t, true, true);
2640 for (tmp = TREE_CHAIN (t); tmp; tmp = TREE_CHAIN (tmp))
2642 if (TREE_CODE (tmp) == TYPE_DECL
2643 && (DECL_NAME (tmp) || TYPE_NAME (TREE_TYPE (tmp))))
2645 /* If same sloc, it means we can ignore the anonymous
2647 if (decl_sloc_common (tmp, true, true) == sloc)
2659 && TREE_CODE (TREE_TYPE (t)) == ENUMERAL_TYPE
2661 && (*IDENTIFIER_POINTER (decl_name) == '.'
2662 || *IDENTIFIER_POINTER (decl_name) == '$'))
2663 /* Skip anonymous enum types (duplicates of real types). */
2668 switch (TREE_CODE (TREE_TYPE (t)))
2672 case QUAL_UNION_TYPE:
2673 /* Skip empty structs (typically forward references to real
2675 if (!TYPE_FIELDS (TREE_TYPE (t)))
2677 pp_string (buffer, "-- skipped empty struct ");
2678 dump_generic_ada_node (buffer, t, type, spc, false, true);
2683 && (*IDENTIFIER_POINTER (decl_name) == '.'
2684 || *IDENTIFIER_POINTER (decl_name) == '$'))
2686 pp_string (buffer, "-- skipped anonymous struct ");
2687 dump_generic_ada_node (buffer, t, type, spc, false, true);
2688 TREE_VISITED (t) = 1;
2692 if (orig && TYPE_NAME (orig) && orig != TREE_TYPE (t))
2693 pp_string (buffer, "subtype ");
2696 dump_nested_types (buffer, t, t, false, spc);
2698 if (separate_class_package (t))
2701 pp_string (buffer, "package Class_");
2702 dump_generic_ada_node (buffer, t, type, spc, false, true);
2703 pp_string (buffer, " is");
2705 newline_and_indent (buffer, spc);
2708 pp_string (buffer, "type ");
2714 case REFERENCE_TYPE:
2715 if ((orig && TYPE_NAME (orig) && orig != TREE_TYPE (t))
2716 || is_char_array (t))
2717 pp_string (buffer, "subtype ");
2719 pp_string (buffer, "type ");
2723 pp_string (buffer, "-- skipped function type ");
2724 dump_generic_ada_node (buffer, t, type, spc, false, true);
2729 if ((orig && TYPE_NAME (orig) && orig != TREE_TYPE (t))
2730 || !is_simple_enum (TREE_TYPE (t)))
2731 pp_string (buffer, "subtype ");
2733 pp_string (buffer, "type ");
2737 pp_string (buffer, "subtype ");
2739 TREE_VISITED (t) = 1;
2743 if (TREE_CODE (t) == VAR_DECL
2745 && *IDENTIFIER_POINTER (decl_name) == '_')
2751 /* Print the type and name. */
2752 if (TREE_CODE (TREE_TYPE (t)) == ARRAY_TYPE)
2757 /* Print variable's name. */
2758 dump_generic_ada_node (buffer, t, type, spc, false, true);
2760 if (TREE_CODE (t) == TYPE_DECL)
2762 pp_string (buffer, " is ");
2764 if (orig && TYPE_NAME (orig) && orig != TREE_TYPE (t))
2765 dump_generic_ada_node
2766 (buffer, TYPE_NAME (orig), type, spc, false, true);
2768 dump_ada_array_type (buffer, t, spc);
2772 tree tmp = TYPE_NAME (TREE_TYPE (t));
2774 if (spc == INDENT_INCR || TREE_STATIC (t))
2777 pp_string (buffer, " : ");
2781 if (TREE_CODE (TREE_TYPE (tmp)) != POINTER_TYPE
2782 && TREE_CODE (tmp) != INTEGER_TYPE)
2783 pp_string (buffer, "aliased ");
2785 dump_generic_ada_node (buffer, tmp, type, spc, false, true);
2789 pp_string (buffer, "aliased ");
2792 dump_ada_array_type (buffer, t, spc);
2794 dump_ada_double_name (buffer, type, t, "_array");
2798 else if (TREE_CODE (t) == FUNCTION_DECL)
2800 bool is_function, is_abstract_class = false;
2801 bool is_method = TREE_CODE (TREE_TYPE (t)) == METHOD_TYPE;
2802 tree decl_name = DECL_NAME (t);
2803 int prev_in_function = in_function;
2804 bool is_abstract = false;
2805 bool is_constructor = false;
2806 bool is_destructor = false;
2807 bool is_copy_constructor = false;
2814 is_abstract = cpp_check (t, IS_ABSTRACT);
2815 is_constructor = cpp_check (t, IS_CONSTRUCTOR);
2816 is_destructor = cpp_check (t, IS_DESTRUCTOR);
2817 is_copy_constructor = cpp_check (t, IS_COPY_CONSTRUCTOR);
2820 /* Skip copy constructors: some are internal only, and those that are
2821 not cannot be called easily from Ada anyway. */
2822 if (is_copy_constructor)
2825 if (is_constructor || is_destructor)
2827 /* Only consider constructors/destructors for complete objects. */
2828 if (strncmp (IDENTIFIER_POINTER (decl_name), "__comp", 6) != 0)
2832 /* If this function has an entry in the vtable, we cannot omit it. */
2833 else if (!DECL_VINDEX (t) && *IDENTIFIER_POINTER (decl_name) == '_')
2836 pp_string (buffer, "-- skipped func ");
2837 pp_string (buffer, IDENTIFIER_POINTER (decl_name));
2844 if (VOID_TYPE_P (TREE_TYPE (TREE_TYPE (t))) && !is_constructor)
2846 pp_string (buffer, "procedure ");
2847 is_function = false;
2851 pp_string (buffer, "function ");
2855 in_function = is_function;
2858 print_constructor (buffer, t);
2859 else if (is_destructor)
2860 print_destructor (buffer, t);
2862 dump_ada_decl_name (buffer, t, false);
2864 dump_ada_function_declaration
2865 (buffer, t, is_method, is_constructor, is_destructor, spc);
2866 in_function = prev_in_function;
2870 pp_string (buffer, " return ");
2872 = is_constructor ? DECL_CONTEXT (t) : TREE_TYPE (TREE_TYPE (t));
2873 dump_generic_ada_node (buffer, ret_type, type, spc, false, true);
2877 && RECORD_OR_UNION_TYPE_P (type)
2878 && TYPE_METHODS (type))
2882 for (tmp = TYPE_METHODS (type); tmp; tmp = TREE_CHAIN (tmp))
2883 if (cpp_check (tmp, IS_ABSTRACT))
2885 is_abstract_class = true;
2890 if (is_abstract || is_abstract_class)
2891 pp_string (buffer, " is abstract");
2893 pp_semicolon (buffer);
2894 pp_string (buffer, " -- ");
2895 dump_sloc (buffer, t);
2897 if (is_abstract || !DECL_ASSEMBLER_NAME (t))
2900 newline_and_indent (buffer, spc);
2904 pp_string (buffer, "pragma CPP_Constructor (");
2905 print_constructor (buffer, t);
2906 pp_string (buffer, ", \"");
2907 pp_asm_name (buffer, t);
2908 pp_string (buffer, "\");");
2910 else if (is_destructor)
2912 pp_string (buffer, "pragma Import (CPP, ");
2913 print_destructor (buffer, t);
2914 pp_string (buffer, ", \"");
2915 pp_asm_name (buffer, t);
2916 pp_string (buffer, "\");");
2920 dump_ada_import (buffer, t);
2925 else if (TREE_CODE (t) == TYPE_DECL && !DECL_ORIGINAL_TYPE (t))
2927 int is_interface = 0;
2928 int is_abstract_record = 0;
2933 /* Anonymous structs/unions */
2934 dump_generic_ada_node (buffer, TREE_TYPE (t), t, spc, false, true);
2936 if (TREE_CODE (TREE_TYPE (t)) == UNION_TYPE
2937 || TREE_CODE (TREE_TYPE (t)) == QUAL_UNION_TYPE)
2939 pp_string (buffer, " (discr : unsigned := 0)");
2942 pp_string (buffer, " is ");
2944 /* Check whether we have an Ada interface compatible class. */
2946 && RECORD_OR_UNION_TYPE_P (TREE_TYPE (t))
2947 && TYPE_METHODS (TREE_TYPE (t)))
2952 /* Check that there are no fields other than the virtual table. */
2953 for (tmp = TYPE_FIELDS (TREE_TYPE (t)); tmp; tmp = TREE_CHAIN (tmp))
2955 if (TREE_CODE (tmp) == TYPE_DECL)
2960 if (num_fields == 1)
2963 /* Also check that there are only virtual methods. */
2964 for (tmp = TYPE_METHODS (TREE_TYPE (t)); tmp; tmp = TREE_CHAIN (tmp))
2966 if (cpp_check (tmp, IS_ABSTRACT))
2967 is_abstract_record = 1;
2973 TREE_VISITED (t) = 1;
2976 pp_string (buffer, "limited interface; -- ");
2977 dump_sloc (buffer, t);
2978 newline_and_indent (buffer, spc);
2979 pp_string (buffer, "pragma Import (CPP, ");
2980 dump_generic_ada_node
2981 (buffer, TYPE_NAME (TREE_TYPE (t)), type, spc, false, true);
2982 pp_right_paren (buffer);
2984 print_ada_methods (buffer, TREE_TYPE (t), spc);
2988 if (is_abstract_record)
2989 pp_string (buffer, "abstract ");
2990 dump_generic_ada_node (buffer, t, t, spc, false, false);
2998 if (TREE_CODE (t) == FIELD_DECL && DECL_NAME (t))
2999 check_name (buffer, t);
3001 /* Print variable/type's name. */
3002 dump_generic_ada_node (buffer, t, t, spc, false, true);
3004 if (TREE_CODE (t) == TYPE_DECL)
3006 tree orig = DECL_ORIGINAL_TYPE (t);
3007 int is_subtype = orig && TYPE_NAME (orig) && orig != TREE_TYPE (t);
3010 && (TREE_CODE (TREE_TYPE (t)) == UNION_TYPE
3011 || TREE_CODE (TREE_TYPE (t)) == QUAL_UNION_TYPE))
3012 pp_string (buffer, " (discr : unsigned := 0)");
3014 pp_string (buffer, " is ");
3016 dump_generic_ada_node (buffer, orig, t, spc, false, is_subtype);
3020 if (spc == INDENT_INCR || TREE_STATIC (t))
3023 pp_string (buffer, " : ");
3025 /* Print type declaration. */
3027 if (TREE_CODE (TREE_TYPE (t)) == UNION_TYPE
3028 && !TYPE_NAME (TREE_TYPE (t)))
3030 dump_ada_double_name (buffer, type, t, "_union");
3032 else if (RECORD_OR_UNION_TYPE_P (TREE_TYPE (t)))
3034 if (TREE_CODE (TREE_TYPE (t)) == RECORD_TYPE)
3035 pp_string (buffer, "aliased ");
3037 dump_generic_ada_node
3038 (buffer, TREE_TYPE (t), t, spc, false, true);
3042 if (TREE_CODE (TREE_TYPE (t)) != POINTER_TYPE
3043 && (TYPE_NAME (TREE_TYPE (t))
3044 || TREE_CODE (TREE_TYPE (t)) != INTEGER_TYPE))
3045 pp_string (buffer, "aliased ");
3047 dump_generic_ada_node
3048 (buffer, TREE_TYPE (t), TREE_TYPE (t), spc, false, true);
3056 newline_and_indent (buffer, spc);
3057 pp_string (buffer, "end;");
3058 newline_and_indent (buffer, spc);
3059 pp_string (buffer, "use Class_");
3060 dump_generic_ada_node (buffer, t, type, spc, false, true);
3061 pp_semicolon (buffer);
3062 pp_newline (buffer);
3064 /* All needed indentation/newline performed already, so return 0. */
3069 pp_string (buffer, "; -- ");
3070 dump_sloc (buffer, t);
3075 newline_and_indent (buffer, spc);
3076 dump_ada_import (buffer, t);
3082 /* Prints in BUFFER a structure NODE of type TYPE: name, fields, and methods
3083 with Ada syntax. SPC is the indentation level. If DISPLAY_CONVENTION is
3084 true, also print the pragma Convention for NODE. */
3087 print_ada_struct_decl (pretty_printer *buffer, tree node, tree type, int spc,
3088 bool display_convention)
3092 = TREE_CODE (node) == UNION_TYPE || TREE_CODE (node) == QUAL_UNION_TYPE;
3095 int field_spc = spc + INDENT_INCR;
3098 bitfield_used = false;
3100 if (!TYPE_FIELDS (node))
3101 pp_string (buffer, "null record;");
3104 pp_string (buffer, "record");
3106 /* Print the contents of the structure. */
3110 newline_and_indent (buffer, spc + INDENT_INCR);
3111 pp_string (buffer, "case discr is");
3112 field_spc = spc + INDENT_INCR * 3;
3115 pp_newline (buffer);
3117 /* Print the non-static fields of the structure. */
3118 for (tmp = TYPE_FIELDS (node); tmp; tmp = TREE_CHAIN (tmp))
3120 /* Add parent field if needed. */
3121 if (!DECL_NAME (tmp))
3123 if (!is_tagged_type (TREE_TYPE (tmp)))
3125 if (!TYPE_NAME (TREE_TYPE (tmp)))
3126 print_ada_declaration (buffer, tmp, type, field_spc);
3132 pp_string (buffer, "parent : aliased ");
3135 sprintf (buf, "field_%d : aliased ", field_num + 1);
3136 pp_string (buffer, buf);
3139 (buffer, TYPE_NAME (TREE_TYPE (tmp)), false);
3140 pp_semicolon (buffer);
3142 pp_newline (buffer);
3146 /* Avoid printing the structure recursively. */
3147 else if ((TREE_TYPE (tmp) != node
3148 || (TREE_CODE (TREE_TYPE (tmp)) == POINTER_TYPE
3149 && TREE_TYPE (TREE_TYPE (tmp)) != node))
3150 && TREE_CODE (tmp) != TYPE_DECL
3151 && !TREE_STATIC (tmp))
3153 /* Skip internal virtual table field. */
3154 if (strncmp (IDENTIFIER_POINTER (DECL_NAME (tmp)), "_vptr", 5))
3158 if (TREE_CHAIN (tmp)
3159 && TREE_TYPE (TREE_CHAIN (tmp)) != node
3160 && TREE_CODE (TREE_CHAIN (tmp)) != TYPE_DECL)
3161 sprintf (buf, "when %d =>", field_num);
3163 sprintf (buf, "when others =>");
3165 INDENT (spc + INDENT_INCR * 2);
3166 pp_string (buffer, buf);
3167 pp_newline (buffer);
3170 if (print_ada_declaration (buffer, tmp, type, field_spc))
3172 pp_newline (buffer);
3181 INDENT (spc + INDENT_INCR);
3182 pp_string (buffer, "end case;");
3183 pp_newline (buffer);
3188 INDENT (spc + INDENT_INCR);
3189 pp_string (buffer, "null;");
3190 pp_newline (buffer);
3194 pp_string (buffer, "end record;");
3197 newline_and_indent (buffer, spc);
3199 if (!display_convention)
3202 if (RECORD_OR_UNION_TYPE_P (TREE_TYPE (type)))
3204 if (has_nontrivial_methods (TREE_TYPE (type)))
3205 pp_string (buffer, "pragma Import (CPP, ");
3207 pp_string (buffer, "pragma Convention (C_Pass_By_Copy, ");
3210 pp_string (buffer, "pragma Convention (C, ");
3212 package_prefix = false;
3213 dump_generic_ada_node (buffer, TREE_TYPE (type), type, spc, false, true);
3214 package_prefix = true;
3215 pp_right_paren (buffer);
3219 pp_semicolon (buffer);
3220 newline_and_indent (buffer, spc);
3221 pp_string (buffer, "pragma Unchecked_Union (");
3223 dump_generic_ada_node (buffer, TREE_TYPE (type), type, spc, false, true);
3224 pp_right_paren (buffer);
3229 pp_semicolon (buffer);
3230 newline_and_indent (buffer, spc);
3231 pp_string (buffer, "pragma Pack (");
3232 dump_generic_ada_node
3233 (buffer, TREE_TYPE (type), type, spc, false, true);
3234 pp_right_paren (buffer);
3235 bitfield_used = false;
3238 need_semicolon = !print_ada_methods (buffer, node, spc);
3240 /* Print the static fields of the structure, if any. */
3241 for (tmp = TYPE_FIELDS (node); tmp; tmp = TREE_CHAIN (tmp))
3243 if (DECL_NAME (tmp) && TREE_STATIC (tmp))
3247 need_semicolon = false;
3248 pp_semicolon (buffer);
3250 pp_newline (buffer);
3251 pp_newline (buffer);
3252 print_ada_declaration (buffer, tmp, type, spc);
3257 /* Dump all the declarations in SOURCE_FILE to an Ada spec.
3258 COLLECT_ALL_REFS is a front-end callback used to collect all relevant
3259 nodes for SOURCE_FILE. CHECK is used to perform C++ queries on nodes. */
3262 dump_ads (const char *source_file,
3263 void (*collect_all_refs)(const char *),
3264 int (*check)(tree, cpp_operation))
3271 pkg_name = get_ada_package (source_file);
3273 /* Construct the .ads filename and package name. */
3274 ads_name = xstrdup (pkg_name);
3276 for (s = ads_name; *s; s++)
3282 ads_name = reconcat (ads_name, ads_name, ".ads", NULL);
3284 /* Write out the .ads file. */
3285 f = fopen (ads_name, "w");
3290 pp_needs_newline (&pp) = true;
3291 pp.buffer->stream = f;
3293 /* Dump all relevant macros. */
3294 dump_ada_macros (&pp, source_file);
3296 /* Reset the table of withs for this file. */
3299 (*collect_all_refs) (source_file);
3301 /* Dump all references. */
3303 dump_ada_nodes (&pp, source_file);
3305 /* Requires Ada 2005 syntax, so generate corresponding pragma.
3306 Also, disable style checks since this file is auto-generated. */
3307 fprintf (f, "pragma Ada_2005;\npragma Style_Checks (Off);\n\n");
3312 fprintf (f, "\npackage %s is\n\n", pkg_name);
3313 pp_write_text_to_stream (&pp);
3314 /* ??? need to free pp */
3315 fprintf (f, "end %s;\n", pkg_name);
3323 static const char **source_refs = NULL;
3324 static int source_refs_used = 0;
3325 static int source_refs_allocd = 0;
3327 /* Add an entry for FILENAME to the table SOURCE_REFS. */
3330 collect_source_ref (const char *filename)
3337 if (source_refs_allocd == 0)
3339 source_refs_allocd = 1024;
3340 source_refs = XNEWVEC (const char *, source_refs_allocd);
3343 for (i = 0; i < source_refs_used; i++)
3344 if (filename == source_refs[i])
3347 if (source_refs_used == source_refs_allocd)
3349 source_refs_allocd *= 2;
3350 source_refs = XRESIZEVEC (const char *, source_refs, source_refs_allocd);
3353 source_refs[source_refs_used++] = filename;
3356 /* Main entry point: dump all Ada specs corresponding to SOURCE_REFS
3357 using callbacks COLLECT_ALL_REFS and CHECK.
3358 COLLECT_ALL_REFS is a front-end callback used to collect all relevant
3359 nodes for a given source file.
3360 CHECK is used to perform C++ queries on nodes, or NULL for the C
3364 dump_ada_specs (void (*collect_all_refs)(const char *),
3365 int (*check)(tree, cpp_operation))
3369 /* Iterate over the list of files to dump specs for */
3370 for (i = 0; i < source_refs_used; i++)
3371 dump_ads (source_refs[i], collect_all_refs, check);
3373 /* Free files table. */