PR libgomp/25884
[official-gcc.git] / gcc / tree-pretty-print.c
blobb23416df306cc20f6cf0454db2fa334a1dce2061
1 /* Pretty formatting of GENERIC trees in C syntax.
2 Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006
3 Free Software Foundation, Inc.
4 Adapted from c-pretty-print.c by Diego Novillo <dnovillo@redhat.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 2, or (at your option) any later
11 version.
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
16 for more details.
18 You should have received a copy of the GNU General Public License
19 along with GCC; see the file COPYING. If not, write to the Free
20 Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
21 02110-1301, USA. */
23 #include "config.h"
24 #include "system.h"
25 #include "coretypes.h"
26 #include "tm.h"
27 #include "tree.h"
28 #include "diagnostic.h"
29 #include "real.h"
30 #include "hashtab.h"
31 #include "tree-flow.h"
32 #include "langhooks.h"
33 #include "tree-iterator.h"
34 #include "tree-chrec.h"
35 #include "tree-pass.h"
37 /* Local functions, macros and variables. */
38 static int op_prio (tree);
39 static const char *op_symbol_1 (enum tree_code);
40 static const char *op_symbol (tree);
41 static void pretty_print_string (pretty_printer *, const char*);
42 static void print_call_name (pretty_printer *, tree);
43 static void newline_and_indent (pretty_printer *, int);
44 static void maybe_init_pretty_print (FILE *);
45 static void print_declaration (pretty_printer *, tree, int, int);
46 static void print_struct_decl (pretty_printer *, tree, int, int);
47 static void do_niy (pretty_printer *, tree);
48 static void dump_vops (pretty_printer *, tree, int, int);
49 static void dump_generic_bb_buff (pretty_printer *, basic_block, int, int);
51 #define INDENT(SPACE) do { \
52 int i; for (i = 0; i<SPACE; i++) pp_space (buffer); } while (0)
54 #define NIY do_niy(buffer,node)
56 #define PRINT_FUNCTION_NAME(NODE) pp_printf \
57 (buffer, "%s", TREE_CODE (NODE) == NOP_EXPR ? \
58 lang_hooks.decl_printable_name (TREE_OPERAND (NODE, 0), 1) : \
59 lang_hooks.decl_printable_name (NODE, 1))
61 static pretty_printer buffer;
62 static int initialized = 0;
64 /* Try to print something for an unknown tree code. */
66 static void
67 do_niy (pretty_printer *buffer, tree node)
69 int i, len;
71 pp_string (buffer, "<<< Unknown tree: ");
72 pp_string (buffer, tree_code_name[(int) TREE_CODE (node)]);
74 if (EXPR_P (node))
76 len = TREE_CODE_LENGTH (TREE_CODE (node));
77 for (i = 0; i < len; ++i)
79 newline_and_indent (buffer, 2);
80 dump_generic_node (buffer, TREE_OPERAND (node, i), 2, 0, false);
84 pp_string (buffer, " >>>\n");
87 void
88 debug_generic_expr (tree t)
90 print_generic_expr (stderr, t, TDF_VOPS|TDF_UID);
91 fprintf (stderr, "\n");
94 void
95 debug_generic_stmt (tree t)
97 print_generic_stmt (stderr, t, TDF_VOPS|TDF_UID);
98 fprintf (stderr, "\n");
101 void
102 debug_tree_chain (tree t)
104 print_generic_expr (stderr, t, TDF_VOPS|TDF_UID|TDF_CHAIN);
105 fprintf (stderr, "\n");
108 /* Prints declaration DECL to the FILE with details specified by FLAGS. */
109 void
110 print_generic_decl (FILE *file, tree decl, int flags)
112 maybe_init_pretty_print (file);
113 print_declaration (&buffer, decl, 2, flags);
114 pp_write_text_to_stream (&buffer);
117 /* Print tree T, and its successors, on file FILE. FLAGS specifies details
118 to show in the dump. See TDF_* in tree.h. */
120 void
121 print_generic_stmt (FILE *file, tree t, int flags)
123 maybe_init_pretty_print (file);
124 dump_generic_node (&buffer, t, 0, flags, true);
125 pp_flush (&buffer);
128 /* Print tree T, and its successors, on file FILE. FLAGS specifies details
129 to show in the dump. See TDF_* in tree.h. The output is indented by
130 INDENT spaces. */
132 void
133 print_generic_stmt_indented (FILE *file, tree t, int flags, int indent)
135 int i;
137 maybe_init_pretty_print (file);
139 for (i = 0; i < indent; i++)
140 pp_space (&buffer);
141 dump_generic_node (&buffer, t, indent, flags, true);
142 pp_flush (&buffer);
145 /* Print a single expression T on file FILE. FLAGS specifies details to show
146 in the dump. See TDF_* in tree.h. */
148 void
149 print_generic_expr (FILE *file, tree t, int flags)
151 maybe_init_pretty_print (file);
152 dump_generic_node (&buffer, t, 0, flags, false);
155 /* Dump the name of a _DECL node and its DECL_UID if TDF_UID is set
156 in FLAGS. */
158 static void
159 dump_decl_name (pretty_printer *buffer, tree node, int flags)
161 tree t = node;
163 while (t)
165 if (DECL_NAME (t))
166 pp_tree_identifier (buffer, DECL_NAME (t));
168 if ((flags & TDF_UID)
169 || DECL_NAME (t) == NULL_TREE)
171 if (TREE_CODE (t) == LABEL_DECL
172 && LABEL_DECL_UID (t) != -1)
173 pp_printf (buffer, "L." HOST_WIDE_INT_PRINT_DEC,
174 LABEL_DECL_UID (t));
175 else
177 char c = TREE_CODE (t) == CONST_DECL ? 'C' : 'D';
178 pp_printf (buffer, "%c.%u", c, DECL_UID (t));
182 if (flags & TDF_CHAIN)
184 t = TREE_CHAIN (t);
185 pp_string (buffer, " ");
187 else
188 t = NULL_TREE;
192 /* Like the above, but used for pretty printing function calls. */
194 static void
195 dump_function_name (pretty_printer *buffer, tree node)
197 if (DECL_NAME (node))
198 PRINT_FUNCTION_NAME (node);
199 else
200 dump_decl_name (buffer, node, 0);
203 /* Dump a function declaration. NODE is the FUNCTION_TYPE. BUFFER, SPC and
204 FLAGS are as in dump_generic_node. */
206 static void
207 dump_function_declaration (pretty_printer *buffer, tree node,
208 int spc, int flags)
210 bool wrote_arg = false;
211 tree arg;
213 pp_space (buffer);
214 pp_character (buffer, '(');
216 /* Print the argument types. The last element in the list is a VOID_TYPE.
217 The following avoids printing the last element. */
218 arg = TYPE_ARG_TYPES (node);
219 while (arg && TREE_CHAIN (arg) && arg != error_mark_node)
221 wrote_arg = true;
222 dump_generic_node (buffer, TREE_VALUE (arg), spc, flags, false);
223 arg = TREE_CHAIN (arg);
224 if (TREE_CHAIN (arg) && TREE_CODE (TREE_CHAIN (arg)) == TREE_LIST)
226 pp_character (buffer, ',');
227 pp_space (buffer);
231 if (!wrote_arg)
232 pp_string (buffer, "void");
234 pp_character (buffer, ')');
237 /* Dump the domain associated with an array. */
239 static void
240 dump_array_domain (pretty_printer *buffer, tree domain, int spc, int flags)
242 pp_character (buffer, '[');
243 if (domain)
245 tree min = TYPE_MIN_VALUE (domain);
246 tree max = TYPE_MAX_VALUE (domain);
248 if (min && max
249 && integer_zerop (min)
250 && host_integerp (max, 0))
251 pp_wide_integer (buffer, TREE_INT_CST_LOW (max) + 1);
252 else
254 if (min)
255 dump_generic_node (buffer, min, spc, flags, false);
256 pp_character (buffer, ':');
257 if (max)
258 dump_generic_node (buffer, max, spc, flags, false);
261 else
262 pp_string (buffer, "<unknown>");
263 pp_character (buffer, ']');
266 /* Dump the list of OpenMP clauses. */
268 static void
269 dump_omp_clauses (pretty_printer *buffer, tree clause, int spc, int flags)
271 const char *name;
273 if (clause == NULL)
274 return;
276 pp_space (buffer);
277 while (1)
279 switch (TREE_CODE (clause))
281 case OMP_CLAUSE_PRIVATE:
282 name = "private";
283 goto print_remap;
284 case OMP_CLAUSE_SHARED:
285 name = "shared";
286 goto print_remap;
287 case OMP_CLAUSE_FIRSTPRIVATE:
288 name = "firstprivate";
289 goto print_remap;
290 case OMP_CLAUSE_LASTPRIVATE:
291 name = "lastprivate";
292 goto print_remap;
293 case OMP_CLAUSE_COPYIN:
294 name = "copyin";
295 goto print_remap;
296 case OMP_CLAUSE_COPYPRIVATE:
297 name = "copyprivate";
298 goto print_remap;
299 print_remap:
300 pp_string (buffer, name);
301 pp_character (buffer, '(');
302 dump_generic_node (buffer, OMP_CLAUSE_DECL (clause),
303 spc, flags, false);
304 pp_character (buffer, ')');
305 break;
307 case OMP_CLAUSE_REDUCTION:
308 pp_string (buffer, "reduction(");
309 pp_string (buffer, op_symbol_1 (OMP_CLAUSE_REDUCTION_CODE (clause)));
310 pp_character (buffer, ':');
311 dump_generic_node (buffer, OMP_CLAUSE_DECL (clause),
312 spc, flags, false);
313 pp_character (buffer, ')');
314 break;
316 case OMP_CLAUSE_IF:
317 pp_string (buffer, "if(");
318 dump_generic_node (buffer, OMP_CLAUSE_IF_EXPR (clause),
319 spc, flags, false);
320 pp_character (buffer, ')');
321 break;
323 case OMP_CLAUSE_NUM_THREADS:
324 pp_string (buffer, "num_threads(");
325 dump_generic_node (buffer, OMP_CLAUSE_NUM_THREADS_EXPR (clause),
326 spc, flags, false);
327 pp_character (buffer, ')');
328 break;
330 case OMP_CLAUSE_NOWAIT:
331 pp_string (buffer, "nowait");
332 break;
333 case OMP_CLAUSE_ORDERED:
334 pp_string (buffer, "ordered");
335 break;
337 case OMP_CLAUSE_DEFAULT:
338 pp_string (buffer, "default(");
339 switch (OMP_CLAUSE_DEFAULT_KIND (clause))
341 case OMP_CLAUSE_DEFAULT_UNSPECIFIED:
342 break;
343 case OMP_CLAUSE_DEFAULT_SHARED:
344 pp_string (buffer, "shared");
345 break;
346 case OMP_CLAUSE_DEFAULT_NONE:
347 pp_string (buffer, "none");
348 break;
349 case OMP_CLAUSE_DEFAULT_PRIVATE:
350 pp_string (buffer, "private");
351 break;
352 default:
353 gcc_unreachable ();
355 pp_character (buffer, ')');
356 break;
358 case OMP_CLAUSE_SCHEDULE:
359 pp_string (buffer, "schedule(");
360 switch (OMP_CLAUSE_SCHEDULE_KIND (clause))
362 case OMP_CLAUSE_SCHEDULE_STATIC:
363 pp_string (buffer, "static");
364 break;
365 case OMP_CLAUSE_SCHEDULE_DYNAMIC:
366 pp_string (buffer, "dynamic");
367 break;
368 case OMP_CLAUSE_SCHEDULE_GUIDED:
369 pp_string (buffer, "guided");
370 break;
371 case OMP_CLAUSE_SCHEDULE_RUNTIME:
372 pp_string (buffer, "runtime");
373 break;
374 default:
375 gcc_unreachable ();
377 if (OMP_CLAUSE_SCHEDULE_CHUNK_EXPR (clause))
379 pp_character (buffer, ',');
380 dump_generic_node (buffer,
381 OMP_CLAUSE_SCHEDULE_CHUNK_EXPR (clause),
382 spc, flags, false);
384 pp_character (buffer, ')');
385 break;
387 default:
388 /* Should never happen. */
389 dump_generic_node (buffer, clause, spc, flags, false);
390 break;
393 clause = OMP_CLAUSE_CHAIN (clause);
394 if (clause == NULL)
395 return;
396 pp_space (buffer);
400 /* Dump the node NODE on the pretty_printer BUFFER, SPC spaces of indent.
401 FLAGS specifies details to show in the dump (see TDF_* in tree.h). If
402 IS_STMT is true, the object printed is considered to be a statement
403 and it is terminated by ';' if appropriate. */
406 dump_generic_node (pretty_printer *buffer, tree node, int spc, int flags,
407 bool is_stmt)
409 tree type;
410 tree op0, op1;
411 const char *str;
412 bool is_expr;
414 if (node == NULL_TREE)
415 return spc;
417 is_expr = EXPR_P (node);
419 if (TREE_CODE (node) != ERROR_MARK
420 && is_gimple_stmt (node)
421 && (flags & TDF_VOPS)
422 && stmt_ann (node)
423 && TREE_CODE (node) != PHI_NODE)
424 dump_vops (buffer, node, spc, flags);
426 if (is_stmt && (flags & TDF_STMTADDR))
427 pp_printf (buffer, "<&%p> ", (void *)node);
429 if ((flags & TDF_LINENO) && EXPR_HAS_LOCATION (node))
431 expanded_location xloc = expand_location (EXPR_LOCATION (node));
432 pp_character (buffer, '[');
433 if (xloc.file)
435 pp_string (buffer, xloc.file);
436 pp_string (buffer, " : ");
438 pp_decimal_int (buffer, xloc.line);
439 pp_string (buffer, "] ");
442 switch (TREE_CODE (node))
444 case ERROR_MARK:
445 pp_string (buffer, "<<< error >>>");
446 break;
448 case IDENTIFIER_NODE:
449 pp_tree_identifier (buffer, node);
450 break;
452 case TREE_LIST:
453 while (node && node != error_mark_node)
455 if (TREE_PURPOSE (node))
457 dump_generic_node (buffer, TREE_PURPOSE (node), spc, flags, false);
458 pp_space (buffer);
460 dump_generic_node (buffer, TREE_VALUE (node), spc, flags, false);
461 node = TREE_CHAIN (node);
462 if (node && TREE_CODE (node) == TREE_LIST)
464 pp_character (buffer, ',');
465 pp_space (buffer);
468 break;
470 case TREE_BINFO:
471 dump_generic_node (buffer, BINFO_TYPE (node), spc, flags, false);
473 case TREE_VEC:
475 size_t i;
476 if (TREE_VEC_LENGTH (node) > 0)
478 size_t len = TREE_VEC_LENGTH (node);
479 for (i = 0; i < len - 1; i++)
481 dump_generic_node (buffer, TREE_VEC_ELT (node, i), spc, flags,
482 false);
483 pp_character (buffer, ',');
484 pp_space (buffer);
486 dump_generic_node (buffer, TREE_VEC_ELT (node, len - 1), spc,
487 flags, false);
490 break;
492 case VOID_TYPE:
493 case INTEGER_TYPE:
494 case REAL_TYPE:
495 case COMPLEX_TYPE:
496 case VECTOR_TYPE:
497 case ENUMERAL_TYPE:
498 case BOOLEAN_TYPE:
499 case CHAR_TYPE:
501 unsigned int quals = TYPE_QUALS (node);
502 enum tree_code_class class;
504 if (quals & TYPE_QUAL_CONST)
505 pp_string (buffer, "const ");
506 else if (quals & TYPE_QUAL_VOLATILE)
507 pp_string (buffer, "volatile ");
508 else if (quals & TYPE_QUAL_RESTRICT)
509 pp_string (buffer, "restrict ");
511 class = TREE_CODE_CLASS (TREE_CODE (node));
513 if (class == tcc_declaration)
515 if (DECL_NAME (node))
516 dump_decl_name (buffer, node, flags);
517 else
518 pp_string (buffer, "<unnamed type decl>");
520 else if (class == tcc_type)
522 if (TYPE_NAME (node))
524 if (TREE_CODE (TYPE_NAME (node)) == IDENTIFIER_NODE)
525 pp_tree_identifier (buffer, TYPE_NAME (node));
526 else if (TREE_CODE (TYPE_NAME (node)) == TYPE_DECL
527 && DECL_NAME (TYPE_NAME (node)))
528 dump_decl_name (buffer, TYPE_NAME (node), flags);
529 else
530 pp_string (buffer, "<unnamed type>");
532 else if (TREE_CODE (node) == VECTOR_TYPE)
534 pp_string (buffer, "vector ");
535 dump_generic_node (buffer, TREE_TYPE (node),
536 spc, flags, false);
538 else
539 pp_string (buffer, "<unnamed type>");
541 break;
544 case POINTER_TYPE:
545 case REFERENCE_TYPE:
546 str = (TREE_CODE (node) == POINTER_TYPE ? "*" : "&");
548 if (TREE_CODE (TREE_TYPE (node)) == FUNCTION_TYPE)
550 tree fnode = TREE_TYPE (node);
552 dump_generic_node (buffer, TREE_TYPE (fnode), spc, flags, false);
553 pp_space (buffer);
554 pp_character (buffer, '(');
555 pp_string (buffer, str);
556 if (TYPE_NAME (node) && DECL_NAME (TYPE_NAME (node)))
557 dump_decl_name (buffer, TYPE_NAME (node), flags);
558 else
559 pp_printf (buffer, "<T%x>", TYPE_UID (node));
561 pp_character (buffer, ')');
562 dump_function_declaration (buffer, fnode, spc, flags);
564 else
566 unsigned int quals = TYPE_QUALS (node);
568 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
569 pp_space (buffer);
570 pp_string (buffer, str);
572 if (quals & TYPE_QUAL_CONST)
573 pp_string (buffer, " const");
574 else if (quals & TYPE_QUAL_VOLATILE)
575 pp_string (buffer, "volatile");
576 else if (quals & TYPE_QUAL_RESTRICT)
577 pp_string (buffer, " restrict");
579 if (TYPE_REF_CAN_ALIAS_ALL (node))
580 pp_string (buffer, " {ref-all}");
582 break;
584 case OFFSET_TYPE:
585 NIY;
586 break;
588 case METHOD_TYPE:
589 dump_decl_name (buffer, TYPE_NAME (TYPE_METHOD_BASETYPE (node)), flags);
590 pp_string (buffer, "::");
591 break;
593 case TARGET_MEM_REF:
595 const char *sep = "";
596 tree tmp;
598 pp_string (buffer, "MEM[");
600 tmp = TMR_SYMBOL (node);
601 if (tmp)
603 pp_string (buffer, sep);
604 sep = ", ";
605 pp_string (buffer, "symbol: ");
606 dump_generic_node (buffer, tmp, spc, flags, false);
608 tmp = TMR_BASE (node);
609 if (tmp)
611 pp_string (buffer, sep);
612 sep = ", ";
613 pp_string (buffer, "base: ");
614 dump_generic_node (buffer, tmp, spc, flags, false);
616 tmp = TMR_INDEX (node);
617 if (tmp)
619 pp_string (buffer, sep);
620 sep = ", ";
621 pp_string (buffer, "index: ");
622 dump_generic_node (buffer, tmp, spc, flags, false);
624 tmp = TMR_STEP (node);
625 if (tmp)
627 pp_string (buffer, sep);
628 sep = ", ";
629 pp_string (buffer, "step: ");
630 dump_generic_node (buffer, tmp, spc, flags, false);
632 tmp = TMR_OFFSET (node);
633 if (tmp)
635 pp_string (buffer, sep);
636 sep = ", ";
637 pp_string (buffer, "offset: ");
638 dump_generic_node (buffer, tmp, spc, flags, false);
640 pp_string (buffer, "]");
641 if (flags & TDF_DETAILS)
643 pp_string (buffer, "{");
644 dump_generic_node (buffer, TMR_ORIGINAL (node), spc, flags,
645 false);
646 pp_string (buffer, "}");
649 break;
651 case ARRAY_TYPE:
653 tree tmp;
655 /* Print the innermost component type. */
656 for (tmp = TREE_TYPE (node); TREE_CODE (tmp) == ARRAY_TYPE;
657 tmp = TREE_TYPE (tmp))
659 dump_generic_node (buffer, tmp, spc, flags, false);
661 /* Print the dimensions. */
662 for (tmp = node; TREE_CODE (tmp) == ARRAY_TYPE; tmp = TREE_TYPE (tmp))
663 dump_array_domain (buffer, TYPE_DOMAIN (tmp), spc, flags);
664 break;
667 case RECORD_TYPE:
668 case UNION_TYPE:
669 case QUAL_UNION_TYPE:
670 /* Print the name of the structure. */
671 if (TREE_CODE (node) == RECORD_TYPE)
672 pp_string (buffer, "struct ");
673 else if (TREE_CODE (node) == UNION_TYPE)
674 pp_string (buffer, "union ");
676 if (TYPE_NAME (node))
677 dump_generic_node (buffer, TYPE_NAME (node), spc, flags, false);
678 else
679 print_struct_decl (buffer, node, spc, flags);
680 break;
682 case LANG_TYPE:
683 NIY;
684 break;
686 case INTEGER_CST:
687 if (TREE_CODE (TREE_TYPE (node)) == POINTER_TYPE)
689 /* In the case of a pointer, one may want to divide by the
690 size of the pointed-to type. Unfortunately, this not
691 straightforward. The C front-end maps expressions
693 (int *) 5
694 int *p; (p + 5)
696 in such a way that the two INTEGER_CST nodes for "5" have
697 different values but identical types. In the latter
698 case, the 5 is multiplied by sizeof (int) in c-common.c
699 (pointer_int_sum) to convert it to a byte address, and
700 yet the type of the node is left unchanged. Argh. What
701 is consistent though is that the number value corresponds
702 to bytes (UNITS) offset.
704 NB: Neither of the following divisors can be trivially
705 used to recover the original literal:
707 TREE_INT_CST_LOW (TYPE_SIZE_UNIT (TREE_TYPE (node)))
708 TYPE_PRECISION (TREE_TYPE (TREE_TYPE (node))) */
709 pp_wide_integer (buffer, TREE_INT_CST_LOW (node));
710 pp_string (buffer, "B"); /* pseudo-unit */
712 else if (! host_integerp (node, 0))
714 tree val = node;
716 if (tree_int_cst_sgn (val) < 0)
718 pp_character (buffer, '-');
719 val = build_int_cst_wide (NULL_TREE,
720 -TREE_INT_CST_LOW (val),
721 ~TREE_INT_CST_HIGH (val)
722 + !TREE_INT_CST_LOW (val));
724 /* Would "%x%0*x" or "%x%*0x" get zero-padding on all
725 systems? */
727 static char format[10]; /* "%x%09999x\0" */
728 if (!format[0])
729 sprintf (format, "%%x%%0%dx", HOST_BITS_PER_INT / 4);
730 sprintf (pp_buffer (buffer)->digit_buffer, format,
731 TREE_INT_CST_HIGH (val),
732 TREE_INT_CST_LOW (val));
733 pp_string (buffer, pp_buffer (buffer)->digit_buffer);
736 else
737 pp_wide_integer (buffer, TREE_INT_CST_LOW (node));
738 break;
740 case REAL_CST:
741 /* Code copied from print_node. */
743 REAL_VALUE_TYPE d;
744 if (TREE_OVERFLOW (node))
745 pp_string (buffer, " overflow");
747 #if !defined(REAL_IS_NOT_DOUBLE) || defined(REAL_ARITHMETIC)
748 d = TREE_REAL_CST (node);
749 if (REAL_VALUE_ISINF (d))
750 pp_string (buffer, " Inf");
751 else if (REAL_VALUE_ISNAN (d))
752 pp_string (buffer, " Nan");
753 else
755 char string[100];
756 real_to_decimal (string, &d, sizeof (string), 0, 1);
757 pp_string (buffer, string);
759 #else
761 HOST_WIDE_INT i;
762 unsigned char *p = (unsigned char *) &TREE_REAL_CST (node);
763 pp_string (buffer, "0x");
764 for (i = 0; i < sizeof TREE_REAL_CST (node); i++)
765 output_formatted_integer (buffer, "%02x", *p++);
767 #endif
768 break;
771 case COMPLEX_CST:
772 pp_string (buffer, "__complex__ (");
773 dump_generic_node (buffer, TREE_REALPART (node), spc, flags, false);
774 pp_string (buffer, ", ");
775 dump_generic_node (buffer, TREE_IMAGPART (node), spc, flags, false);
776 pp_string (buffer, ")");
777 break;
779 case STRING_CST:
780 pp_string (buffer, "\"");
781 pretty_print_string (buffer, TREE_STRING_POINTER (node));
782 pp_string (buffer, "\"");
783 break;
785 case VECTOR_CST:
787 tree elt;
788 pp_string (buffer, "{ ");
789 for (elt = TREE_VECTOR_CST_ELTS (node); elt; elt = TREE_CHAIN (elt))
791 dump_generic_node (buffer, TREE_VALUE (elt), spc, flags, false);
792 if (TREE_CHAIN (elt))
793 pp_string (buffer, ", ");
795 pp_string (buffer, " }");
797 break;
799 case FUNCTION_TYPE:
800 break;
802 case FUNCTION_DECL:
803 case CONST_DECL:
804 dump_decl_name (buffer, node, flags);
805 break;
807 case LABEL_DECL:
808 if (DECL_NAME (node))
809 dump_decl_name (buffer, node, flags);
810 else if (LABEL_DECL_UID (node) != -1)
811 pp_printf (buffer, "<L" HOST_WIDE_INT_PRINT_DEC ">",
812 LABEL_DECL_UID (node));
813 else
814 pp_printf (buffer, "<D%u>", DECL_UID (node));
815 break;
817 case TYPE_DECL:
818 if (DECL_IS_BUILTIN (node))
820 /* Don't print the declaration of built-in types. */
821 break;
823 if (DECL_NAME (node))
824 dump_decl_name (buffer, node, flags);
825 else
827 if ((TREE_CODE (TREE_TYPE (node)) == RECORD_TYPE
828 || TREE_CODE (TREE_TYPE (node)) == UNION_TYPE)
829 && TYPE_METHODS (TREE_TYPE (node)))
831 /* The type is a c++ class: all structures have at least
832 4 methods. */
833 pp_string (buffer, "class ");
834 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
836 else
838 pp_string (buffer,
839 (TREE_CODE (TREE_TYPE (node)) == UNION_TYPE
840 ? "union" : "struct "));
841 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
844 break;
846 case TYPE_MEMORY_TAG:
847 case NAME_MEMORY_TAG:
848 case STRUCT_FIELD_TAG:
849 case VAR_DECL:
850 case PARM_DECL:
851 case FIELD_DECL:
852 case NAMESPACE_DECL:
853 dump_decl_name (buffer, node, flags);
854 break;
856 case RESULT_DECL:
857 pp_string (buffer, "<retval>");
858 break;
860 case COMPONENT_REF:
861 op0 = TREE_OPERAND (node, 0);
862 str = ".";
863 if (TREE_CODE (op0) == INDIRECT_REF)
865 op0 = TREE_OPERAND (op0, 0);
866 str = "->";
868 if (op_prio (op0) < op_prio (node))
869 pp_character (buffer, '(');
870 dump_generic_node (buffer, op0, spc, flags, false);
871 if (op_prio (op0) < op_prio (node))
872 pp_character (buffer, ')');
873 pp_string (buffer, str);
874 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
876 if (TREE_CODE (op0) != VALUE_HANDLE)
878 op0 = component_ref_field_offset (node);
879 if (op0 && TREE_CODE (op0) != INTEGER_CST)
881 pp_string (buffer, "{off: ");
882 dump_generic_node (buffer, op0, spc, flags, false);
883 pp_character (buffer, '}');
886 break;
888 case BIT_FIELD_REF:
889 pp_string (buffer, "BIT_FIELD_REF <");
890 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
891 pp_string (buffer, ", ");
892 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
893 pp_string (buffer, ", ");
894 dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
895 pp_string (buffer, ">");
896 break;
898 case ARRAY_REF:
899 case ARRAY_RANGE_REF:
900 op0 = TREE_OPERAND (node, 0);
901 if (op_prio (op0) < op_prio (node))
902 pp_character (buffer, '(');
903 dump_generic_node (buffer, op0, spc, flags, false);
904 if (op_prio (op0) < op_prio (node))
905 pp_character (buffer, ')');
906 pp_character (buffer, '[');
907 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
908 if (TREE_CODE (node) == ARRAY_RANGE_REF)
909 pp_string (buffer, " ...");
910 pp_character (buffer, ']');
912 op0 = array_ref_low_bound (node);
913 op1 = array_ref_element_size (node);
915 if (!integer_zerop (op0)
916 || (TYPE_SIZE_UNIT (TREE_TYPE (node))
917 && !operand_equal_p (op1, TYPE_SIZE_UNIT (TREE_TYPE (node)), 0)))
919 pp_string (buffer, "{lb: ");
920 dump_generic_node (buffer, op0, spc, flags, false);
921 pp_string (buffer, " sz: ");
922 dump_generic_node (buffer, op1, spc, flags, false);
923 pp_character (buffer, '}');
925 break;
927 case CONSTRUCTOR:
929 unsigned HOST_WIDE_INT ix;
930 tree field, val;
931 bool is_struct_init = FALSE;
932 pp_character (buffer, '{');
933 if (TREE_CODE (TREE_TYPE (node)) == RECORD_TYPE
934 || TREE_CODE (TREE_TYPE (node)) == UNION_TYPE)
935 is_struct_init = TRUE;
936 FOR_EACH_CONSTRUCTOR_ELT (CONSTRUCTOR_ELTS (node), ix, field, val)
938 if (field && is_struct_init)
940 pp_character (buffer, '.');
941 dump_generic_node (buffer, field, spc, flags, false);
942 pp_string (buffer, "=");
944 if (val && TREE_CODE (val) == ADDR_EXPR)
945 if (TREE_CODE (TREE_OPERAND (val, 0)) == FUNCTION_DECL)
946 val = TREE_OPERAND (val, 0);
947 if (val && TREE_CODE (val) == FUNCTION_DECL)
948 dump_decl_name (buffer, val, flags);
949 else
950 dump_generic_node (buffer, val, spc, flags, false);
951 if (ix != VEC_length (constructor_elt, CONSTRUCTOR_ELTS (node)) - 1)
953 pp_character (buffer, ',');
954 pp_space (buffer);
957 pp_character (buffer, '}');
959 break;
961 case COMPOUND_EXPR:
963 tree *tp;
964 if (flags & TDF_SLIM)
966 pp_string (buffer, "<COMPOUND_EXPR>");
967 break;
970 dump_generic_node (buffer, TREE_OPERAND (node, 0),
971 spc, flags, !(flags & TDF_SLIM));
972 if (flags & TDF_SLIM)
973 newline_and_indent (buffer, spc);
974 else
976 pp_character (buffer, ',');
977 pp_space (buffer);
980 for (tp = &TREE_OPERAND (node, 1);
981 TREE_CODE (*tp) == COMPOUND_EXPR;
982 tp = &TREE_OPERAND (*tp, 1))
984 dump_generic_node (buffer, TREE_OPERAND (*tp, 0),
985 spc, flags, !(flags & TDF_SLIM));
986 if (flags & TDF_SLIM)
987 newline_and_indent (buffer, spc);
988 else
990 pp_character (buffer, ',');
991 pp_space (buffer);
995 dump_generic_node (buffer, *tp, spc, flags, !(flags & TDF_SLIM));
997 break;
999 case STATEMENT_LIST:
1001 tree_stmt_iterator si;
1002 bool first = true;
1004 if (flags & TDF_SLIM)
1006 pp_string (buffer, "<STATEMENT_LIST>");
1007 break;
1010 for (si = tsi_start (node); !tsi_end_p (si); tsi_next (&si))
1012 if (!first)
1013 newline_and_indent (buffer, spc);
1014 else
1015 first = false;
1016 dump_generic_node (buffer, tsi_stmt (si), spc, flags, true);
1019 break;
1021 case MODIFY_EXPR:
1022 case INIT_EXPR:
1023 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1024 pp_space (buffer);
1025 pp_character (buffer, '=');
1026 pp_space (buffer);
1027 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1028 break;
1030 case TARGET_EXPR:
1031 pp_string (buffer, "TARGET_EXPR <");
1032 dump_generic_node (buffer, TARGET_EXPR_SLOT (node), spc, flags, false);
1033 pp_character (buffer, ',');
1034 pp_space (buffer);
1035 dump_generic_node (buffer, TARGET_EXPR_INITIAL (node), spc, flags, false);
1036 pp_character (buffer, '>');
1037 break;
1039 case DECL_EXPR:
1040 print_declaration (buffer, DECL_EXPR_DECL (node), spc, flags);
1041 is_stmt = false;
1042 break;
1044 case COND_EXPR:
1045 if (TREE_TYPE (node) == NULL || TREE_TYPE (node) == void_type_node)
1047 pp_string (buffer, "if (");
1048 dump_generic_node (buffer, COND_EXPR_COND (node), spc, flags, false);
1049 pp_character (buffer, ')');
1050 /* The lowered cond_exprs should always be printed in full. */
1051 if (COND_EXPR_THEN (node)
1052 && (IS_EMPTY_STMT (COND_EXPR_THEN (node))
1053 || TREE_CODE (COND_EXPR_THEN (node)) == GOTO_EXPR)
1054 && COND_EXPR_ELSE (node)
1055 && (IS_EMPTY_STMT (COND_EXPR_ELSE (node))
1056 || TREE_CODE (COND_EXPR_ELSE (node)) == GOTO_EXPR))
1058 pp_space (buffer);
1059 dump_generic_node (buffer, COND_EXPR_THEN (node), 0, flags, true);
1060 pp_string (buffer, " else ");
1061 dump_generic_node (buffer, COND_EXPR_ELSE (node), 0, flags, true);
1063 else if (!(flags & TDF_SLIM))
1065 /* Output COND_EXPR_THEN. */
1066 if (COND_EXPR_THEN (node))
1068 newline_and_indent (buffer, spc+2);
1069 pp_character (buffer, '{');
1070 newline_and_indent (buffer, spc+4);
1071 dump_generic_node (buffer, COND_EXPR_THEN (node), spc+4,
1072 flags, true);
1073 newline_and_indent (buffer, spc+2);
1074 pp_character (buffer, '}');
1077 /* Output COND_EXPR_ELSE. */
1078 if (COND_EXPR_ELSE (node))
1080 newline_and_indent (buffer, spc);
1081 pp_string (buffer, "else");
1082 newline_and_indent (buffer, spc+2);
1083 pp_character (buffer, '{');
1084 newline_and_indent (buffer, spc+4);
1085 dump_generic_node (buffer, COND_EXPR_ELSE (node), spc+4,
1086 flags, true);
1087 newline_and_indent (buffer, spc+2);
1088 pp_character (buffer, '}');
1091 is_expr = false;
1093 else
1095 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1096 pp_space (buffer);
1097 pp_character (buffer, '?');
1098 pp_space (buffer);
1099 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1100 pp_space (buffer);
1101 pp_character (buffer, ':');
1102 pp_space (buffer);
1103 dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
1105 break;
1107 case BIND_EXPR:
1108 pp_character (buffer, '{');
1109 if (!(flags & TDF_SLIM))
1111 if (BIND_EXPR_VARS (node))
1113 pp_newline (buffer);
1115 for (op0 = BIND_EXPR_VARS (node); op0; op0 = TREE_CHAIN (op0))
1117 print_declaration (buffer, op0, spc+2, flags);
1118 pp_newline (buffer);
1122 newline_and_indent (buffer, spc+2);
1123 dump_generic_node (buffer, BIND_EXPR_BODY (node), spc+2, flags, true);
1124 newline_and_indent (buffer, spc);
1125 pp_character (buffer, '}');
1127 is_expr = false;
1128 break;
1130 case CALL_EXPR:
1131 print_call_name (buffer, node);
1133 /* Print parameters. */
1134 pp_space (buffer);
1135 pp_character (buffer, '(');
1136 op1 = TREE_OPERAND (node, 1);
1137 if (op1)
1138 dump_generic_node (buffer, op1, spc, flags, false);
1139 pp_character (buffer, ')');
1141 op1 = TREE_OPERAND (node, 2);
1142 if (op1)
1144 pp_string (buffer, " [static-chain: ");
1145 dump_generic_node (buffer, op1, spc, flags, false);
1146 pp_character (buffer, ']');
1149 if (CALL_EXPR_RETURN_SLOT_OPT (node))
1150 pp_string (buffer, " [return slot optimization]");
1151 if (CALL_EXPR_TAILCALL (node))
1152 pp_string (buffer, " [tail call]");
1153 break;
1155 case WITH_CLEANUP_EXPR:
1156 NIY;
1157 break;
1159 case CLEANUP_POINT_EXPR:
1160 pp_string (buffer, "<<cleanup_point ");
1161 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1162 pp_string (buffer, ">>");
1163 break;
1165 case PLACEHOLDER_EXPR:
1166 pp_string (buffer, "<PLACEHOLDER_EXPR ");
1167 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
1168 pp_character (buffer, '>');
1169 break;
1171 /* Binary arithmetic and logic expressions. */
1172 case WIDEN_SUM_EXPR:
1173 case WIDEN_MULT_EXPR:
1174 case MULT_EXPR:
1175 case PLUS_EXPR:
1176 case MINUS_EXPR:
1177 case TRUNC_DIV_EXPR:
1178 case CEIL_DIV_EXPR:
1179 case FLOOR_DIV_EXPR:
1180 case ROUND_DIV_EXPR:
1181 case TRUNC_MOD_EXPR:
1182 case CEIL_MOD_EXPR:
1183 case FLOOR_MOD_EXPR:
1184 case ROUND_MOD_EXPR:
1185 case RDIV_EXPR:
1186 case EXACT_DIV_EXPR:
1187 case LSHIFT_EXPR:
1188 case RSHIFT_EXPR:
1189 case LROTATE_EXPR:
1190 case RROTATE_EXPR:
1191 case VEC_LSHIFT_EXPR:
1192 case VEC_RSHIFT_EXPR:
1193 case BIT_IOR_EXPR:
1194 case BIT_XOR_EXPR:
1195 case BIT_AND_EXPR:
1196 case TRUTH_ANDIF_EXPR:
1197 case TRUTH_ORIF_EXPR:
1198 case TRUTH_AND_EXPR:
1199 case TRUTH_OR_EXPR:
1200 case TRUTH_XOR_EXPR:
1201 case LT_EXPR:
1202 case LE_EXPR:
1203 case GT_EXPR:
1204 case GE_EXPR:
1205 case EQ_EXPR:
1206 case NE_EXPR:
1207 case UNLT_EXPR:
1208 case UNLE_EXPR:
1209 case UNGT_EXPR:
1210 case UNGE_EXPR:
1211 case UNEQ_EXPR:
1212 case LTGT_EXPR:
1213 case ORDERED_EXPR:
1214 case UNORDERED_EXPR:
1216 const char *op = op_symbol (node);
1217 op0 = TREE_OPERAND (node, 0);
1218 op1 = TREE_OPERAND (node, 1);
1220 /* When the operands are expressions with less priority,
1221 keep semantics of the tree representation. */
1222 if (op_prio (op0) < op_prio (node))
1224 pp_character (buffer, '(');
1225 dump_generic_node (buffer, op0, spc, flags, false);
1226 pp_character (buffer, ')');
1228 else
1229 dump_generic_node (buffer, op0, spc, flags, false);
1231 pp_space (buffer);
1232 pp_string (buffer, op);
1233 pp_space (buffer);
1235 /* When the operands are expressions with less priority,
1236 keep semantics of the tree representation. */
1237 if (op_prio (op1) < op_prio (node))
1239 pp_character (buffer, '(');
1240 dump_generic_node (buffer, op1, spc, flags, false);
1241 pp_character (buffer, ')');
1243 else
1244 dump_generic_node (buffer, op1, spc, flags, false);
1246 break;
1248 /* Unary arithmetic and logic expressions. */
1249 case NEGATE_EXPR:
1250 case BIT_NOT_EXPR:
1251 case TRUTH_NOT_EXPR:
1252 case ADDR_EXPR:
1253 case PREDECREMENT_EXPR:
1254 case PREINCREMENT_EXPR:
1255 case ALIGN_INDIRECT_REF:
1256 case MISALIGNED_INDIRECT_REF:
1257 case INDIRECT_REF:
1258 if (TREE_CODE (node) == ADDR_EXPR
1259 && (TREE_CODE (TREE_OPERAND (node, 0)) == STRING_CST
1260 || TREE_CODE (TREE_OPERAND (node, 0)) == FUNCTION_DECL))
1261 ; /* Do not output '&' for strings and function pointers. */
1262 else
1263 pp_string (buffer, op_symbol (node));
1265 if (op_prio (TREE_OPERAND (node, 0)) < op_prio (node))
1267 pp_character (buffer, '(');
1268 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1269 pp_character (buffer, ')');
1271 else
1272 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1274 if (TREE_CODE (node) == MISALIGNED_INDIRECT_REF)
1276 pp_string (buffer, "{misalignment: ");
1277 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1278 pp_character (buffer, '}');
1280 break;
1282 case POSTDECREMENT_EXPR:
1283 case POSTINCREMENT_EXPR:
1284 if (op_prio (TREE_OPERAND (node, 0)) < op_prio (node))
1286 pp_character (buffer, '(');
1287 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1288 pp_character (buffer, ')');
1290 else
1291 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1292 pp_string (buffer, op_symbol (node));
1293 break;
1295 case MIN_EXPR:
1296 pp_string (buffer, "MIN_EXPR <");
1297 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1298 pp_string (buffer, ", ");
1299 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1300 pp_character (buffer, '>');
1301 break;
1303 case MAX_EXPR:
1304 pp_string (buffer, "MAX_EXPR <");
1305 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1306 pp_string (buffer, ", ");
1307 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1308 pp_character (buffer, '>');
1309 break;
1311 case ABS_EXPR:
1312 pp_string (buffer, "ABS_EXPR <");
1313 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1314 pp_character (buffer, '>');
1315 break;
1317 case RANGE_EXPR:
1318 NIY;
1319 break;
1321 case FIX_TRUNC_EXPR:
1322 case FIX_CEIL_EXPR:
1323 case FIX_FLOOR_EXPR:
1324 case FIX_ROUND_EXPR:
1325 case FLOAT_EXPR:
1326 case CONVERT_EXPR:
1327 case NOP_EXPR:
1328 type = TREE_TYPE (node);
1329 op0 = TREE_OPERAND (node, 0);
1330 if (type != TREE_TYPE (op0))
1332 pp_character (buffer, '(');
1333 dump_generic_node (buffer, type, spc, flags, false);
1334 pp_string (buffer, ") ");
1336 if (op_prio (op0) < op_prio (node))
1337 pp_character (buffer, '(');
1338 dump_generic_node (buffer, op0, spc, flags, false);
1339 if (op_prio (op0) < op_prio (node))
1340 pp_character (buffer, ')');
1341 break;
1343 case VIEW_CONVERT_EXPR:
1344 pp_string (buffer, "VIEW_CONVERT_EXPR<");
1345 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
1346 pp_string (buffer, ">(");
1347 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1348 pp_character (buffer, ')');
1349 break;
1351 case NON_LVALUE_EXPR:
1352 pp_string (buffer, "NON_LVALUE_EXPR <");
1353 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1354 pp_character (buffer, '>');
1355 break;
1357 case SAVE_EXPR:
1358 pp_string (buffer, "SAVE_EXPR <");
1359 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1360 pp_character (buffer, '>');
1361 break;
1363 case COMPLEX_EXPR:
1364 pp_string (buffer, "COMPLEX_EXPR <");
1365 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1366 pp_string (buffer, ", ");
1367 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1368 pp_string (buffer, ">");
1369 break;
1371 case CONJ_EXPR:
1372 pp_string (buffer, "CONJ_EXPR <");
1373 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1374 pp_string (buffer, ">");
1375 break;
1377 case REALPART_EXPR:
1378 pp_string (buffer, "REALPART_EXPR <");
1379 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1380 pp_string (buffer, ">");
1381 break;
1383 case IMAGPART_EXPR:
1384 pp_string (buffer, "IMAGPART_EXPR <");
1385 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1386 pp_string (buffer, ">");
1387 break;
1389 case VA_ARG_EXPR:
1390 pp_string (buffer, "VA_ARG_EXPR <");
1391 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1392 pp_string (buffer, ">");
1393 break;
1395 case TRY_FINALLY_EXPR:
1396 case TRY_CATCH_EXPR:
1397 pp_string (buffer, "try");
1398 newline_and_indent (buffer, spc+2);
1399 pp_string (buffer, "{");
1400 newline_and_indent (buffer, spc+4);
1401 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc+4, flags, true);
1402 newline_and_indent (buffer, spc+2);
1403 pp_string (buffer, "}");
1404 newline_and_indent (buffer, spc);
1405 pp_string (buffer,
1406 (TREE_CODE (node) == TRY_CATCH_EXPR) ? "catch" : "finally");
1407 newline_and_indent (buffer, spc+2);
1408 pp_string (buffer, "{");
1409 newline_and_indent (buffer, spc+4);
1410 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc+4, flags, true);
1411 newline_and_indent (buffer, spc+2);
1412 pp_string (buffer, "}");
1413 is_expr = false;
1414 break;
1416 case CATCH_EXPR:
1417 pp_string (buffer, "catch (");
1418 dump_generic_node (buffer, CATCH_TYPES (node), spc+2, flags, false);
1419 pp_string (buffer, ")");
1420 newline_and_indent (buffer, spc+2);
1421 pp_string (buffer, "{");
1422 newline_and_indent (buffer, spc+4);
1423 dump_generic_node (buffer, CATCH_BODY (node), spc+4, flags, true);
1424 newline_and_indent (buffer, spc+2);
1425 pp_string (buffer, "}");
1426 is_expr = false;
1427 break;
1429 case EH_FILTER_EXPR:
1430 pp_string (buffer, "<<<eh_filter (");
1431 dump_generic_node (buffer, EH_FILTER_TYPES (node), spc+2, flags, false);
1432 pp_string (buffer, ")>>>");
1433 newline_and_indent (buffer, spc+2);
1434 pp_string (buffer, "{");
1435 newline_and_indent (buffer, spc+4);
1436 dump_generic_node (buffer, EH_FILTER_FAILURE (node), spc+4, flags, true);
1437 newline_and_indent (buffer, spc+2);
1438 pp_string (buffer, "}");
1439 is_expr = false;
1440 break;
1442 case LABEL_EXPR:
1443 op0 = TREE_OPERAND (node, 0);
1444 /* If this is for break or continue, don't bother printing it. */
1445 if (DECL_NAME (op0))
1447 const char *name = IDENTIFIER_POINTER (DECL_NAME (op0));
1448 if (strcmp (name, "break") == 0
1449 || strcmp (name, "continue") == 0)
1450 break;
1452 dump_generic_node (buffer, op0, spc, flags, false);
1453 pp_character (buffer, ':');
1454 if (DECL_NONLOCAL (op0))
1455 pp_string (buffer, " [non-local]");
1456 break;
1458 case EXC_PTR_EXPR:
1459 pp_string (buffer, "<<<exception object>>>");
1460 break;
1462 case FILTER_EXPR:
1463 pp_string (buffer, "<<<filter object>>>");
1464 break;
1466 case LOOP_EXPR:
1467 pp_string (buffer, "while (1)");
1468 if (!(flags & TDF_SLIM))
1470 newline_and_indent (buffer, spc+2);
1471 pp_character (buffer, '{');
1472 newline_and_indent (buffer, spc+4);
1473 dump_generic_node (buffer, LOOP_EXPR_BODY (node), spc+4, flags, true);
1474 newline_and_indent (buffer, spc+2);
1475 pp_character (buffer, '}');
1477 is_expr = false;
1478 break;
1480 case RETURN_EXPR:
1481 pp_string (buffer, "return");
1482 op0 = TREE_OPERAND (node, 0);
1483 if (op0)
1485 pp_space (buffer);
1486 if (TREE_CODE (op0) == MODIFY_EXPR)
1487 dump_generic_node (buffer, TREE_OPERAND (op0, 1), spc, flags, false);
1488 else
1489 dump_generic_node (buffer, op0, spc, flags, false);
1491 break;
1493 case EXIT_EXPR:
1494 pp_string (buffer, "if (");
1495 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1496 pp_string (buffer, ") break");
1497 break;
1499 case SWITCH_EXPR:
1500 pp_string (buffer, "switch (");
1501 dump_generic_node (buffer, SWITCH_COND (node), spc, flags, false);
1502 pp_character (buffer, ')');
1503 if (!(flags & TDF_SLIM))
1505 newline_and_indent (buffer, spc+2);
1506 pp_character (buffer, '{');
1507 if (SWITCH_BODY (node))
1509 newline_and_indent (buffer, spc+4);
1510 dump_generic_node (buffer, SWITCH_BODY (node), spc+4, flags,
1511 true);
1513 else
1515 tree vec = SWITCH_LABELS (node);
1516 size_t i, n = TREE_VEC_LENGTH (vec);
1517 for (i = 0; i < n; ++i)
1519 tree elt = TREE_VEC_ELT (vec, i);
1520 newline_and_indent (buffer, spc+4);
1521 if (elt)
1523 dump_generic_node (buffer, elt, spc+4, flags, false);
1524 pp_string (buffer, " goto ");
1525 dump_generic_node (buffer, CASE_LABEL (elt), spc+4,
1526 flags, true);
1527 pp_semicolon (buffer);
1529 else
1530 pp_string (buffer, "case ???: goto ???;");
1533 newline_and_indent (buffer, spc+2);
1534 pp_character (buffer, '}');
1536 is_expr = false;
1537 break;
1539 case GOTO_EXPR:
1540 op0 = GOTO_DESTINATION (node);
1541 if (TREE_CODE (op0) != SSA_NAME && DECL_P (op0) && DECL_NAME (op0))
1543 const char *name = IDENTIFIER_POINTER (DECL_NAME (op0));
1544 if (strcmp (name, "break") == 0
1545 || strcmp (name, "continue") == 0)
1547 pp_string (buffer, name);
1548 break;
1551 pp_string (buffer, "goto ");
1552 dump_generic_node (buffer, op0, spc, flags, false);
1553 break;
1555 case RESX_EXPR:
1556 pp_string (buffer, "resx");
1557 /* ??? Any sensible way to present the eh region? */
1558 break;
1560 case ASM_EXPR:
1561 pp_string (buffer, "__asm__");
1562 if (ASM_VOLATILE_P (node))
1563 pp_string (buffer, " __volatile__");
1564 pp_character (buffer, '(');
1565 dump_generic_node (buffer, ASM_STRING (node), spc, flags, false);
1566 pp_character (buffer, ':');
1567 dump_generic_node (buffer, ASM_OUTPUTS (node), spc, flags, false);
1568 pp_character (buffer, ':');
1569 dump_generic_node (buffer, ASM_INPUTS (node), spc, flags, false);
1570 if (ASM_CLOBBERS (node))
1572 pp_character (buffer, ':');
1573 dump_generic_node (buffer, ASM_CLOBBERS (node), spc, flags, false);
1575 pp_string (buffer, ")");
1576 break;
1578 case CASE_LABEL_EXPR:
1579 if (CASE_LOW (node) && CASE_HIGH (node))
1581 pp_string (buffer, "case ");
1582 dump_generic_node (buffer, CASE_LOW (node), spc, flags, false);
1583 pp_string (buffer, " ... ");
1584 dump_generic_node (buffer, CASE_HIGH (node), spc, flags, false);
1586 else if (CASE_LOW (node))
1588 pp_string (buffer, "case ");
1589 dump_generic_node (buffer, CASE_LOW (node), spc, flags, false);
1591 else
1592 pp_string (buffer, "default ");
1593 pp_character (buffer, ':');
1594 break;
1596 case OBJ_TYPE_REF:
1597 pp_string (buffer, "OBJ_TYPE_REF(");
1598 dump_generic_node (buffer, OBJ_TYPE_REF_EXPR (node), spc, flags, false);
1599 pp_character (buffer, ';');
1600 dump_generic_node (buffer, OBJ_TYPE_REF_OBJECT (node), spc, flags, false);
1601 pp_character (buffer, '-');
1602 pp_character (buffer, '>');
1603 dump_generic_node (buffer, OBJ_TYPE_REF_TOKEN (node), spc, flags, false);
1604 pp_character (buffer, ')');
1605 break;
1607 case PHI_NODE:
1609 int i;
1611 dump_generic_node (buffer, PHI_RESULT (node), spc, flags, false);
1612 pp_string (buffer, " = PHI <");
1613 for (i = 0; i < PHI_NUM_ARGS (node); i++)
1615 dump_generic_node (buffer, PHI_ARG_DEF (node, i), spc, flags, false);
1616 pp_string (buffer, "(");
1617 pp_decimal_int (buffer, PHI_ARG_EDGE (node, i)->src->index);
1618 pp_string (buffer, ")");
1619 if (i < PHI_NUM_ARGS (node) - 1)
1620 pp_string (buffer, ", ");
1622 pp_string (buffer, ">;");
1624 break;
1626 case SSA_NAME:
1627 dump_generic_node (buffer, SSA_NAME_VAR (node), spc, flags, false);
1628 pp_string (buffer, "_");
1629 pp_decimal_int (buffer, SSA_NAME_VERSION (node));
1630 if (SSA_NAME_OCCURS_IN_ABNORMAL_PHI (node))
1631 pp_string (buffer, "(ab)");
1632 break;
1634 case WITH_SIZE_EXPR:
1635 pp_string (buffer, "WITH_SIZE_EXPR <");
1636 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1637 pp_string (buffer, ", ");
1638 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1639 pp_string (buffer, ">");
1640 break;
1642 case VALUE_HANDLE:
1643 pp_printf (buffer, "VH.%d", VALUE_HANDLE_ID (node));
1644 break;
1646 case ASSERT_EXPR:
1647 pp_string (buffer, "ASSERT_EXPR <");
1648 dump_generic_node (buffer, ASSERT_EXPR_VAR (node), spc, flags, false);
1649 pp_string (buffer, ", ");
1650 dump_generic_node (buffer, ASSERT_EXPR_COND (node), spc, flags, false);
1651 pp_string (buffer, ">");
1652 break;
1654 case SCEV_KNOWN:
1655 pp_string (buffer, "scev_known");
1656 break;
1658 case SCEV_NOT_KNOWN:
1659 pp_string (buffer, "scev_not_known");
1660 break;
1662 case POLYNOMIAL_CHREC:
1663 pp_string (buffer, "{");
1664 dump_generic_node (buffer, CHREC_LEFT (node), spc, flags, false);
1665 pp_string (buffer, ", +, ");
1666 dump_generic_node (buffer, CHREC_RIGHT (node), spc, flags, false);
1667 pp_string (buffer, "}_");
1668 dump_generic_node (buffer, CHREC_VAR (node), spc, flags, false);
1669 is_stmt = false;
1670 break;
1672 case REALIGN_LOAD_EXPR:
1673 pp_string (buffer, "REALIGN_LOAD <");
1674 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1675 pp_string (buffer, ", ");
1676 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1677 pp_string (buffer, ", ");
1678 dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
1679 pp_string (buffer, ">");
1680 break;
1682 case VEC_COND_EXPR:
1683 pp_string (buffer, " VEC_COND_EXPR < ");
1684 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1685 pp_string (buffer, " , ");
1686 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1687 pp_string (buffer, " , ");
1688 dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
1689 pp_string (buffer, " > ");
1690 break;
1692 case DOT_PROD_EXPR:
1693 pp_string (buffer, " DOT_PROD_EXPR < ");
1694 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1695 pp_string (buffer, " , ");
1696 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1697 pp_string (buffer, " , ");
1698 dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
1699 pp_string (buffer, " > ");
1700 break;
1702 case OMP_PARALLEL:
1703 pp_string (buffer, "#pragma omp parallel");
1704 dump_omp_clauses (buffer, OMP_PARALLEL_CLAUSES (node), spc, flags);
1705 if (OMP_PARALLEL_FN (node))
1707 pp_string (buffer, " [child fn: ");
1708 dump_generic_node (buffer, OMP_PARALLEL_FN (node), spc, flags, false);
1710 pp_string (buffer, " (");
1712 if (OMP_PARALLEL_DATA_ARG (node))
1713 dump_generic_node (buffer, OMP_PARALLEL_DATA_ARG (node), spc, flags,
1714 false);
1715 else
1716 pp_string (buffer, "???");
1718 pp_string (buffer, ")]");
1721 dump_omp_body:
1722 if (!(flags & TDF_SLIM) && OMP_BODY (node))
1724 newline_and_indent (buffer, spc + 2);
1725 pp_character (buffer, '{');
1726 newline_and_indent (buffer, spc + 4);
1727 dump_generic_node (buffer, OMP_BODY (node), spc + 4, flags, false);
1728 newline_and_indent (buffer, spc + 2);
1729 pp_character (buffer, '}');
1731 is_expr = false;
1732 break;
1734 case OMP_FOR:
1735 pp_string (buffer, "#pragma omp for");
1736 dump_omp_clauses (buffer, OMP_FOR_CLAUSES (node), spc, flags);
1738 if (!(flags & TDF_SLIM))
1740 if (OMP_FOR_PRE_BODY (node))
1742 newline_and_indent (buffer, spc + 2);
1743 pp_character (buffer, '{');
1744 spc += 4;
1745 newline_and_indent (buffer, spc);
1746 dump_generic_node (buffer, OMP_FOR_PRE_BODY (node),
1747 spc, flags, false);
1749 newline_and_indent (buffer, spc);
1750 pp_string (buffer, "for (");
1751 dump_generic_node (buffer, OMP_FOR_INIT (node), spc, flags, false);
1752 pp_string (buffer, "; ");
1753 dump_generic_node (buffer, OMP_FOR_COND (node), spc, flags, false);
1754 pp_string (buffer, "; ");
1755 dump_generic_node (buffer, OMP_FOR_INCR (node), spc, flags, false);
1756 pp_string (buffer, ")");
1757 if (OMP_FOR_BODY (node))
1759 newline_and_indent (buffer, spc + 2);
1760 pp_character (buffer, '{');
1761 newline_and_indent (buffer, spc + 4);
1762 dump_generic_node (buffer, OMP_FOR_BODY (node), spc + 4, flags,
1763 false);
1764 newline_and_indent (buffer, spc + 2);
1765 pp_character (buffer, '}');
1767 if (OMP_FOR_PRE_BODY (node))
1769 spc -= 4;
1770 newline_and_indent (buffer, spc + 2);
1771 pp_character (buffer, '}');
1774 is_expr = false;
1775 break;
1777 case OMP_SECTIONS:
1778 pp_string (buffer, "#pragma omp sections");
1779 dump_omp_clauses (buffer, OMP_SECTIONS_CLAUSES (node), spc, flags);
1780 goto dump_omp_body;
1782 case OMP_SECTION:
1783 pp_string (buffer, "#pragma omp section");
1784 goto dump_omp_body;
1786 case OMP_MASTER:
1787 pp_string (buffer, "#pragma omp master");
1788 goto dump_omp_body;
1790 case OMP_ORDERED:
1791 pp_string (buffer, "#pragma omp ordered");
1792 goto dump_omp_body;
1794 case OMP_CRITICAL:
1795 pp_string (buffer, "#pragma omp critical");
1796 if (OMP_CRITICAL_NAME (node))
1798 pp_space (buffer);
1799 pp_character (buffer, '(');
1800 dump_generic_node (buffer, OMP_CRITICAL_NAME (node), spc,
1801 flags, false);
1802 pp_character (buffer, ')');
1804 goto dump_omp_body;
1806 case OMP_ATOMIC:
1807 pp_string (buffer, "#pragma omp atomic");
1808 newline_and_indent (buffer, spc + 2);
1809 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1810 pp_space (buffer);
1811 pp_character (buffer, '=');
1812 pp_space (buffer);
1813 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1814 break;
1816 case OMP_SINGLE:
1817 pp_string (buffer, "#pragma omp single");
1818 dump_omp_clauses (buffer, OMP_SINGLE_CLAUSES (node), spc, flags);
1819 goto dump_omp_body;
1821 case OMP_RETURN_EXPR:
1822 pp_string (buffer, "OMP_RETURN");
1823 is_expr = false;
1824 break;
1826 case REDUC_MAX_EXPR:
1827 pp_string (buffer, " REDUC_MAX_EXPR < ");
1828 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1829 pp_string (buffer, " > ");
1830 break;
1832 case REDUC_MIN_EXPR:
1833 pp_string (buffer, " REDUC_MIN_EXPR < ");
1834 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1835 pp_string (buffer, " > ");
1836 break;
1838 case REDUC_PLUS_EXPR:
1839 pp_string (buffer, " REDUC_PLUS_EXPR < ");
1840 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1841 pp_string (buffer, " > ");
1842 break;
1844 case BLOCK:
1846 tree t;
1847 pp_string (buffer, "BLOCK");
1849 if (BLOCK_ABSTRACT (node))
1850 pp_string (buffer, " [abstract]");
1852 if (TREE_ASM_WRITTEN (node))
1853 pp_string (buffer, " [written]");
1855 newline_and_indent (buffer, spc + 2);
1857 if (BLOCK_SUPERCONTEXT (node))
1859 pp_string (buffer, "SUPERCONTEXT: ");
1860 if (TREE_CODE (BLOCK_SUPERCONTEXT (node)) == BLOCK)
1861 pp_printf (buffer, "BLOCK %p",
1862 (void *)BLOCK_SUPERCONTEXT (node));
1863 else
1864 dump_generic_node (buffer, BLOCK_SUPERCONTEXT (node), 0, flags,
1865 false);
1866 newline_and_indent (buffer, spc + 2);
1869 if (BLOCK_SUBBLOCKS (node))
1871 pp_string (buffer, "SUBBLOCKS: ");
1872 for (t = BLOCK_SUBBLOCKS (node); t; t = BLOCK_CHAIN (t))
1873 pp_printf (buffer, "%p ", (void *)t);
1874 newline_and_indent (buffer, spc + 2);
1877 if (BLOCK_VARS (node))
1879 pp_string (buffer, "VARS: ");
1880 for (t = BLOCK_VARS (node); t; t = TREE_CHAIN (t))
1882 dump_generic_node (buffer, t, 0, flags, false);
1883 pp_string (buffer, " ");
1885 newline_and_indent (buffer, spc + 2);
1888 if (BLOCK_ABSTRACT_ORIGIN (node))
1890 pp_string (buffer, "ABSTRACT_ORIGIN: ");
1891 if (TREE_CODE (BLOCK_ABSTRACT_ORIGIN (node)) == BLOCK)
1892 pp_printf (buffer, "BLOCK %p",
1893 (void *)BLOCK_ABSTRACT_ORIGIN (node));
1894 else
1895 dump_generic_node (buffer, BLOCK_ABSTRACT_ORIGIN (node), 0, flags,
1896 false);
1897 newline_and_indent (buffer, spc + 2);
1900 break;
1902 default:
1903 NIY;
1906 if (is_stmt && is_expr)
1907 pp_semicolon (buffer);
1908 pp_write_text_to_stream (buffer);
1910 return spc;
1913 /* Print the declaration of a variable. */
1915 static void
1916 print_declaration (pretty_printer *buffer, tree t, int spc, int flags)
1918 INDENT (spc);
1920 if (TREE_CODE (t) == TYPE_DECL)
1921 pp_string (buffer, "typedef ");
1923 if (CODE_CONTAINS_STRUCT (TREE_CODE (t), TS_DECL_WRTL) && DECL_REGISTER (t))
1924 pp_string (buffer, "register ");
1926 if (TREE_PUBLIC (t) && DECL_EXTERNAL (t))
1927 pp_string (buffer, "extern ");
1928 else if (TREE_STATIC (t))
1929 pp_string (buffer, "static ");
1931 /* Print the type and name. */
1932 if (TREE_CODE (TREE_TYPE (t)) == ARRAY_TYPE)
1934 tree tmp;
1936 /* Print array's type. */
1937 tmp = TREE_TYPE (t);
1938 while (TREE_CODE (TREE_TYPE (tmp)) == ARRAY_TYPE)
1939 tmp = TREE_TYPE (tmp);
1940 dump_generic_node (buffer, TREE_TYPE (tmp), spc, flags, false);
1942 /* Print variable's name. */
1943 pp_space (buffer);
1944 dump_generic_node (buffer, t, spc, flags, false);
1946 /* Print the dimensions. */
1947 tmp = TREE_TYPE (t);
1948 while (TREE_CODE (tmp) == ARRAY_TYPE)
1950 dump_array_domain (buffer, TYPE_DOMAIN (tmp), spc, flags);
1951 tmp = TREE_TYPE (tmp);
1954 else if (TREE_CODE (t) == FUNCTION_DECL)
1956 dump_generic_node (buffer, TREE_TYPE (TREE_TYPE (t)), spc, flags, false);
1957 pp_space (buffer);
1958 dump_decl_name (buffer, t, flags);
1959 dump_function_declaration (buffer, TREE_TYPE (t), spc, flags);
1961 else
1963 /* Print type declaration. */
1964 dump_generic_node (buffer, TREE_TYPE (t), spc, flags, false);
1966 /* Print variable's name. */
1967 pp_space (buffer);
1968 dump_generic_node (buffer, t, spc, flags, false);
1971 if (TREE_CODE (t) == VAR_DECL && DECL_HARD_REGISTER (t))
1973 pp_string (buffer, " __asm__ ");
1974 pp_character (buffer, '(');
1975 dump_generic_node (buffer, DECL_ASSEMBLER_NAME (t), spc, flags, false);
1976 pp_character (buffer, ')');
1979 /* The initial value of a function serves to determine wether the function
1980 is declared or defined. So the following does not apply to function
1981 nodes. */
1982 if (TREE_CODE (t) != FUNCTION_DECL)
1984 /* Print the initial value. */
1985 if (DECL_INITIAL (t))
1987 pp_space (buffer);
1988 pp_character (buffer, '=');
1989 pp_space (buffer);
1990 dump_generic_node (buffer, DECL_INITIAL (t), spc, flags, false);
1994 if (TREE_CODE (t) == VAR_DECL && DECL_HAS_VALUE_EXPR_P (t))
1996 pp_string (buffer, " [value-expr: ");
1997 dump_generic_node (buffer, DECL_VALUE_EXPR (t), spc, flags, false);
1998 pp_character (buffer, ']');
2001 pp_character (buffer, ';');
2005 /* Prints a structure: name, fields, and methods.
2006 FIXME: Still incomplete. */
2008 static void
2009 print_struct_decl (pretty_printer *buffer, tree node, int spc, int flags)
2011 /* Print the name of the structure. */
2012 if (TYPE_NAME (node))
2014 INDENT (spc);
2015 if (TREE_CODE (node) == RECORD_TYPE)
2016 pp_string (buffer, "struct ");
2017 else if ((TREE_CODE (node) == UNION_TYPE
2018 || TREE_CODE (node) == QUAL_UNION_TYPE))
2019 pp_string (buffer, "union ");
2021 dump_generic_node (buffer, TYPE_NAME (node), spc, 0, false);
2024 /* Print the contents of the structure. */
2025 pp_newline (buffer);
2026 INDENT (spc);
2027 pp_character (buffer, '{');
2028 pp_newline (buffer);
2030 /* Print the fields of the structure. */
2032 tree tmp;
2033 tmp = TYPE_FIELDS (node);
2034 while (tmp)
2036 /* Avoid to print recursively the structure. */
2037 /* FIXME : Not implemented correctly...,
2038 what about the case when we have a cycle in the contain graph? ...
2039 Maybe this could be solved by looking at the scope in which the
2040 structure was declared. */
2041 if (TREE_TYPE (tmp) != node
2042 || (TREE_CODE (TREE_TYPE (tmp)) == POINTER_TYPE
2043 && TREE_TYPE (TREE_TYPE (tmp)) != node))
2045 print_declaration (buffer, tmp, spc+2, flags);
2046 pp_newline (buffer);
2048 tmp = TREE_CHAIN (tmp);
2051 INDENT (spc);
2052 pp_character (buffer, '}');
2055 /* Return the priority of the operator OP.
2057 From lowest to highest precedence with either left-to-right (L-R)
2058 or right-to-left (R-L) associativity]:
2060 1 [L-R] ,
2061 2 [R-L] = += -= *= /= %= &= ^= |= <<= >>=
2062 3 [R-L] ?:
2063 4 [L-R] ||
2064 5 [L-R] &&
2065 6 [L-R] |
2066 7 [L-R] ^
2067 8 [L-R] &
2068 9 [L-R] == !=
2069 10 [L-R] < <= > >=
2070 11 [L-R] << >>
2071 12 [L-R] + -
2072 13 [L-R] * / %
2073 14 [R-L] ! ~ ++ -- + - * & (type) sizeof
2074 15 [L-R] fn() [] -> .
2076 unary +, - and * have higher precedence than the corresponding binary
2077 operators. */
2079 static int
2080 op_prio (tree op)
2082 if (op == NULL)
2083 return 9999;
2085 switch (TREE_CODE (op))
2087 case TREE_LIST:
2088 case COMPOUND_EXPR:
2089 case BIND_EXPR:
2090 return 1;
2092 case MODIFY_EXPR:
2093 case INIT_EXPR:
2094 return 2;
2096 case COND_EXPR:
2097 return 3;
2099 case TRUTH_OR_EXPR:
2100 case TRUTH_ORIF_EXPR:
2101 return 4;
2103 case TRUTH_AND_EXPR:
2104 case TRUTH_ANDIF_EXPR:
2105 return 5;
2107 case BIT_IOR_EXPR:
2108 return 6;
2110 case BIT_XOR_EXPR:
2111 case TRUTH_XOR_EXPR:
2112 return 7;
2114 case BIT_AND_EXPR:
2115 return 8;
2117 case EQ_EXPR:
2118 case NE_EXPR:
2119 return 9;
2121 case UNLT_EXPR:
2122 case UNLE_EXPR:
2123 case UNGT_EXPR:
2124 case UNGE_EXPR:
2125 case UNEQ_EXPR:
2126 case LTGT_EXPR:
2127 case ORDERED_EXPR:
2128 case UNORDERED_EXPR:
2129 case LT_EXPR:
2130 case LE_EXPR:
2131 case GT_EXPR:
2132 case GE_EXPR:
2133 return 10;
2135 case LSHIFT_EXPR:
2136 case RSHIFT_EXPR:
2137 case LROTATE_EXPR:
2138 case RROTATE_EXPR:
2139 return 11;
2141 case WIDEN_SUM_EXPR:
2142 case PLUS_EXPR:
2143 case MINUS_EXPR:
2144 return 12;
2146 case WIDEN_MULT_EXPR:
2147 case DOT_PROD_EXPR:
2148 case MULT_EXPR:
2149 case TRUNC_DIV_EXPR:
2150 case CEIL_DIV_EXPR:
2151 case FLOOR_DIV_EXPR:
2152 case ROUND_DIV_EXPR:
2153 case RDIV_EXPR:
2154 case EXACT_DIV_EXPR:
2155 case TRUNC_MOD_EXPR:
2156 case CEIL_MOD_EXPR:
2157 case FLOOR_MOD_EXPR:
2158 case ROUND_MOD_EXPR:
2159 return 13;
2161 case TRUTH_NOT_EXPR:
2162 case BIT_NOT_EXPR:
2163 case POSTINCREMENT_EXPR:
2164 case POSTDECREMENT_EXPR:
2165 case PREINCREMENT_EXPR:
2166 case PREDECREMENT_EXPR:
2167 case NEGATE_EXPR:
2168 case ALIGN_INDIRECT_REF:
2169 case MISALIGNED_INDIRECT_REF:
2170 case INDIRECT_REF:
2171 case ADDR_EXPR:
2172 case FLOAT_EXPR:
2173 case NOP_EXPR:
2174 case CONVERT_EXPR:
2175 case FIX_TRUNC_EXPR:
2176 case FIX_CEIL_EXPR:
2177 case FIX_FLOOR_EXPR:
2178 case FIX_ROUND_EXPR:
2179 case TARGET_EXPR:
2180 return 14;
2182 case CALL_EXPR:
2183 case ARRAY_REF:
2184 case ARRAY_RANGE_REF:
2185 case COMPONENT_REF:
2186 return 15;
2188 /* Special expressions. */
2189 case MIN_EXPR:
2190 case MAX_EXPR:
2191 case ABS_EXPR:
2192 case REALPART_EXPR:
2193 case IMAGPART_EXPR:
2194 case REDUC_MAX_EXPR:
2195 case REDUC_MIN_EXPR:
2196 case REDUC_PLUS_EXPR:
2197 case VEC_LSHIFT_EXPR:
2198 case VEC_RSHIFT_EXPR:
2199 return 16;
2201 case SAVE_EXPR:
2202 case NON_LVALUE_EXPR:
2203 return op_prio (TREE_OPERAND (op, 0));
2205 default:
2206 /* Return an arbitrarily high precedence to avoid surrounding single
2207 VAR_DECLs in ()s. */
2208 return 9999;
2213 /* Return the symbol associated with operator OP. */
2215 static const char *
2216 op_symbol_1 (enum tree_code code)
2218 switch (code)
2220 case MODIFY_EXPR:
2221 return "=";
2223 case TRUTH_OR_EXPR:
2224 case TRUTH_ORIF_EXPR:
2225 return "||";
2227 case TRUTH_AND_EXPR:
2228 case TRUTH_ANDIF_EXPR:
2229 return "&&";
2231 case BIT_IOR_EXPR:
2232 return "|";
2234 case TRUTH_XOR_EXPR:
2235 case BIT_XOR_EXPR:
2236 return "^";
2238 case ADDR_EXPR:
2239 case BIT_AND_EXPR:
2240 return "&";
2242 case ORDERED_EXPR:
2243 return "ord";
2244 case UNORDERED_EXPR:
2245 return "unord";
2247 case EQ_EXPR:
2248 return "==";
2249 case UNEQ_EXPR:
2250 return "u==";
2252 case NE_EXPR:
2253 return "!=";
2255 case LT_EXPR:
2256 return "<";
2257 case UNLT_EXPR:
2258 return "u<";
2260 case LE_EXPR:
2261 return "<=";
2262 case UNLE_EXPR:
2263 return "u<=";
2265 case GT_EXPR:
2266 return ">";
2267 case UNGT_EXPR:
2268 return "u>";
2270 case GE_EXPR:
2271 return ">=";
2272 case UNGE_EXPR:
2273 return "u>=";
2275 case LTGT_EXPR:
2276 return "<>";
2278 case LSHIFT_EXPR:
2279 return "<<";
2281 case RSHIFT_EXPR:
2282 return ">>";
2284 case LROTATE_EXPR:
2285 return "r<<";
2287 case RROTATE_EXPR:
2288 return "r>>";
2290 case VEC_LSHIFT_EXPR:
2291 return "v<<";
2293 case VEC_RSHIFT_EXPR:
2294 return "v>>";
2296 case PLUS_EXPR:
2297 return "+";
2299 case REDUC_PLUS_EXPR:
2300 return "r+";
2302 case WIDEN_SUM_EXPR:
2303 return "w+";
2305 case WIDEN_MULT_EXPR:
2306 return "w*";
2308 case NEGATE_EXPR:
2309 case MINUS_EXPR:
2310 return "-";
2312 case BIT_NOT_EXPR:
2313 return "~";
2315 case TRUTH_NOT_EXPR:
2316 return "!";
2318 case MULT_EXPR:
2319 case INDIRECT_REF:
2320 return "*";
2322 case ALIGN_INDIRECT_REF:
2323 return "A*";
2325 case MISALIGNED_INDIRECT_REF:
2326 return "M*";
2328 case TRUNC_DIV_EXPR:
2329 case RDIV_EXPR:
2330 return "/";
2332 case CEIL_DIV_EXPR:
2333 return "/[cl]";
2335 case FLOOR_DIV_EXPR:
2336 return "/[fl]";
2338 case ROUND_DIV_EXPR:
2339 return "/[rd]";
2341 case EXACT_DIV_EXPR:
2342 return "/[ex]";
2344 case TRUNC_MOD_EXPR:
2345 return "%";
2347 case CEIL_MOD_EXPR:
2348 return "%[cl]";
2350 case FLOOR_MOD_EXPR:
2351 return "%[fl]";
2353 case ROUND_MOD_EXPR:
2354 return "%[rd]";
2356 case PREDECREMENT_EXPR:
2357 return " --";
2359 case PREINCREMENT_EXPR:
2360 return " ++";
2362 case POSTDECREMENT_EXPR:
2363 return "-- ";
2365 case POSTINCREMENT_EXPR:
2366 return "++ ";
2368 case MAX_EXPR:
2369 return "max";
2371 case MIN_EXPR:
2372 return "min";
2374 default:
2375 return "<<< ??? >>>";
2379 static const char *
2380 op_symbol (tree op)
2382 return op_symbol_1 (TREE_CODE (op));
2385 /* Prints the name of a CALL_EXPR. */
2387 static void
2388 print_call_name (pretty_printer *buffer, tree node)
2390 tree op0;
2392 gcc_assert (TREE_CODE (node) == CALL_EXPR);
2394 op0 = TREE_OPERAND (node, 0);
2396 if (TREE_CODE (op0) == NON_LVALUE_EXPR)
2397 op0 = TREE_OPERAND (op0, 0);
2399 switch (TREE_CODE (op0))
2401 case VAR_DECL:
2402 case PARM_DECL:
2403 dump_function_name (buffer, op0);
2404 break;
2406 case ADDR_EXPR:
2407 case INDIRECT_REF:
2408 case NOP_EXPR:
2409 dump_generic_node (buffer, TREE_OPERAND (op0, 0), 0, 0, false);
2410 break;
2412 case COND_EXPR:
2413 pp_string (buffer, "(");
2414 dump_generic_node (buffer, TREE_OPERAND (op0, 0), 0, 0, false);
2415 pp_string (buffer, ") ? ");
2416 dump_generic_node (buffer, TREE_OPERAND (op0, 1), 0, 0, false);
2417 pp_string (buffer, " : ");
2418 dump_generic_node (buffer, TREE_OPERAND (op0, 2), 0, 0, false);
2419 break;
2421 case COMPONENT_REF:
2422 /* The function is a pointer contained in a structure. */
2423 if (TREE_CODE (TREE_OPERAND (op0, 0)) == INDIRECT_REF ||
2424 TREE_CODE (TREE_OPERAND (op0, 0)) == VAR_DECL)
2425 dump_function_name (buffer, TREE_OPERAND (op0, 1));
2426 else
2427 dump_generic_node (buffer, TREE_OPERAND (op0, 0), 0, 0, false);
2428 /* else
2429 We can have several levels of structures and a function
2430 pointer inside. This is not implemented yet... */
2431 /* NIY;*/
2432 break;
2434 case ARRAY_REF:
2435 if (TREE_CODE (TREE_OPERAND (op0, 0)) == VAR_DECL)
2436 dump_function_name (buffer, TREE_OPERAND (op0, 0));
2437 else
2438 dump_generic_node (buffer, op0, 0, 0, false);
2439 break;
2441 case SSA_NAME:
2442 case OBJ_TYPE_REF:
2443 dump_generic_node (buffer, op0, 0, 0, false);
2444 break;
2446 default:
2447 NIY;
2451 /* Parses the string STR and replaces new-lines by '\n', tabs by '\t', ... */
2453 static void
2454 pretty_print_string (pretty_printer *buffer, const char *str)
2456 if (str == NULL)
2457 return;
2459 while (*str)
2461 switch (str[0])
2463 case '\b':
2464 pp_string (buffer, "\\b");
2465 break;
2467 case '\f':
2468 pp_string (buffer, "\\f");
2469 break;
2471 case '\n':
2472 pp_string (buffer, "\\n");
2473 break;
2475 case '\r':
2476 pp_string (buffer, "\\r");
2477 break;
2479 case '\t':
2480 pp_string (buffer, "\\t");
2481 break;
2483 case '\v':
2484 pp_string (buffer, "\\v");
2485 break;
2487 case '\\':
2488 pp_string (buffer, "\\\\");
2489 break;
2491 case '\"':
2492 pp_string (buffer, "\\\"");
2493 break;
2495 case '\'':
2496 pp_string (buffer, "\\'");
2497 break;
2499 case '\0':
2500 pp_string (buffer, "\\0");
2501 break;
2503 case '\1':
2504 pp_string (buffer, "\\1");
2505 break;
2507 case '\2':
2508 pp_string (buffer, "\\2");
2509 break;
2511 case '\3':
2512 pp_string (buffer, "\\3");
2513 break;
2515 case '\4':
2516 pp_string (buffer, "\\4");
2517 break;
2519 case '\5':
2520 pp_string (buffer, "\\5");
2521 break;
2523 case '\6':
2524 pp_string (buffer, "\\6");
2525 break;
2527 case '\7':
2528 pp_string (buffer, "\\7");
2529 break;
2531 default:
2532 pp_character (buffer, str[0]);
2533 break;
2535 str++;
2539 static void
2540 maybe_init_pretty_print (FILE *file)
2542 if (!initialized)
2544 pp_construct (&buffer, /* prefix */NULL, /* line-width */0);
2545 pp_needs_newline (&buffer) = true;
2546 initialized = 1;
2549 buffer.buffer->stream = file;
2552 static void
2553 newline_and_indent (pretty_printer *buffer, int spc)
2555 pp_newline (buffer);
2556 INDENT (spc);
2559 static void
2560 dump_vops (pretty_printer *buffer, tree stmt, int spc, int flags)
2562 tree use;
2563 use_operand_p use_p;
2564 def_operand_p def_p;
2565 use_operand_p kill_p;
2566 ssa_op_iter iter;
2568 if (!ssa_operands_active ())
2569 return;
2571 FOR_EACH_SSA_MAYDEF_OPERAND (def_p, use_p, stmt, iter)
2573 pp_string (buffer, "# ");
2574 dump_generic_node (buffer, DEF_FROM_PTR (def_p),
2575 spc + 2, flags, false);
2576 pp_string (buffer, " = V_MAY_DEF <");
2577 dump_generic_node (buffer, USE_FROM_PTR (use_p),
2578 spc + 2, flags, false);
2579 pp_string (buffer, ">;");
2580 newline_and_indent (buffer, spc);
2583 FOR_EACH_SSA_MUSTDEF_OPERAND (def_p, kill_p, stmt, iter)
2585 pp_string (buffer, "# ");
2586 dump_generic_node (buffer, DEF_FROM_PTR (def_p),
2587 spc + 2, flags, false);
2588 pp_string (buffer, " = V_MUST_DEF <");
2589 dump_generic_node (buffer, USE_FROM_PTR (kill_p),
2590 spc + 2, flags, false);
2591 pp_string (buffer, ">;");
2592 newline_and_indent (buffer, spc);
2595 FOR_EACH_SSA_TREE_OPERAND (use, stmt, iter, SSA_OP_VUSE)
2597 pp_string (buffer, "# VUSE <");
2598 dump_generic_node (buffer, use, spc + 2, flags, false);
2599 pp_string (buffer, ">;");
2600 newline_and_indent (buffer, spc);
2604 /* Dumps basic block BB to FILE with details described by FLAGS and
2605 indented by INDENT spaces. */
2607 void
2608 dump_generic_bb (FILE *file, basic_block bb, int indent, int flags)
2610 maybe_init_pretty_print (file);
2611 dump_generic_bb_buff (&buffer, bb, indent, flags);
2612 pp_flush (&buffer);
2615 /* Dumps header of basic block BB to buffer BUFFER indented by INDENT
2616 spaces and details described by flags. */
2618 static void
2619 dump_bb_header (pretty_printer *buffer, basic_block bb, int indent, int flags)
2621 edge e;
2622 tree stmt;
2623 edge_iterator ei;
2625 if (flags & TDF_BLOCKS)
2627 INDENT (indent);
2628 pp_string (buffer, "# BLOCK ");
2629 pp_decimal_int (buffer, bb->index);
2630 if (bb->frequency)
2632 pp_string (buffer, " freq:");
2633 pp_decimal_int (buffer, bb->frequency);
2635 if (bb->count)
2637 pp_string (buffer, " count:");
2638 pp_widest_integer (buffer, bb->count);
2641 if (flags & TDF_LINENO)
2643 block_stmt_iterator bsi;
2645 for (bsi = bsi_start (bb); !bsi_end_p (bsi); bsi_next (&bsi))
2646 if (get_lineno (bsi_stmt (bsi)) != -1)
2648 pp_string (buffer, ", starting at line ");
2649 pp_decimal_int (buffer, get_lineno (bsi_stmt (bsi)));
2650 break;
2653 newline_and_indent (buffer, indent);
2655 pp_string (buffer, "# PRED:");
2656 pp_write_text_to_stream (buffer);
2657 FOR_EACH_EDGE (e, ei, bb->preds)
2658 if (flags & TDF_SLIM)
2660 pp_string (buffer, " ");
2661 if (e->src == ENTRY_BLOCK_PTR)
2662 pp_string (buffer, "ENTRY");
2663 else
2664 pp_decimal_int (buffer, e->src->index);
2666 else
2667 dump_edge_info (buffer->buffer->stream, e, 0);
2668 pp_newline (buffer);
2670 else
2672 stmt = first_stmt (bb);
2673 if (!stmt || TREE_CODE (stmt) != LABEL_EXPR)
2675 INDENT (indent - 2);
2676 pp_string (buffer, "<bb ");
2677 pp_decimal_int (buffer, bb->index);
2678 pp_string (buffer, ">:");
2679 pp_newline (buffer);
2682 pp_write_text_to_stream (buffer);
2683 check_bb_profile (bb, buffer->buffer->stream);
2686 /* Dumps end of basic block BB to buffer BUFFER indented by INDENT
2687 spaces. */
2689 static void
2690 dump_bb_end (pretty_printer *buffer, basic_block bb, int indent, int flags)
2692 edge e;
2693 edge_iterator ei;
2695 INDENT (indent);
2696 pp_string (buffer, "# SUCC:");
2697 pp_write_text_to_stream (buffer);
2698 FOR_EACH_EDGE (e, ei, bb->succs)
2699 if (flags & TDF_SLIM)
2701 pp_string (buffer, " ");
2702 if (e->dest == EXIT_BLOCK_PTR)
2703 pp_string (buffer, "EXIT");
2704 else
2705 pp_decimal_int (buffer, e->dest->index);
2707 else
2708 dump_edge_info (buffer->buffer->stream, e, 1);
2709 pp_newline (buffer);
2712 /* Dumps phi nodes of basic block BB to buffer BUFFER with details described by
2713 FLAGS indented by INDENT spaces. */
2715 static void
2716 dump_phi_nodes (pretty_printer *buffer, basic_block bb, int indent, int flags)
2718 tree phi = phi_nodes (bb);
2719 if (!phi)
2720 return;
2722 for (; phi; phi = PHI_CHAIN (phi))
2724 if (is_gimple_reg (PHI_RESULT (phi)) || (flags & TDF_VOPS))
2726 INDENT (indent);
2727 pp_string (buffer, "# ");
2728 dump_generic_node (buffer, phi, indent, flags, false);
2729 pp_newline (buffer);
2734 /* Dump jump to basic block BB that is represented implicitly in the cfg
2735 to BUFFER. */
2737 static void
2738 pp_cfg_jump (pretty_printer *buffer, basic_block bb)
2740 tree stmt;
2742 stmt = first_stmt (bb);
2744 pp_string (buffer, "goto <bb ");
2745 pp_decimal_int (buffer, bb->index);
2746 pp_string (buffer, ">");
2747 if (stmt && TREE_CODE (stmt) == LABEL_EXPR)
2749 pp_string (buffer, " (");
2750 dump_generic_node (buffer, LABEL_EXPR_LABEL (stmt), 0, 0, false);
2751 pp_string (buffer, ")");
2753 pp_semicolon (buffer);
2756 /* Dump edges represented implicitly in basic block BB to BUFFER, indented
2757 by INDENT spaces, with details given by FLAGS. */
2759 static void
2760 dump_implicit_edges (pretty_printer *buffer, basic_block bb, int indent,
2761 int flags)
2763 edge e;
2764 edge_iterator ei;
2766 /* If there is a fallthru edge, we may need to add an artificial goto to the
2767 dump. */
2768 FOR_EACH_EDGE (e, ei, bb->succs)
2769 if (e->flags & EDGE_FALLTHRU)
2770 break;
2771 if (e && e->dest != bb->next_bb)
2773 INDENT (indent);
2775 if ((flags & TDF_LINENO)
2776 #ifdef USE_MAPPED_LOCATION
2777 && e->goto_locus != UNKNOWN_LOCATION
2778 #else
2779 && e->goto_locus
2780 #endif
2783 expanded_location goto_xloc;
2784 #ifdef USE_MAPPED_LOCATION
2785 goto_xloc = expand_location (e->goto_locus);
2786 #else
2787 goto_xloc = *e->goto_locus;
2788 #endif
2789 pp_character (buffer, '[');
2790 if (goto_xloc.file)
2792 pp_string (buffer, goto_xloc.file);
2793 pp_string (buffer, " : ");
2795 pp_decimal_int (buffer, goto_xloc.line);
2796 pp_string (buffer, "] ");
2799 pp_cfg_jump (buffer, e->dest);
2800 pp_newline (buffer);
2804 /* Dumps basic block BB to buffer BUFFER with details described by FLAGS and
2805 indented by INDENT spaces. */
2807 static void
2808 dump_generic_bb_buff (pretty_printer *buffer, basic_block bb,
2809 int indent, int flags)
2811 block_stmt_iterator bsi;
2812 tree stmt;
2813 int label_indent = indent - 2;
2815 if (label_indent < 0)
2816 label_indent = 0;
2818 dump_bb_header (buffer, bb, indent, flags);
2820 dump_phi_nodes (buffer, bb, indent, flags);
2822 for (bsi = bsi_start (bb); !bsi_end_p (bsi); bsi_next (&bsi))
2824 int curr_indent;
2826 stmt = bsi_stmt (bsi);
2828 curr_indent = TREE_CODE (stmt) == LABEL_EXPR ? label_indent : indent;
2830 INDENT (curr_indent);
2831 dump_generic_node (buffer, stmt, curr_indent, flags, true);
2832 pp_newline (buffer);
2835 dump_implicit_edges (buffer, bb, indent, flags);
2837 if (flags & TDF_BLOCKS)
2838 dump_bb_end (buffer, bb, indent, flags);