OSDN Git Service

2011-09-27 Sriraman Tallam <tmsriram@google.com>
[pf3gnuchains/gcc-fork.git] / gcc / tree-pretty-print.c
1 /* Pretty formatting of GENERIC trees in C syntax.
2    Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010,
3    2011  Free Software Foundation, Inc.
4    Adapted from c-pretty-print.c by Diego Novillo <dnovillo@redhat.com>
5
6 This file is part of GCC.
7
8 GCC is free software; you can redistribute it and/or modify it under
9 the terms of the GNU General Public License as published by the Free
10 Software Foundation; either version 3, or (at your option) any later
11 version.
12
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.
17
18 You should have received a copy of the GNU General Public License
19 along with GCC; see the file COPYING3.  If not see
20 <http://www.gnu.org/licenses/>.  */
21
22 #include "config.h"
23 #include "system.h"
24 #include "coretypes.h"
25 #include "tm.h"
26 #include "tree.h"
27 #include "output.h"
28 #include "tree-pretty-print.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"
35 #include "value-prof.h"
36 #include "predict.h"
37
38 /* Local functions, macros and variables.  */
39 static const char *op_symbol (const_tree);
40 static void pretty_print_string (pretty_printer *, const char*);
41 static void newline_and_indent (pretty_printer *, int);
42 static void maybe_init_pretty_print (FILE *);
43 static void print_struct_decl (pretty_printer *, const_tree, int, int);
44 static void do_niy (pretty_printer *, const_tree);
45
46 #define INDENT(SPACE) do { \
47   int i; for (i = 0; i<SPACE; i++) pp_space (buffer); } while (0)
48
49 #define NIY do_niy(buffer,node)
50
51 static pretty_printer buffer;
52 static int initialized = 0;
53
54 /* Try to print something for an unknown tree code.  */
55
56 static void
57 do_niy (pretty_printer *buffer, const_tree node)
58 {
59   int i, len;
60
61   pp_string (buffer, "<<< Unknown tree: ");
62   pp_string (buffer, tree_code_name[(int) TREE_CODE (node)]);
63
64   if (EXPR_P (node))
65     {
66       len = TREE_OPERAND_LENGTH (node);
67       for (i = 0; i < len; ++i)
68         {
69           newline_and_indent (buffer, 2);
70           dump_generic_node (buffer, TREE_OPERAND (node, i), 2, 0, false);
71         }
72     }
73
74   pp_string (buffer, " >>>");
75 }
76
77 /* Debugging function to print out a generic expression.  */
78
79 DEBUG_FUNCTION void
80 debug_generic_expr (tree t)
81 {
82   print_generic_expr (stderr, t, TDF_VOPS|TDF_MEMSYMS);
83   fprintf (stderr, "\n");
84 }
85
86 /* Debugging function to print out a generic statement.  */
87
88 DEBUG_FUNCTION void
89 debug_generic_stmt (tree t)
90 {
91   print_generic_stmt (stderr, t, TDF_VOPS|TDF_MEMSYMS);
92   fprintf (stderr, "\n");
93 }
94
95 /* Debugging function to print out a chain of trees .  */
96
97 DEBUG_FUNCTION void
98 debug_tree_chain (tree t)
99 {
100   struct pointer_set_t *seen = pointer_set_create ();
101
102   while (t)
103     {
104       print_generic_expr (stderr, t, TDF_VOPS|TDF_MEMSYMS|TDF_UID);
105       fprintf (stderr, " ");
106       t = TREE_CHAIN (t);
107       if (pointer_set_insert (seen, t))
108         {
109           fprintf (stderr, "... [cycled back to ");
110           print_generic_expr (stderr, t, TDF_VOPS|TDF_MEMSYMS|TDF_UID);
111           fprintf (stderr, "]");
112           break;
113         }
114     }
115   fprintf (stderr, "\n");
116
117   pointer_set_destroy (seen);
118 }
119
120 /* Prints declaration DECL to the FILE with details specified by FLAGS.  */
121 void
122 print_generic_decl (FILE *file, tree decl, int flags)
123 {
124   maybe_init_pretty_print (file);
125   print_declaration (&buffer, decl, 2, flags);
126   pp_write_text_to_stream (&buffer);
127 }
128
129 /* Print tree T, and its successors, on file FILE.  FLAGS specifies details
130    to show in the dump.  See TDF_* in tree-pass.h.  */
131
132 void
133 print_generic_stmt (FILE *file, tree t, int flags)
134 {
135   maybe_init_pretty_print (file);
136   dump_generic_node (&buffer, t, 0, flags, true);
137   pp_flush (&buffer);
138 }
139
140 /* Print tree T, and its successors, on file FILE.  FLAGS specifies details
141    to show in the dump.  See TDF_* in tree-pass.h.  The output is indented by
142    INDENT spaces.  */
143
144 void
145 print_generic_stmt_indented (FILE *file, tree t, int flags, int indent)
146 {
147   int i;
148
149   maybe_init_pretty_print (file);
150
151   for (i = 0; i < indent; i++)
152     pp_space (&buffer);
153   dump_generic_node (&buffer, t, indent, flags, true);
154   pp_flush (&buffer);
155 }
156
157 /* Print a single expression T on file FILE.  FLAGS specifies details to show
158    in the dump.  See TDF_* in tree-pass.h.  */
159
160 void
161 print_generic_expr (FILE *file, tree t, int flags)
162 {
163   maybe_init_pretty_print (file);
164   dump_generic_node (&buffer, t, 0, flags, false);
165 }
166
167 /* Dump the name of a _DECL node and its DECL_UID if TDF_UID is set
168    in FLAGS.  */
169
170 static void
171 dump_decl_name (pretty_printer *buffer, tree node, int flags)
172 {
173   if (DECL_NAME (node))
174     {
175       if ((flags & TDF_ASMNAME) && DECL_ASSEMBLER_NAME_SET_P (node))
176         pp_tree_identifier (buffer, DECL_ASSEMBLER_NAME (node));
177       else
178         pp_tree_identifier (buffer, DECL_NAME (node));
179     }
180   if ((flags & TDF_UID) || DECL_NAME (node) == NULL_TREE)
181     {
182       if (TREE_CODE (node) == LABEL_DECL && LABEL_DECL_UID (node) != -1)
183         pp_printf (buffer, "L.%d", (int) LABEL_DECL_UID (node));
184       else if (TREE_CODE (node) == DEBUG_EXPR_DECL)
185         {
186           if (flags & TDF_NOUID)
187             pp_string (buffer, "D#xxxx");
188           else
189             pp_printf (buffer, "D#%i", DEBUG_TEMP_UID (node));
190         }
191       else
192         {
193           char c = TREE_CODE (node) == CONST_DECL ? 'C' : 'D';
194           if (flags & TDF_NOUID)
195             pp_printf (buffer, "%c.xxxx", c);
196           else
197             pp_printf (buffer, "%c.%u", c, DECL_UID (node));
198         }
199     }
200   if ((flags & TDF_ALIAS) && DECL_PT_UID (node) != DECL_UID (node))
201     {
202       if (flags & TDF_NOUID)
203         pp_printf (buffer, "ptD.xxxx");
204       else
205         pp_printf (buffer, "ptD.%u", DECL_PT_UID (node));
206     }
207 }
208
209 /* Like the above, but used for pretty printing function calls.  */
210
211 static void
212 dump_function_name (pretty_printer *buffer, tree node, int flags)
213 {
214   if (TREE_CODE (node) == NOP_EXPR)
215     node = TREE_OPERAND (node, 0);
216   if (DECL_NAME (node) && (flags & TDF_ASMNAME) == 0)
217     pp_string (buffer, lang_hooks.decl_printable_name (node, 1));
218   else
219     dump_decl_name (buffer, node, flags);
220 }
221
222 /* Dump a function declaration.  NODE is the FUNCTION_TYPE.  BUFFER, SPC and
223    FLAGS are as in dump_generic_node.  */
224
225 static void
226 dump_function_declaration (pretty_printer *buffer, tree node,
227                            int spc, int flags)
228 {
229   bool wrote_arg = false;
230   tree arg;
231
232   pp_space (buffer);
233   pp_character (buffer, '(');
234
235   /* Print the argument types.  */
236   arg = TYPE_ARG_TYPES (node);
237   while (arg && arg != void_list_node && arg != error_mark_node)
238     {
239       if (wrote_arg)
240         {
241           pp_character (buffer, ',');
242           pp_space (buffer);
243         }
244       wrote_arg = true;
245       dump_generic_node (buffer, TREE_VALUE (arg), spc, flags, false);
246       arg = TREE_CHAIN (arg);
247     }
248
249   /* Drop the trailing void_type_node if we had any previous argument.  */
250   if (arg == void_list_node && !wrote_arg)
251     pp_string (buffer, "void");
252   /* Properly dump vararg function types.  */
253   else if (!arg && wrote_arg)
254     pp_string (buffer, ", ...");
255   /* Avoid printing any arg for unprototyped functions.  */
256
257   pp_character (buffer, ')');
258 }
259
260 /* Dump the domain associated with an array.  */
261
262 static void
263 dump_array_domain (pretty_printer *buffer, tree domain, int spc, int flags)
264 {
265   pp_character (buffer, '[');
266   if (domain)
267     {
268       tree min = TYPE_MIN_VALUE (domain);
269       tree max = TYPE_MAX_VALUE (domain);
270
271       if (min && max
272           && integer_zerop (min)
273           && host_integerp (max, 0))
274         pp_wide_integer (buffer, TREE_INT_CST_LOW (max) + 1);
275       else
276         {
277           if (min)
278             dump_generic_node (buffer, min, spc, flags, false);
279           pp_character (buffer, ':');
280           if (max)
281             dump_generic_node (buffer, max, spc, flags, false);
282         }
283     }
284   else
285     pp_string (buffer, "<unknown>");
286   pp_character (buffer, ']');
287 }
288
289
290 /* Dump OpenMP clause CLAUSE.  BUFFER, CLAUSE, SPC and FLAGS are as in
291    dump_generic_node.  */
292
293 static void
294 dump_omp_clause (pretty_printer *buffer, tree clause, int spc, int flags)
295 {
296   const char *name;
297
298   switch (OMP_CLAUSE_CODE (clause))
299     {
300     case OMP_CLAUSE_PRIVATE:
301       name = "private";
302       goto print_remap;
303     case OMP_CLAUSE_SHARED:
304       name = "shared";
305       goto print_remap;
306     case OMP_CLAUSE_FIRSTPRIVATE:
307       name = "firstprivate";
308       goto print_remap;
309     case OMP_CLAUSE_LASTPRIVATE:
310       name = "lastprivate";
311       goto print_remap;
312     case OMP_CLAUSE_COPYIN:
313       name = "copyin";
314       goto print_remap;
315     case OMP_CLAUSE_COPYPRIVATE:
316       name = "copyprivate";
317       goto print_remap;
318   print_remap:
319       pp_string (buffer, name);
320       pp_character (buffer, '(');
321       dump_generic_node (buffer, OMP_CLAUSE_DECL (clause),
322           spc, flags, false);
323       pp_character (buffer, ')');
324       break;
325
326     case OMP_CLAUSE_REDUCTION:
327       pp_string (buffer, "reduction(");
328       pp_string (buffer, op_symbol_code (OMP_CLAUSE_REDUCTION_CODE (clause)));
329       pp_character (buffer, ':');
330       dump_generic_node (buffer, OMP_CLAUSE_DECL (clause),
331           spc, flags, false);
332       pp_character (buffer, ')');
333       break;
334
335     case OMP_CLAUSE_IF:
336       pp_string (buffer, "if(");
337       dump_generic_node (buffer, OMP_CLAUSE_IF_EXPR (clause),
338           spc, flags, false);
339       pp_character (buffer, ')');
340       break;
341
342     case OMP_CLAUSE_NUM_THREADS:
343       pp_string (buffer, "num_threads(");
344       dump_generic_node (buffer, OMP_CLAUSE_NUM_THREADS_EXPR (clause),
345           spc, flags, false);
346       pp_character (buffer, ')');
347       break;
348
349     case OMP_CLAUSE_NOWAIT:
350       pp_string (buffer, "nowait");
351       break;
352     case OMP_CLAUSE_ORDERED:
353       pp_string (buffer, "ordered");
354       break;
355
356     case OMP_CLAUSE_DEFAULT:
357       pp_string (buffer, "default(");
358       switch (OMP_CLAUSE_DEFAULT_KIND (clause))
359         {
360         case OMP_CLAUSE_DEFAULT_UNSPECIFIED:
361           break;
362         case OMP_CLAUSE_DEFAULT_SHARED:
363           pp_string (buffer, "shared");
364           break;
365         case OMP_CLAUSE_DEFAULT_NONE:
366           pp_string (buffer, "none");
367           break;
368         case OMP_CLAUSE_DEFAULT_PRIVATE:
369           pp_string (buffer, "private");
370           break;
371         case OMP_CLAUSE_DEFAULT_FIRSTPRIVATE:
372           pp_string (buffer, "firstprivate");
373           break;
374         default:
375           gcc_unreachable ();
376         }
377       pp_character (buffer, ')');
378       break;
379
380     case OMP_CLAUSE_SCHEDULE:
381       pp_string (buffer, "schedule(");
382       switch (OMP_CLAUSE_SCHEDULE_KIND (clause))
383         {
384       case OMP_CLAUSE_SCHEDULE_STATIC:
385         pp_string (buffer, "static");
386         break;
387       case OMP_CLAUSE_SCHEDULE_DYNAMIC:
388         pp_string (buffer, "dynamic");
389         break;
390       case OMP_CLAUSE_SCHEDULE_GUIDED:
391         pp_string (buffer, "guided");
392         break;
393       case OMP_CLAUSE_SCHEDULE_RUNTIME:
394         pp_string (buffer, "runtime");
395         break;
396       case OMP_CLAUSE_SCHEDULE_AUTO:
397         pp_string (buffer, "auto");
398         break;
399       default:
400         gcc_unreachable ();
401         }
402       if (OMP_CLAUSE_SCHEDULE_CHUNK_EXPR (clause))
403         {
404           pp_character (buffer, ',');
405           dump_generic_node (buffer,
406               OMP_CLAUSE_SCHEDULE_CHUNK_EXPR (clause),
407               spc, flags, false);
408         }
409       pp_character (buffer, ')');
410       break;
411
412     case OMP_CLAUSE_UNTIED:
413       pp_string (buffer, "untied");
414       break;
415
416     case OMP_CLAUSE_COLLAPSE:
417       pp_string (buffer, "collapse(");
418       dump_generic_node (buffer,
419                          OMP_CLAUSE_COLLAPSE_EXPR (clause),
420                          spc, flags, false);
421       pp_character (buffer, ')');
422       break;
423
424     case OMP_CLAUSE_FINAL:
425       pp_string (buffer, "final(");
426       dump_generic_node (buffer, OMP_CLAUSE_FINAL_EXPR (clause),
427           spc, flags, false);
428       pp_character (buffer, ')');
429       break;
430
431     case OMP_CLAUSE_MERGEABLE:
432       pp_string (buffer, "mergeable");
433       break;
434
435     default:
436       /* Should never happen.  */
437       dump_generic_node (buffer, clause, spc, flags, false);
438       break;
439     }
440 }
441
442
443 /* Dump the list of OpenMP clauses.  BUFFER, SPC and FLAGS are as in
444    dump_generic_node.  */
445
446 void
447 dump_omp_clauses (pretty_printer *buffer, tree clause, int spc, int flags)
448 {
449   if (clause == NULL)
450     return;
451
452   pp_space (buffer);
453   while (1)
454     {
455       dump_omp_clause (buffer, clause, spc, flags);
456       clause = OMP_CLAUSE_CHAIN (clause);
457       if (clause == NULL)
458         return;
459       pp_space (buffer);
460     }
461 }
462
463
464 /* Dump location LOC to BUFFER.  */
465
466 static void
467 dump_location (pretty_printer *buffer, location_t loc)
468 {
469   expanded_location xloc = expand_location (loc);
470
471   pp_character (buffer, '[');
472   if (xloc.file)
473     {
474       pp_string (buffer, xloc.file);
475       pp_string (buffer, " : ");
476     }
477   pp_decimal_int (buffer, xloc.line);
478   pp_string (buffer, "] ");
479 }
480
481
482 /* Dump lexical block BLOCK.  BUFFER, SPC and FLAGS are as in
483    dump_generic_node.  */
484
485 static void
486 dump_block_node (pretty_printer *buffer, tree block, int spc, int flags)
487 {
488   tree t;
489
490   pp_printf (buffer, "BLOCK #%d ", BLOCK_NUMBER (block));
491
492   if (flags & TDF_ADDRESS)
493     pp_printf (buffer, "[%p] ", (void *) block);
494
495   if (BLOCK_ABSTRACT (block))
496     pp_string (buffer, "[abstract] ");
497
498   if (TREE_ASM_WRITTEN (block))
499     pp_string (buffer, "[written] ");
500
501   if (flags & TDF_SLIM)
502     return;
503
504   if (BLOCK_SOURCE_LOCATION (block))
505     dump_location (buffer, BLOCK_SOURCE_LOCATION (block));
506
507   newline_and_indent (buffer, spc + 2);
508
509   if (BLOCK_SUPERCONTEXT (block))
510     {
511       pp_string (buffer, "SUPERCONTEXT: ");
512       dump_generic_node (buffer, BLOCK_SUPERCONTEXT (block), 0,
513                          flags | TDF_SLIM, false);
514       newline_and_indent (buffer, spc + 2);
515     }
516
517   if (BLOCK_SUBBLOCKS (block))
518     {
519       pp_string (buffer, "SUBBLOCKS: ");
520       for (t = BLOCK_SUBBLOCKS (block); t; t = BLOCK_CHAIN (t))
521         {
522           dump_generic_node (buffer, t, 0, flags | TDF_SLIM, false);
523           pp_string (buffer, " ");
524         }
525       newline_and_indent (buffer, spc + 2);
526     }
527
528   if (BLOCK_CHAIN (block))
529     {
530       pp_string (buffer, "SIBLINGS: ");
531       for (t = BLOCK_CHAIN (block); t; t = BLOCK_CHAIN (t))
532         {
533           dump_generic_node (buffer, t, 0, flags | TDF_SLIM, false);
534           pp_string (buffer, " ");
535         }
536       newline_and_indent (buffer, spc + 2);
537     }
538
539   if (BLOCK_VARS (block))
540     {
541       pp_string (buffer, "VARS: ");
542       for (t = BLOCK_VARS (block); t; t = TREE_CHAIN (t))
543         {
544           dump_generic_node (buffer, t, 0, flags, false);
545           pp_string (buffer, " ");
546         }
547       newline_and_indent (buffer, spc + 2);
548     }
549
550   if (VEC_length (tree, BLOCK_NONLOCALIZED_VARS (block)) > 0)
551     {
552       unsigned i;
553       VEC(tree,gc) *nlv = BLOCK_NONLOCALIZED_VARS (block);
554
555       pp_string (buffer, "NONLOCALIZED_VARS: ");
556       FOR_EACH_VEC_ELT (tree, nlv, i, t)
557         {
558           dump_generic_node (buffer, t, 0, flags, false);
559           pp_string (buffer, " ");
560         }
561       newline_and_indent (buffer, spc + 2);
562     }
563
564   if (BLOCK_ABSTRACT_ORIGIN (block))
565     {
566       pp_string (buffer, "ABSTRACT_ORIGIN: ");
567       dump_generic_node (buffer, BLOCK_ABSTRACT_ORIGIN (block), 0,
568                          flags | TDF_SLIM, false);
569       newline_and_indent (buffer, spc + 2);
570     }
571
572   if (BLOCK_FRAGMENT_ORIGIN (block))
573     {
574       pp_string (buffer, "FRAGMENT_ORIGIN: ");
575       dump_generic_node (buffer, BLOCK_FRAGMENT_ORIGIN (block), 0,
576                          flags | TDF_SLIM, false);
577       newline_and_indent (buffer, spc + 2);
578     }
579
580   if (BLOCK_FRAGMENT_CHAIN (block))
581     {
582       pp_string (buffer, "FRAGMENT_CHAIN: ");
583       for (t = BLOCK_FRAGMENT_CHAIN (block); t; t = BLOCK_FRAGMENT_CHAIN (t))
584         {
585           dump_generic_node (buffer, t, 0, flags | TDF_SLIM, false);
586           pp_string (buffer, " ");
587         }
588       newline_and_indent (buffer, spc + 2);
589     }
590 }
591
592
593 /* Dump the node NODE on the pretty_printer BUFFER, SPC spaces of
594    indent.  FLAGS specifies details to show in the dump (see TDF_* in
595    tree-pass.h).  If IS_STMT is true, the object printed is considered
596    to be a statement and it is terminated by ';' if appropriate.  */
597
598 int
599 dump_generic_node (pretty_printer *buffer, tree node, int spc, int flags,
600                    bool is_stmt)
601 {
602   tree type;
603   tree op0, op1;
604   const char *str;
605   bool is_expr;
606
607   if (node == NULL_TREE)
608     return spc;
609
610   is_expr = EXPR_P (node);
611
612   if (is_stmt && (flags & TDF_STMTADDR))
613     pp_printf (buffer, "<&%p> ", (void *)node);
614
615   if ((flags & TDF_LINENO) && EXPR_HAS_LOCATION (node))
616     dump_location (buffer, EXPR_LOCATION (node));
617
618   switch (TREE_CODE (node))
619     {
620     case ERROR_MARK:
621       pp_string (buffer, "<<< error >>>");
622       break;
623
624     case IDENTIFIER_NODE:
625       pp_tree_identifier (buffer, node);
626       break;
627
628     case TREE_LIST:
629       while (node && node != error_mark_node)
630         {
631           if (TREE_PURPOSE (node))
632             {
633               dump_generic_node (buffer, TREE_PURPOSE (node), spc, flags, false);
634               pp_space (buffer);
635             }
636           dump_generic_node (buffer, TREE_VALUE (node), spc, flags, false);
637           node = TREE_CHAIN (node);
638           if (node && TREE_CODE (node) == TREE_LIST)
639             {
640               pp_character (buffer, ',');
641               pp_space (buffer);
642             }
643         }
644       break;
645
646     case TREE_BINFO:
647       dump_generic_node (buffer, BINFO_TYPE (node), spc, flags, false);
648       break;
649
650     case TREE_VEC:
651       {
652         size_t i;
653         if (TREE_VEC_LENGTH (node) > 0)
654           {
655             size_t len = TREE_VEC_LENGTH (node);
656             for (i = 0; i < len - 1; i++)
657               {
658                 dump_generic_node (buffer, TREE_VEC_ELT (node, i), spc, flags,
659                                    false);
660                 pp_character (buffer, ',');
661                 pp_space (buffer);
662               }
663             dump_generic_node (buffer, TREE_VEC_ELT (node, len - 1), spc,
664                                flags, false);
665           }
666       }
667       break;
668
669     case VOID_TYPE:
670     case INTEGER_TYPE:
671     case REAL_TYPE:
672     case FIXED_POINT_TYPE:
673     case COMPLEX_TYPE:
674     case VECTOR_TYPE:
675     case ENUMERAL_TYPE:
676     case BOOLEAN_TYPE:
677       {
678         unsigned int quals = TYPE_QUALS (node);
679         enum tree_code_class tclass;
680
681         if (quals & TYPE_QUAL_CONST)
682           pp_string (buffer, "const ");
683         else if (quals & TYPE_QUAL_VOLATILE)
684           pp_string (buffer, "volatile ");
685         else if (quals & TYPE_QUAL_RESTRICT)
686           pp_string (buffer, "restrict ");
687
688         if (!ADDR_SPACE_GENERIC_P (TYPE_ADDR_SPACE (node)))
689           {
690             pp_string (buffer, "<address-space-");
691             pp_decimal_int (buffer, TYPE_ADDR_SPACE (node));
692             pp_string (buffer, "> ");
693           }
694
695         tclass = TREE_CODE_CLASS (TREE_CODE (node));
696
697         if (tclass == tcc_declaration)
698           {
699             if (DECL_NAME (node))
700               dump_decl_name (buffer, node, flags);
701             else
702               pp_string (buffer, "<unnamed type decl>");
703           }
704         else if (tclass == tcc_type)
705           {
706             if (TYPE_NAME (node))
707               {
708                 if (TREE_CODE (TYPE_NAME (node)) == IDENTIFIER_NODE)
709                   pp_tree_identifier (buffer, TYPE_NAME (node));
710                 else if (TREE_CODE (TYPE_NAME (node)) == TYPE_DECL
711                          && DECL_NAME (TYPE_NAME (node)))
712                   dump_decl_name (buffer, TYPE_NAME (node), flags);
713                 else
714                   pp_string (buffer, "<unnamed type>");
715               }
716             else if (TREE_CODE (node) == VECTOR_TYPE)
717               {
718                 pp_string (buffer, "vector");
719                 pp_character (buffer, '(');
720                 pp_wide_integer (buffer, TYPE_VECTOR_SUBPARTS (node));
721                 pp_string (buffer, ") ");
722                 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
723               }
724             else if (TREE_CODE (node) == INTEGER_TYPE)
725               {
726                 pp_string (buffer, (TYPE_UNSIGNED (node)
727                                     ? "<unnamed-unsigned:"
728                                     : "<unnamed-signed:"));
729                 pp_decimal_int (buffer, TYPE_PRECISION (node));
730                 pp_string (buffer, ">");
731               }
732             else if (TREE_CODE (node) == COMPLEX_TYPE)
733               {
734                 pp_string (buffer, "__complex__ ");
735                 dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
736               }
737             else if (TREE_CODE (node) == REAL_TYPE)
738               {
739                 pp_string (buffer, "<float:");
740                 pp_decimal_int (buffer, TYPE_PRECISION (node));
741                 pp_string (buffer, ">");
742               }
743             else if (TREE_CODE (node) == FIXED_POINT_TYPE)
744               {
745                 pp_string (buffer, "<fixed-point-");
746                 pp_string (buffer, TYPE_SATURATING (node) ? "sat:" : "nonsat:");
747                 pp_decimal_int (buffer, TYPE_PRECISION (node));
748                 pp_string (buffer, ">");
749               }
750             else if (TREE_CODE (node) == VOID_TYPE)
751               pp_string (buffer, "void");
752             else
753               pp_string (buffer, "<unnamed type>");
754           }
755         break;
756       }
757
758     case POINTER_TYPE:
759     case REFERENCE_TYPE:
760       str = (TREE_CODE (node) == POINTER_TYPE ? "*" : "&");
761
762       if (TREE_TYPE (node) == NULL)
763         {
764           pp_string (buffer, str);
765           pp_string (buffer, "<null type>");
766         }
767       else if (TREE_CODE (TREE_TYPE (node)) == FUNCTION_TYPE)
768         {
769           tree fnode = TREE_TYPE (node);
770
771           dump_generic_node (buffer, TREE_TYPE (fnode), spc, flags, false);
772           pp_space (buffer);
773           pp_character (buffer, '(');
774           pp_string (buffer, str);
775           if (TYPE_NAME (node) && DECL_NAME (TYPE_NAME (node)))
776             dump_decl_name (buffer, TYPE_NAME (node), flags);
777           else if (flags & TDF_NOUID)
778             pp_printf (buffer, "<Txxxx>");
779           else
780             pp_printf (buffer, "<T%x>", TYPE_UID (node));
781
782           pp_character (buffer, ')');
783           dump_function_declaration (buffer, fnode, spc, flags);
784         }
785       else
786         {
787           unsigned int quals = TYPE_QUALS (node);
788
789           dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
790           pp_space (buffer);
791           pp_string (buffer, str);
792
793           if (quals & TYPE_QUAL_CONST)
794             pp_string (buffer, " const");
795           if (quals & TYPE_QUAL_VOLATILE)
796             pp_string (buffer, " volatile");
797           if (quals & TYPE_QUAL_RESTRICT)
798             pp_string (buffer, " restrict");
799
800           if (!ADDR_SPACE_GENERIC_P (TYPE_ADDR_SPACE (node)))
801             {
802               pp_string (buffer, " <address-space-");
803               pp_decimal_int (buffer, TYPE_ADDR_SPACE (node));
804               pp_string (buffer, ">");
805             }
806
807           if (TYPE_REF_CAN_ALIAS_ALL (node))
808             pp_string (buffer, " {ref-all}");
809         }
810       break;
811
812     case OFFSET_TYPE:
813       NIY;
814       break;
815
816     case MEM_REF:
817       {
818         if (integer_zerop (TREE_OPERAND (node, 1))
819             /* Dump the types of INTEGER_CSTs explicitly, for we can't
820                infer them and MEM_ATTR caching will share MEM_REFs
821                with differently-typed op0s.  */
822             && TREE_CODE (TREE_OPERAND (node, 0)) != INTEGER_CST
823             /* Released SSA_NAMES have no TREE_TYPE.  */
824             && TREE_TYPE (TREE_OPERAND (node, 0)) != NULL_TREE
825             /* Same pointer types, but ignoring POINTER_TYPE vs.
826                REFERENCE_TYPE.  */
827             && (TREE_TYPE (TREE_TYPE (TREE_OPERAND (node, 0)))
828                 == TREE_TYPE (TREE_TYPE (TREE_OPERAND (node, 1))))
829             && (TYPE_MODE (TREE_TYPE (TREE_OPERAND (node, 0)))
830                 == TYPE_MODE (TREE_TYPE (TREE_OPERAND (node, 1))))
831             && (TYPE_REF_CAN_ALIAS_ALL (TREE_TYPE (TREE_OPERAND (node, 0)))
832                 == TYPE_REF_CAN_ALIAS_ALL (TREE_TYPE (TREE_OPERAND (node, 1))))
833             /* Same value types ignoring qualifiers.  */
834             && (TYPE_MAIN_VARIANT (TREE_TYPE (node))
835                 == TYPE_MAIN_VARIANT
836                     (TREE_TYPE (TREE_TYPE (TREE_OPERAND (node, 1))))))
837           {
838             if (TREE_CODE (TREE_OPERAND (node, 0)) != ADDR_EXPR)
839               {
840                 pp_string (buffer, "*");
841                 dump_generic_node (buffer, TREE_OPERAND (node, 0),
842                                    spc, flags, false);
843               }
844             else
845               dump_generic_node (buffer,
846                                  TREE_OPERAND (TREE_OPERAND (node, 0), 0),
847                                  spc, flags, false);
848           }
849         else
850           {
851             tree ptype;
852
853             pp_string (buffer, "MEM[");
854             pp_string (buffer, "(");
855             ptype = TYPE_MAIN_VARIANT (TREE_TYPE (TREE_OPERAND (node, 1)));
856             dump_generic_node (buffer, ptype,
857                                spc, flags | TDF_SLIM, false);
858             pp_string (buffer, ")");
859             dump_generic_node (buffer, TREE_OPERAND (node, 0),
860                                spc, flags, false);
861             if (!integer_zerop (TREE_OPERAND (node, 1)))
862               {
863                 pp_string (buffer, " + ");
864                 dump_generic_node (buffer, TREE_OPERAND (node, 1),
865                                    spc, flags, false);
866               }
867             pp_string (buffer, "]");
868           }
869         break;
870       }
871
872     case TARGET_MEM_REF:
873       {
874         const char *sep = "";
875         tree tmp;
876
877         pp_string (buffer, "MEM[");
878
879         if (TREE_CODE (TMR_BASE (node)) == ADDR_EXPR)
880           {
881             pp_string (buffer, sep);
882             sep = ", ";
883             pp_string (buffer, "symbol: ");
884             dump_generic_node (buffer, TREE_OPERAND (TMR_BASE (node), 0),
885                                spc, flags, false);
886           }
887         else
888           {
889             pp_string (buffer, sep);
890             sep = ", ";
891             pp_string (buffer, "base: ");
892             dump_generic_node (buffer, TMR_BASE (node), spc, flags, false);
893           }
894         tmp = TMR_INDEX2 (node);
895         if (tmp)
896           {
897             pp_string (buffer, sep);
898             sep = ", ";
899             pp_string (buffer, "base: ");
900             dump_generic_node (buffer, tmp, spc, flags, false);
901           }
902         tmp = TMR_INDEX (node);
903         if (tmp)
904           {
905             pp_string (buffer, sep);
906             sep = ", ";
907             pp_string (buffer, "index: ");
908             dump_generic_node (buffer, tmp, spc, flags, false);
909           }
910         tmp = TMR_STEP (node);
911         if (tmp)
912           {
913             pp_string (buffer, sep);
914             sep = ", ";
915             pp_string (buffer, "step: ");
916             dump_generic_node (buffer, tmp, spc, flags, false);
917           }
918         tmp = TMR_OFFSET (node);
919         if (tmp)
920           {
921             pp_string (buffer, sep);
922             sep = ", ";
923             pp_string (buffer, "offset: ");
924             dump_generic_node (buffer, tmp, spc, flags, false);
925           }
926         pp_string (buffer, "]");
927       }
928       break;
929
930     case ARRAY_TYPE:
931       {
932         tree tmp;
933
934         /* Print the innermost component type.  */
935         for (tmp = TREE_TYPE (node); TREE_CODE (tmp) == ARRAY_TYPE;
936              tmp = TREE_TYPE (tmp))
937           ;
938         dump_generic_node (buffer, tmp, spc, flags, false);
939
940         /* Print the dimensions.  */
941         for (tmp = node; TREE_CODE (tmp) == ARRAY_TYPE; tmp = TREE_TYPE (tmp))
942           dump_array_domain (buffer, TYPE_DOMAIN (tmp), spc, flags);
943         break;
944       }
945
946     case RECORD_TYPE:
947     case UNION_TYPE:
948     case QUAL_UNION_TYPE:
949       {
950         unsigned int quals = TYPE_QUALS (node);
951
952         if (quals & TYPE_QUAL_CONST)
953           pp_string (buffer, "const ");
954         if (quals & TYPE_QUAL_VOLATILE)
955           pp_string (buffer, "volatile ");
956
957         /* Print the name of the structure.  */
958         if (TREE_CODE (node) == RECORD_TYPE)
959           pp_string (buffer, "struct ");
960         else if (TREE_CODE (node) == UNION_TYPE)
961           pp_string (buffer, "union ");
962
963         if (TYPE_NAME (node))
964           dump_generic_node (buffer, TYPE_NAME (node), spc, flags, false);
965         else if (!(flags & TDF_SLIM))
966           /* FIXME: If we eliminate the 'else' above and attempt
967              to show the fields for named types, we may get stuck
968              following a cycle of pointers to structs.  The alleged
969              self-reference check in print_struct_decl will not detect
970              cycles involving more than one pointer or struct type.  */
971           print_struct_decl (buffer, node, spc, flags);
972         break;
973       }
974
975     case LANG_TYPE:
976       NIY;
977       break;
978
979     case INTEGER_CST:
980       if (TREE_CODE (TREE_TYPE (node)) == POINTER_TYPE)
981         {
982           /* In the case of a pointer, one may want to divide by the
983              size of the pointed-to type.  Unfortunately, this not
984              straightforward.  The C front-end maps expressions
985
986              (int *) 5
987              int *p; (p + 5)
988
989              in such a way that the two INTEGER_CST nodes for "5" have
990              different values but identical types.  In the latter
991              case, the 5 is multiplied by sizeof (int) in c-common.c
992              (pointer_int_sum) to convert it to a byte address, and
993              yet the type of the node is left unchanged.  Argh.  What
994              is consistent though is that the number value corresponds
995              to bytes (UNITS) offset.
996
997              NB: Neither of the following divisors can be trivially
998              used to recover the original literal:
999
1000              TREE_INT_CST_LOW (TYPE_SIZE_UNIT (TREE_TYPE (node)))
1001              TYPE_PRECISION (TREE_TYPE (TREE_TYPE (node)))  */
1002           pp_wide_integer (buffer, TREE_INT_CST_LOW (node));
1003           pp_string (buffer, "B"); /* pseudo-unit */
1004         }
1005       else if (host_integerp (node, 0))
1006         pp_wide_integer (buffer, TREE_INT_CST_LOW (node));
1007       else if (host_integerp (node, 1))
1008         pp_unsigned_wide_integer (buffer, TREE_INT_CST_LOW (node));
1009       else
1010         {
1011           tree val = node;
1012           unsigned HOST_WIDE_INT low = TREE_INT_CST_LOW (val);
1013           HOST_WIDE_INT high = TREE_INT_CST_HIGH (val);
1014
1015           if (tree_int_cst_sgn (val) < 0)
1016             {
1017               pp_character (buffer, '-');
1018               high = ~high + !low;
1019               low = -low;
1020             }
1021           /* Would "%x%0*x" or "%x%*0x" get zero-padding on all
1022              systems?  */
1023           sprintf (pp_buffer (buffer)->digit_buffer,
1024                    HOST_WIDE_INT_PRINT_DOUBLE_HEX,
1025                    (unsigned HOST_WIDE_INT) high, low);
1026           pp_string (buffer, pp_buffer (buffer)->digit_buffer);
1027         }
1028       break;
1029
1030     case REAL_CST:
1031       /* Code copied from print_node.  */
1032       {
1033         REAL_VALUE_TYPE d;
1034         if (TREE_OVERFLOW (node))
1035           pp_string (buffer, " overflow");
1036
1037 #if !defined(REAL_IS_NOT_DOUBLE) || defined(REAL_ARITHMETIC)
1038         d = TREE_REAL_CST (node);
1039         if (REAL_VALUE_ISINF (d))
1040           pp_string (buffer, REAL_VALUE_NEGATIVE (d) ? " -Inf" : " Inf");
1041         else if (REAL_VALUE_ISNAN (d))
1042           pp_string (buffer, " Nan");
1043         else
1044           {
1045             char string[100];
1046             real_to_decimal (string, &d, sizeof (string), 0, 1);
1047             pp_string (buffer, string);
1048           }
1049 #else
1050         {
1051           HOST_WIDE_INT i;
1052           unsigned char *p = (unsigned char *) &TREE_REAL_CST (node);
1053           pp_string (buffer, "0x");
1054           for (i = 0; i < sizeof TREE_REAL_CST (node); i++)
1055             output_formatted_integer (buffer, "%02x", *p++);
1056         }
1057 #endif
1058         break;
1059       }
1060
1061     case FIXED_CST:
1062       {
1063         char string[100];
1064         fixed_to_decimal (string, TREE_FIXED_CST_PTR (node), sizeof (string));
1065         pp_string (buffer, string);
1066         break;
1067       }
1068
1069     case COMPLEX_CST:
1070       pp_string (buffer, "__complex__ (");
1071       dump_generic_node (buffer, TREE_REALPART (node), spc, flags, false);
1072       pp_string (buffer, ", ");
1073       dump_generic_node (buffer, TREE_IMAGPART (node), spc, flags, false);
1074       pp_string (buffer, ")");
1075       break;
1076
1077     case STRING_CST:
1078       pp_string (buffer, "\"");
1079       pretty_print_string (buffer, TREE_STRING_POINTER (node));
1080       pp_string (buffer, "\"");
1081       break;
1082
1083     case VECTOR_CST:
1084       {
1085         tree elt;
1086         pp_string (buffer, "{ ");
1087         for (elt = TREE_VECTOR_CST_ELTS (node); elt; elt = TREE_CHAIN (elt))
1088           {
1089             dump_generic_node (buffer, TREE_VALUE (elt), spc, flags, false);
1090             if (TREE_CHAIN (elt))
1091               pp_string (buffer, ", ");
1092           }
1093         pp_string (buffer, " }");
1094       }
1095       break;
1096
1097     case FUNCTION_TYPE:
1098     case METHOD_TYPE:
1099       dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
1100       pp_space (buffer);
1101       if (TREE_CODE (node) == METHOD_TYPE)
1102         {
1103           if (TYPE_METHOD_BASETYPE (node))
1104             dump_decl_name (buffer, TYPE_NAME (TYPE_METHOD_BASETYPE (node)),
1105                             flags);
1106           else
1107             pp_string (buffer, "<null method basetype>");
1108           pp_string (buffer, "::");
1109         }
1110       if (TYPE_NAME (node) && DECL_NAME (TYPE_NAME (node)))
1111         dump_decl_name (buffer, TYPE_NAME (node), flags);
1112       else if (flags & TDF_NOUID)
1113         pp_printf (buffer, "<Txxxx>");
1114       else
1115         pp_printf (buffer, "<T%x>", TYPE_UID (node));
1116       dump_function_declaration (buffer, node, spc, flags);
1117       break;
1118
1119     case FUNCTION_DECL:
1120     case CONST_DECL:
1121       dump_decl_name (buffer, node, flags);
1122       break;
1123
1124     case LABEL_DECL:
1125       if (DECL_NAME (node))
1126         dump_decl_name (buffer, node, flags);
1127       else if (LABEL_DECL_UID (node) != -1)
1128         pp_printf (buffer, "<L%d>", (int) LABEL_DECL_UID (node));
1129       else
1130         {
1131           if (flags & TDF_NOUID)
1132             pp_string (buffer, "<D.xxxx>");
1133           else
1134             pp_printf (buffer, "<D.%u>", DECL_UID (node));
1135         }
1136       break;
1137
1138     case TYPE_DECL:
1139       if (DECL_IS_BUILTIN (node))
1140         {
1141           /* Don't print the declaration of built-in types.  */
1142           break;
1143         }
1144       if (DECL_NAME (node))
1145         dump_decl_name (buffer, node, flags);
1146       else if (TYPE_NAME (TREE_TYPE (node)) != node)
1147         {
1148           if ((TREE_CODE (TREE_TYPE (node)) == RECORD_TYPE
1149                || TREE_CODE (TREE_TYPE (node)) == UNION_TYPE)
1150               && TYPE_METHODS (TREE_TYPE (node)))
1151             {
1152               /* The type is a c++ class: all structures have at least
1153                  4 methods.  */
1154               pp_string (buffer, "class ");
1155               dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
1156             }
1157           else
1158             {
1159               pp_string (buffer,
1160                          (TREE_CODE (TREE_TYPE (node)) == UNION_TYPE
1161                           ? "union" : "struct "));
1162               dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
1163             }
1164         }
1165       else
1166         pp_string (buffer, "<anon>");
1167       break;
1168
1169     case VAR_DECL:
1170     case PARM_DECL:
1171     case FIELD_DECL:
1172     case DEBUG_EXPR_DECL:
1173     case NAMESPACE_DECL:
1174       dump_decl_name (buffer, node, flags);
1175       break;
1176
1177     case RESULT_DECL:
1178       pp_string (buffer, "<retval>");
1179       break;
1180
1181     case COMPONENT_REF:
1182       op0 = TREE_OPERAND (node, 0);
1183       str = ".";
1184       if (op0
1185           && (TREE_CODE (op0) == INDIRECT_REF
1186               || (TREE_CODE (op0) == MEM_REF
1187                   && TREE_CODE (TREE_OPERAND (op0, 0)) != ADDR_EXPR
1188                   && integer_zerop (TREE_OPERAND (op0, 1))
1189                   /* Dump the types of INTEGER_CSTs explicitly, for we
1190                      can't infer them and MEM_ATTR caching will share
1191                      MEM_REFs with differently-typed op0s.  */
1192                   && TREE_CODE (TREE_OPERAND (op0, 0)) != INTEGER_CST
1193                   /* Released SSA_NAMES have no TREE_TYPE.  */
1194                   && TREE_TYPE (TREE_OPERAND (op0, 0)) != NULL_TREE
1195                   /* Same pointer types, but ignoring POINTER_TYPE vs.
1196                      REFERENCE_TYPE.  */
1197                   && (TREE_TYPE (TREE_TYPE (TREE_OPERAND (op0, 0)))
1198                       == TREE_TYPE (TREE_TYPE (TREE_OPERAND (op0, 1))))
1199                   && (TYPE_MODE (TREE_TYPE (TREE_OPERAND (op0, 0)))
1200                       == TYPE_MODE (TREE_TYPE (TREE_OPERAND (op0, 1))))
1201                   && (TYPE_REF_CAN_ALIAS_ALL (TREE_TYPE (TREE_OPERAND (op0, 0)))
1202                       == TYPE_REF_CAN_ALIAS_ALL (TREE_TYPE (TREE_OPERAND (op0, 1))))
1203                   /* Same value types ignoring qualifiers.  */
1204                   && (TYPE_MAIN_VARIANT (TREE_TYPE (op0))
1205                       == TYPE_MAIN_VARIANT
1206                           (TREE_TYPE (TREE_TYPE (TREE_OPERAND (op0, 1))))))))
1207         {
1208           op0 = TREE_OPERAND (op0, 0);
1209           str = "->";
1210         }
1211       if (op_prio (op0) < op_prio (node))
1212         pp_character (buffer, '(');
1213       dump_generic_node (buffer, op0, spc, flags, false);
1214       if (op_prio (op0) < op_prio (node))
1215         pp_character (buffer, ')');
1216       pp_string (buffer, str);
1217       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1218       op0 = component_ref_field_offset (node);
1219       if (op0 && TREE_CODE (op0) != INTEGER_CST)
1220         {
1221           pp_string (buffer, "{off: ");
1222               dump_generic_node (buffer, op0, spc, flags, false);
1223               pp_character (buffer, '}');
1224         }
1225       break;
1226
1227     case BIT_FIELD_REF:
1228       pp_string (buffer, "BIT_FIELD_REF <");
1229       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1230       pp_string (buffer, ", ");
1231       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1232       pp_string (buffer, ", ");
1233       dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
1234       pp_string (buffer, ">");
1235       break;
1236
1237     case ARRAY_REF:
1238     case ARRAY_RANGE_REF:
1239       op0 = TREE_OPERAND (node, 0);
1240       if (op_prio (op0) < op_prio (node))
1241         pp_character (buffer, '(');
1242       dump_generic_node (buffer, op0, spc, flags, false);
1243       if (op_prio (op0) < op_prio (node))
1244         pp_character (buffer, ')');
1245       pp_character (buffer, '[');
1246       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1247       if (TREE_CODE (node) == ARRAY_RANGE_REF)
1248         pp_string (buffer, " ...");
1249       pp_character (buffer, ']');
1250
1251       op0 = array_ref_low_bound (node);
1252       op1 = array_ref_element_size (node);
1253
1254       if (!integer_zerop (op0)
1255           || TREE_OPERAND (node, 2)
1256           || TREE_OPERAND (node, 3))
1257         {
1258           pp_string (buffer, "{lb: ");
1259           dump_generic_node (buffer, op0, spc, flags, false);
1260           pp_string (buffer, " sz: ");
1261           dump_generic_node (buffer, op1, spc, flags, false);
1262           pp_character (buffer, '}');
1263         }
1264       break;
1265
1266     case CONSTRUCTOR:
1267       {
1268         unsigned HOST_WIDE_INT ix;
1269         tree field, val;
1270         bool is_struct_init = false;
1271         bool is_array_init = false;
1272         double_int curidx = double_int_zero;
1273         pp_character (buffer, '{');
1274         if (TREE_CODE (TREE_TYPE (node)) == RECORD_TYPE
1275             || TREE_CODE (TREE_TYPE (node)) == UNION_TYPE)
1276           is_struct_init = true;
1277         else if (TREE_CODE (TREE_TYPE (node)) == ARRAY_TYPE
1278                  && TYPE_DOMAIN (TREE_TYPE (node))
1279                  && TYPE_MIN_VALUE (TYPE_DOMAIN (TREE_TYPE (node)))
1280                  && TREE_CODE (TYPE_MIN_VALUE (TYPE_DOMAIN (TREE_TYPE (node))))
1281                     == INTEGER_CST)
1282           {
1283             tree minv = TYPE_MIN_VALUE (TYPE_DOMAIN (TREE_TYPE (node)));
1284             is_array_init = true;
1285             curidx = tree_to_double_int (minv);
1286           }
1287         FOR_EACH_CONSTRUCTOR_ELT (CONSTRUCTOR_ELTS (node), ix, field, val)
1288           {
1289             if (field)
1290               {
1291                 if (is_struct_init)
1292                   {
1293                     pp_character (buffer, '.');
1294                     dump_generic_node (buffer, field, spc, flags, false);
1295                     pp_character (buffer, '=');
1296                   }
1297                 else if (is_array_init
1298                          && (TREE_CODE (field) != INTEGER_CST
1299                              || !double_int_equal_p (tree_to_double_int (field),
1300                                                      curidx)))
1301                   {
1302                     pp_character (buffer, '[');
1303                     if (TREE_CODE (field) == RANGE_EXPR)
1304                       {
1305                         dump_generic_node (buffer, TREE_OPERAND (field, 0), spc,
1306                                            flags, false);
1307                         pp_string (buffer, " ... ");
1308                         dump_generic_node (buffer, TREE_OPERAND (field, 1), spc,
1309                                            flags, false);
1310                         if (TREE_CODE (TREE_OPERAND (field, 1)) == INTEGER_CST)
1311                           curidx = tree_to_double_int (TREE_OPERAND (field, 1));
1312                       }
1313                     else
1314                       dump_generic_node (buffer, field, spc, flags, false);
1315                     if (TREE_CODE (field) == INTEGER_CST)
1316                       curidx = tree_to_double_int (field);
1317                     pp_string (buffer, "]=");
1318                   }
1319               }
1320             if (is_array_init)
1321               curidx = double_int_add (curidx, double_int_one);
1322             if (val && TREE_CODE (val) == ADDR_EXPR)
1323               if (TREE_CODE (TREE_OPERAND (val, 0)) == FUNCTION_DECL)
1324                 val = TREE_OPERAND (val, 0);
1325             if (val && TREE_CODE (val) == FUNCTION_DECL)
1326                 dump_decl_name (buffer, val, flags);
1327             else
1328                 dump_generic_node (buffer, val, spc, flags, false);
1329             if (ix != VEC_length (constructor_elt, CONSTRUCTOR_ELTS (node)) - 1)
1330               {
1331                 pp_character (buffer, ',');
1332                 pp_space (buffer);
1333               }
1334           }
1335         pp_character (buffer, '}');
1336       }
1337       break;
1338
1339     case COMPOUND_EXPR:
1340       {
1341         tree *tp;
1342         if (flags & TDF_SLIM)
1343           {
1344             pp_string (buffer, "<COMPOUND_EXPR>");
1345             break;
1346           }
1347
1348         dump_generic_node (buffer, TREE_OPERAND (node, 0),
1349                            spc, flags, !(flags & TDF_SLIM));
1350         if (flags & TDF_SLIM)
1351           newline_and_indent (buffer, spc);
1352         else
1353           {
1354             pp_character (buffer, ',');
1355             pp_space (buffer);
1356           }
1357
1358         for (tp = &TREE_OPERAND (node, 1);
1359              TREE_CODE (*tp) == COMPOUND_EXPR;
1360              tp = &TREE_OPERAND (*tp, 1))
1361           {
1362             dump_generic_node (buffer, TREE_OPERAND (*tp, 0),
1363                                spc, flags, !(flags & TDF_SLIM));
1364             if (flags & TDF_SLIM)
1365               newline_and_indent (buffer, spc);
1366             else
1367               {
1368                 pp_character (buffer, ',');
1369                 pp_space (buffer);
1370               }
1371           }
1372
1373         dump_generic_node (buffer, *tp, spc, flags, !(flags & TDF_SLIM));
1374       }
1375       break;
1376
1377     case STATEMENT_LIST:
1378       {
1379         tree_stmt_iterator si;
1380         bool first = true;
1381
1382         if (flags & TDF_SLIM)
1383           {
1384             pp_string (buffer, "<STATEMENT_LIST>");
1385             break;
1386           }
1387
1388         for (si = tsi_start (node); !tsi_end_p (si); tsi_next (&si))
1389           {
1390             if (!first)
1391               newline_and_indent (buffer, spc);
1392             else
1393               first = false;
1394             dump_generic_node (buffer, tsi_stmt (si), spc, flags, true);
1395           }
1396       }
1397       break;
1398
1399     case MODIFY_EXPR:
1400     case INIT_EXPR:
1401       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags,
1402                          false);
1403       pp_space (buffer);
1404       pp_character (buffer, '=');
1405       if (TREE_CODE (node) == MODIFY_EXPR
1406           && MOVE_NONTEMPORAL (node))
1407         pp_string (buffer, "{nt}");
1408       pp_space (buffer);
1409       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags,
1410                          false);
1411       break;
1412
1413     case TARGET_EXPR:
1414       pp_string (buffer, "TARGET_EXPR <");
1415       dump_generic_node (buffer, TARGET_EXPR_SLOT (node), spc, flags, false);
1416       pp_character (buffer, ',');
1417       pp_space (buffer);
1418       dump_generic_node (buffer, TARGET_EXPR_INITIAL (node), spc, flags, false);
1419       pp_character (buffer, '>');
1420       break;
1421
1422     case DECL_EXPR:
1423       print_declaration (buffer, DECL_EXPR_DECL (node), spc, flags);
1424       is_stmt = false;
1425       break;
1426
1427     case COND_EXPR:
1428       if (TREE_TYPE (node) == NULL || TREE_TYPE (node) == void_type_node)
1429         {
1430           pp_string (buffer, "if (");
1431           dump_generic_node (buffer, COND_EXPR_COND (node), spc, flags, false);
1432           pp_character (buffer, ')');
1433           /* The lowered cond_exprs should always be printed in full.  */
1434           if (COND_EXPR_THEN (node)
1435               && (IS_EMPTY_STMT (COND_EXPR_THEN (node))
1436                   || TREE_CODE (COND_EXPR_THEN (node)) == GOTO_EXPR)
1437               && COND_EXPR_ELSE (node)
1438               && (IS_EMPTY_STMT (COND_EXPR_ELSE (node))
1439                   || TREE_CODE (COND_EXPR_ELSE (node)) == GOTO_EXPR))
1440             {
1441               pp_space (buffer);
1442               dump_generic_node (buffer, COND_EXPR_THEN (node),
1443                                  0, flags, true);
1444               if (!IS_EMPTY_STMT (COND_EXPR_ELSE (node)))
1445                 {
1446                   pp_string (buffer, " else ");
1447                   dump_generic_node (buffer, COND_EXPR_ELSE (node),
1448                                      0, flags, true);
1449                 }
1450             }
1451           else if (!(flags & TDF_SLIM))
1452             {
1453               /* Output COND_EXPR_THEN.  */
1454               if (COND_EXPR_THEN (node))
1455                 {
1456                   newline_and_indent (buffer, spc+2);
1457                   pp_character (buffer, '{');
1458                   newline_and_indent (buffer, spc+4);
1459                   dump_generic_node (buffer, COND_EXPR_THEN (node), spc+4,
1460                                      flags, true);
1461                   newline_and_indent (buffer, spc+2);
1462                   pp_character (buffer, '}');
1463                 }
1464
1465               /* Output COND_EXPR_ELSE.  */
1466               if (COND_EXPR_ELSE (node)
1467                   && !IS_EMPTY_STMT (COND_EXPR_ELSE (node)))
1468                 {
1469                   newline_and_indent (buffer, spc);
1470                   pp_string (buffer, "else");
1471                   newline_and_indent (buffer, spc+2);
1472                   pp_character (buffer, '{');
1473                   newline_and_indent (buffer, spc+4);
1474                   dump_generic_node (buffer, COND_EXPR_ELSE (node), spc+4,
1475                                      flags, true);
1476                   newline_and_indent (buffer, spc+2);
1477                   pp_character (buffer, '}');
1478                 }
1479             }
1480           is_expr = false;
1481         }
1482       else
1483         {
1484           dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1485           pp_space (buffer);
1486           pp_character (buffer, '?');
1487           pp_space (buffer);
1488           dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1489           pp_space (buffer);
1490           pp_character (buffer, ':');
1491           pp_space (buffer);
1492           dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
1493         }
1494       break;
1495
1496     case BIND_EXPR:
1497       pp_character (buffer, '{');
1498       if (!(flags & TDF_SLIM))
1499         {
1500           if (BIND_EXPR_VARS (node))
1501             {
1502               pp_newline (buffer);
1503
1504               for (op0 = BIND_EXPR_VARS (node); op0; op0 = DECL_CHAIN (op0))
1505                 {
1506                   print_declaration (buffer, op0, spc+2, flags);
1507                   pp_newline (buffer);
1508                 }
1509             }
1510
1511           newline_and_indent (buffer, spc+2);
1512           dump_generic_node (buffer, BIND_EXPR_BODY (node), spc+2, flags, true);
1513           newline_and_indent (buffer, spc);
1514           pp_character (buffer, '}');
1515         }
1516       is_expr = false;
1517       break;
1518
1519     case CALL_EXPR:
1520       print_call_name (buffer, CALL_EXPR_FN (node), flags);
1521
1522       /* Print parameters.  */
1523       pp_space (buffer);
1524       pp_character (buffer, '(');
1525       {
1526         tree arg;
1527         call_expr_arg_iterator iter;
1528         FOR_EACH_CALL_EXPR_ARG (arg, iter, node)
1529           {
1530             dump_generic_node (buffer, arg, spc, flags, false);
1531             if (more_call_expr_args_p (&iter))
1532               {
1533                 pp_character (buffer, ',');
1534                 pp_space (buffer);
1535               }
1536           }
1537       }
1538       if (CALL_EXPR_VA_ARG_PACK (node))
1539         {
1540           if (call_expr_nargs (node) > 0)
1541             {
1542               pp_character (buffer, ',');
1543               pp_space (buffer);
1544             }
1545           pp_string (buffer, "__builtin_va_arg_pack ()");
1546         }
1547       pp_character (buffer, ')');
1548
1549       op1 = CALL_EXPR_STATIC_CHAIN (node);
1550       if (op1)
1551         {
1552           pp_string (buffer, " [static-chain: ");
1553           dump_generic_node (buffer, op1, spc, flags, false);
1554           pp_character (buffer, ']');
1555         }
1556
1557       if (CALL_EXPR_RETURN_SLOT_OPT (node))
1558         pp_string (buffer, " [return slot optimization]");
1559       if (CALL_EXPR_TAILCALL (node))
1560         pp_string (buffer, " [tail call]");
1561       break;
1562
1563     case WITH_CLEANUP_EXPR:
1564       NIY;
1565       break;
1566
1567     case CLEANUP_POINT_EXPR:
1568       pp_string (buffer, "<<cleanup_point ");
1569       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1570       pp_string (buffer, ">>");
1571       break;
1572
1573     case PLACEHOLDER_EXPR:
1574       pp_string (buffer, "<PLACEHOLDER_EXPR ");
1575       dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
1576       pp_character (buffer, '>');
1577       break;
1578
1579       /* Binary arithmetic and logic expressions.  */
1580     case WIDEN_SUM_EXPR:
1581     case WIDEN_MULT_EXPR:
1582     case MULT_EXPR:
1583     case PLUS_EXPR:
1584     case POINTER_PLUS_EXPR:
1585     case MINUS_EXPR:
1586     case TRUNC_DIV_EXPR:
1587     case CEIL_DIV_EXPR:
1588     case FLOOR_DIV_EXPR:
1589     case ROUND_DIV_EXPR:
1590     case TRUNC_MOD_EXPR:
1591     case CEIL_MOD_EXPR:
1592     case FLOOR_MOD_EXPR:
1593     case ROUND_MOD_EXPR:
1594     case RDIV_EXPR:
1595     case EXACT_DIV_EXPR:
1596     case LSHIFT_EXPR:
1597     case RSHIFT_EXPR:
1598     case LROTATE_EXPR:
1599     case RROTATE_EXPR:
1600     case VEC_LSHIFT_EXPR:
1601     case VEC_RSHIFT_EXPR:
1602     case BIT_IOR_EXPR:
1603     case BIT_XOR_EXPR:
1604     case BIT_AND_EXPR:
1605     case TRUTH_ANDIF_EXPR:
1606     case TRUTH_ORIF_EXPR:
1607     case TRUTH_AND_EXPR:
1608     case TRUTH_OR_EXPR:
1609     case TRUTH_XOR_EXPR:
1610     case LT_EXPR:
1611     case LE_EXPR:
1612     case GT_EXPR:
1613     case GE_EXPR:
1614     case EQ_EXPR:
1615     case NE_EXPR:
1616     case UNLT_EXPR:
1617     case UNLE_EXPR:
1618     case UNGT_EXPR:
1619     case UNGE_EXPR:
1620     case UNEQ_EXPR:
1621     case LTGT_EXPR:
1622     case ORDERED_EXPR:
1623     case UNORDERED_EXPR:
1624       {
1625         const char *op = op_symbol (node);
1626         op0 = TREE_OPERAND (node, 0);
1627         op1 = TREE_OPERAND (node, 1);
1628
1629         /* When the operands are expressions with less priority,
1630            keep semantics of the tree representation.  */
1631         if (op_prio (op0) <= op_prio (node))
1632           {
1633             pp_character (buffer, '(');
1634             dump_generic_node (buffer, op0, spc, flags, false);
1635             pp_character (buffer, ')');
1636           }
1637         else
1638           dump_generic_node (buffer, op0, spc, flags, false);
1639
1640         pp_space (buffer);
1641         pp_string (buffer, op);
1642         pp_space (buffer);
1643
1644         /* When the operands are expressions with less priority,
1645            keep semantics of the tree representation.  */
1646         if (op_prio (op1) <= op_prio (node))
1647           {
1648             pp_character (buffer, '(');
1649             dump_generic_node (buffer, op1, spc, flags, false);
1650             pp_character (buffer, ')');
1651           }
1652         else
1653           dump_generic_node (buffer, op1, spc, flags, false);
1654       }
1655       break;
1656
1657       /* Unary arithmetic and logic expressions.  */
1658     case NEGATE_EXPR:
1659     case BIT_NOT_EXPR:
1660     case TRUTH_NOT_EXPR:
1661     case ADDR_EXPR:
1662     case PREDECREMENT_EXPR:
1663     case PREINCREMENT_EXPR:
1664     case INDIRECT_REF:
1665       if (TREE_CODE (node) == ADDR_EXPR
1666           && (TREE_CODE (TREE_OPERAND (node, 0)) == STRING_CST
1667               || TREE_CODE (TREE_OPERAND (node, 0)) == FUNCTION_DECL))
1668         ;       /* Do not output '&' for strings and function pointers.  */
1669       else
1670         pp_string (buffer, op_symbol (node));
1671
1672       if (op_prio (TREE_OPERAND (node, 0)) < op_prio (node))
1673         {
1674           pp_character (buffer, '(');
1675           dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1676           pp_character (buffer, ')');
1677         }
1678       else
1679         dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1680       break;
1681
1682     case POSTDECREMENT_EXPR:
1683     case POSTINCREMENT_EXPR:
1684       if (op_prio (TREE_OPERAND (node, 0)) < op_prio (node))
1685         {
1686           pp_character (buffer, '(');
1687           dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1688           pp_character (buffer, ')');
1689         }
1690       else
1691         dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1692       pp_string (buffer, op_symbol (node));
1693       break;
1694
1695     case MIN_EXPR:
1696       pp_string (buffer, "MIN_EXPR <");
1697       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1698       pp_string (buffer, ", ");
1699       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1700       pp_character (buffer, '>');
1701       break;
1702
1703     case MAX_EXPR:
1704       pp_string (buffer, "MAX_EXPR <");
1705       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1706       pp_string (buffer, ", ");
1707       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1708       pp_character (buffer, '>');
1709       break;
1710
1711     case ABS_EXPR:
1712       pp_string (buffer, "ABS_EXPR <");
1713       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1714       pp_character (buffer, '>');
1715       break;
1716
1717     case RANGE_EXPR:
1718       NIY;
1719       break;
1720
1721     case ADDR_SPACE_CONVERT_EXPR:
1722     case FIXED_CONVERT_EXPR:
1723     case FIX_TRUNC_EXPR:
1724     case FLOAT_EXPR:
1725     CASE_CONVERT:
1726       type = TREE_TYPE (node);
1727       op0 = TREE_OPERAND (node, 0);
1728       if (type != TREE_TYPE (op0))
1729         {
1730           pp_character (buffer, '(');
1731           dump_generic_node (buffer, type, spc, flags, false);
1732           pp_string (buffer, ") ");
1733         }
1734       if (op_prio (op0) < op_prio (node))
1735         pp_character (buffer, '(');
1736       dump_generic_node (buffer, op0, spc, flags, false);
1737       if (op_prio (op0) < op_prio (node))
1738         pp_character (buffer, ')');
1739       break;
1740
1741     case VIEW_CONVERT_EXPR:
1742       pp_string (buffer, "VIEW_CONVERT_EXPR<");
1743       dump_generic_node (buffer, TREE_TYPE (node), spc, flags, false);
1744       pp_string (buffer, ">(");
1745       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1746       pp_character (buffer, ')');
1747       break;
1748
1749     case PAREN_EXPR:
1750       pp_string (buffer, "((");
1751       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1752       pp_string (buffer, "))");
1753       break;
1754
1755     case NON_LVALUE_EXPR:
1756       pp_string (buffer, "NON_LVALUE_EXPR <");
1757       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1758       pp_character (buffer, '>');
1759       break;
1760
1761     case SAVE_EXPR:
1762       pp_string (buffer, "SAVE_EXPR <");
1763       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1764       pp_character (buffer, '>');
1765       break;
1766
1767     case COMPLEX_EXPR:
1768       pp_string (buffer, "COMPLEX_EXPR <");
1769       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1770       pp_string (buffer, ", ");
1771       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
1772       pp_string (buffer, ">");
1773       break;
1774
1775     case CONJ_EXPR:
1776       pp_string (buffer, "CONJ_EXPR <");
1777       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1778       pp_string (buffer, ">");
1779       break;
1780
1781     case REALPART_EXPR:
1782       pp_string (buffer, "REALPART_EXPR <");
1783       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1784       pp_string (buffer, ">");
1785       break;
1786
1787     case IMAGPART_EXPR:
1788       pp_string (buffer, "IMAGPART_EXPR <");
1789       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1790       pp_string (buffer, ">");
1791       break;
1792
1793     case VA_ARG_EXPR:
1794       pp_string (buffer, "VA_ARG_EXPR <");
1795       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1796       pp_string (buffer, ">");
1797       break;
1798
1799     case TRY_FINALLY_EXPR:
1800     case TRY_CATCH_EXPR:
1801       pp_string (buffer, "try");
1802       newline_and_indent (buffer, spc+2);
1803       pp_string (buffer, "{");
1804       newline_and_indent (buffer, spc+4);
1805       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc+4, flags, true);
1806       newline_and_indent (buffer, spc+2);
1807       pp_string (buffer, "}");
1808       newline_and_indent (buffer, spc);
1809       pp_string (buffer,
1810                          (TREE_CODE (node) == TRY_CATCH_EXPR) ? "catch" : "finally");
1811       newline_and_indent (buffer, spc+2);
1812       pp_string (buffer, "{");
1813       newline_and_indent (buffer, spc+4);
1814       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc+4, flags, true);
1815       newline_and_indent (buffer, spc+2);
1816       pp_string (buffer, "}");
1817       is_expr = false;
1818       break;
1819
1820     case CATCH_EXPR:
1821       pp_string (buffer, "catch (");
1822       dump_generic_node (buffer, CATCH_TYPES (node), spc+2, flags, false);
1823       pp_string (buffer, ")");
1824       newline_and_indent (buffer, spc+2);
1825       pp_string (buffer, "{");
1826       newline_and_indent (buffer, spc+4);
1827       dump_generic_node (buffer, CATCH_BODY (node), spc+4, flags, true);
1828       newline_and_indent (buffer, spc+2);
1829       pp_string (buffer, "}");
1830       is_expr = false;
1831       break;
1832
1833     case EH_FILTER_EXPR:
1834       pp_string (buffer, "<<<eh_filter (");
1835       dump_generic_node (buffer, EH_FILTER_TYPES (node), spc+2, flags, false);
1836       pp_string (buffer, ")>>>");
1837       newline_and_indent (buffer, spc+2);
1838       pp_string (buffer, "{");
1839       newline_and_indent (buffer, spc+4);
1840       dump_generic_node (buffer, EH_FILTER_FAILURE (node), spc+4, flags, true);
1841       newline_and_indent (buffer, spc+2);
1842       pp_string (buffer, "}");
1843       is_expr = false;
1844       break;
1845
1846     case LABEL_EXPR:
1847       op0 = TREE_OPERAND (node, 0);
1848       /* If this is for break or continue, don't bother printing it.  */
1849       if (DECL_NAME (op0))
1850         {
1851           const char *name = IDENTIFIER_POINTER (DECL_NAME (op0));
1852           if (strcmp (name, "break") == 0
1853               || strcmp (name, "continue") == 0)
1854             break;
1855         }
1856       dump_generic_node (buffer, op0, spc, flags, false);
1857       pp_character (buffer, ':');
1858       if (DECL_NONLOCAL (op0))
1859         pp_string (buffer, " [non-local]");
1860       break;
1861
1862     case LOOP_EXPR:
1863       pp_string (buffer, "while (1)");
1864       if (!(flags & TDF_SLIM))
1865         {
1866           newline_and_indent (buffer, spc+2);
1867           pp_character (buffer, '{');
1868           newline_and_indent (buffer, spc+4);
1869           dump_generic_node (buffer, LOOP_EXPR_BODY (node), spc+4, flags, true);
1870           newline_and_indent (buffer, spc+2);
1871           pp_character (buffer, '}');
1872         }
1873       is_expr = false;
1874       break;
1875
1876     case PREDICT_EXPR:
1877       pp_string (buffer, "// predicted ");
1878       if (PREDICT_EXPR_OUTCOME (node))
1879         pp_string (buffer, "likely by ");
1880       else
1881         pp_string (buffer, "unlikely by ");
1882       pp_string (buffer, predictor_name (PREDICT_EXPR_PREDICTOR (node)));
1883       pp_string (buffer, " predictor.");
1884       break;
1885
1886     case RETURN_EXPR:
1887       pp_string (buffer, "return");
1888       op0 = TREE_OPERAND (node, 0);
1889       if (op0)
1890         {
1891           pp_space (buffer);
1892           if (TREE_CODE (op0) == MODIFY_EXPR)
1893             dump_generic_node (buffer, TREE_OPERAND (op0, 1),
1894                                spc, flags, false);
1895           else
1896             dump_generic_node (buffer, op0, spc, flags, false);
1897         }
1898       break;
1899
1900     case EXIT_EXPR:
1901       pp_string (buffer, "if (");
1902       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
1903       pp_string (buffer, ") break");
1904       break;
1905
1906     case SWITCH_EXPR:
1907       pp_string (buffer, "switch (");
1908       dump_generic_node (buffer, SWITCH_COND (node), spc, flags, false);
1909       pp_character (buffer, ')');
1910       if (!(flags & TDF_SLIM))
1911         {
1912           newline_and_indent (buffer, spc+2);
1913           pp_character (buffer, '{');
1914           if (SWITCH_BODY (node))
1915             {
1916               newline_and_indent (buffer, spc+4);
1917               dump_generic_node (buffer, SWITCH_BODY (node), spc+4, flags,
1918                                  true);
1919             }
1920           else
1921             {
1922               tree vec = SWITCH_LABELS (node);
1923               size_t i, n = TREE_VEC_LENGTH (vec);
1924               for (i = 0; i < n; ++i)
1925                 {
1926                   tree elt = TREE_VEC_ELT (vec, i);
1927                   newline_and_indent (buffer, spc+4);
1928                   if (elt)
1929                     {
1930                       dump_generic_node (buffer, elt, spc+4, flags, false);
1931                       pp_string (buffer, " goto ");
1932                       dump_generic_node (buffer, CASE_LABEL (elt), spc+4,
1933                                          flags, true);
1934                       pp_semicolon (buffer);
1935                     }
1936                   else
1937                     pp_string (buffer, "case ???: goto ???;");
1938                 }
1939             }
1940           newline_and_indent (buffer, spc+2);
1941           pp_character (buffer, '}');
1942         }
1943       is_expr = false;
1944       break;
1945
1946     case GOTO_EXPR:
1947       op0 = GOTO_DESTINATION (node);
1948       if (TREE_CODE (op0) != SSA_NAME && DECL_P (op0) && DECL_NAME (op0))
1949         {
1950           const char *name = IDENTIFIER_POINTER (DECL_NAME (op0));
1951           if (strcmp (name, "break") == 0
1952               || strcmp (name, "continue") == 0)
1953             {
1954               pp_string (buffer, name);
1955               break;
1956             }
1957         }
1958       pp_string (buffer, "goto ");
1959       dump_generic_node (buffer, op0, spc, flags, false);
1960       break;
1961
1962     case ASM_EXPR:
1963       pp_string (buffer, "__asm__");
1964       if (ASM_VOLATILE_P (node))
1965         pp_string (buffer, " __volatile__");
1966       pp_character (buffer, '(');
1967       dump_generic_node (buffer, ASM_STRING (node), spc, flags, false);
1968       pp_character (buffer, ':');
1969       dump_generic_node (buffer, ASM_OUTPUTS (node), spc, flags, false);
1970       pp_character (buffer, ':');
1971       dump_generic_node (buffer, ASM_INPUTS (node), spc, flags, false);
1972       if (ASM_CLOBBERS (node))
1973         {
1974           pp_character (buffer, ':');
1975           dump_generic_node (buffer, ASM_CLOBBERS (node), spc, flags, false);
1976         }
1977       pp_string (buffer, ")");
1978       break;
1979
1980     case CASE_LABEL_EXPR:
1981       if (CASE_LOW (node) && CASE_HIGH (node))
1982         {
1983           pp_string (buffer, "case ");
1984           dump_generic_node (buffer, CASE_LOW (node), spc, flags, false);
1985           pp_string (buffer, " ... ");
1986           dump_generic_node (buffer, CASE_HIGH (node), spc, flags, false);
1987         }
1988       else if (CASE_LOW (node))
1989         {
1990           pp_string (buffer, "case ");
1991           dump_generic_node (buffer, CASE_LOW (node), spc, flags, false);
1992         }
1993       else
1994         pp_string (buffer, "default");
1995       pp_character (buffer, ':');
1996       break;
1997
1998     case OBJ_TYPE_REF:
1999       pp_string (buffer, "OBJ_TYPE_REF(");
2000       dump_generic_node (buffer, OBJ_TYPE_REF_EXPR (node), spc, flags, false);
2001       pp_character (buffer, ';');
2002       dump_generic_node (buffer, OBJ_TYPE_REF_OBJECT (node), spc, flags, false);
2003       pp_character (buffer, '-');
2004       pp_character (buffer, '>');
2005       dump_generic_node (buffer, OBJ_TYPE_REF_TOKEN (node), spc, flags, false);
2006       pp_character (buffer, ')');
2007       break;
2008
2009     case SSA_NAME:
2010       dump_generic_node (buffer, SSA_NAME_VAR (node), spc, flags, false);
2011       pp_string (buffer, "_");
2012       pp_decimal_int (buffer, SSA_NAME_VERSION (node));
2013       if (SSA_NAME_OCCURS_IN_ABNORMAL_PHI (node))
2014         pp_string (buffer, "(ab)");
2015       else if (SSA_NAME_IS_DEFAULT_DEF (node))
2016         pp_string (buffer, "(D)");
2017       break;
2018
2019     case WITH_SIZE_EXPR:
2020       pp_string (buffer, "WITH_SIZE_EXPR <");
2021       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2022       pp_string (buffer, ", ");
2023       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2024       pp_string (buffer, ">");
2025       break;
2026
2027     case ASSERT_EXPR:
2028       pp_string (buffer, "ASSERT_EXPR <");
2029       dump_generic_node (buffer, ASSERT_EXPR_VAR (node), spc, flags, false);
2030       pp_string (buffer, ", ");
2031       dump_generic_node (buffer, ASSERT_EXPR_COND (node), spc, flags, false);
2032       pp_string (buffer, ">");
2033       break;
2034
2035     case SCEV_KNOWN:
2036       pp_string (buffer, "scev_known");
2037       break;
2038
2039     case SCEV_NOT_KNOWN:
2040       pp_string (buffer, "scev_not_known");
2041       break;
2042
2043     case POLYNOMIAL_CHREC:
2044       pp_string (buffer, "{");
2045       dump_generic_node (buffer, CHREC_LEFT (node), spc, flags, false);
2046       pp_string (buffer, ", +, ");
2047       dump_generic_node (buffer, CHREC_RIGHT (node), spc, flags, false);
2048       pp_string (buffer, "}_");
2049       dump_generic_node (buffer, CHREC_VAR (node), spc, flags, false);
2050       is_stmt = false;
2051       break;
2052
2053     case REALIGN_LOAD_EXPR:
2054       pp_string (buffer, "REALIGN_LOAD <");
2055       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2056       pp_string (buffer, ", ");
2057       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2058       pp_string (buffer, ", ");
2059       dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
2060       pp_string (buffer, ">");
2061       break;
2062
2063     case VEC_COND_EXPR:
2064       pp_string (buffer, " VEC_COND_EXPR < ");
2065       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2066       pp_string (buffer, " , ");
2067       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2068       pp_string (buffer, " , ");
2069       dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
2070       pp_string (buffer, " > ");
2071       break;
2072
2073     case DOT_PROD_EXPR:
2074       pp_string (buffer, " DOT_PROD_EXPR < ");
2075       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2076       pp_string (buffer, ", ");
2077       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2078       pp_string (buffer, ", ");
2079       dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
2080       pp_string (buffer, " > ");
2081       break;
2082
2083     case WIDEN_MULT_PLUS_EXPR:
2084       pp_string (buffer, " WIDEN_MULT_PLUS_EXPR < ");
2085       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2086       pp_string (buffer, ", ");
2087       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2088       pp_string (buffer, ", ");
2089       dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
2090       pp_string (buffer, " > ");
2091       break;
2092
2093     case WIDEN_MULT_MINUS_EXPR:
2094       pp_string (buffer, " WIDEN_MULT_MINUS_EXPR < ");
2095       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2096       pp_string (buffer, ", ");
2097       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2098       pp_string (buffer, ", ");
2099       dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
2100       pp_string (buffer, " > ");
2101       break;
2102
2103     case FMA_EXPR:
2104       pp_string (buffer, " FMA_EXPR < ");
2105       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2106       pp_string (buffer, ", ");
2107       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2108       pp_string (buffer, ", ");
2109       dump_generic_node (buffer, TREE_OPERAND (node, 2), spc, flags, false);
2110       pp_string (buffer, " > ");
2111       break;
2112
2113     case OMP_PARALLEL:
2114       pp_string (buffer, "#pragma omp parallel");
2115       dump_omp_clauses (buffer, OMP_PARALLEL_CLAUSES (node), spc, flags);
2116
2117     dump_omp_body:
2118       if (!(flags & TDF_SLIM) && OMP_BODY (node))
2119         {
2120           newline_and_indent (buffer, spc + 2);
2121           pp_character (buffer, '{');
2122           newline_and_indent (buffer, spc + 4);
2123           dump_generic_node (buffer, OMP_BODY (node), spc + 4, flags, false);
2124           newline_and_indent (buffer, spc + 2);
2125           pp_character (buffer, '}');
2126         }
2127       is_expr = false;
2128       break;
2129
2130     case OMP_TASK:
2131       pp_string (buffer, "#pragma omp task");
2132       dump_omp_clauses (buffer, OMP_TASK_CLAUSES (node), spc, flags);
2133       goto dump_omp_body;
2134
2135     case OMP_FOR:
2136       pp_string (buffer, "#pragma omp for");
2137       dump_omp_clauses (buffer, OMP_FOR_CLAUSES (node), spc, flags);
2138
2139       if (!(flags & TDF_SLIM))
2140         {
2141           int i;
2142
2143           if (OMP_FOR_PRE_BODY (node))
2144             {
2145               newline_and_indent (buffer, spc + 2);
2146               pp_character (buffer, '{');
2147               spc += 4;
2148               newline_and_indent (buffer, spc);
2149               dump_generic_node (buffer, OMP_FOR_PRE_BODY (node),
2150                   spc, flags, false);
2151             }
2152           spc -= 2;
2153           for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (node)); i++)
2154             {
2155               spc += 2;
2156               newline_and_indent (buffer, spc);
2157               pp_string (buffer, "for (");
2158               dump_generic_node (buffer, TREE_VEC_ELT (OMP_FOR_INIT (node), i),
2159                                  spc, flags, false);
2160               pp_string (buffer, "; ");
2161               dump_generic_node (buffer, TREE_VEC_ELT (OMP_FOR_COND (node), i),
2162                                  spc, flags, false);
2163               pp_string (buffer, "; ");
2164               dump_generic_node (buffer, TREE_VEC_ELT (OMP_FOR_INCR (node), i),
2165                                  spc, flags, false);
2166               pp_string (buffer, ")");
2167             }
2168           if (OMP_FOR_BODY (node))
2169             {
2170               newline_and_indent (buffer, spc + 2);
2171               pp_character (buffer, '{');
2172               newline_and_indent (buffer, spc + 4);
2173               dump_generic_node (buffer, OMP_FOR_BODY (node), spc + 4, flags,
2174                   false);
2175               newline_and_indent (buffer, spc + 2);
2176               pp_character (buffer, '}');
2177             }
2178           spc -= 2 * TREE_VEC_LENGTH (OMP_FOR_INIT (node)) - 2;
2179           if (OMP_FOR_PRE_BODY (node))
2180             {
2181               spc -= 4;
2182               newline_and_indent (buffer, spc + 2);
2183               pp_character (buffer, '}');
2184             }
2185         }
2186       is_expr = false;
2187       break;
2188
2189     case OMP_SECTIONS:
2190       pp_string (buffer, "#pragma omp sections");
2191       dump_omp_clauses (buffer, OMP_SECTIONS_CLAUSES (node), spc, flags);
2192       goto dump_omp_body;
2193
2194     case OMP_SECTION:
2195       pp_string (buffer, "#pragma omp section");
2196       goto dump_omp_body;
2197
2198     case OMP_MASTER:
2199       pp_string (buffer, "#pragma omp master");
2200       goto dump_omp_body;
2201
2202     case OMP_ORDERED:
2203       pp_string (buffer, "#pragma omp ordered");
2204       goto dump_omp_body;
2205
2206     case OMP_CRITICAL:
2207       pp_string (buffer, "#pragma omp critical");
2208       if (OMP_CRITICAL_NAME (node))
2209         {
2210           pp_space (buffer);
2211           pp_character (buffer, '(');
2212           dump_generic_node (buffer, OMP_CRITICAL_NAME (node), spc,
2213                              flags, false);
2214           pp_character (buffer, ')');
2215         }
2216       goto dump_omp_body;
2217
2218     case OMP_ATOMIC:
2219       pp_string (buffer, "#pragma omp atomic");
2220       newline_and_indent (buffer, spc + 2);
2221       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2222       pp_space (buffer);
2223       pp_character (buffer, '=');
2224       pp_space (buffer);
2225       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2226       break;
2227
2228     case OMP_ATOMIC_READ:
2229       pp_string (buffer, "#pragma omp atomic read");
2230       newline_and_indent (buffer, spc + 2);
2231       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2232       pp_space (buffer);
2233       break;
2234
2235     case OMP_ATOMIC_CAPTURE_OLD:
2236     case OMP_ATOMIC_CAPTURE_NEW:
2237       pp_string (buffer, "#pragma omp atomic capture");
2238       newline_and_indent (buffer, spc + 2);
2239       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2240       pp_space (buffer);
2241       pp_character (buffer, '=');
2242       pp_space (buffer);
2243       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2244       break;
2245
2246     case OMP_SINGLE:
2247       pp_string (buffer, "#pragma omp single");
2248       dump_omp_clauses (buffer, OMP_SINGLE_CLAUSES (node), spc, flags);
2249       goto dump_omp_body;
2250
2251     case OMP_CLAUSE:
2252       dump_omp_clause (buffer, node, spc, flags);
2253       is_expr = false;
2254       break;
2255
2256     case REDUC_MAX_EXPR:
2257       pp_string (buffer, " REDUC_MAX_EXPR < ");
2258       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2259       pp_string (buffer, " > ");
2260       break;
2261
2262     case REDUC_MIN_EXPR:
2263       pp_string (buffer, " REDUC_MIN_EXPR < ");
2264       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2265       pp_string (buffer, " > ");
2266       break;
2267
2268     case REDUC_PLUS_EXPR:
2269       pp_string (buffer, " REDUC_PLUS_EXPR < ");
2270       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2271       pp_string (buffer, " > ");
2272       break;
2273
2274     case VEC_WIDEN_MULT_HI_EXPR:
2275       pp_string (buffer, " VEC_WIDEN_MULT_HI_EXPR < ");
2276       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2277       pp_string (buffer, ", ");
2278       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2279       pp_string (buffer, " > ");
2280       break;
2281
2282     case VEC_WIDEN_MULT_LO_EXPR:
2283       pp_string (buffer, " VEC_WIDEN_MULT_LO_EXPR < ");
2284       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2285       pp_string (buffer, ", ");
2286       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2287       pp_string (buffer, " > ");
2288       break;
2289
2290     case VEC_UNPACK_HI_EXPR:
2291       pp_string (buffer, " VEC_UNPACK_HI_EXPR < ");
2292       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2293       pp_string (buffer, " > ");
2294       break;
2295
2296     case VEC_UNPACK_LO_EXPR:
2297       pp_string (buffer, " VEC_UNPACK_LO_EXPR < ");
2298       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2299       pp_string (buffer, " > ");
2300       break;
2301
2302     case VEC_UNPACK_FLOAT_HI_EXPR:
2303       pp_string (buffer, " VEC_UNPACK_FLOAT_HI_EXPR < ");
2304       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2305       pp_string (buffer, " > ");
2306       break;
2307
2308     case VEC_UNPACK_FLOAT_LO_EXPR:
2309       pp_string (buffer, " VEC_UNPACK_FLOAT_LO_EXPR < ");
2310       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2311       pp_string (buffer, " > ");
2312       break;
2313
2314     case VEC_PACK_TRUNC_EXPR:
2315       pp_string (buffer, " VEC_PACK_TRUNC_EXPR < ");
2316       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2317       pp_string (buffer, ", ");
2318       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2319       pp_string (buffer, " > ");
2320       break;
2321
2322     case VEC_PACK_SAT_EXPR:
2323       pp_string (buffer, " VEC_PACK_SAT_EXPR < ");
2324       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2325       pp_string (buffer, ", ");
2326       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2327       pp_string (buffer, " > ");
2328       break;
2329
2330     case VEC_PACK_FIX_TRUNC_EXPR:
2331       pp_string (buffer, " VEC_PACK_FIX_TRUNC_EXPR < ");
2332       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2333       pp_string (buffer, ", ");
2334       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2335       pp_string (buffer, " > ");
2336       break;
2337
2338     case BLOCK:
2339       dump_block_node (buffer, node, spc, flags);
2340       break;
2341
2342     case VEC_EXTRACT_EVEN_EXPR:
2343       pp_string (buffer, " VEC_EXTRACT_EVEN_EXPR < ");
2344       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2345       pp_string (buffer, ", ");
2346       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2347       pp_string (buffer, " > ");
2348       break;
2349
2350     case VEC_EXTRACT_ODD_EXPR:
2351       pp_string (buffer, " VEC_EXTRACT_ODD_EXPR < ");
2352       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2353       pp_string (buffer, ", ");
2354       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2355       pp_string (buffer, " > ");
2356       break;
2357
2358     case VEC_INTERLEAVE_HIGH_EXPR:
2359       pp_string (buffer, " VEC_INTERLEAVE_HIGH_EXPR < ");
2360       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2361       pp_string (buffer, ", ");
2362       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2363       pp_string (buffer, " > ");
2364       break;
2365
2366     case VEC_INTERLEAVE_LOW_EXPR:
2367       pp_string (buffer, " VEC_INTERLEAVE_LOW_EXPR < ");
2368       dump_generic_node (buffer, TREE_OPERAND (node, 0), spc, flags, false);
2369       pp_string (buffer, ", ");
2370       dump_generic_node (buffer, TREE_OPERAND (node, 1), spc, flags, false);
2371       pp_string (buffer, " > ");
2372       break;
2373
2374     default:
2375       NIY;
2376     }
2377
2378   if (is_stmt && is_expr)
2379     pp_semicolon (buffer);
2380
2381   /* If we're building a diagnostic, the formatted text will be written
2382      into BUFFER's stream by the caller; otherwise, write it now.  */
2383   if (!(flags & TDF_DIAGNOSTIC))
2384     pp_write_text_to_stream (buffer);
2385
2386   return spc;
2387 }
2388
2389 /* Print the declaration of a variable.  */
2390
2391 void
2392 print_declaration (pretty_printer *buffer, tree t, int spc, int flags)
2393 {
2394   INDENT (spc);
2395
2396   if (TREE_CODE (t) == TYPE_DECL)
2397     pp_string (buffer, "typedef ");
2398
2399   if (CODE_CONTAINS_STRUCT (TREE_CODE (t), TS_DECL_WRTL) && DECL_REGISTER (t))
2400     pp_string (buffer, "register ");
2401
2402   if (TREE_PUBLIC (t) && DECL_EXTERNAL (t))
2403     pp_string (buffer, "extern ");
2404   else if (TREE_STATIC (t))
2405     pp_string (buffer, "static ");
2406
2407   /* Print the type and name.  */
2408   if (TREE_TYPE (t) && TREE_CODE (TREE_TYPE (t)) == ARRAY_TYPE)
2409     {
2410       tree tmp;
2411
2412       /* Print array's type.  */
2413       tmp = TREE_TYPE (t);
2414       while (TREE_CODE (TREE_TYPE (tmp)) == ARRAY_TYPE)
2415         tmp = TREE_TYPE (tmp);
2416       dump_generic_node (buffer, TREE_TYPE (tmp), spc, flags, false);
2417
2418       /* Print variable's name.  */
2419       pp_space (buffer);
2420       dump_generic_node (buffer, t, spc, flags, false);
2421
2422       /* Print the dimensions.  */
2423       tmp = TREE_TYPE (t);
2424       while (TREE_CODE (tmp) == ARRAY_TYPE)
2425         {
2426           dump_array_domain (buffer, TYPE_DOMAIN (tmp), spc, flags);
2427           tmp = TREE_TYPE (tmp);
2428         }
2429     }
2430   else if (TREE_CODE (t) == FUNCTION_DECL)
2431     {
2432       dump_generic_node (buffer, TREE_TYPE (TREE_TYPE (t)), spc, flags, false);
2433       pp_space (buffer);
2434       dump_decl_name (buffer, t, flags);
2435       dump_function_declaration (buffer, TREE_TYPE (t), spc, flags);
2436     }
2437   else
2438     {
2439       /* Print type declaration.  */
2440       dump_generic_node (buffer, TREE_TYPE (t), spc, flags, false);
2441
2442       /* Print variable's name.  */
2443       pp_space (buffer);
2444       dump_generic_node (buffer, t, spc, flags, false);
2445     }
2446
2447   if (TREE_CODE (t) == VAR_DECL && DECL_HARD_REGISTER (t))
2448     {
2449       pp_string (buffer, " __asm__ ");
2450       pp_character (buffer, '(');
2451       dump_generic_node (buffer, DECL_ASSEMBLER_NAME (t), spc, flags, false);
2452       pp_character (buffer, ')');
2453     }
2454
2455   /* The initial value of a function serves to determine whether the function
2456      is declared or defined.  So the following does not apply to function
2457      nodes.  */
2458   if (TREE_CODE (t) != FUNCTION_DECL)
2459     {
2460       /* Print the initial value.  */
2461       if (DECL_INITIAL (t))
2462         {
2463           pp_space (buffer);
2464           pp_character (buffer, '=');
2465           pp_space (buffer);
2466           dump_generic_node (buffer, DECL_INITIAL (t), spc, flags, false);
2467         }
2468     }
2469
2470   if (TREE_CODE (t) == VAR_DECL && DECL_HAS_VALUE_EXPR_P (t))
2471     {
2472       pp_string (buffer, " [value-expr: ");
2473       dump_generic_node (buffer, DECL_VALUE_EXPR (t), spc, flags, false);
2474       pp_character (buffer, ']');
2475     }
2476
2477   pp_character (buffer, ';');
2478 }
2479
2480
2481 /* Prints a structure: name, fields, and methods.
2482    FIXME: Still incomplete.  */
2483
2484 static void
2485 print_struct_decl (pretty_printer *buffer, const_tree node, int spc, int flags)
2486 {
2487   /* Print the name of the structure.  */
2488   if (TYPE_NAME (node))
2489     {
2490       INDENT (spc);
2491       if (TREE_CODE (node) == RECORD_TYPE)
2492         pp_string (buffer, "struct ");
2493       else if ((TREE_CODE (node) == UNION_TYPE
2494                 || TREE_CODE (node) == QUAL_UNION_TYPE))
2495         pp_string (buffer, "union ");
2496
2497       dump_generic_node (buffer, TYPE_NAME (node), spc, 0, false);
2498     }
2499
2500   /* Print the contents of the structure.  */
2501   pp_newline (buffer);
2502   INDENT (spc);
2503   pp_character (buffer, '{');
2504   pp_newline (buffer);
2505
2506   /* Print the fields of the structure.  */
2507   {
2508     tree tmp;
2509     tmp = TYPE_FIELDS (node);
2510     while (tmp)
2511       {
2512         /* Avoid to print recursively the structure.  */
2513         /* FIXME : Not implemented correctly...,
2514            what about the case when we have a cycle in the contain graph? ...
2515            Maybe this could be solved by looking at the scope in which the
2516            structure was declared.  */
2517         if (TREE_TYPE (tmp) != node
2518             && (TREE_CODE (TREE_TYPE (tmp)) != POINTER_TYPE
2519                 || TREE_TYPE (TREE_TYPE (tmp)) != node))
2520           {
2521             print_declaration (buffer, tmp, spc+2, flags);
2522             pp_newline (buffer);
2523           }
2524         tmp = DECL_CHAIN (tmp);
2525       }
2526   }
2527   INDENT (spc);
2528   pp_character (buffer, '}');
2529 }
2530
2531 /* Return the priority of the operator CODE.
2532
2533    From lowest to highest precedence with either left-to-right (L-R)
2534    or right-to-left (R-L) associativity]:
2535
2536      1  [L-R] ,
2537      2  [R-L] = += -= *= /= %= &= ^= |= <<= >>=
2538      3  [R-L] ?:
2539      4  [L-R] ||
2540      5  [L-R] &&
2541      6  [L-R] |
2542      7  [L-R] ^
2543      8  [L-R] &
2544      9  [L-R] == !=
2545     10  [L-R] < <= > >=
2546     11  [L-R] << >>
2547     12  [L-R] + -
2548     13  [L-R] * / %
2549     14  [R-L] ! ~ ++ -- + - * & (type) sizeof
2550     15  [L-R] fn() [] -> .
2551
2552    unary +, - and * have higher precedence than the corresponding binary
2553    operators.  */
2554
2555 int
2556 op_code_prio (enum tree_code code)
2557 {
2558   switch (code)
2559     {
2560     case TREE_LIST:
2561     case COMPOUND_EXPR:
2562     case BIND_EXPR:
2563       return 1;
2564
2565     case MODIFY_EXPR:
2566     case INIT_EXPR:
2567       return 2;
2568
2569     case COND_EXPR:
2570       return 3;
2571
2572     case TRUTH_OR_EXPR:
2573     case TRUTH_ORIF_EXPR:
2574       return 4;
2575
2576     case TRUTH_AND_EXPR:
2577     case TRUTH_ANDIF_EXPR:
2578       return 5;
2579
2580     case BIT_IOR_EXPR:
2581       return 6;
2582
2583     case BIT_XOR_EXPR:
2584     case TRUTH_XOR_EXPR:
2585       return 7;
2586
2587     case BIT_AND_EXPR:
2588       return 8;
2589
2590     case EQ_EXPR:
2591     case NE_EXPR:
2592       return 9;
2593
2594     case UNLT_EXPR:
2595     case UNLE_EXPR:
2596     case UNGT_EXPR:
2597     case UNGE_EXPR:
2598     case UNEQ_EXPR:
2599     case LTGT_EXPR:
2600     case ORDERED_EXPR:
2601     case UNORDERED_EXPR:
2602     case LT_EXPR:
2603     case LE_EXPR:
2604     case GT_EXPR:
2605     case GE_EXPR:
2606       return 10;
2607
2608     case LSHIFT_EXPR:
2609     case RSHIFT_EXPR:
2610     case LROTATE_EXPR:
2611     case RROTATE_EXPR:
2612       return 11;
2613
2614     case WIDEN_SUM_EXPR:
2615     case PLUS_EXPR:
2616     case POINTER_PLUS_EXPR:
2617     case MINUS_EXPR:
2618       return 12;
2619
2620     case VEC_WIDEN_MULT_HI_EXPR:
2621     case VEC_WIDEN_MULT_LO_EXPR:
2622     case WIDEN_MULT_EXPR:
2623     case DOT_PROD_EXPR:
2624     case WIDEN_MULT_PLUS_EXPR:
2625     case WIDEN_MULT_MINUS_EXPR:
2626     case MULT_EXPR:
2627     case TRUNC_DIV_EXPR:
2628     case CEIL_DIV_EXPR:
2629     case FLOOR_DIV_EXPR:
2630     case ROUND_DIV_EXPR:
2631     case RDIV_EXPR:
2632     case EXACT_DIV_EXPR:
2633     case TRUNC_MOD_EXPR:
2634     case CEIL_MOD_EXPR:
2635     case FLOOR_MOD_EXPR:
2636     case ROUND_MOD_EXPR:
2637     case FMA_EXPR:
2638       return 13;
2639
2640     case TRUTH_NOT_EXPR:
2641     case BIT_NOT_EXPR:
2642     case POSTINCREMENT_EXPR:
2643     case POSTDECREMENT_EXPR:
2644     case PREINCREMENT_EXPR:
2645     case PREDECREMENT_EXPR:
2646     case NEGATE_EXPR:
2647     case INDIRECT_REF:
2648     case ADDR_EXPR:
2649     case FLOAT_EXPR:
2650     CASE_CONVERT:
2651     case FIX_TRUNC_EXPR:
2652     case TARGET_EXPR:
2653       return 14;
2654
2655     case CALL_EXPR:
2656     case ARRAY_REF:
2657     case ARRAY_RANGE_REF:
2658     case COMPONENT_REF:
2659       return 15;
2660
2661       /* Special expressions.  */
2662     case MIN_EXPR:
2663     case MAX_EXPR:
2664     case ABS_EXPR:
2665     case REALPART_EXPR:
2666     case IMAGPART_EXPR:
2667     case REDUC_MAX_EXPR:
2668     case REDUC_MIN_EXPR:
2669     case REDUC_PLUS_EXPR:
2670     case VEC_LSHIFT_EXPR:
2671     case VEC_RSHIFT_EXPR:
2672     case VEC_UNPACK_HI_EXPR:
2673     case VEC_UNPACK_LO_EXPR:
2674     case VEC_UNPACK_FLOAT_HI_EXPR:
2675     case VEC_UNPACK_FLOAT_LO_EXPR:
2676     case VEC_PACK_TRUNC_EXPR:
2677     case VEC_PACK_SAT_EXPR:
2678       return 16;
2679
2680     default:
2681       /* Return an arbitrarily high precedence to avoid surrounding single
2682          VAR_DECLs in ()s.  */
2683       return 9999;
2684     }
2685 }
2686
2687 /* Return the priority of the operator OP.  */
2688
2689 int
2690 op_prio (const_tree op)
2691 {
2692   enum tree_code code;
2693
2694   if (op == NULL)
2695     return 9999;
2696
2697   code = TREE_CODE (op);
2698   if (code == SAVE_EXPR || code == NON_LVALUE_EXPR)
2699     return op_prio (TREE_OPERAND (op, 0));
2700
2701   return op_code_prio (code);
2702 }
2703
2704 /* Return the symbol associated with operator CODE.  */
2705
2706 const char *
2707 op_symbol_code (enum tree_code code)
2708 {
2709   switch (code)
2710     {
2711     case MODIFY_EXPR:
2712       return "=";
2713
2714     case TRUTH_OR_EXPR:
2715     case TRUTH_ORIF_EXPR:
2716       return "||";
2717
2718     case TRUTH_AND_EXPR:
2719     case TRUTH_ANDIF_EXPR:
2720       return "&&";
2721
2722     case BIT_IOR_EXPR:
2723       return "|";
2724
2725     case TRUTH_XOR_EXPR:
2726     case BIT_XOR_EXPR:
2727       return "^";
2728
2729     case ADDR_EXPR:
2730     case BIT_AND_EXPR:
2731       return "&";
2732
2733     case ORDERED_EXPR:
2734       return "ord";
2735     case UNORDERED_EXPR:
2736       return "unord";
2737
2738     case EQ_EXPR:
2739       return "==";
2740     case UNEQ_EXPR:
2741       return "u==";
2742
2743     case NE_EXPR:
2744       return "!=";
2745
2746     case LT_EXPR:
2747       return "<";
2748     case UNLT_EXPR:
2749       return "u<";
2750
2751     case LE_EXPR:
2752       return "<=";
2753     case UNLE_EXPR:
2754       return "u<=";
2755
2756     case GT_EXPR:
2757       return ">";
2758     case UNGT_EXPR:
2759       return "u>";
2760
2761     case GE_EXPR:
2762       return ">=";
2763     case UNGE_EXPR:
2764       return "u>=";
2765
2766     case LTGT_EXPR:
2767       return "<>";
2768
2769     case LSHIFT_EXPR:
2770       return "<<";
2771
2772     case RSHIFT_EXPR:
2773       return ">>";
2774
2775     case LROTATE_EXPR:
2776       return "r<<";
2777
2778     case RROTATE_EXPR:
2779       return "r>>";
2780
2781     case VEC_LSHIFT_EXPR:
2782       return "v<<";
2783
2784     case VEC_RSHIFT_EXPR:
2785       return "v>>";
2786
2787     case POINTER_PLUS_EXPR:
2788       return "+";
2789
2790     case PLUS_EXPR:
2791       return "+";
2792
2793     case REDUC_PLUS_EXPR:
2794       return "r+";
2795
2796     case WIDEN_SUM_EXPR:
2797       return "w+";
2798
2799     case WIDEN_MULT_EXPR:
2800       return "w*";
2801
2802     case NEGATE_EXPR:
2803     case MINUS_EXPR:
2804       return "-";
2805
2806     case BIT_NOT_EXPR:
2807       return "~";
2808
2809     case TRUTH_NOT_EXPR:
2810       return "!";
2811
2812     case MULT_EXPR:
2813     case INDIRECT_REF:
2814       return "*";
2815
2816     case TRUNC_DIV_EXPR:
2817     case RDIV_EXPR:
2818       return "/";
2819
2820     case CEIL_DIV_EXPR:
2821       return "/[cl]";
2822
2823     case FLOOR_DIV_EXPR:
2824       return "/[fl]";
2825
2826     case ROUND_DIV_EXPR:
2827       return "/[rd]";
2828
2829     case EXACT_DIV_EXPR:
2830       return "/[ex]";
2831
2832     case TRUNC_MOD_EXPR:
2833       return "%";
2834
2835     case CEIL_MOD_EXPR:
2836       return "%[cl]";
2837
2838     case FLOOR_MOD_EXPR:
2839       return "%[fl]";
2840
2841     case ROUND_MOD_EXPR:
2842       return "%[rd]";
2843
2844     case PREDECREMENT_EXPR:
2845       return " --";
2846
2847     case PREINCREMENT_EXPR:
2848       return " ++";
2849
2850     case POSTDECREMENT_EXPR:
2851       return "-- ";
2852
2853     case POSTINCREMENT_EXPR:
2854       return "++ ";
2855
2856     case MAX_EXPR:
2857       return "max";
2858
2859     case MIN_EXPR:
2860       return "min";
2861
2862     default:
2863       return "<<< ??? >>>";
2864     }
2865 }
2866
2867 /* Return the symbol associated with operator OP.  */
2868
2869 static const char *
2870 op_symbol (const_tree op)
2871 {
2872   return op_symbol_code (TREE_CODE (op));
2873 }
2874
2875 /* Prints the name of a call.  NODE is the CALL_EXPR_FN of a CALL_EXPR or
2876    the gimple_call_fn of a GIMPLE_CALL.  */
2877
2878 void
2879 print_call_name (pretty_printer *buffer, tree node, int flags)
2880 {
2881   tree op0 = node;
2882
2883   if (TREE_CODE (op0) == NON_LVALUE_EXPR)
2884     op0 = TREE_OPERAND (op0, 0);
2885
2886  again:
2887   switch (TREE_CODE (op0))
2888     {
2889     case VAR_DECL:
2890     case PARM_DECL:
2891     case FUNCTION_DECL:
2892       dump_function_name (buffer, op0, flags);
2893       break;
2894
2895     case ADDR_EXPR:
2896     case INDIRECT_REF:
2897     case NOP_EXPR:
2898       op0 = TREE_OPERAND (op0, 0);
2899       goto again;
2900
2901     case COND_EXPR:
2902       pp_string (buffer, "(");
2903       dump_generic_node (buffer, TREE_OPERAND (op0, 0), 0, flags, false);
2904       pp_string (buffer, ") ? ");
2905       dump_generic_node (buffer, TREE_OPERAND (op0, 1), 0, flags, false);
2906       pp_string (buffer, " : ");
2907       dump_generic_node (buffer, TREE_OPERAND (op0, 2), 0, flags, false);
2908       break;
2909
2910     case ARRAY_REF:
2911       if (TREE_CODE (TREE_OPERAND (op0, 0)) == VAR_DECL)
2912         dump_function_name (buffer, TREE_OPERAND (op0, 0), flags);
2913       else
2914         dump_generic_node (buffer, op0, 0, flags, false);
2915       break;
2916
2917     case MEM_REF:
2918       if (integer_zerop (TREE_OPERAND (op0, 1)))
2919         {
2920           op0 = TREE_OPERAND (op0, 0);
2921           goto again;
2922         }
2923       /* Fallthru.  */
2924     case COMPONENT_REF:
2925     case SSA_NAME:
2926     case OBJ_TYPE_REF:
2927       dump_generic_node (buffer, op0, 0, flags, false);
2928       break;
2929
2930     default:
2931       NIY;
2932     }
2933 }
2934
2935 /* Parses the string STR and replaces new-lines by '\n', tabs by '\t', ...  */
2936
2937 static void
2938 pretty_print_string (pretty_printer *buffer, const char *str)
2939 {
2940   if (str == NULL)
2941     return;
2942
2943   while (*str)
2944     {
2945       switch (str[0])
2946         {
2947         case '\b':
2948           pp_string (buffer, "\\b");
2949           break;
2950
2951         case '\f':
2952           pp_string (buffer, "\\f");
2953           break;
2954
2955         case '\n':
2956           pp_string (buffer, "\\n");
2957           break;
2958
2959         case '\r':
2960           pp_string (buffer, "\\r");
2961           break;
2962
2963         case '\t':
2964           pp_string (buffer, "\\t");
2965           break;
2966
2967         case '\v':
2968           pp_string (buffer, "\\v");
2969           break;
2970
2971         case '\\':
2972           pp_string (buffer, "\\\\");
2973           break;
2974
2975         case '\"':
2976           pp_string (buffer, "\\\"");
2977           break;
2978
2979         case '\'':
2980           pp_string (buffer, "\\'");
2981           break;
2982
2983           /* No need to handle \0; the loop terminates on \0.  */
2984
2985         case '\1':
2986           pp_string (buffer, "\\1");
2987           break;
2988
2989         case '\2':
2990           pp_string (buffer, "\\2");
2991           break;
2992
2993         case '\3':
2994           pp_string (buffer, "\\3");
2995           break;
2996
2997         case '\4':
2998           pp_string (buffer, "\\4");
2999           break;
3000
3001         case '\5':
3002           pp_string (buffer, "\\5");
3003           break;
3004
3005         case '\6':
3006           pp_string (buffer, "\\6");
3007           break;
3008
3009         case '\7':
3010           pp_string (buffer, "\\7");
3011           break;
3012
3013         default:
3014           pp_character (buffer, str[0]);
3015           break;
3016         }
3017       str++;
3018     }
3019 }
3020
3021 static void
3022 maybe_init_pretty_print (FILE *file)
3023 {
3024   if (!initialized)
3025     {
3026       pp_construct (&buffer, /* prefix */NULL, /* line-width */0);
3027       pp_needs_newline (&buffer) = true;
3028       pp_translate_identifiers (&buffer) = false;
3029       initialized = 1;
3030     }
3031
3032   buffer.buffer->stream = file;
3033 }
3034
3035 static void
3036 newline_and_indent (pretty_printer *buffer, int spc)
3037 {
3038   pp_newline (buffer);
3039   INDENT (spc);
3040 }
3041
3042 /* Handle a %K format for TEXT.  Separate from default_tree_printer so
3043    it can also be used in front ends.
3044    %K: a statement, from which EXPR_LOCATION and TREE_BLOCK will be recorded.
3045 */
3046
3047 void
3048 percent_K_format (text_info *text)
3049 {
3050   tree t = va_arg (*text->args_ptr, tree), block;
3051   gcc_assert (text->locus != NULL);
3052   *text->locus = EXPR_LOCATION (t);
3053   gcc_assert (pp_ti_abstract_origin (text) != NULL);
3054   block = TREE_BLOCK (t);
3055   *pp_ti_abstract_origin (text) = NULL;
3056   while (block
3057          && TREE_CODE (block) == BLOCK
3058          && BLOCK_ABSTRACT_ORIGIN (block))
3059     {
3060       tree ao = BLOCK_ABSTRACT_ORIGIN (block);
3061
3062       while (TREE_CODE (ao) == BLOCK
3063              && BLOCK_ABSTRACT_ORIGIN (ao)
3064              && BLOCK_ABSTRACT_ORIGIN (ao) != ao)
3065         ao = BLOCK_ABSTRACT_ORIGIN (ao);
3066
3067       if (TREE_CODE (ao) == FUNCTION_DECL)
3068         {
3069           *pp_ti_abstract_origin (text) = block;
3070           break;
3071         }
3072       block = BLOCK_SUPERCONTEXT (block);
3073     }
3074 }
3075
3076 /* Print the identifier ID to PRETTY-PRINTER.  */
3077
3078 void
3079 pp_base_tree_identifier (pretty_printer *pp, tree id)
3080 {
3081   if (pp_translate_identifiers (pp))
3082     {
3083       const char *text = identifier_to_locale (IDENTIFIER_POINTER (id));
3084       pp_append_text (pp, text, text + strlen (text));
3085     }
3086   else
3087     pp_append_text (pp, IDENTIFIER_POINTER (id),
3088                     IDENTIFIER_POINTER (id) + IDENTIFIER_LENGTH (id));
3089 }
3090
3091 /* A helper function that is used to dump function information before the
3092    function dump.  */
3093
3094 void
3095 dump_function_header (FILE *dump_file, tree fdecl, int flags)
3096 {
3097   const char *dname, *aname;
3098   struct cgraph_node *node = cgraph_get_node (fdecl);
3099   struct function *fun = DECL_STRUCT_FUNCTION (fdecl);
3100
3101   dname = lang_hooks.decl_printable_name (fdecl, 2);
3102
3103   if (DECL_ASSEMBLER_NAME_SET_P (fdecl))
3104     aname = (IDENTIFIER_POINTER
3105              (DECL_ASSEMBLER_NAME (fdecl)));
3106   else
3107     aname = "<unset-asm-name>";
3108
3109   fprintf (dump_file, "\n;; Function %s (%s, funcdef_no=%d",
3110            dname, aname, fun->funcdef_no);
3111   if (!(flags & TDF_NOUID))
3112     fprintf (dump_file, ", decl_uid=%d", DECL_UID (fdecl));
3113   if (node)
3114     {
3115       fprintf (dump_file, ", cgraph_uid=%d)%s\n\n", node->uid,
3116                node->frequency == NODE_FREQUENCY_HOT
3117                ? " (hot)"
3118                : node->frequency == NODE_FREQUENCY_UNLIKELY_EXECUTED
3119                ? " (unlikely executed)"
3120                : node->frequency == NODE_FREQUENCY_EXECUTED_ONCE
3121                ? " (executed once)"
3122                : "");
3123     }
3124   else
3125     fprintf (dump_file, ")\n\n");
3126 }