2005-07-07 Adrian Straetling <straetling@de.ibm.com>
[official-gcc.git] / gcc / tree-pretty-print.c
blob17de6f361fcb10024997f021bd995db5119f3cdf
1 /* Pretty formatting of GENERIC trees in C syntax.
2 Copyright (C) 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
3 Adapted from c-pretty-print.c by Diego Novillo <dnovillo@redhat.com>
5 This file is part of GCC.
7 GCC is free software; you can redistribute it and/or modify it under
8 the terms of the GNU General Public License as published by the Free
9 Software Foundation; either version 2, or (at your option) any later
10 version.
12 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13 WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15 for more details.
17 You should have received a copy of the GNU General Public License
18 along with GCC; see the file COPYING. If not, write to the Free
19 Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
20 02110-1301, USA. */
22 #include "config.h"
23 #include "system.h"
24 #include "coretypes.h"
25 #include "tm.h"
26 #include "tree.h"
27 #include "diagnostic.h"
28 #include "real.h"
29 #include "hashtab.h"
30 #include "tree-flow.h"
31 #include "langhooks.h"
32 #include "tree-iterator.h"
33 #include "tree-chrec.h"
34 #include "tree-pass.h"
36 /* Local functions, macros and variables. */
37 static int op_prio (tree);
38 static const char *op_symbol (tree);
39 static void pretty_print_string (pretty_printer *, const char*);
40 static void print_call_name (pretty_printer *, tree);
41 static void newline_and_indent (pretty_printer *, int);
42 static void maybe_init_pretty_print (FILE *);
43 static void print_declaration (pretty_printer *, tree, int, int);
44 static void print_struct_decl (pretty_printer *, tree, int, int);
45 static void do_niy (pretty_printer *, tree);
46 static void dump_vops (pretty_printer *, tree, int, int);
47 static void dump_generic_bb_buff (pretty_printer *, basic_block, int, int);
49 #define INDENT(SPACE) do { \
50 int i; for (i = 0; i<SPACE; i++) pp_space (buffer); } while (0)
52 #define NIY do_niy(buffer,node)
54 #define PRINT_FUNCTION_NAME(NODE) pp_printf \
55 (buffer, "%s", TREE_CODE (NODE) == NOP_EXPR ? \
56 lang_hooks.decl_printable_name (TREE_OPERAND (NODE, 0), 1) : \
57 lang_hooks.decl_printable_name (NODE, 1))
59 static pretty_printer buffer;
60 static int initialized = 0;
61 static bool dumping_stmts;
63 /* Try to print something for an unknown tree code. */
65 static void
66 do_niy (pretty_printer *buffer, tree node)
68 int i, len;
70 pp_string (buffer, "<<< Unknown tree: ");
71 pp_string (buffer, tree_code_name[(int) TREE_CODE (node)]);
73 if (EXPR_P (node))
75 len = TREE_CODE_LENGTH (TREE_CODE (node));
76 for (i = 0; i < len; ++i)
78 newline_and_indent (buffer, 2);
79 dump_generic_node (buffer, TREE_OPERAND (node, i), 2, 0, false);
83 pp_string (buffer, " >>>\n");
86 void
87 debug_generic_expr (tree t)
89 print_generic_expr (stderr, t, TDF_VOPS|TDF_UID);
90 fprintf (stderr, "\n");
93 void
94 debug_generic_stmt (tree t)
96 print_generic_stmt (stderr, t, TDF_VOPS|TDF_UID);
97 fprintf (stderr, "\n");
100 /* Prints declaration DECL to the FILE with details specified by FLAGS. */
101 void
102 print_generic_decl (FILE *file, tree decl, int flags)
104 maybe_init_pretty_print (file);
105 dumping_stmts = true;
106 print_declaration (&buffer, decl, 2, flags);
107 pp_write_text_to_stream (&buffer);
110 /* Print tree T, and its successors, on file FILE. FLAGS specifies details
111 to show in the dump. See TDF_* in tree.h. */
113 void
114 print_generic_stmt (FILE *file, tree t, int flags)
116 maybe_init_pretty_print (file);
117 dumping_stmts = true;
118 dump_generic_node (&buffer, t, 0, flags, true);
119 pp_flush (&buffer);
122 /* Print tree T, and its successors, on file FILE. FLAGS specifies details
123 to show in the dump. See TDF_* in tree.h. The output is indented by
124 INDENT spaces. */
126 void
127 print_generic_stmt_indented (FILE *file, tree t, int flags, int indent)
129 int i;
131 maybe_init_pretty_print (file);
132 dumping_stmts = true;
134 for (i = 0; i < indent; i++)
135 pp_space (&buffer);
136 dump_generic_node (&buffer, t, indent, flags, true);
137 pp_flush (&buffer);
140 /* Print a single expression T on file FILE. FLAGS specifies details to show
141 in the dump. See TDF_* in tree.h. */
143 void
144 print_generic_expr (FILE *file, tree t, int flags)
146 maybe_init_pretty_print (file);
147 dumping_stmts = false;
148 dump_generic_node (&buffer, t, 0, flags, false);
151 /* Dump the name of a _DECL node and its DECL_UID if TDF_UID is set
152 in FLAGS. */
154 static void
155 dump_decl_name (pretty_printer *buffer, tree node, int flags)
157 if (DECL_NAME (node))
158 pp_tree_identifier (buffer, DECL_NAME (node));
160 if ((flags & TDF_UID)
161 || DECL_NAME (node) == NULL_TREE)
163 if (TREE_CODE (node) == LABEL_DECL
164 && LABEL_DECL_UID (node) != -1)
165 pp_printf (buffer, "L." HOST_WIDE_INT_PRINT_DEC,
166 LABEL_DECL_UID (node));
167 else
169 char c = TREE_CODE (node) == CONST_DECL ? 'C' : 'D';
170 pp_printf (buffer, "%c.%u", c, DECL_UID (node));
175 /* Like the above, but used for pretty printing function calls. */
177 static void
178 dump_function_name (pretty_printer *buffer, tree node)
180 if (DECL_NAME (node))
181 PRINT_FUNCTION_NAME (node);
182 else
183 dump_decl_name (buffer, node, 0);
186 /* Dump a function declaration. NODE is the FUNCTION_TYPE. BUFFER, SPC and
187 FLAGS are as in dump_generic_node. */
189 static void
190 dump_function_declaration (pretty_printer *buffer, tree node,
191 int spc, int flags)
193 bool wrote_arg = false;
194 tree arg;
196 pp_space (buffer);
197 pp_character (buffer, '(');
199 /* Print the argument types. The last element in the list is a VOID_TYPE.
200 The following avoids printing the last element. */
201 arg = TYPE_ARG_TYPES (node);
202 while (arg && TREE_CHAIN (arg) && arg != error_mark_node)
204 wrote_arg = true;
205 dump_generic_node (buffer, TREE_VALUE (arg), spc, flags, false);
206 arg = TREE_CHAIN (arg);
207 if (TREE_CHAIN (arg) && TREE_CODE (TREE_CHAIN (arg)) == TREE_LIST)
209 pp_character (buffer, ',');
210 pp_space (buffer);
214 if (!wrote_arg)
215 pp_string (buffer, "void");
217 pp_character (buffer, ')');
220 /* Dump the domain associated with an array. */
222 static void
223 dump_array_domain (pretty_printer *buffer, tree domain, int spc, int flags)
225 pp_character (buffer, '[');
226 if (domain)
228 tree min = TYPE_MIN_VALUE (domain);
229 tree max = TYPE_MAX_VALUE (domain);
231 if (min && max
232 && integer_zerop (min)
233 && host_integerp (max, 0))
234 pp_wide_integer (buffer, TREE_INT_CST_LOW (max) + 1);
235 else
237 if (min)
238 dump_generic_node (buffer, min, spc, flags, false);
239 pp_character (buffer, ':');
240 if (max)
241 dump_generic_node (buffer, max, spc, flags, false);
244 else
245 pp_string (buffer, "<unknown>");
246 pp_character (buffer, ']');
249 /* Dump the node NODE on the pretty_printer BUFFER, SPC spaces of indent.
250 FLAGS specifies details to show in the dump (see TDF_* in tree.h). If
251 IS_STMT is true, the object printed is considered to be a statement
252 and it is terminated by ';' if appropriate. */
255 dump_generic_node (pretty_printer *buffer, tree node, int spc, int flags,
256 bool is_stmt)
258 tree type;
259 tree op0, op1;
260 const char *str;
261 bool is_expr;
263 if (node == NULL_TREE)
264 return spc;
266 is_expr = EXPR_P (node);
268 if (TREE_CODE (node) != ERROR_MARK
269 && is_gimple_stmt (node)
270 && (flags & TDF_VOPS)
271 && stmt_ann (node)
272 && TREE_CODE (node) != PHI_NODE)
273 dump_vops (buffer, node, spc, flags);
275 if (is_stmt && (flags & TDF_STMTADDR))
276 pp_printf (buffer, "<&%p> ", (void *)node);
278 if (dumping_stmts
279 && (flags & TDF_LINENO)
280 && EXPR_HAS_LOCATION (node))
282 expanded_location xloc = expand_location (EXPR_LOCATION (node));
283 pp_character (buffer, '[');
284 if (xloc.file)
286 pp_string (buffer, xloc.file);
287 pp_string (buffer, " : ");
289 pp_decimal_int (buffer, xloc.line);
290 pp_string (buffer, "] ");
293 switch (TREE_CODE (node))
295 case ERROR_MARK:
296 pp_string (buffer, "<<< error >>>");
297 break;
299 case IDENTIFIER_NODE:
300 pp_tree_identifier (buffer, node);
301 break;
303 case TREE_LIST:
304 while (node && node != error_mark_node)
306 if (TREE_PURPOSE (node))
308 dump_generic_node (buffer, TREE_PURPOSE (node), spc, flags, false);
309 pp_space (buffer);
311 dump_generic_node (buffer, TREE_VALUE (node), spc, flags, false);
312 node = TREE_CHAIN (node);
313 if (node && TREE_CODE (node) == TREE_LIST)
315 pp_character (buffer, ',');
316 pp_space (buffer);
319 break;
321 case TREE_BINFO:
322 dump_generic_node (buffer, BINFO_TYPE (node), spc, flags, false);
324 case TREE_VEC:
326 size_t i;
327 if (TREE_VEC_LENGTH (node) > 0)
329 size_t len = TREE_VEC_LENGTH (node);
330 for (i = 0; i < len - 1; i++)
332 dump_generic_node (buffer, TREE_VEC_ELT (node, i), spc, flags,
333 false);
334 pp_character (buffer, ',');
335 pp_space (buffer);
337 dump_generic_node (buffer, TREE_VEC_ELT (node, len - 1), spc,
338 flags, false);
341 break;
343 case BLOCK:
344 NIY;
345 break;
347 case VOID_TYPE:
348 case INTEGER_TYPE:
349 case REAL_TYPE:
350 case COMPLEX_TYPE:
351 case VECTOR_TYPE:
352 case ENUMERAL_TYPE:
353 case BOOLEAN_TYPE:
354 case CHAR_TYPE:
356 unsigned int quals = TYPE_QUALS (node);
357 enum tree_code_class class;
359 if (quals & TYPE_QUAL_CONST)
360 pp_string (buffer, "const ");
361 else if (quals & TYPE_QUAL_VOLATILE)
362 pp_string (buffer, "volatile ");
363 else if (quals & TYPE_QUAL_RESTRICT)
364 pp_string (buffer, "restrict ");
366 class = TREE_CODE_CLASS (TREE_CODE (node));
368 if (class == tcc_declaration)
370 if (DECL_NAME (node))
371 dump_decl_name (buffer, node, flags);
372 else
373 pp_string (buffer, "<unnamed type decl>");
375 else if (class == tcc_type)
377 if (TYPE_NAME (node))
379 if (TREE_CODE (TYPE_NAME (node)) == IDENTIFIER_NODE)
380 pp_tree_identifier (buffer, TYPE_NAME (node));
381 else if (TREE_CODE (TYPE_NAME (node)) == TYPE_DECL
382 && DECL_NAME (TYPE_NAME (node)))
383 dump_decl_name (buffer, TYPE_NAME (node), flags);
384 else
385 pp_string (buffer, "<unnamed type>");
387 else if (TREE_CODE (node) == VECTOR_TYPE)
389 pp_string (buffer, "vector ");
390 dump_generic_node (buffer, TREE_TYPE (node),
391 spc, flags, false);
393 else
394 pp_string (buffer, "<unnamed type>");
396 break;
399 case POINTER_TYPE:
400 case REFERENCE_TYPE:
401 str = (TREE_CODE (node) == POINTER_TYPE ? "*" : "&");
403 if (TREE_CODE (TREE_TYPE (node)) == FUNCTION_TYPE)
405 tree fnode = TREE_TYPE (node);
407 dump_generic_node (buffer, TREE_TYPE (fnode), spc, flags, false);
408 pp_space (buffer);
409 pp_character (buffer, '(');
410 pp_string (buffer, str);
411 if (TYPE_NAME (node) && DECL_NAME (TYPE_NAME (node)))
412 dump_decl_name (buffer, TYPE_NAME (node), flags);
413 else
414 pp_printf (buffer, "<T%x>", TYPE_UID (node));
416 pp_character (buffer, ')');
417 dump_function_declaration (buffer, fnode, spc, flags);
419 else
421 unsigned int quals = TYPE_QUALS (node);
423 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
424 pp_space (buffer);
425 pp_string (buffer, str);
427 if (quals & TYPE_QUAL_CONST)
428 pp_string (buffer, " const");
429 else if (quals & TYPE_QUAL_VOLATILE)
430 pp_string (buffer, "volatile");
431 else if (quals & TYPE_QUAL_RESTRICT)
432 pp_string (buffer, " restrict");
434 if (TYPE_REF_CAN_ALIAS_ALL (node))
435 pp_string (buffer, " {ref-all}");
437 break;
439 case OFFSET_TYPE:
440 NIY;
441 break;
443 case METHOD_TYPE:
444 dump_decl_name (buffer, TYPE_NAME (TYPE_METHOD_BASETYPE (node)), flags);
445 pp_string (buffer, "::");
446 break;
448 case TARGET_MEM_REF:
450 const char *sep = "";
451 tree tmp;
453 pp_string (buffer, "MEM[");
455 tmp = TMR_SYMBOL (node);
456 if (tmp)
458 pp_string (buffer, sep);
459 sep = ", ";
460 pp_string (buffer, "symbol: ");
461 dump_generic_node (buffer, tmp, spc, flags, false);
463 tmp = TMR_BASE (node);
464 if (tmp)
466 pp_string (buffer, sep);
467 sep = ", ";
468 pp_string (buffer, "base: ");
469 dump_generic_node (buffer, tmp, spc, flags, false);
471 tmp = TMR_INDEX (node);
472 if (tmp)
474 pp_string (buffer, sep);
475 sep = ", ";
476 pp_string (buffer, "index: ");
477 dump_generic_node (buffer, tmp, spc, flags, false);
479 tmp = TMR_STEP (node);
480 if (tmp)
482 pp_string (buffer, sep);
483 sep = ", ";
484 pp_string (buffer, "step: ");
485 dump_generic_node (buffer, tmp, spc, flags, false);
487 tmp = TMR_OFFSET (node);
488 if (tmp)
490 pp_string (buffer, sep);
491 sep = ", ";
492 pp_string (buffer, "offset: ");
493 dump_generic_node (buffer, tmp, spc, flags, false);
495 pp_string (buffer, "]");
496 if (flags & TDF_DETAILS)
498 pp_string (buffer, "{");
499 dump_generic_node (buffer, TMR_ORIGINAL (node), spc, flags,
500 false);
501 pp_string (buffer, "}");
504 break;
506 case ARRAY_TYPE:
508 tree tmp;
510 /* Print the innermost component type. */
511 for (tmp = TREE_TYPE (node); TREE_CODE (tmp) == ARRAY_TYPE;
512 tmp = TREE_TYPE (tmp))
514 dump_generic_node (buffer, tmp, spc, flags, false);
516 /* Print the dimensions. */
517 for (tmp = node; TREE_CODE (tmp) == ARRAY_TYPE; tmp = TREE_TYPE (tmp))
518 dump_array_domain (buffer, TYPE_DOMAIN (tmp), spc, flags);
519 break;
522 case RECORD_TYPE:
523 case UNION_TYPE:
524 case QUAL_UNION_TYPE:
525 /* Print the name of the structure. */
526 if (TREE_CODE (node) == RECORD_TYPE)
527 pp_string (buffer, "struct ");
528 else if (TREE_CODE (node) == UNION_TYPE)
529 pp_string (buffer, "union ");
531 if (TYPE_NAME (node))
532 dump_generic_node (buffer, TYPE_NAME (node), spc, flags, false);
533 else
534 print_struct_decl (buffer, node, spc, flags);
535 break;
537 case LANG_TYPE:
538 NIY;
539 break;
541 case INTEGER_CST:
542 if (TREE_CODE (TREE_TYPE (node)) == POINTER_TYPE)
544 /* In the case of a pointer, one may want to divide by the
545 size of the pointed-to type. Unfortunately, this not
546 straightforward. The C front-end maps expressions
548 (int *) 5
549 int *p; (p + 5)
551 in such a way that the two INTEGER_CST nodes for "5" have
552 different values but identical types. In the latter
553 case, the 5 is multiplied by sizeof (int) in c-common.c
554 (pointer_int_sum) to convert it to a byte address, and
555 yet the type of the node is left unchanged. Argh. What
556 is consistent though is that the number value corresponds
557 to bytes (UNITS) offset.
559 NB: Neither of the following divisors can be trivially
560 used to recover the original literal:
562 TREE_INT_CST_LOW (TYPE_SIZE_UNIT (TREE_TYPE (node)))
563 TYPE_PRECISION (TREE_TYPE (TREE_TYPE (node))) */
564 pp_wide_integer (buffer, TREE_INT_CST_LOW (node));
565 pp_string (buffer, "B"); /* pseudo-unit */
567 else if (! host_integerp (node, 0))
569 tree val = node;
571 if (tree_int_cst_sgn (val) < 0)
573 pp_character (buffer, '-');
574 val = build_int_cst_wide (NULL_TREE,
575 -TREE_INT_CST_LOW (val),
576 ~TREE_INT_CST_HIGH (val)
577 + !TREE_INT_CST_LOW (val));
579 /* Would "%x%0*x" or "%x%*0x" get zero-padding on all
580 systems? */
582 static char format[10]; /* "%x%09999x\0" */
583 if (!format[0])
584 sprintf (format, "%%x%%0%dx", HOST_BITS_PER_INT / 4);
585 sprintf (pp_buffer (buffer)->digit_buffer, format,
586 TREE_INT_CST_HIGH (val),
587 TREE_INT_CST_LOW (val));
588 pp_string (buffer, pp_buffer (buffer)->digit_buffer);
591 else
592 pp_wide_integer (buffer, TREE_INT_CST_LOW (node));
593 break;
595 case REAL_CST:
596 /* Code copied from print_node. */
598 REAL_VALUE_TYPE d;
599 if (TREE_OVERFLOW (node))
600 pp_string (buffer, " overflow");
602 #if !defined(REAL_IS_NOT_DOUBLE) || defined(REAL_ARITHMETIC)
603 d = TREE_REAL_CST (node);
604 if (REAL_VALUE_ISINF (d))
605 pp_string (buffer, " Inf");
606 else if (REAL_VALUE_ISNAN (d))
607 pp_string (buffer, " Nan");
608 else
610 char string[100];
611 real_to_decimal (string, &d, sizeof (string), 0, 1);
612 pp_string (buffer, string);
614 #else
616 HOST_WIDE_INT i;
617 unsigned char *p = (unsigned char *) &TREE_REAL_CST (node);
618 pp_string (buffer, "0x");
619 for (i = 0; i < sizeof TREE_REAL_CST (node); i++)
620 output_formatted_integer (buffer, "%02x", *p++);
622 #endif
623 break;
626 case COMPLEX_CST:
627 pp_string (buffer, "__complex__ (");
628 dump_generic_node (buffer, TREE_REALPART (node), spc, flags, false);
629 pp_string (buffer, ", ");
630 dump_generic_node (buffer, TREE_IMAGPART (node), spc, flags, false);
631 pp_string (buffer, ")");
632 break;
634 case STRING_CST:
635 pp_string (buffer, "\"");
636 pretty_print_string (buffer, TREE_STRING_POINTER (node));
637 pp_string (buffer, "\"");
638 break;
640 case VECTOR_CST:
642 tree elt;
643 pp_string (buffer, "{ ");
644 for (elt = TREE_VECTOR_CST_ELTS (node); elt; elt = TREE_CHAIN (elt))
646 dump_generic_node (buffer, TREE_VALUE (elt), spc, flags, false);
647 if (TREE_CHAIN (elt))
648 pp_string (buffer, ", ");
650 pp_string (buffer, " }");
652 break;
654 case FUNCTION_TYPE:
655 break;
657 case FUNCTION_DECL:
658 case CONST_DECL:
659 dump_decl_name (buffer, node, flags);
660 break;
662 case LABEL_DECL:
663 if (DECL_NAME (node))
664 dump_decl_name (buffer, node, flags);
665 else if (LABEL_DECL_UID (node) != -1)
666 pp_printf (buffer, "<L" HOST_WIDE_INT_PRINT_DEC ">",
667 LABEL_DECL_UID (node));
668 else
669 pp_printf (buffer, "<D%u>", DECL_UID (node));
670 break;
672 case TYPE_DECL:
673 if (DECL_IS_BUILTIN (node))
675 /* Don't print the declaration of built-in types. */
676 break;
678 if (DECL_NAME (node))
679 dump_decl_name (buffer, node, flags);
680 else
682 if ((TREE_CODE (TREE_TYPE (node)) == RECORD_TYPE
683 || TREE_CODE (TREE_TYPE (node)) == UNION_TYPE)
684 && TYPE_METHODS (TREE_TYPE (node)))
686 /* The type is a c++ class: all structures have at least
687 4 methods. */
688 pp_string (buffer, "class ");
689 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
691 else
693 pp_string (buffer,
694 (TREE_CODE (TREE_TYPE (node)) == UNION_TYPE
695 ? "union" : "struct "));
696 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
699 break;
701 case VAR_DECL:
702 case PARM_DECL:
703 case FIELD_DECL:
704 case NAMESPACE_DECL:
705 dump_decl_name (buffer, node, flags);
706 break;
708 case RESULT_DECL:
709 pp_string (buffer, "<retval>");
710 break;
712 case COMPONENT_REF:
713 op0 = TREE_OPERAND (node, 0);
714 str = ".";
715 if (TREE_CODE (op0) == INDIRECT_REF)
717 op0 = TREE_OPERAND (op0, 0);
718 str = "->";
720 if (op_prio (op0) < op_prio (node))
721 pp_character (buffer, '(');
722 dump_generic_node (buffer, op0, spc, flags, false);
723 if (op_prio (op0) < op_prio (node))
724 pp_character (buffer, ')');
725 pp_string (buffer, str);
726 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
728 if (TREE_CODE (op0) != VALUE_HANDLE)
730 op0 = component_ref_field_offset (node);
731 if (op0 && TREE_CODE (op0) != INTEGER_CST)
733 pp_string (buffer, "{off: ");
734 dump_generic_node (buffer, op0, spc, flags, false);
735 pp_character (buffer, '}');
738 break;
740 case BIT_FIELD_REF:
741 pp_string (buffer, "BIT_FIELD_REF <");
742 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
743 pp_string (buffer, ", ");
744 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
745 pp_string (buffer, ", ");
746 dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
747 pp_string (buffer, ">");
748 break;
750 case ARRAY_REF:
751 case ARRAY_RANGE_REF:
752 op0 = TREE_OPERAND (node, 0);
753 if (op_prio (op0) < op_prio (node))
754 pp_character (buffer, '(');
755 dump_generic_node (buffer, op0, spc, flags, false);
756 if (op_prio (op0) < op_prio (node))
757 pp_character (buffer, ')');
758 pp_character (buffer, '[');
759 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
760 if (TREE_CODE (node) == ARRAY_RANGE_REF)
761 pp_string (buffer, " ...");
762 pp_character (buffer, ']');
764 op0 = array_ref_low_bound (node);
765 op1 = array_ref_element_size (node);
767 if (!integer_zerop (op0)
768 || (TYPE_SIZE_UNIT (TREE_TYPE (node))
769 && !operand_equal_p (op1, TYPE_SIZE_UNIT (TREE_TYPE (node)), 0)))
771 pp_string (buffer, "{lb: ");
772 dump_generic_node (buffer, op0, spc, flags, false);
773 pp_string (buffer, " sz: ");
774 dump_generic_node (buffer, op1, spc, flags, false);
775 pp_character (buffer, '}');
777 break;
779 case CONSTRUCTOR:
781 tree lnode;
782 bool is_struct_init = FALSE;
783 pp_character (buffer, '{');
784 lnode = CONSTRUCTOR_ELTS (node);
785 if (TREE_CODE (TREE_TYPE (node)) == RECORD_TYPE
786 || TREE_CODE (TREE_TYPE (node)) == UNION_TYPE)
787 is_struct_init = TRUE;
788 while (lnode && lnode != error_mark_node)
790 tree val;
791 if (TREE_PURPOSE (lnode) && is_struct_init)
793 pp_character (buffer, '.');
794 dump_generic_node (buffer, TREE_PURPOSE (lnode), spc, flags, false);
795 pp_string (buffer, "=");
797 val = TREE_VALUE (lnode);
798 if (val && TREE_CODE (val) == ADDR_EXPR)
799 if (TREE_CODE (TREE_OPERAND (val, 0)) == FUNCTION_DECL)
800 val = TREE_OPERAND (val, 0);
801 if (val && TREE_CODE (val) == FUNCTION_DECL)
803 dump_decl_name (buffer, val, flags);
805 else
807 dump_generic_node (buffer, TREE_VALUE (lnode), spc, flags, false);
809 lnode = TREE_CHAIN (lnode);
810 if (lnode && TREE_CODE (lnode) == TREE_LIST)
812 pp_character (buffer, ',');
813 pp_space (buffer);
816 pp_character (buffer, '}');
818 break;
820 case COMPOUND_EXPR:
822 tree *tp;
823 if (flags & TDF_SLIM)
825 pp_string (buffer, "<COMPOUND_EXPR>");
826 break;
829 dump_generic_node (buffer, TREE_OPERAND (node, 0),
830 spc, flags, dumping_stmts);
831 if (dumping_stmts)
832 newline_and_indent (buffer, spc);
833 else
835 pp_character (buffer, ',');
836 pp_space (buffer);
839 for (tp = &TREE_OPERAND (node, 1);
840 TREE_CODE (*tp) == COMPOUND_EXPR;
841 tp = &TREE_OPERAND (*tp, 1))
843 dump_generic_node (buffer, TREE_OPERAND (*tp, 0),
844 spc, flags, dumping_stmts);
845 if (dumping_stmts)
846 newline_and_indent (buffer, spc);
847 else
849 pp_character (buffer, ',');
850 pp_space (buffer);
854 dump_generic_node (buffer, *tp, spc, flags, dumping_stmts);
856 break;
858 case STATEMENT_LIST:
860 tree_stmt_iterator si;
861 bool first = true;
863 if ((flags & TDF_SLIM) || !dumping_stmts)
865 pp_string (buffer, "<STATEMENT_LIST>");
866 break;
869 for (si = tsi_start (node); !tsi_end_p (si); tsi_next (&si))
871 if (!first)
872 newline_and_indent (buffer, spc);
873 else
874 first = false;
875 dump_generic_node (buffer, tsi_stmt (si), spc, flags, true);
878 break;
880 case MODIFY_EXPR:
881 case INIT_EXPR:
882 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
883 pp_space (buffer);
884 pp_character (buffer, '=');
885 pp_space (buffer);
886 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
887 break;
889 case TARGET_EXPR:
890 pp_string (buffer, "TARGET_EXPR <");
891 dump_generic_node (buffer, TARGET_EXPR_SLOT (node), spc, flags, false);
892 pp_character (buffer, ',');
893 pp_space (buffer);
894 dump_generic_node (buffer, TARGET_EXPR_INITIAL (node), spc, flags, false);
895 pp_character (buffer, '>');
896 break;
898 case DECL_EXPR:
899 print_declaration (buffer, DECL_EXPR_DECL (node), spc, flags);
900 is_stmt = false;
901 break;
903 case COND_EXPR:
904 if (TREE_TYPE (node) == NULL || TREE_TYPE (node) == void_type_node)
906 pp_string (buffer, "if (");
907 dump_generic_node (buffer, COND_EXPR_COND (node), spc, flags, false);
908 pp_character (buffer, ')');
909 /* The lowered cond_exprs should always be printed in full. */
910 if (COND_EXPR_THEN (node)
911 && (IS_EMPTY_STMT (COND_EXPR_THEN (node))
912 || TREE_CODE (COND_EXPR_THEN (node)) == GOTO_EXPR)
913 && COND_EXPR_ELSE (node)
914 && (IS_EMPTY_STMT (COND_EXPR_ELSE (node))
915 || TREE_CODE (COND_EXPR_ELSE (node)) == GOTO_EXPR))
917 pp_space (buffer);
918 dump_generic_node (buffer, COND_EXPR_THEN (node), 0, flags, true);
919 pp_string (buffer, " else ");
920 dump_generic_node (buffer, COND_EXPR_ELSE (node), 0, flags, true);
922 else if (!(flags & TDF_SLIM))
924 /* Output COND_EXPR_THEN. */
925 if (COND_EXPR_THEN (node))
927 newline_and_indent (buffer, spc+2);
928 pp_character (buffer, '{');
929 newline_and_indent (buffer, spc+4);
930 dump_generic_node (buffer, COND_EXPR_THEN (node), spc+4,
931 flags, true);
932 newline_and_indent (buffer, spc+2);
933 pp_character (buffer, '}');
936 /* Output COND_EXPR_ELSE. */
937 if (COND_EXPR_ELSE (node))
939 newline_and_indent (buffer, spc);
940 pp_string (buffer, "else");
941 newline_and_indent (buffer, spc+2);
942 pp_character (buffer, '{');
943 newline_and_indent (buffer, spc+4);
944 dump_generic_node (buffer, COND_EXPR_ELSE (node), spc+4,
945 flags, true);
946 newline_and_indent (buffer, spc+2);
947 pp_character (buffer, '}');
950 is_expr = false;
952 else
954 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
955 pp_space (buffer);
956 pp_character (buffer, '?');
957 pp_space (buffer);
958 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
959 pp_space (buffer);
960 pp_character (buffer, ':');
961 pp_space (buffer);
962 dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
964 break;
966 case BIND_EXPR:
967 pp_character (buffer, '{');
968 if (!(flags & TDF_SLIM))
970 if (BIND_EXPR_VARS (node))
972 pp_newline (buffer);
974 for (op0 = BIND_EXPR_VARS (node); op0; op0 = TREE_CHAIN (op0))
976 print_declaration (buffer, op0, spc+2, flags);
977 pp_newline (buffer);
981 newline_and_indent (buffer, spc+2);
982 dump_generic_node (buffer, BIND_EXPR_BODY (node), spc+2, flags, true);
983 newline_and_indent (buffer, spc);
984 pp_character (buffer, '}');
986 is_expr = false;
987 break;
989 case CALL_EXPR:
990 print_call_name (buffer, node);
992 /* Print parameters. */
993 pp_space (buffer);
994 pp_character (buffer, '(');
995 op1 = TREE_OPERAND (node, 1);
996 if (op1)
997 dump_generic_node (buffer, op1, spc, flags, false);
998 pp_character (buffer, ')');
1000 op1 = TREE_OPERAND (node, 2);
1001 if (op1)
1003 pp_string (buffer, " [static-chain: ");
1004 dump_generic_node (buffer, op1, spc, flags, false);
1005 pp_character (buffer, ']');
1008 if (CALL_EXPR_RETURN_SLOT_OPT (node))
1009 pp_string (buffer, " [return slot optimization]");
1010 if (CALL_EXPR_TAILCALL (node))
1011 pp_string (buffer, " [tail call]");
1012 break;
1014 case WITH_CLEANUP_EXPR:
1015 NIY;
1016 break;
1018 case CLEANUP_POINT_EXPR:
1019 pp_string (buffer, "<<cleanup_point ");
1020 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1021 pp_string (buffer, ">>");
1022 break;
1024 case PLACEHOLDER_EXPR:
1025 pp_string (buffer, "<PLACEHOLDER_EXPR ");
1026 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
1027 pp_character (buffer, '>');
1028 break;
1030 /* Binary arithmetic and logic expressions. */
1031 case MULT_EXPR:
1032 case PLUS_EXPR:
1033 case MINUS_EXPR:
1034 case TRUNC_DIV_EXPR:
1035 case CEIL_DIV_EXPR:
1036 case FLOOR_DIV_EXPR:
1037 case ROUND_DIV_EXPR:
1038 case TRUNC_MOD_EXPR:
1039 case CEIL_MOD_EXPR:
1040 case FLOOR_MOD_EXPR:
1041 case ROUND_MOD_EXPR:
1042 case RDIV_EXPR:
1043 case EXACT_DIV_EXPR:
1044 case LSHIFT_EXPR:
1045 case RSHIFT_EXPR:
1046 case LROTATE_EXPR:
1047 case RROTATE_EXPR:
1048 case VEC_LSHIFT_EXPR:
1049 case VEC_RSHIFT_EXPR:
1050 case BIT_IOR_EXPR:
1051 case BIT_XOR_EXPR:
1052 case BIT_AND_EXPR:
1053 case TRUTH_ANDIF_EXPR:
1054 case TRUTH_ORIF_EXPR:
1055 case TRUTH_AND_EXPR:
1056 case TRUTH_OR_EXPR:
1057 case TRUTH_XOR_EXPR:
1058 case LT_EXPR:
1059 case LE_EXPR:
1060 case GT_EXPR:
1061 case GE_EXPR:
1062 case EQ_EXPR:
1063 case NE_EXPR:
1064 case UNLT_EXPR:
1065 case UNLE_EXPR:
1066 case UNGT_EXPR:
1067 case UNGE_EXPR:
1068 case UNEQ_EXPR:
1069 case LTGT_EXPR:
1070 case ORDERED_EXPR:
1071 case UNORDERED_EXPR:
1073 const char *op = op_symbol (node);
1074 op0 = TREE_OPERAND (node, 0);
1075 op1 = TREE_OPERAND (node, 1);
1077 /* When the operands are expressions with less priority,
1078 keep semantics of the tree representation. */
1079 if (op_prio (op0) < op_prio (node))
1081 pp_character (buffer, '(');
1082 dump_generic_node (buffer, op0, spc, flags, false);
1083 pp_character (buffer, ')');
1085 else
1086 dump_generic_node (buffer, op0, spc, flags, false);
1088 pp_space (buffer);
1089 pp_string (buffer, op);
1090 pp_space (buffer);
1092 /* When the operands are expressions with less priority,
1093 keep semantics of the tree representation. */
1094 if (op_prio (op1) < op_prio (node))
1096 pp_character (buffer, '(');
1097 dump_generic_node (buffer, op1, spc, flags, false);
1098 pp_character (buffer, ')');
1100 else
1101 dump_generic_node (buffer, op1, spc, flags, false);
1103 break;
1105 /* Unary arithmetic and logic expressions. */
1106 case NEGATE_EXPR:
1107 case BIT_NOT_EXPR:
1108 case TRUTH_NOT_EXPR:
1109 case ADDR_EXPR:
1110 case PREDECREMENT_EXPR:
1111 case PREINCREMENT_EXPR:
1112 case ALIGN_INDIRECT_REF:
1113 case MISALIGNED_INDIRECT_REF:
1114 case INDIRECT_REF:
1115 if (TREE_CODE (node) == ADDR_EXPR
1116 && (TREE_CODE (TREE_OPERAND (node, 0)) == STRING_CST
1117 || TREE_CODE (TREE_OPERAND (node, 0)) == FUNCTION_DECL))
1118 ; /* Do not output '&' for strings and function pointers. */
1119 else
1120 pp_string (buffer, op_symbol (node));
1122 if (op_prio (TREE_OPERAND (node, 0)) < op_prio (node))
1124 pp_character (buffer, '(');
1125 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1126 pp_character (buffer, ')');
1128 else
1129 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1131 if (TREE_CODE (node) == MISALIGNED_INDIRECT_REF)
1133 pp_string (buffer, "{misalignment: ");
1134 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1135 pp_character (buffer, '}');
1137 break;
1139 case POSTDECREMENT_EXPR:
1140 case POSTINCREMENT_EXPR:
1141 if (op_prio (TREE_OPERAND (node, 0)) < op_prio (node))
1143 pp_character (buffer, '(');
1144 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1145 pp_character (buffer, ')');
1147 else
1148 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1149 pp_string (buffer, op_symbol (node));
1150 break;
1152 case MIN_EXPR:
1153 pp_string (buffer, "MIN_EXPR <");
1154 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1155 pp_string (buffer, ", ");
1156 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1157 pp_character (buffer, '>');
1158 break;
1160 case MAX_EXPR:
1161 pp_string (buffer, "MAX_EXPR <");
1162 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1163 pp_string (buffer, ", ");
1164 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1165 pp_character (buffer, '>');
1166 break;
1168 case ABS_EXPR:
1169 pp_string (buffer, "ABS_EXPR <");
1170 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1171 pp_character (buffer, '>');
1172 break;
1174 case RANGE_EXPR:
1175 NIY;
1176 break;
1178 case FIX_TRUNC_EXPR:
1179 case FIX_CEIL_EXPR:
1180 case FIX_FLOOR_EXPR:
1181 case FIX_ROUND_EXPR:
1182 case FLOAT_EXPR:
1183 case CONVERT_EXPR:
1184 case NOP_EXPR:
1185 type = TREE_TYPE (node);
1186 op0 = TREE_OPERAND (node, 0);
1187 if (type != TREE_TYPE (op0))
1189 pp_character (buffer, '(');
1190 dump_generic_node (buffer, type, spc, flags, false);
1191 pp_string (buffer, ") ");
1193 if (op_prio (op0) < op_prio (node))
1194 pp_character (buffer, '(');
1195 dump_generic_node (buffer, op0, spc, flags, false);
1196 if (op_prio (op0) < op_prio (node))
1197 pp_character (buffer, ')');
1198 break;
1200 case VIEW_CONVERT_EXPR:
1201 pp_string (buffer, "VIEW_CONVERT_EXPR<");
1202 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
1203 pp_string (buffer, ">(");
1204 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1205 pp_character (buffer, ')');
1206 break;
1208 case NON_LVALUE_EXPR:
1209 pp_string (buffer, "NON_LVALUE_EXPR <");
1210 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1211 pp_character (buffer, '>');
1212 break;
1214 case SAVE_EXPR:
1215 pp_string (buffer, "SAVE_EXPR <");
1216 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1217 pp_character (buffer, '>');
1218 break;
1220 case COMPLEX_EXPR:
1221 pp_string (buffer, "COMPLEX_EXPR <");
1222 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1223 pp_string (buffer, ", ");
1224 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1225 pp_string (buffer, ">");
1226 break;
1228 case CONJ_EXPR:
1229 pp_string (buffer, "CONJ_EXPR <");
1230 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1231 pp_string (buffer, ">");
1232 break;
1234 case REALPART_EXPR:
1235 pp_string (buffer, "REALPART_EXPR <");
1236 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1237 pp_string (buffer, ">");
1238 break;
1240 case IMAGPART_EXPR:
1241 pp_string (buffer, "IMAGPART_EXPR <");
1242 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1243 pp_string (buffer, ">");
1244 break;
1246 case VA_ARG_EXPR:
1247 pp_string (buffer, "VA_ARG_EXPR <");
1248 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1249 pp_string (buffer, ">");
1250 break;
1252 case TRY_FINALLY_EXPR:
1253 case TRY_CATCH_EXPR:
1254 pp_string (buffer, "try");
1255 newline_and_indent (buffer, spc+2);
1256 pp_string (buffer, "{");
1257 newline_and_indent (buffer, spc+4);
1258 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc+4, flags, true);
1259 newline_and_indent (buffer, spc+2);
1260 pp_string (buffer, "}");
1261 newline_and_indent (buffer, spc);
1262 pp_string (buffer,
1263 (TREE_CODE (node) == TRY_CATCH_EXPR) ? "catch" : "finally");
1264 newline_and_indent (buffer, spc+2);
1265 pp_string (buffer, "{");
1266 newline_and_indent (buffer, spc+4);
1267 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc+4, flags, true);
1268 newline_and_indent (buffer, spc+2);
1269 pp_string (buffer, "}");
1270 is_expr = false;
1271 break;
1273 case CATCH_EXPR:
1274 pp_string (buffer, "catch (");
1275 dump_generic_node (buffer, CATCH_TYPES (node), spc+2, flags, false);
1276 pp_string (buffer, ")");
1277 newline_and_indent (buffer, spc+2);
1278 pp_string (buffer, "{");
1279 newline_and_indent (buffer, spc+4);
1280 dump_generic_node (buffer, CATCH_BODY (node), spc+4, flags, true);
1281 newline_and_indent (buffer, spc+2);
1282 pp_string (buffer, "}");
1283 is_expr = false;
1284 break;
1286 case EH_FILTER_EXPR:
1287 pp_string (buffer, "<<<eh_filter (");
1288 dump_generic_node (buffer, EH_FILTER_TYPES (node), spc+2, flags, false);
1289 pp_string (buffer, ")>>>");
1290 newline_and_indent (buffer, spc+2);
1291 pp_string (buffer, "{");
1292 newline_and_indent (buffer, spc+4);
1293 dump_generic_node (buffer, EH_FILTER_FAILURE (node), spc+4, flags, true);
1294 newline_and_indent (buffer, spc+2);
1295 pp_string (buffer, "}");
1296 is_expr = false;
1297 break;
1299 case LABEL_EXPR:
1300 op0 = TREE_OPERAND (node, 0);
1301 /* If this is for break or continue, don't bother printing it. */
1302 if (DECL_NAME (op0))
1304 const char *name = IDENTIFIER_POINTER (DECL_NAME (op0));
1305 if (strcmp (name, "break") == 0
1306 || strcmp (name, "continue") == 0)
1307 break;
1309 dump_generic_node (buffer, op0, spc, flags, false);
1310 pp_character (buffer, ':');
1311 if (DECL_NONLOCAL (op0))
1312 pp_string (buffer, " [non-local]");
1313 break;
1315 case EXC_PTR_EXPR:
1316 pp_string (buffer, "<<<exception object>>>");
1317 break;
1319 case FILTER_EXPR:
1320 pp_string (buffer, "<<<filter object>>>");
1321 break;
1323 case LOOP_EXPR:
1324 pp_string (buffer, "while (1)");
1325 if (!(flags & TDF_SLIM))
1327 newline_and_indent (buffer, spc+2);
1328 pp_character (buffer, '{');
1329 newline_and_indent (buffer, spc+4);
1330 dump_generic_node (buffer, LOOP_EXPR_BODY (node), spc+4, flags, true);
1331 newline_and_indent (buffer, spc+2);
1332 pp_character (buffer, '}');
1334 is_expr = false;
1335 break;
1337 case RETURN_EXPR:
1338 pp_string (buffer, "return");
1339 op0 = TREE_OPERAND (node, 0);
1340 if (op0)
1342 pp_space (buffer);
1343 if (TREE_CODE (op0) == MODIFY_EXPR)
1344 dump_generic_node (buffer, TREE_OPERAND (op0, 1), spc, flags, false);
1345 else
1346 dump_generic_node (buffer, op0, spc, flags, false);
1348 break;
1350 case EXIT_EXPR:
1351 pp_string (buffer, "if (");
1352 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1353 pp_string (buffer, ") break");
1354 break;
1356 case SWITCH_EXPR:
1357 pp_string (buffer, "switch (");
1358 dump_generic_node (buffer, SWITCH_COND (node), spc, flags, false);
1359 pp_character (buffer, ')');
1360 if (!(flags & TDF_SLIM))
1362 newline_and_indent (buffer, spc+2);
1363 pp_character (buffer, '{');
1364 if (SWITCH_BODY (node))
1366 newline_and_indent (buffer, spc+4);
1367 dump_generic_node (buffer, SWITCH_BODY (node), spc+4, flags, true);
1369 else
1371 tree vec = SWITCH_LABELS (node);
1372 size_t i, n = TREE_VEC_LENGTH (vec);
1373 for (i = 0; i < n; ++i)
1375 tree elt = TREE_VEC_ELT (vec, i);
1376 newline_and_indent (buffer, spc+4);
1377 dump_generic_node (buffer, elt, spc+4, flags, false);
1378 pp_string (buffer, " goto ");
1379 dump_generic_node (buffer, CASE_LABEL (elt), spc+4, flags, true);
1380 pp_semicolon (buffer);
1383 newline_and_indent (buffer, spc+2);
1384 pp_character (buffer, '}');
1386 is_expr = false;
1387 break;
1389 case GOTO_EXPR:
1390 op0 = GOTO_DESTINATION (node);
1391 if (TREE_CODE (op0) != SSA_NAME && DECL_P (op0) && DECL_NAME (op0))
1393 const char *name = IDENTIFIER_POINTER (DECL_NAME (op0));
1394 if (strcmp (name, "break") == 0
1395 || strcmp (name, "continue") == 0)
1397 pp_string (buffer, name);
1398 break;
1401 pp_string (buffer, "goto ");
1402 dump_generic_node (buffer, op0, spc, flags, false);
1403 break;
1405 case RESX_EXPR:
1406 pp_string (buffer, "resx");
1407 /* ??? Any sensible way to present the eh region? */
1408 break;
1410 case ASM_EXPR:
1411 pp_string (buffer, "__asm__");
1412 if (ASM_VOLATILE_P (node))
1413 pp_string (buffer, " __volatile__");
1414 pp_character (buffer, '(');
1415 dump_generic_node (buffer, ASM_STRING (node), spc, flags, false);
1416 pp_character (buffer, ':');
1417 dump_generic_node (buffer, ASM_OUTPUTS (node), spc, flags, false);
1418 pp_character (buffer, ':');
1419 dump_generic_node (buffer, ASM_INPUTS (node), spc, flags, false);
1420 if (ASM_CLOBBERS (node))
1422 pp_character (buffer, ':');
1423 dump_generic_node (buffer, ASM_CLOBBERS (node), spc, flags, false);
1425 pp_string (buffer, ")");
1426 break;
1428 case CASE_LABEL_EXPR:
1429 if (CASE_LOW (node) && CASE_HIGH (node))
1431 pp_string (buffer, "case ");
1432 dump_generic_node (buffer, CASE_LOW (node), spc, flags, false);
1433 pp_string (buffer, " ... ");
1434 dump_generic_node (buffer, CASE_HIGH (node), spc, flags, false);
1436 else if (CASE_LOW (node))
1438 pp_string (buffer, "case ");
1439 dump_generic_node (buffer, CASE_LOW (node), spc, flags, false);
1441 else
1442 pp_string (buffer, "default ");
1443 pp_character (buffer, ':');
1444 break;
1446 case OBJ_TYPE_REF:
1447 pp_string (buffer, "OBJ_TYPE_REF(");
1448 dump_generic_node (buffer, OBJ_TYPE_REF_EXPR (node), spc, flags, false);
1449 pp_character (buffer, ';');
1450 dump_generic_node (buffer, OBJ_TYPE_REF_OBJECT (node), spc, flags, false);
1451 pp_character (buffer, '-');
1452 pp_character (buffer, '>');
1453 dump_generic_node (buffer, OBJ_TYPE_REF_TOKEN (node), spc, flags, false);
1454 pp_character (buffer, ')');
1455 break;
1457 case PHI_NODE:
1459 int i;
1461 dump_generic_node (buffer, PHI_RESULT (node), spc, flags, false);
1462 pp_string (buffer, " = PHI <");
1463 for (i = 0; i < PHI_NUM_ARGS (node); i++)
1465 dump_generic_node (buffer, PHI_ARG_DEF (node, i), spc, flags, false);
1466 pp_string (buffer, "(");
1467 pp_decimal_int (buffer, PHI_ARG_EDGE (node, i)->src->index);
1468 pp_string (buffer, ")");
1469 if (i < PHI_NUM_ARGS (node) - 1)
1470 pp_string (buffer, ", ");
1472 pp_string (buffer, ">;");
1474 break;
1476 case SSA_NAME:
1477 dump_generic_node (buffer, SSA_NAME_VAR (node), spc, flags, false);
1478 pp_string (buffer, "_");
1479 pp_decimal_int (buffer, SSA_NAME_VERSION (node));
1480 if (SSA_NAME_OCCURS_IN_ABNORMAL_PHI (node))
1481 pp_string (buffer, "(ab)");
1482 break;
1484 case WITH_SIZE_EXPR:
1485 pp_string (buffer, "WITH_SIZE_EXPR <");
1486 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1487 pp_string (buffer, ", ");
1488 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1489 pp_string (buffer, ">");
1490 break;
1492 case VALUE_HANDLE:
1493 pp_printf (buffer, "VH.%d", VALUE_HANDLE_ID (node));
1494 break;
1496 case ASSERT_EXPR:
1497 pp_string (buffer, "ASSERT_EXPR <");
1498 dump_generic_node (buffer, ASSERT_EXPR_VAR (node), spc, flags, false);
1499 pp_string (buffer, ", ");
1500 dump_generic_node (buffer, ASSERT_EXPR_COND (node), spc, flags, false);
1501 pp_string (buffer, ">");
1502 break;
1504 case SCEV_KNOWN:
1505 pp_string (buffer, "scev_known");
1506 break;
1508 case SCEV_NOT_KNOWN:
1509 pp_string (buffer, "scev_not_known");
1510 break;
1512 case POLYNOMIAL_CHREC:
1513 pp_string (buffer, "{");
1514 dump_generic_node (buffer, CHREC_LEFT (node), spc, flags, false);
1515 pp_string (buffer, ", +, ");
1516 dump_generic_node (buffer, CHREC_RIGHT (node), spc, flags, false);
1517 pp_string (buffer, "}_");
1518 dump_generic_node (buffer, CHREC_VAR (node), spc, flags, false);
1519 is_stmt = false;
1520 break;
1522 case REALIGN_LOAD_EXPR:
1523 pp_string (buffer, "REALIGN_LOAD <");
1524 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1525 pp_string (buffer, ", ");
1526 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1527 pp_string (buffer, ", ");
1528 dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
1529 pp_string (buffer, ">");
1530 break;
1532 case VEC_COND_EXPR:
1533 pp_string (buffer, " VEC_COND_EXPR < ");
1534 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1535 pp_string (buffer, " , ");
1536 dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1537 pp_string (buffer, " , ");
1538 dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
1539 pp_string (buffer, " > ");
1540 break;
1542 case REDUC_MAX_EXPR:
1543 pp_string (buffer, " REDUC_MAX_EXPR < ");
1544 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1545 pp_string (buffer, " > ");
1546 break;
1548 case REDUC_MIN_EXPR:
1549 pp_string (buffer, " REDUC_MIN_EXPR < ");
1550 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1551 pp_string (buffer, " > ");
1552 break;
1554 case REDUC_PLUS_EXPR:
1555 pp_string (buffer, " REDUC_PLUS_EXPR < ");
1556 dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1557 pp_string (buffer, " > ");
1558 break;
1560 default:
1561 NIY;
1564 if (is_stmt && is_expr)
1565 pp_semicolon (buffer);
1566 pp_write_text_to_stream (buffer);
1568 return spc;
1571 /* Print the declaration of a variable. */
1573 static void
1574 print_declaration (pretty_printer *buffer, tree t, int spc, int flags)
1576 INDENT (spc);
1578 if (TREE_CODE (t) == TYPE_DECL)
1579 pp_string (buffer, "typedef ");
1581 if (DECL_REGISTER (t))
1582 pp_string (buffer, "register ");
1584 if (TREE_PUBLIC (t) && DECL_EXTERNAL (t))
1585 pp_string (buffer, "extern ");
1586 else if (TREE_STATIC (t))
1587 pp_string (buffer, "static ");
1589 /* Print the type and name. */
1590 if (TREE_CODE (TREE_TYPE (t)) == ARRAY_TYPE)
1592 tree tmp;
1594 /* Print array's type. */
1595 tmp = TREE_TYPE (t);
1596 while (TREE_CODE (TREE_TYPE (tmp)) == ARRAY_TYPE)
1597 tmp = TREE_TYPE (tmp);
1598 dump_generic_node (buffer, TREE_TYPE (tmp), spc, flags, false);
1600 /* Print variable's name. */
1601 pp_space (buffer);
1602 dump_generic_node (buffer, t, spc, flags, false);
1604 /* Print the dimensions. */
1605 tmp = TREE_TYPE (t);
1606 while (TREE_CODE (tmp) == ARRAY_TYPE)
1608 dump_array_domain (buffer, TYPE_DOMAIN (tmp), spc, flags);
1609 tmp = TREE_TYPE (tmp);
1612 else if (TREE_CODE (t) == FUNCTION_DECL)
1614 dump_generic_node (buffer, TREE_TYPE (TREE_TYPE (t)), spc, flags, false);
1615 pp_space (buffer);
1616 dump_decl_name (buffer, t, flags);
1617 dump_function_declaration (buffer, TREE_TYPE (t), spc, flags);
1619 else
1621 /* Print type declaration. */
1622 dump_generic_node (buffer, TREE_TYPE (t), spc, flags, false);
1624 /* Print variable's name. */
1625 pp_space (buffer);
1626 dump_generic_node (buffer, t, spc, flags, false);
1629 if (TREE_CODE (t) == VAR_DECL && DECL_HARD_REGISTER (t))
1631 pp_string (buffer, " __asm__ ");
1632 pp_character (buffer, '(');
1633 dump_generic_node (buffer, DECL_ASSEMBLER_NAME (t), spc, flags, false);
1634 pp_character (buffer, ')');
1637 /* The initial value of a function serves to determine wether the function
1638 is declared or defined. So the following does not apply to function
1639 nodes. */
1640 if (TREE_CODE (t) != FUNCTION_DECL)
1642 /* Print the initial value. */
1643 if (DECL_INITIAL (t))
1645 pp_space (buffer);
1646 pp_character (buffer, '=');
1647 pp_space (buffer);
1648 dump_generic_node (buffer, DECL_INITIAL (t), spc, flags, false);
1652 pp_character (buffer, ';');
1656 /* Prints a structure: name, fields, and methods.
1657 FIXME: Still incomplete. */
1659 static void
1660 print_struct_decl (pretty_printer *buffer, tree node, int spc, int flags)
1662 /* Print the name of the structure. */
1663 if (TYPE_NAME (node))
1665 INDENT (spc);
1666 if (TREE_CODE (node) == RECORD_TYPE)
1667 pp_string (buffer, "struct ");
1668 else if ((TREE_CODE (node) == UNION_TYPE
1669 || TREE_CODE (node) == QUAL_UNION_TYPE))
1670 pp_string (buffer, "union ");
1672 dump_generic_node (buffer, TYPE_NAME (node), spc, 0, false);
1675 /* Print the contents of the structure. */
1676 pp_newline (buffer);
1677 INDENT (spc);
1678 pp_character (buffer, '{');
1679 pp_newline (buffer);
1681 /* Print the fields of the structure. */
1683 tree tmp;
1684 tmp = TYPE_FIELDS (node);
1685 while (tmp)
1687 /* Avoid to print recursively the structure. */
1688 /* FIXME : Not implemented correctly...,
1689 what about the case when we have a cycle in the contain graph? ...
1690 Maybe this could be solved by looking at the scope in which the
1691 structure was declared. */
1692 if (TREE_TYPE (tmp) != node
1693 || (TREE_CODE (TREE_TYPE (tmp)) == POINTER_TYPE
1694 && TREE_TYPE (TREE_TYPE (tmp)) != node))
1696 print_declaration (buffer, tmp, spc+2, flags);
1697 pp_newline (buffer);
1699 tmp = TREE_CHAIN (tmp);
1702 INDENT (spc);
1703 pp_character (buffer, '}');
1706 /* Return the priority of the operator OP.
1708 From lowest to highest precedence with either left-to-right (L-R)
1709 or right-to-left (R-L) associativity]:
1711 1 [L-R] ,
1712 2 [R-L] = += -= *= /= %= &= ^= |= <<= >>=
1713 3 [R-L] ?:
1714 4 [L-R] ||
1715 5 [L-R] &&
1716 6 [L-R] |
1717 7 [L-R] ^
1718 8 [L-R] &
1719 9 [L-R] == !=
1720 10 [L-R] < <= > >=
1721 11 [L-R] << >>
1722 12 [L-R] + -
1723 13 [L-R] * / %
1724 14 [R-L] ! ~ ++ -- + - * & (type) sizeof
1725 15 [L-R] fn() [] -> .
1727 unary +, - and * have higher precedence than the corresponding binary
1728 operators. */
1730 static int
1731 op_prio (tree op)
1733 if (op == NULL)
1734 return 9999;
1736 switch (TREE_CODE (op))
1738 case TREE_LIST:
1739 case COMPOUND_EXPR:
1740 case BIND_EXPR:
1741 return 1;
1743 case MODIFY_EXPR:
1744 case INIT_EXPR:
1745 return 2;
1747 case COND_EXPR:
1748 return 3;
1750 case TRUTH_OR_EXPR:
1751 case TRUTH_ORIF_EXPR:
1752 return 4;
1754 case TRUTH_AND_EXPR:
1755 case TRUTH_ANDIF_EXPR:
1756 return 5;
1758 case BIT_IOR_EXPR:
1759 return 6;
1761 case BIT_XOR_EXPR:
1762 case TRUTH_XOR_EXPR:
1763 return 7;
1765 case BIT_AND_EXPR:
1766 return 8;
1768 case EQ_EXPR:
1769 case NE_EXPR:
1770 return 9;
1772 case UNLT_EXPR:
1773 case UNLE_EXPR:
1774 case UNGT_EXPR:
1775 case UNGE_EXPR:
1776 case UNEQ_EXPR:
1777 case LTGT_EXPR:
1778 case ORDERED_EXPR:
1779 case UNORDERED_EXPR:
1780 case LT_EXPR:
1781 case LE_EXPR:
1782 case GT_EXPR:
1783 case GE_EXPR:
1784 return 10;
1786 case LSHIFT_EXPR:
1787 case RSHIFT_EXPR:
1788 case LROTATE_EXPR:
1789 case RROTATE_EXPR:
1790 return 11;
1792 case PLUS_EXPR:
1793 case MINUS_EXPR:
1794 return 12;
1796 case MULT_EXPR:
1797 case TRUNC_DIV_EXPR:
1798 case CEIL_DIV_EXPR:
1799 case FLOOR_DIV_EXPR:
1800 case ROUND_DIV_EXPR:
1801 case RDIV_EXPR:
1802 case EXACT_DIV_EXPR:
1803 case TRUNC_MOD_EXPR:
1804 case CEIL_MOD_EXPR:
1805 case FLOOR_MOD_EXPR:
1806 case ROUND_MOD_EXPR:
1807 return 13;
1809 case TRUTH_NOT_EXPR:
1810 case BIT_NOT_EXPR:
1811 case POSTINCREMENT_EXPR:
1812 case POSTDECREMENT_EXPR:
1813 case PREINCREMENT_EXPR:
1814 case PREDECREMENT_EXPR:
1815 case NEGATE_EXPR:
1816 case ALIGN_INDIRECT_REF:
1817 case MISALIGNED_INDIRECT_REF:
1818 case INDIRECT_REF:
1819 case ADDR_EXPR:
1820 case FLOAT_EXPR:
1821 case NOP_EXPR:
1822 case CONVERT_EXPR:
1823 case FIX_TRUNC_EXPR:
1824 case FIX_CEIL_EXPR:
1825 case FIX_FLOOR_EXPR:
1826 case FIX_ROUND_EXPR:
1827 case TARGET_EXPR:
1828 return 14;
1830 case CALL_EXPR:
1831 case ARRAY_REF:
1832 case ARRAY_RANGE_REF:
1833 case COMPONENT_REF:
1834 return 15;
1836 /* Special expressions. */
1837 case MIN_EXPR:
1838 case MAX_EXPR:
1839 case ABS_EXPR:
1840 case REALPART_EXPR:
1841 case IMAGPART_EXPR:
1842 case REDUC_MAX_EXPR:
1843 case REDUC_MIN_EXPR:
1844 case REDUC_PLUS_EXPR:
1845 case VEC_LSHIFT_EXPR:
1846 case VEC_RSHIFT_EXPR:
1847 return 16;
1849 case SAVE_EXPR:
1850 case NON_LVALUE_EXPR:
1851 return op_prio (TREE_OPERAND (op, 0));
1853 default:
1854 /* Return an arbitrarily high precedence to avoid surrounding single
1855 VAR_DECLs in ()s. */
1856 return 9999;
1861 /* Return the symbol associated with operator OP. */
1863 static const char *
1864 op_symbol (tree op)
1866 gcc_assert (op);
1868 switch (TREE_CODE (op))
1870 case MODIFY_EXPR:
1871 return "=";
1873 case TRUTH_OR_EXPR:
1874 case TRUTH_ORIF_EXPR:
1875 return "||";
1877 case TRUTH_AND_EXPR:
1878 case TRUTH_ANDIF_EXPR:
1879 return "&&";
1881 case BIT_IOR_EXPR:
1882 return "|";
1884 case TRUTH_XOR_EXPR:
1885 case BIT_XOR_EXPR:
1886 return "^";
1888 case ADDR_EXPR:
1889 case BIT_AND_EXPR:
1890 return "&";
1892 case ORDERED_EXPR:
1893 return "ord";
1894 case UNORDERED_EXPR:
1895 return "unord";
1897 case EQ_EXPR:
1898 return "==";
1899 case UNEQ_EXPR:
1900 return "u==";
1902 case NE_EXPR:
1903 return "!=";
1905 case LT_EXPR:
1906 return "<";
1907 case UNLT_EXPR:
1908 return "u<";
1910 case LE_EXPR:
1911 return "<=";
1912 case UNLE_EXPR:
1913 return "u<=";
1915 case GT_EXPR:
1916 return ">";
1917 case UNGT_EXPR:
1918 return "u>";
1920 case GE_EXPR:
1921 return ">=";
1922 case UNGE_EXPR:
1923 return "u>=";
1925 case LTGT_EXPR:
1926 return "<>";
1928 case LSHIFT_EXPR:
1929 return "<<";
1931 case RSHIFT_EXPR:
1932 return ">>";
1934 case VEC_LSHIFT_EXPR:
1935 return "v<<";
1937 case VEC_RSHIFT_EXPR:
1938 return "v>>";
1940 case PLUS_EXPR:
1941 return "+";
1943 case REDUC_PLUS_EXPR:
1944 return "r+";
1946 case NEGATE_EXPR:
1947 case MINUS_EXPR:
1948 return "-";
1950 case BIT_NOT_EXPR:
1951 return "~";
1953 case TRUTH_NOT_EXPR:
1954 return "!";
1956 case MULT_EXPR:
1957 case INDIRECT_REF:
1958 return "*";
1960 case ALIGN_INDIRECT_REF:
1961 return "A*";
1963 case MISALIGNED_INDIRECT_REF:
1964 return "M*";
1966 case TRUNC_DIV_EXPR:
1967 case RDIV_EXPR:
1968 return "/";
1970 case CEIL_DIV_EXPR:
1971 return "/[cl]";
1973 case FLOOR_DIV_EXPR:
1974 return "/[fl]";
1976 case ROUND_DIV_EXPR:
1977 return "/[rd]";
1979 case EXACT_DIV_EXPR:
1980 return "/[ex]";
1982 case TRUNC_MOD_EXPR:
1983 return "%";
1985 case CEIL_MOD_EXPR:
1986 return "%[cl]";
1988 case FLOOR_MOD_EXPR:
1989 return "%[fl]";
1991 case ROUND_MOD_EXPR:
1992 return "%[rd]";
1994 case PREDECREMENT_EXPR:
1995 return " --";
1997 case PREINCREMENT_EXPR:
1998 return " ++";
2000 case POSTDECREMENT_EXPR:
2001 return "-- ";
2003 case POSTINCREMENT_EXPR:
2004 return "++ ";
2006 default:
2007 return "<<< ??? >>>";
2011 /* Prints the name of a CALL_EXPR. */
2013 static void
2014 print_call_name (pretty_printer *buffer, tree node)
2016 tree op0;
2018 gcc_assert (TREE_CODE (node) == CALL_EXPR);
2020 op0 = TREE_OPERAND (node, 0);
2022 if (TREE_CODE (op0) == NON_LVALUE_EXPR)
2023 op0 = TREE_OPERAND (op0, 0);
2025 switch (TREE_CODE (op0))
2027 case VAR_DECL:
2028 case PARM_DECL:
2029 dump_function_name (buffer, op0);
2030 break;
2032 case ADDR_EXPR:
2033 case INDIRECT_REF:
2034 case NOP_EXPR:
2035 dump_generic_node (buffer, TREE_OPERAND (op0, 0), 0, 0, false);
2036 break;
2038 case COND_EXPR:
2039 pp_string (buffer, "(");
2040 dump_generic_node (buffer, TREE_OPERAND (op0, 0), 0, 0, false);
2041 pp_string (buffer, ") ? ");
2042 dump_generic_node (buffer, TREE_OPERAND (op0, 1), 0, 0, false);
2043 pp_string (buffer, " : ");
2044 dump_generic_node (buffer, TREE_OPERAND (op0, 2), 0, 0, false);
2045 break;
2047 case COMPONENT_REF:
2048 /* The function is a pointer contained in a structure. */
2049 if (TREE_CODE (TREE_OPERAND (op0, 0)) == INDIRECT_REF ||
2050 TREE_CODE (TREE_OPERAND (op0, 0)) == VAR_DECL)
2051 dump_function_name (buffer, TREE_OPERAND (op0, 1));
2052 else
2053 dump_generic_node (buffer, TREE_OPERAND (op0, 0), 0, 0, false);
2054 /* else
2055 We can have several levels of structures and a function
2056 pointer inside. This is not implemented yet... */
2057 /* NIY;*/
2058 break;
2060 case ARRAY_REF:
2061 if (TREE_CODE (TREE_OPERAND (op0, 0)) == VAR_DECL)
2062 dump_function_name (buffer, TREE_OPERAND (op0, 0));
2063 else
2064 dump_generic_node (buffer, op0, 0, 0, false);
2065 break;
2067 case SSA_NAME:
2068 case OBJ_TYPE_REF:
2069 dump_generic_node (buffer, op0, 0, 0, false);
2070 break;
2072 default:
2073 NIY;
2077 /* Parses the string STR and replaces new-lines by '\n', tabs by '\t', ... */
2079 static void
2080 pretty_print_string (pretty_printer *buffer, const char *str)
2082 if (str == NULL)
2083 return;
2085 while (*str)
2087 switch (str[0])
2089 case '\b':
2090 pp_string (buffer, "\\b");
2091 break;
2093 case '\f':
2094 pp_string (buffer, "\\f");
2095 break;
2097 case '\n':
2098 pp_string (buffer, "\\n");
2099 break;
2101 case '\r':
2102 pp_string (buffer, "\\r");
2103 break;
2105 case '\t':
2106 pp_string (buffer, "\\t");
2107 break;
2109 case '\v':
2110 pp_string (buffer, "\\v");
2111 break;
2113 case '\\':
2114 pp_string (buffer, "\\\\");
2115 break;
2117 case '\"':
2118 pp_string (buffer, "\\\"");
2119 break;
2121 case '\'':
2122 pp_string (buffer, "\\'");
2123 break;
2125 case '\0':
2126 pp_string (buffer, "\\0");
2127 break;
2129 case '\1':
2130 pp_string (buffer, "\\1");
2131 break;
2133 case '\2':
2134 pp_string (buffer, "\\2");
2135 break;
2137 case '\3':
2138 pp_string (buffer, "\\3");
2139 break;
2141 case '\4':
2142 pp_string (buffer, "\\4");
2143 break;
2145 case '\5':
2146 pp_string (buffer, "\\5");
2147 break;
2149 case '\6':
2150 pp_string (buffer, "\\6");
2151 break;
2153 case '\7':
2154 pp_string (buffer, "\\7");
2155 break;
2157 default:
2158 pp_character (buffer, str[0]);
2159 break;
2161 str++;
2165 static void
2166 maybe_init_pretty_print (FILE *file)
2168 if (!initialized)
2170 pp_construct (&buffer, /* prefix */NULL, /* line-width */0);
2171 pp_needs_newline (&buffer) = true;
2172 initialized = 1;
2175 buffer.buffer->stream = file;
2178 static void
2179 newline_and_indent (pretty_printer *buffer, int spc)
2181 pp_newline (buffer);
2182 INDENT (spc);
2185 static void
2186 dump_vops (pretty_printer *buffer, tree stmt, int spc, int flags)
2188 tree use;
2189 use_operand_p use_p;
2190 def_operand_p def_p;
2191 use_operand_p kill_p;
2192 ssa_op_iter iter;
2194 if (!ssa_operands_active ())
2195 return;
2197 FOR_EACH_SSA_MAYDEF_OPERAND (def_p, use_p, stmt, iter)
2199 pp_string (buffer, "# ");
2200 dump_generic_node (buffer, DEF_FROM_PTR (def_p),
2201 spc + 2, flags, false);
2202 pp_string (buffer, " = V_MAY_DEF <");
2203 dump_generic_node (buffer, USE_FROM_PTR (use_p),
2204 spc + 2, flags, false);
2205 pp_string (buffer, ">;");
2206 newline_and_indent (buffer, spc);
2209 FOR_EACH_SSA_MUSTDEF_OPERAND (def_p, kill_p, stmt, iter)
2211 pp_string (buffer, "# ");
2212 dump_generic_node (buffer, DEF_FROM_PTR (def_p),
2213 spc + 2, flags, false);
2214 pp_string (buffer, " = V_MUST_DEF <");
2215 dump_generic_node (buffer, USE_FROM_PTR (kill_p),
2216 spc + 2, flags, false);
2217 pp_string (buffer, ">;");
2218 newline_and_indent (buffer, spc);
2221 FOR_EACH_SSA_TREE_OPERAND (use, stmt, iter, SSA_OP_VUSE)
2223 pp_string (buffer, "# VUSE <");
2224 dump_generic_node (buffer, use, spc + 2, flags, false);
2225 pp_string (buffer, ">;");
2226 newline_and_indent (buffer, spc);
2230 /* Dumps basic block BB to FILE with details described by FLAGS and
2231 indented by INDENT spaces. */
2233 void
2234 dump_generic_bb (FILE *file, basic_block bb, int indent, int flags)
2236 maybe_init_pretty_print (file);
2237 dumping_stmts = true;
2238 dump_generic_bb_buff (&buffer, bb, indent, flags);
2239 pp_flush (&buffer);
2242 /* Dumps header of basic block BB to buffer BUFFER indented by INDENT
2243 spaces and details described by flags. */
2245 static void
2246 dump_bb_header (pretty_printer *buffer, basic_block bb, int indent, int flags)
2248 edge e;
2249 tree stmt;
2250 edge_iterator ei;
2252 if (flags & TDF_BLOCKS)
2254 INDENT (indent);
2255 pp_string (buffer, "# BLOCK ");
2256 pp_decimal_int (buffer, bb->index);
2258 if (flags & TDF_LINENO)
2260 block_stmt_iterator bsi;
2262 for (bsi = bsi_start (bb); !bsi_end_p (bsi); bsi_next (&bsi))
2263 if (get_lineno (bsi_stmt (bsi)) != -1)
2265 pp_string (buffer, ", starting at line ");
2266 pp_decimal_int (buffer, get_lineno (bsi_stmt (bsi)));
2267 break;
2270 newline_and_indent (buffer, indent);
2272 pp_string (buffer, "# PRED:");
2273 pp_write_text_to_stream (buffer);
2274 FOR_EACH_EDGE (e, ei, bb->preds)
2275 if (flags & TDF_SLIM)
2277 pp_string (buffer, " ");
2278 if (e->src == ENTRY_BLOCK_PTR)
2279 pp_string (buffer, "ENTRY");
2280 else
2281 pp_decimal_int (buffer, e->src->index);
2283 else
2284 dump_edge_info (buffer->buffer->stream, e, 0);
2285 pp_newline (buffer);
2287 else
2289 stmt = first_stmt (bb);
2290 if (!stmt || TREE_CODE (stmt) != LABEL_EXPR)
2292 INDENT (indent - 2);
2293 pp_string (buffer, "<bb ");
2294 pp_decimal_int (buffer, bb->index);
2295 pp_string (buffer, ">:");
2296 pp_newline (buffer);
2299 pp_write_text_to_stream (buffer);
2300 check_bb_profile (bb, buffer->buffer->stream);
2303 /* Dumps end of basic block BB to buffer BUFFER indented by INDENT
2304 spaces. */
2306 static void
2307 dump_bb_end (pretty_printer *buffer, basic_block bb, int indent, int flags)
2309 edge e;
2310 edge_iterator ei;
2312 INDENT (indent);
2313 pp_string (buffer, "# SUCC:");
2314 pp_write_text_to_stream (buffer);
2315 FOR_EACH_EDGE (e, ei, bb->succs)
2316 if (flags & TDF_SLIM)
2318 pp_string (buffer, " ");
2319 if (e->dest == EXIT_BLOCK_PTR)
2320 pp_string (buffer, "EXIT");
2321 else
2322 pp_decimal_int (buffer, e->dest->index);
2324 else
2325 dump_edge_info (buffer->buffer->stream, e, 1);
2326 pp_newline (buffer);
2329 /* Dumps phi nodes of basic block BB to buffer BUFFER with details described by
2330 FLAGS indented by INDENT spaces. */
2332 static void
2333 dump_phi_nodes (pretty_printer *buffer, basic_block bb, int indent, int flags)
2335 tree phi = phi_nodes (bb);
2336 if (!phi)
2337 return;
2339 for (; phi; phi = PHI_CHAIN (phi))
2341 if (is_gimple_reg (PHI_RESULT (phi)) || (flags & TDF_VOPS))
2343 INDENT (indent);
2344 pp_string (buffer, "# ");
2345 dump_generic_node (buffer, phi, indent, flags, false);
2346 pp_newline (buffer);
2351 /* Dump jump to basic block BB that is represented implicitly in the cfg
2352 to BUFFER. */
2354 static void
2355 pp_cfg_jump (pretty_printer *buffer, basic_block bb)
2357 tree stmt;
2359 stmt = first_stmt (bb);
2361 pp_string (buffer, "goto <bb ");
2362 pp_decimal_int (buffer, bb->index);
2363 pp_string (buffer, ">");
2364 if (stmt && TREE_CODE (stmt) == LABEL_EXPR)
2366 pp_string (buffer, " (");
2367 dump_generic_node (buffer, LABEL_EXPR_LABEL (stmt), 0, 0, false);
2368 pp_string (buffer, ")");
2370 pp_semicolon (buffer);
2373 /* Dump edges represented implicitly in basic block BB to BUFFER, indented
2374 by INDENT spaces, with details given by FLAGS. */
2376 static void
2377 dump_implicit_edges (pretty_printer *buffer, basic_block bb, int indent,
2378 int flags)
2380 edge e;
2381 edge_iterator ei;
2383 /* If there is a fallthru edge, we may need to add an artificial goto to the
2384 dump. */
2385 FOR_EACH_EDGE (e, ei, bb->succs)
2386 if (e->flags & EDGE_FALLTHRU)
2387 break;
2388 if (e && e->dest != bb->next_bb)
2390 INDENT (indent);
2392 if ((flags & TDF_LINENO)
2393 #ifdef USE_MAPPED_LOCATION
2394 && e->goto_locus != UNKNOWN_LOCATION
2395 #else
2396 && e->goto_locus
2397 #endif
2400 expanded_location goto_xloc;
2401 #ifdef USE_MAPPED_LOCATION
2402 goto_xloc = expand_location (e->goto_locus);
2403 #else
2404 goto_xloc = *e->goto_locus;
2405 #endif
2406 pp_character (buffer, '[');
2407 if (goto_xloc.file)
2409 pp_string (buffer, goto_xloc.file);
2410 pp_string (buffer, " : ");
2412 pp_decimal_int (buffer, goto_xloc.line);
2413 pp_string (buffer, "] ");
2416 pp_cfg_jump (buffer, e->dest);
2417 pp_newline (buffer);
2421 /* Dumps basic block BB to buffer BUFFER with details described by FLAGS and
2422 indented by INDENT spaces. */
2424 static void
2425 dump_generic_bb_buff (pretty_printer *buffer, basic_block bb,
2426 int indent, int flags)
2428 block_stmt_iterator bsi;
2429 tree stmt;
2430 int label_indent = indent - 2;
2432 if (label_indent < 0)
2433 label_indent = 0;
2435 dump_bb_header (buffer, bb, indent, flags);
2437 dump_phi_nodes (buffer, bb, indent, flags);
2439 for (bsi = bsi_start (bb); !bsi_end_p (bsi); bsi_next (&bsi))
2441 int curr_indent;
2443 stmt = bsi_stmt (bsi);
2445 curr_indent = TREE_CODE (stmt) == LABEL_EXPR ? label_indent : indent;
2447 INDENT (curr_indent);
2448 dump_generic_node (buffer, stmt, curr_indent, flags, true);
2449 pp_newline (buffer);
2452 dump_implicit_edges (buffer, bb, indent, flags);
2454 if (flags & TDF_BLOCKS)
2455 dump_bb_end (buffer, bb, indent, flags);