OSDN Git Service

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