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