OSDN Git Service

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