comparison gcc/pretty-print.c @ 111:04ced10e8804

gcc 7
author kono
date Fri, 27 Oct 2017 22:46:09 +0900
parents f6334be47118
children 84e7813d76e9
comparison
equal deleted inserted replaced
68:561a7518be6b 111:04ced10e8804
1 /* Various declarations for language-independent pretty-print subroutines. 1 /* Various declarations for language-independent pretty-print subroutines.
2 Copyright (C) 2003, 2004, 2005, 2007, 2008, 2009, 2010 2 Copyright (C) 2003-2017 Free Software Foundation, Inc.
3 Free Software Foundation, Inc.
4 Contributed by Gabriel Dos Reis <gdr@integrable-solutions.net> 3 Contributed by Gabriel Dos Reis <gdr@integrable-solutions.net>
5 4
6 This file is part of GCC. 5 This file is part of GCC.
7 6
8 GCC is free software; you can redistribute it and/or modify it under 7 GCC is free software; you can redistribute it and/or modify it under
22 #include "config.h" 21 #include "config.h"
23 #include "system.h" 22 #include "system.h"
24 #include "coretypes.h" 23 #include "coretypes.h"
25 #include "intl.h" 24 #include "intl.h"
26 #include "pretty-print.h" 25 #include "pretty-print.h"
26 #include "diagnostic-color.h"
27 #include "selftest.h"
27 28
28 #if HAVE_ICONV 29 #if HAVE_ICONV
29 #include <iconv.h> 30 #include <iconv.h>
30 #endif 31 #endif
31 32
32 /* A pointer to the formatted diagnostic message. */ 33 #ifdef __MINGW32__
33 #define pp_formatted_text_data(PP) \ 34
34 ((const char *) obstack_base (pp_base (PP)->buffer->obstack)) 35 /* Replacement for fputs() that handles ANSI escape codes on Windows NT.
36 Contributed by: Liu Hao (lh_mouse at 126 dot com)
37
38 XXX: This file is compiled into libcommon.a that will be self-contained.
39 It looks like that these functions can be put nowhere else. */
40
41 #include <io.h>
42 #define WIN32_LEAN_AND_MEAN 1
43 #include <windows.h>
44
45 /* Write all bytes in [s,s+n) into the specified stream.
46 Errors are ignored. */
47 static void
48 write_all (HANDLE h, const char *s, size_t n)
49 {
50 size_t rem = n;
51 DWORD step;
52
53 while (rem != 0)
54 {
55 if (rem <= UINT_MAX)
56 step = rem;
57 else
58 step = UINT_MAX;
59 if (!WriteFile (h, s + n - rem, step, &step, NULL))
60 break;
61 rem -= step;
62 }
63 }
64
65 /* Find the beginning of an escape sequence.
66 There are two cases:
67 1. If the sequence begins with an ESC character (0x1B) and a second
68 character X in [0x40,0x5F], returns X and stores a pointer to
69 the third character into *head.
70 2. If the sequence begins with a character X in [0x80,0x9F], returns
71 (X-0x40) and stores a pointer to the second character into *head.
72 Stores the number of ESC character(s) in *prefix_len.
73 Returns 0 if no such sequence can be found. */
74 static int
75 find_esc_head (int *prefix_len, const char **head, const char *str)
76 {
77 int c;
78 const char *r = str;
79 int escaped = 0;
80
81 for (;;)
82 {
83 c = (unsigned char) *r;
84 if (c == 0)
85 {
86 /* Not found. */
87 return 0;
88 }
89 if (escaped && 0x40 <= c && c <= 0x5F)
90 {
91 /* Found (case 1). */
92 *prefix_len = 2;
93 *head = r + 1;
94 return c;
95 }
96 if (0x80 <= c && c <= 0x9F)
97 {
98 /* Found (case 2). */
99 *prefix_len = 1;
100 *head = r + 1;
101 return c - 0x40;
102 }
103 ++r;
104 escaped = c == 0x1B;
105 }
106 }
107
108 /* Find the terminator of an escape sequence.
109 str should be the value stored in *head by a previous successful
110 call to find_esc_head().
111 Returns 0 if no such sequence can be found. */
112 static int
113 find_esc_terminator (const char **term, const char *str)
114 {
115 int c;
116 const char *r = str;
117
118 for (;;)
119 {
120 c = (unsigned char) *r;
121 if (c == 0)
122 {
123 /* Not found. */
124 return 0;
125 }
126 if (0x40 <= c && c <= 0x7E)
127 {
128 /* Found. */
129 *term = r;
130 return c;
131 }
132 ++r;
133 }
134 }
135
136 /* Handle a sequence of codes. Sequences that are invalid, reserved,
137 unrecognized or unimplemented are ignored silently.
138 There isn't much we can do because of lameness of Windows consoles. */
139 static void
140 eat_esc_sequence (HANDLE h, int esc_code,
141 const char *esc_head, const char *esc_term)
142 {
143 /* Numbers in an escape sequence cannot be negative, because
144 a minus sign in the middle of it would have terminated it. */
145 long n1, n2;
146 char *eptr, *delim;
147 CONSOLE_SCREEN_BUFFER_INFO sb;
148 COORD cr;
149 /* ED and EL parameters. */
150 DWORD cnt, step;
151 long rows;
152 /* SGR parameters. */
153 WORD attrib_add, attrib_rm;
154 const char *param;
155
156 switch (MAKEWORD (esc_code, *esc_term))
157 {
158 /* ESC [ n1 'A'
159 Move the cursor up by n1 characters. */
160 case MAKEWORD ('[', 'A'):
161 if (esc_head == esc_term)
162 n1 = 1;
163 else
164 {
165 n1 = strtol (esc_head, &eptr, 10);
166 if (eptr != esc_term)
167 break;
168 }
169
170 if (GetConsoleScreenBufferInfo (h, &sb))
171 {
172 cr = sb.dwCursorPosition;
173 /* Stop at the topmost boundary. */
174 if (cr.Y > n1)
175 cr.Y -= n1;
176 else
177 cr.Y = 0;
178 SetConsoleCursorPosition (h, cr);
179 }
180 break;
181
182 /* ESC [ n1 'B'
183 Move the cursor down by n1 characters. */
184 case MAKEWORD ('[', 'B'):
185 if (esc_head == esc_term)
186 n1 = 1;
187 else
188 {
189 n1 = strtol (esc_head, &eptr, 10);
190 if (eptr != esc_term)
191 break;
192 }
193
194 if (GetConsoleScreenBufferInfo (h, &sb))
195 {
196 cr = sb.dwCursorPosition;
197 /* Stop at the bottommost boundary. */
198 if (sb.dwSize.Y - cr.Y > n1)
199 cr.Y += n1;
200 else
201 cr.Y = sb.dwSize.Y;
202 SetConsoleCursorPosition (h, cr);
203 }
204 break;
205
206 /* ESC [ n1 'C'
207 Move the cursor right by n1 characters. */
208 case MAKEWORD ('[', 'C'):
209 if (esc_head == esc_term)
210 n1 = 1;
211 else
212 {
213 n1 = strtol (esc_head, &eptr, 10);
214 if (eptr != esc_term)
215 break;
216 }
217
218 if (GetConsoleScreenBufferInfo (h, &sb))
219 {
220 cr = sb.dwCursorPosition;
221 /* Stop at the rightmost boundary. */
222 if (sb.dwSize.X - cr.X > n1)
223 cr.X += n1;
224 else
225 cr.X = sb.dwSize.X;
226 SetConsoleCursorPosition (h, cr);
227 }
228 break;
229
230 /* ESC [ n1 'D'
231 Move the cursor left by n1 characters. */
232 case MAKEWORD ('[', 'D'):
233 if (esc_head == esc_term)
234 n1 = 1;
235 else
236 {
237 n1 = strtol (esc_head, &eptr, 10);
238 if (eptr != esc_term)
239 break;
240 }
241
242 if (GetConsoleScreenBufferInfo (h, &sb))
243 {
244 cr = sb.dwCursorPosition;
245 /* Stop at the leftmost boundary. */
246 if (cr.X > n1)
247 cr.X -= n1;
248 else
249 cr.X = 0;
250 SetConsoleCursorPosition (h, cr);
251 }
252 break;
253
254 /* ESC [ n1 'E'
255 Move the cursor to the beginning of the n1-th line downwards. */
256 case MAKEWORD ('[', 'E'):
257 if (esc_head == esc_term)
258 n1 = 1;
259 else
260 {
261 n1 = strtol (esc_head, &eptr, 10);
262 if (eptr != esc_term)
263 break;
264 }
265
266 if (GetConsoleScreenBufferInfo (h, &sb))
267 {
268 cr = sb.dwCursorPosition;
269 cr.X = 0;
270 /* Stop at the bottommost boundary. */
271 if (sb.dwSize.Y - cr.Y > n1)
272 cr.Y += n1;
273 else
274 cr.Y = sb.dwSize.Y;
275 SetConsoleCursorPosition (h, cr);
276 }
277 break;
278
279 /* ESC [ n1 'F'
280 Move the cursor to the beginning of the n1-th line upwards. */
281 case MAKEWORD ('[', 'F'):
282 if (esc_head == esc_term)
283 n1 = 1;
284 else
285 {
286 n1 = strtol (esc_head, &eptr, 10);
287 if (eptr != esc_term)
288 break;
289 }
290
291 if (GetConsoleScreenBufferInfo (h, &sb))
292 {
293 cr = sb.dwCursorPosition;
294 cr.X = 0;
295 /* Stop at the topmost boundary. */
296 if (cr.Y > n1)
297 cr.Y -= n1;
298 else
299 cr.Y = 0;
300 SetConsoleCursorPosition (h, cr);
301 }
302 break;
303
304 /* ESC [ n1 'G'
305 Move the cursor to the (1-based) n1-th column. */
306 case MAKEWORD ('[', 'G'):
307 if (esc_head == esc_term)
308 n1 = 1;
309 else
310 {
311 n1 = strtol (esc_head, &eptr, 10);
312 if (eptr != esc_term)
313 break;
314 }
315
316 if (GetConsoleScreenBufferInfo (h, &sb))
317 {
318 cr = sb.dwCursorPosition;
319 n1 -= 1;
320 /* Stop at the leftmost or rightmost boundary. */
321 if (n1 < 0)
322 cr.X = 0;
323 else if (n1 > sb.dwSize.X)
324 cr.X = sb.dwSize.X;
325 else
326 cr.X = n1;
327 SetConsoleCursorPosition (h, cr);
328 }
329 break;
330
331 /* ESC [ n1 ';' n2 'H'
332 ESC [ n1 ';' n2 'f'
333 Move the cursor to the (1-based) n1-th row and
334 (also 1-based) n2-th column. */
335 case MAKEWORD ('[', 'H'):
336 case MAKEWORD ('[', 'f'):
337 if (esc_head == esc_term)
338 {
339 /* Both parameters are omitted and set to 1 by default. */
340 n1 = 1;
341 n2 = 1;
342 }
343 else if (!(delim = (char *) memchr (esc_head, ';',
344 esc_term - esc_head)))
345 {
346 /* Only the first parameter is given. The second one is
347 set to 1 by default. */
348 n1 = strtol (esc_head, &eptr, 10);
349 if (eptr != esc_term)
350 break;
351 n2 = 1;
352 }
353 else
354 {
355 /* Both parameters are given. The first one shall be
356 terminated by the semicolon. */
357 n1 = strtol (esc_head, &eptr, 10);
358 if (eptr != delim)
359 break;
360 n2 = strtol (delim + 1, &eptr, 10);
361 if (eptr != esc_term)
362 break;
363 }
364
365 if (GetConsoleScreenBufferInfo (h, &sb))
366 {
367 cr = sb.dwCursorPosition;
368 n1 -= 1;
369 n2 -= 1;
370 /* The cursor position shall be relative to the view coord of
371 the console window, which is usually smaller than the actual
372 buffer. FWIW, the 'appropriate' solution will be shrinking
373 the buffer to match the size of the console window,
374 destroying scrollback in the process. */
375 n1 += sb.srWindow.Top;
376 n2 += sb.srWindow.Left;
377 /* Stop at the topmost or bottommost boundary. */
378 if (n1 < 0)
379 cr.Y = 0;
380 else if (n1 > sb.dwSize.Y)
381 cr.Y = sb.dwSize.Y;
382 else
383 cr.Y = n1;
384 /* Stop at the leftmost or rightmost boundary. */
385 if (n2 < 0)
386 cr.X = 0;
387 else if (n2 > sb.dwSize.X)
388 cr.X = sb.dwSize.X;
389 else
390 cr.X = n2;
391 SetConsoleCursorPosition (h, cr);
392 }
393 break;
394
395 /* ESC [ n1 'J'
396 Erase display. */
397 case MAKEWORD ('[', 'J'):
398 if (esc_head == esc_term)
399 /* This is one of the very few codes whose parameters have
400 a default value of zero. */
401 n1 = 0;
402 else
403 {
404 n1 = strtol (esc_head, &eptr, 10);
405 if (eptr != esc_term)
406 break;
407 }
408
409 if (GetConsoleScreenBufferInfo (h, &sb))
410 {
411 /* The cursor is not necessarily in the console window, which
412 makes the behavior of this code harder to define. */
413 switch (n1)
414 {
415 case 0:
416 /* If the cursor is in or above the window, erase from
417 it to the bottom of the window; otherwise, do nothing. */
418 cr = sb.dwCursorPosition;
419 cnt = sb.dwSize.X - sb.dwCursorPosition.X;
420 rows = sb.srWindow.Bottom - sb.dwCursorPosition.Y;
421 break;
422 case 1:
423 /* If the cursor is in or under the window, erase from
424 it to the top of the window; otherwise, do nothing. */
425 cr.X = 0;
426 cr.Y = sb.srWindow.Top;
427 cnt = sb.dwCursorPosition.X + 1;
428 rows = sb.dwCursorPosition.Y - sb.srWindow.Top;
429 break;
430 case 2:
431 /* Erase the entire window. */
432 cr.X = sb.srWindow.Left;
433 cr.Y = sb.srWindow.Top;
434 cnt = 0;
435 rows = sb.srWindow.Bottom - sb.srWindow.Top + 1;
436 break;
437 default:
438 /* Erase the entire buffer. */
439 cr.X = 0;
440 cr.Y = 0;
441 cnt = 0;
442 rows = sb.dwSize.Y;
443 break;
444 }
445 if (rows < 0)
446 break;
447 cnt += rows * sb.dwSize.X;
448 FillConsoleOutputCharacterW (h, L' ', cnt, cr, &step);
449 FillConsoleOutputAttribute (h, sb.wAttributes, cnt, cr, &step);
450 }
451 break;
452
453 /* ESC [ n1 'K'
454 Erase line. */
455 case MAKEWORD ('[', 'K'):
456 if (esc_head == esc_term)
457 /* This is one of the very few codes whose parameters have
458 a default value of zero. */
459 n1 = 0;
460 else
461 {
462 n1 = strtol (esc_head, &eptr, 10);
463 if (eptr != esc_term)
464 break;
465 }
466
467 if (GetConsoleScreenBufferInfo (h, &sb))
468 {
469 switch (n1)
470 {
471 case 0:
472 /* Erase from the cursor to the end. */
473 cr = sb.dwCursorPosition;
474 cnt = sb.dwSize.X - sb.dwCursorPosition.X;
475 break;
476 case 1:
477 /* Erase from the cursor to the beginning. */
478 cr = sb.dwCursorPosition;
479 cr.X = 0;
480 cnt = sb.dwCursorPosition.X + 1;
481 break;
482 default:
483 /* Erase the entire line. */
484 cr = sb.dwCursorPosition;
485 cr.X = 0;
486 cnt = sb.dwSize.X;
487 break;
488 }
489 FillConsoleOutputCharacterW (h, L' ', cnt, cr, &step);
490 FillConsoleOutputAttribute (h, sb.wAttributes, cnt, cr, &step);
491 }
492 break;
493
494 /* ESC [ n1 ';' n2 'm'
495 Set SGR parameters. Zero or more parameters will follow. */
496 case MAKEWORD ('[', 'm'):
497 attrib_add = 0;
498 attrib_rm = 0;
499 if (esc_head == esc_term)
500 {
501 /* When no parameter is given, reset the console. */
502 attrib_add |= (FOREGROUND_RED | FOREGROUND_GREEN
503 | FOREGROUND_BLUE);
504 attrib_rm = -1; /* Removes everything. */
505 goto sgr_set_it;
506 }
507 param = esc_head;
508 do
509 {
510 /* Parse a parameter. */
511 n1 = strtol (param, &eptr, 10);
512 if (*eptr != ';' && eptr != esc_term)
513 goto sgr_set_it;
514
515 switch (n1)
516 {
517 case 0:
518 /* Reset. */
519 attrib_add |= (FOREGROUND_RED | FOREGROUND_GREEN
520 | FOREGROUND_BLUE);
521 attrib_rm = -1; /* Removes everything. */
522 break;
523 case 1:
524 /* Bold. */
525 attrib_add |= FOREGROUND_INTENSITY;
526 break;
527 case 4:
528 /* Underline. */
529 attrib_add |= COMMON_LVB_UNDERSCORE;
530 break;
531 case 5:
532 /* Blink. */
533 /* XXX: It is not BLINKING at all! */
534 attrib_add |= BACKGROUND_INTENSITY;
535 break;
536 case 7:
537 /* Reverse. */
538 attrib_add |= COMMON_LVB_REVERSE_VIDEO;
539 break;
540 case 22:
541 /* No bold. */
542 attrib_add &= ~FOREGROUND_INTENSITY;
543 attrib_rm |= FOREGROUND_INTENSITY;
544 break;
545 case 24:
546 /* No underline. */
547 attrib_add &= ~COMMON_LVB_UNDERSCORE;
548 attrib_rm |= COMMON_LVB_UNDERSCORE;
549 break;
550 case 25:
551 /* No blink. */
552 /* XXX: It is not BLINKING at all! */
553 attrib_add &= ~BACKGROUND_INTENSITY;
554 attrib_rm |= BACKGROUND_INTENSITY;
555 break;
556 case 27:
557 /* No reverse. */
558 attrib_add &= ~COMMON_LVB_REVERSE_VIDEO;
559 attrib_rm |= COMMON_LVB_REVERSE_VIDEO;
560 break;
561 case 30:
562 case 31:
563 case 32:
564 case 33:
565 case 34:
566 case 35:
567 case 36:
568 case 37:
569 /* Foreground color. */
570 attrib_add &= ~(FOREGROUND_RED | FOREGROUND_GREEN
571 | FOREGROUND_BLUE);
572 n1 -= 30;
573 if (n1 & 1)
574 attrib_add |= FOREGROUND_RED;
575 if (n1 & 2)
576 attrib_add |= FOREGROUND_GREEN;
577 if (n1 & 4)
578 attrib_add |= FOREGROUND_BLUE;
579 attrib_rm |= (FOREGROUND_RED | FOREGROUND_GREEN
580 | FOREGROUND_BLUE);
581 break;
582 case 38:
583 /* Reserved for extended foreground color.
584 Don't know how to handle parameters remaining.
585 Bail out. */
586 goto sgr_set_it;
587 case 39:
588 /* Reset foreground color. */
589 /* Set to grey. */
590 attrib_add |= (FOREGROUND_RED | FOREGROUND_GREEN
591 | FOREGROUND_BLUE);
592 attrib_rm |= (FOREGROUND_RED | FOREGROUND_GREEN
593 | FOREGROUND_BLUE);
594 break;
595 case 40:
596 case 41:
597 case 42:
598 case 43:
599 case 44:
600 case 45:
601 case 46:
602 case 47:
603 /* Background color. */
604 attrib_add &= ~(BACKGROUND_RED | BACKGROUND_GREEN
605 | BACKGROUND_BLUE);
606 n1 -= 40;
607 if (n1 & 1)
608 attrib_add |= BACKGROUND_RED;
609 if (n1 & 2)
610 attrib_add |= BACKGROUND_GREEN;
611 if (n1 & 4)
612 attrib_add |= BACKGROUND_BLUE;
613 attrib_rm |= (BACKGROUND_RED | BACKGROUND_GREEN
614 | BACKGROUND_BLUE);
615 break;
616 case 48:
617 /* Reserved for extended background color.
618 Don't know how to handle parameters remaining.
619 Bail out. */
620 goto sgr_set_it;
621 case 49:
622 /* Reset background color. */
623 /* Set to black. */
624 attrib_add &= ~(BACKGROUND_RED | BACKGROUND_GREEN
625 | BACKGROUND_BLUE);
626 attrib_rm |= (BACKGROUND_RED | BACKGROUND_GREEN
627 | BACKGROUND_BLUE);
628 break;
629 }
630
631 /* Prepare the next parameter. */
632 param = eptr + 1;
633 }
634 while (param != esc_term);
635
636 sgr_set_it:
637 /* 0xFFFF removes everything. If it is not the case,
638 care must be taken to preserve old attributes. */
639 if (attrib_rm != 0xFFFF && GetConsoleScreenBufferInfo (h, &sb))
640 {
641 attrib_add |= sb.wAttributes & ~attrib_rm;
642 }
643 SetConsoleTextAttribute (h, attrib_add);
644 break;
645 }
646 }
647
648 int
649 mingw_ansi_fputs (const char *str, FILE *fp)
650 {
651 const char *read = str;
652 HANDLE h;
653 DWORD mode;
654 int esc_code, prefix_len;
655 const char *esc_head, *esc_term;
656
657 h = (HANDLE) _get_osfhandle (_fileno (fp));
658 if (h == INVALID_HANDLE_VALUE)
659 return EOF;
660
661 /* Don't mess up stdio functions with Windows APIs. */
662 fflush (fp);
663
664 if (GetConsoleMode (h, &mode))
665 /* If it is a console, translate ANSI escape codes as needed. */
666 for (;;)
667 {
668 if ((esc_code = find_esc_head (&prefix_len, &esc_head, read)) == 0)
669 {
670 /* Write all remaining characters, then exit. */
671 write_all (h, read, strlen (read));
672 break;
673 }
674 if (find_esc_terminator (&esc_term, esc_head) == 0)
675 /* Ignore incomplete escape sequences at the moment.
676 FIXME: The escape state shall be cached for further calls
677 to this function. */
678 break;
679 write_all (h, read, esc_head - prefix_len - read);
680 eat_esc_sequence (h, esc_code, esc_head, esc_term);
681 read = esc_term + 1;
682 }
683 else
684 /* If it is not a console, write everything as-is. */
685 write_all (h, read, strlen (read));
686
687 _close ((intptr_t) h);
688 return 1;
689 }
690
691 #endif /* __MINGW32__ */
692
693 static void pp_quoted_string (pretty_printer *, const char *, size_t = -1);
694
695 /* Overwrite the given location/range within this text_info's rich_location.
696 For use e.g. when implementing "+" in client format decoders. */
697
698 void
699 text_info::set_location (unsigned int idx, location_t loc, bool show_caret_p)
700 {
701 gcc_checking_assert (m_richloc);
702 m_richloc->set_range (line_table, idx, loc, show_caret_p);
703 }
704
705 location_t
706 text_info::get_location (unsigned int index_of_location) const
707 {
708 gcc_checking_assert (m_richloc);
709
710 if (index_of_location == 0)
711 return m_richloc->get_loc ();
712 else
713 return UNKNOWN_LOCATION;
714 }
715
716 // Default construct an output buffer.
717
718 output_buffer::output_buffer ()
719 : formatted_obstack (),
720 chunk_obstack (),
721 obstack (&formatted_obstack),
722 cur_chunk_array (),
723 stream (stderr),
724 line_length (),
725 digit_buffer (),
726 flush_p (true)
727 {
728 obstack_init (&formatted_obstack);
729 obstack_init (&chunk_obstack);
730 }
731
732 // Release resources owned by an output buffer at the end of lifetime.
733
734 output_buffer::~output_buffer ()
735 {
736 obstack_free (&chunk_obstack, NULL);
737 obstack_free (&formatted_obstack, NULL);
738 }
739
35 740
36 /* Format an integer given by va_arg (ARG, type-specifier T) where 741 /* Format an integer given by va_arg (ARG, type-specifier T) where
37 type-specifier is a precision modifier as indicated by PREC. F is 742 type-specifier is a precision modifier as indicated by PREC. F is
38 a string used to construct the appropriate format-specifier. */ 743 a string used to construct the appropriate format-specifier. */
39 #define pp_integer_with_precision(PP, ARG, PREC, T, F) \ 744 #define pp_integer_with_precision(PP, ARG, PREC, T, F) \
93 /* Flush the formatted text of PRETTY-PRINTER onto the attached stream. */ 798 /* Flush the formatted text of PRETTY-PRINTER onto the attached stream. */
94 void 799 void
95 pp_write_text_to_stream (pretty_printer *pp) 800 pp_write_text_to_stream (pretty_printer *pp)
96 { 801 {
97 const char *text = pp_formatted_text (pp); 802 const char *text = pp_formatted_text (pp);
98 fputs (text, pp->buffer->stream); 803 #ifdef __MINGW32__
804 mingw_ansi_fputs (text, pp_buffer (pp)->stream);
805 #else
806 fputs (text, pp_buffer (pp)->stream);
807 #endif
808 pp_clear_output_area (pp);
809 }
810
811 /* As pp_write_text_to_stream, but for GraphViz label output.
812
813 Flush the formatted text of pretty-printer PP onto the attached stream.
814 Replace characters in PPF that have special meaning in a GraphViz .dot
815 file.
816
817 This routine is not very fast, but it doesn't have to be as this is only
818 be used by routines dumping intermediate representations in graph form. */
819
820 void
821 pp_write_text_as_dot_label_to_stream (pretty_printer *pp, bool for_record)
822 {
823 const char *text = pp_formatted_text (pp);
824 const char *p = text;
825 FILE *fp = pp_buffer (pp)->stream;
826
827 for (;*p; p++)
828 {
829 bool escape_char;
830 switch (*p)
831 {
832 /* Print newlines as a left-aligned newline. */
833 case '\n':
834 fputs ("\\l", fp);
835 escape_char = true;
836 break;
837
838 /* The following characters are only special for record-shape nodes. */
839 case '|':
840 case '{':
841 case '}':
842 case '<':
843 case '>':
844 case ' ':
845 escape_char = for_record;
846 break;
847
848 /* The following characters always have to be escaped
849 for use in labels. */
850 case '\\':
851 /* There is a bug in some (f.i. 2.36.0) versions of graphiz
852 ( http://www.graphviz.org/mantisbt/view.php?id=2524 ) related to
853 backslash as last char in label. Let's avoid triggering it. */
854 gcc_assert (*(p + 1) != '\0');
855 /* Fall through. */
856 case '"':
857 escape_char = true;
858 break;
859
860 default:
861 escape_char = false;
862 break;
863 }
864
865 if (escape_char)
866 fputc ('\\', fp);
867
868 fputc (*p, fp);
869 }
870
99 pp_clear_output_area (pp); 871 pp_clear_output_area (pp);
100 } 872 }
101 873
102 /* Wrap a text delimited by START and END into PRETTY-PRINTER. */ 874 /* Wrap a text delimited by START and END into PRETTY-PRINTER. */
103 static void 875 static void
145 /* Append to the output area of PRETTY-PRINTER a string specified by its 917 /* Append to the output area of PRETTY-PRINTER a string specified by its
146 STARTing character and LENGTH. */ 918 STARTing character and LENGTH. */
147 static inline void 919 static inline void
148 pp_append_r (pretty_printer *pp, const char *start, int length) 920 pp_append_r (pretty_printer *pp, const char *start, int length)
149 { 921 {
150 obstack_grow (pp->buffer->obstack, start, length); 922 output_buffer_append_r (pp_buffer (pp), start, length);
151 pp->buffer->line_length += length;
152 } 923 }
153 924
154 /* Insert enough spaces into the output area of PRETTY-PRINTER to bring 925 /* Insert enough spaces into the output area of PRETTY-PRINTER to bring
155 the column position to the current indentation level, assuming that a 926 the column position to the current indentation level, assuming that a
156 newline has just been written to the buffer. */ 927 newline has just been written to the buffer. */
157 void 928 void
158 pp_base_indent (pretty_printer *pp) 929 pp_indent (pretty_printer *pp)
159 { 930 {
160 int n = pp_indentation (pp); 931 int n = pp_indentation (pp);
161 int i; 932 int i;
162 933
163 for (i = 0; i < n; ++i) 934 for (i = 0; i < n; ++i)
172 %ld, %li, %lo, %lu, %lx: long versions of the above. 943 %ld, %li, %lo, %lu, %lx: long versions of the above.
173 %lld, %lli, %llo, %llu, %llx: long long versions. 944 %lld, %lli, %llo, %llu, %llx: long long versions.
174 %wd, %wi, %wo, %wu, %wx: HOST_WIDE_INT versions. 945 %wd, %wi, %wo, %wu, %wx: HOST_WIDE_INT versions.
175 %c: character. 946 %c: character.
176 %s: string. 947 %s: string.
177 %p: pointer. 948 %p: pointer (printed in a host-dependent manner).
949 %r: if pp_show_color(pp), switch to color identified by const char *.
950 %R: if pp_show_color(pp), reset color.
178 %m: strerror(text->err_no) - does not consume a value from args_ptr. 951 %m: strerror(text->err_no) - does not consume a value from args_ptr.
179 %%: '%'. 952 %%: '%'.
180 %<: opening quote. 953 %<: opening quote.
181 %>: closing quote. 954 %>: closing quote.
182 %': apostrophe (should only be used in untranslated messages; 955 %': apostrophe (should only be used in untranslated messages;
183 translations should use appropriate punctuation directly). 956 translations should use appropriate punctuation directly).
184 %.*s: a substring the length of which is specified by an argument 957 %.*s: a substring the length of which is specified by an argument
185 integer. 958 integer.
186 %Ns: likewise, but length specified as constant in the format string. 959 %Ns: likewise, but length specified as constant in the format string.
187 Flag 'q': quote formatted text (must come immediately after '%'). 960 Flag 'q': quote formatted text (must come immediately after '%').
961 %Z: Requires two arguments - array of int, and len. Prints elements
962 of the array.
188 963
189 Arguments can be used sequentially, or through %N$ resp. *N$ 964 Arguments can be used sequentially, or through %N$ resp. *N$
190 notation Nth argument after the format string. If %N$ / *N$ 965 notation Nth argument after the format string. If %N$ / *N$
191 notation is used, it must be used for all arguments, except %m, %%, 966 notation is used, it must be used for all arguments, except %m, %%,
192 %<, %> and %', which may not have a number, as they do not consume 967 %<, %> and %', which may not have a number, as they do not consume
195 format string must have conversion specifiers with argument numbers 970 format string must have conversion specifiers with argument numbers
196 1 up to highest argument; each argument may only be used once. 971 1 up to highest argument; each argument may only be used once.
197 A format string can have at most 30 arguments. */ 972 A format string can have at most 30 arguments. */
198 973
199 /* Formatting phases 1 and 2: render TEXT->format_spec plus 974 /* Formatting phases 1 and 2: render TEXT->format_spec plus
200 TEXT->args_ptr into a series of chunks in PP->buffer->args[]. 975 TEXT->args_ptr into a series of chunks in pp_buffer (PP)->args[].
201 Phase 3 is in pp_base_format_text. */ 976 Phase 3 is in pp_output_formatted_text. */
202 977
203 void 978 void
204 pp_base_format (pretty_printer *pp, text_info *text) 979 pp_format (pretty_printer *pp, text_info *text)
205 { 980 {
206 output_buffer *buffer = pp->buffer; 981 output_buffer *buffer = pp_buffer (pp);
207 const char *p; 982 const char *p;
208 const char **args; 983 const char **args;
209 struct chunk_info *new_chunk_array; 984 struct chunk_info *new_chunk_array;
210 985
211 unsigned int curarg = 0, chunk = 0, argno; 986 unsigned int curarg = 0, chunk = 0, argno;
218 new_chunk_array->prev = buffer->cur_chunk_array; 993 new_chunk_array->prev = buffer->cur_chunk_array;
219 buffer->cur_chunk_array = new_chunk_array; 994 buffer->cur_chunk_array = new_chunk_array;
220 args = new_chunk_array->args; 995 args = new_chunk_array->args;
221 996
222 /* Formatting phase 1: split up TEXT->format_spec into chunks in 997 /* Formatting phase 1: split up TEXT->format_spec into chunks in
223 PP->buffer->args[]. Even-numbered chunks are to be output 998 pp_buffer (PP)->args[]. Even-numbered chunks are to be output
224 verbatim, odd-numbered chunks are format specifiers. 999 verbatim, odd-numbered chunks are format specifiers.
225 %m, %%, %<, %>, and %' are replaced with the appropriate text at 1000 %m, %%, %<, %>, and %' are replaced with the appropriate text at
226 this point. */ 1001 this point. */
227 1002
228 memset (formatters, 0, sizeof formatters); 1003 memset (formatters, 0, sizeof formatters);
247 obstack_1grow (&buffer->chunk_obstack, '%'); 1022 obstack_1grow (&buffer->chunk_obstack, '%');
248 p++; 1023 p++;
249 continue; 1024 continue;
250 1025
251 case '<': 1026 case '<':
252 obstack_grow (&buffer->chunk_obstack, 1027 {
253 open_quote, strlen (open_quote)); 1028 obstack_grow (&buffer->chunk_obstack,
254 p++; 1029 open_quote, strlen (open_quote));
255 continue; 1030 const char *colorstr
1031 = colorize_start (pp_show_color (pp), "quote");
1032 obstack_grow (&buffer->chunk_obstack, colorstr, strlen (colorstr));
1033 p++;
1034 continue;
1035 }
256 1036
257 case '>': 1037 case '>':
1038 {
1039 const char *colorstr = colorize_stop (pp_show_color (pp));
1040 obstack_grow (&buffer->chunk_obstack, colorstr, strlen (colorstr));
1041 }
1042 /* FALLTHRU */
258 case '\'': 1043 case '\'':
259 obstack_grow (&buffer->chunk_obstack, 1044 obstack_grow (&buffer->chunk_obstack,
260 close_quote, strlen (close_quote)); 1045 close_quote, strlen (close_quote));
261 p++; 1046 p++;
262 continue; 1047 continue;
1048
1049 case 'R':
1050 {
1051 const char *colorstr = colorize_stop (pp_show_color (pp));
1052 obstack_grow (&buffer->chunk_obstack, colorstr,
1053 strlen (colorstr));
1054 p++;
1055 continue;
1056 }
263 1057
264 case 'm': 1058 case 'm':
265 { 1059 {
266 const char *errstr = xstrerror (text->err_no); 1060 const char *errstr = xstrerror (text->err_no);
267 obstack_grow (&buffer->chunk_obstack, errstr, strlen (errstr)); 1061 obstack_grow (&buffer->chunk_obstack, errstr, strlen (errstr));
413 } 1207 }
414 1208
415 gcc_assert (!wide || precision == 0); 1209 gcc_assert (!wide || precision == 0);
416 1210
417 if (quote) 1211 if (quote)
418 pp_string (pp, open_quote); 1212 {
1213 pp_string (pp, open_quote);
1214 pp_string (pp, colorize_start (pp_show_color (pp), "quote"));
1215 }
419 1216
420 switch (*p) 1217 switch (*p)
421 { 1218 {
1219 case 'r':
1220 pp_string (pp, colorize_start (pp_show_color (pp),
1221 va_arg (*text->args_ptr,
1222 const char *)));
1223 break;
1224
422 case 'c': 1225 case 'c':
423 pp_character (pp, va_arg (*text->args_ptr, int)); 1226 {
424 break; 1227 /* When quoting, print alphanumeric, punctuation, and the space
1228 character unchanged, and all others in hexadecimal with the
1229 "\x" prefix. Otherwise print them all unchanged. */
1230 int chr = va_arg (*text->args_ptr, int);
1231 if (ISPRINT (chr) || !quote)
1232 pp_character (pp, chr);
1233 else
1234 {
1235 const char str [2] = { chr, '\0' };
1236 pp_quoted_string (pp, str, 1);
1237 }
1238 break;
1239 }
425 1240
426 case 'd': 1241 case 'd':
427 case 'i': 1242 case 'i':
428 if (wide) 1243 if (wide)
429 pp_wide_integer (pp, va_arg (*text->args_ptr, HOST_WIDE_INT)); 1244 pp_wide_integer (pp, va_arg (*text->args_ptr, HOST_WIDE_INT));
440 pp_integer_with_precision 1255 pp_integer_with_precision
441 (pp, *text->args_ptr, precision, unsigned, "o"); 1256 (pp, *text->args_ptr, precision, unsigned, "o");
442 break; 1257 break;
443 1258
444 case 's': 1259 case 's':
445 pp_string (pp, va_arg (*text->args_ptr, const char *)); 1260 if (quote)
1261 pp_quoted_string (pp, va_arg (*text->args_ptr, const char *));
1262 else
1263 pp_string (pp, va_arg (*text->args_ptr, const char *));
446 break; 1264 break;
447 1265
448 case 'p': 1266 case 'p':
449 pp_pointer (pp, va_arg (*text->args_ptr, void *)); 1267 pp_pointer (pp, va_arg (*text->args_ptr, void *));
450 break; 1268 break;
455 va_arg (*text->args_ptr, unsigned HOST_WIDE_INT)); 1273 va_arg (*text->args_ptr, unsigned HOST_WIDE_INT));
456 else 1274 else
457 pp_integer_with_precision 1275 pp_integer_with_precision
458 (pp, *text->args_ptr, precision, unsigned, "u"); 1276 (pp, *text->args_ptr, precision, unsigned, "u");
459 break; 1277 break;
1278
1279 case 'Z':
1280 {
1281 int *v = va_arg (*text->args_ptr, int *);
1282 unsigned len = va_arg (*text->args_ptr, unsigned);
1283
1284 for (unsigned i = 0; i < len; ++i)
1285 {
1286 pp_scalar (pp, "%i", v[i]);
1287 if (i < len - 1)
1288 {
1289 pp_comma (pp);
1290 pp_space (pp);
1291 }
1292 }
1293 break;
1294 }
460 1295
461 case 'x': 1296 case 'x':
462 if (wide) 1297 if (wide)
463 pp_scalar (pp, HOST_WIDE_INT_PRINT_HEX, 1298 pp_scalar (pp, HOST_WIDE_INT_PRINT_HEX,
464 va_arg (*text->args_ptr, unsigned HOST_WIDE_INT)); 1299 va_arg (*text->args_ptr, unsigned HOST_WIDE_INT));
494 gcc_assert (formatters[argno] == formatters[argno+1]); 1329 gcc_assert (formatters[argno] == formatters[argno+1]);
495 argno++; 1330 argno++;
496 } 1331 }
497 1332
498 s = va_arg (*text->args_ptr, const char *); 1333 s = va_arg (*text->args_ptr, const char *);
499 pp_append_text (pp, s, s + n); 1334
1335 /* Append the lesser of precision and strlen (s) characters
1336 from the array (which need not be a nul-terminated string).
1337 Negative precision is treated as if it were omitted. */
1338 size_t len = n < 0 ? strlen (s) : strnlen (s, n);
1339
1340 pp_append_text (pp, s, s + len);
500 } 1341 }
501 break; 1342 break;
502 1343
503 default: 1344 default:
504 { 1345 {
505 bool ok; 1346 bool ok;
506 1347
507 gcc_assert (pp_format_decoder (pp)); 1348 gcc_assert (pp_format_decoder (pp));
508 ok = pp_format_decoder (pp) (pp, text, p, 1349 ok = pp_format_decoder (pp) (pp, text, p,
509 precision, wide, plus, hash); 1350 precision, wide, plus, hash, quote,
1351 formatters[argno]);
510 gcc_assert (ok); 1352 gcc_assert (ok);
511 } 1353 }
512 } 1354 }
513 1355
514 if (quote) 1356 if (quote)
515 pp_string (pp, close_quote); 1357 {
1358 pp_string (pp, colorize_stop (pp_show_color (pp)));
1359 pp_string (pp, close_quote);
1360 }
516 1361
517 obstack_1grow (&buffer->chunk_obstack, '\0'); 1362 obstack_1grow (&buffer->chunk_obstack, '\0');
518 *formatters[argno] = XOBFINISH (&buffer->chunk_obstack, const char *); 1363 *formatters[argno] = XOBFINISH (&buffer->chunk_obstack, const char *);
519 } 1364 }
520 1365
521 #ifdef ENABLE_CHECKING 1366 if (CHECKING_P)
522 for (; argno < PP_NL_ARGMAX; argno++) 1367 for (; argno < PP_NL_ARGMAX; argno++)
523 gcc_assert (!formatters[argno]); 1368 gcc_assert (!formatters[argno]);
524 #endif 1369
1370 /* If the client supplied a postprocessing object, call its "handle"
1371 hook here. */
1372 if (pp->m_format_postprocessor)
1373 pp->m_format_postprocessor->handle (pp);
525 1374
526 /* Revert to normal obstack and wrapping mode. */ 1375 /* Revert to normal obstack and wrapping mode. */
527 buffer->obstack = &buffer->formatted_obstack; 1376 buffer->obstack = &buffer->formatted_obstack;
528 buffer->line_length = 0; 1377 buffer->line_length = 0;
529 pp_wrapping_mode (pp) = old_wrapping_mode; 1378 pp_wrapping_mode (pp) = old_wrapping_mode;
530 pp_clear_state (pp); 1379 pp_clear_state (pp);
531 } 1380 }
532 1381
533 /* Format of a message pointed to by TEXT. */ 1382 /* Format of a message pointed to by TEXT. */
534 void 1383 void
535 pp_base_output_formatted_text (pretty_printer *pp) 1384 pp_output_formatted_text (pretty_printer *pp)
536 { 1385 {
537 unsigned int chunk; 1386 unsigned int chunk;
538 output_buffer *buffer = pp_buffer (pp); 1387 output_buffer *buffer = pp_buffer (pp);
539 struct chunk_info *chunk_array = buffer->cur_chunk_array; 1388 struct chunk_info *chunk_array = buffer->cur_chunk_array;
540 const char **args = chunk_array->args; 1389 const char **args = chunk_array->args;
541 1390
542 gcc_assert (buffer->obstack == &buffer->formatted_obstack); 1391 gcc_assert (buffer->obstack == &buffer->formatted_obstack);
543 gcc_assert (buffer->line_length == 0); 1392 gcc_assert (buffer->line_length == 0);
544 1393
545 /* This is a third phase, first 2 phases done in pp_base_format_args. 1394 /* This is a third phase, first 2 phases done in pp_format_args.
546 Now we actually print it. */ 1395 Now we actually print it. */
547 for (chunk = 0; args[chunk]; chunk++) 1396 for (chunk = 0; args[chunk]; chunk++)
548 pp_string (pp, args[chunk]); 1397 pp_string (pp, args[chunk]);
549 1398
550 /* Deallocate the chunk structure and everything after it (i.e. the 1399 /* Deallocate the chunk structure and everything after it (i.e. the
554 } 1403 }
555 1404
556 /* Helper subroutine of output_verbatim and verbatim. Do the appropriate 1405 /* Helper subroutine of output_verbatim and verbatim. Do the appropriate
557 settings needed by BUFFER for a verbatim formatting. */ 1406 settings needed by BUFFER for a verbatim formatting. */
558 void 1407 void
559 pp_base_format_verbatim (pretty_printer *pp, text_info *text) 1408 pp_format_verbatim (pretty_printer *pp, text_info *text)
560 { 1409 {
561 /* Set verbatim mode. */ 1410 /* Set verbatim mode. */
562 pp_wrapping_mode_t oldmode = pp_set_verbatim_wrapping (pp); 1411 pp_wrapping_mode_t oldmode = pp_set_verbatim_wrapping (pp);
563 1412
564 /* Do the actual formatting. */ 1413 /* Do the actual formatting. */
567 1416
568 /* Restore previous settings. */ 1417 /* Restore previous settings. */
569 pp_wrapping_mode (pp) = oldmode; 1418 pp_wrapping_mode (pp) = oldmode;
570 } 1419 }
571 1420
572 /* Flush the content of BUFFER onto the attached stream. */ 1421 /* Flush the content of BUFFER onto the attached stream. This
573 void 1422 function does nothing unless pp->output_buffer->flush_p. */
574 pp_base_flush (pretty_printer *pp) 1423 void
575 { 1424 pp_flush (pretty_printer *pp)
1425 {
1426 pp_clear_state (pp);
1427 if (!pp->buffer->flush_p)
1428 return;
576 pp_write_text_to_stream (pp); 1429 pp_write_text_to_stream (pp);
1430 fflush (pp_buffer (pp)->stream);
1431 }
1432
1433 /* Flush the content of BUFFER onto the attached stream independently
1434 of the value of pp->output_buffer->flush_p. */
1435 void
1436 pp_really_flush (pretty_printer *pp)
1437 {
577 pp_clear_state (pp); 1438 pp_clear_state (pp);
578 fputc ('\n', pp->buffer->stream); 1439 pp_write_text_to_stream (pp);
579 fflush (pp->buffer->stream); 1440 fflush (pp_buffer (pp)->stream);
580 pp_needs_newline (pp) = false;
581 } 1441 }
582 1442
583 /* Sets the number of maximum characters per line PRETTY-PRINTER can 1443 /* Sets the number of maximum characters per line PRETTY-PRINTER can
584 output in line-wrapping mode. A LENGTH value 0 suppresses 1444 output in line-wrapping mode. A LENGTH value 0 suppresses
585 line-wrapping. */ 1445 line-wrapping. */
586 void 1446 void
587 pp_base_set_line_maximum_length (pretty_printer *pp, int length) 1447 pp_set_line_maximum_length (pretty_printer *pp, int length)
588 { 1448 {
589 pp_line_cutoff (pp) = length; 1449 pp_line_cutoff (pp) = length;
590 pp_set_real_maximum_length (pp); 1450 pp_set_real_maximum_length (pp);
591 } 1451 }
592 1452
593 /* Clear PRETTY-PRINTER output area text info. */ 1453 /* Clear PRETTY-PRINTER output area text info. */
594 void 1454 void
595 pp_base_clear_output_area (pretty_printer *pp) 1455 pp_clear_output_area (pretty_printer *pp)
596 { 1456 {
597 obstack_free (pp->buffer->obstack, obstack_base (pp->buffer->obstack)); 1457 obstack_free (pp_buffer (pp)->obstack,
598 pp->buffer->line_length = 0; 1458 obstack_base (pp_buffer (pp)->obstack));
1459 pp_buffer (pp)->line_length = 0;
599 } 1460 }
600 1461
601 /* Set PREFIX for PRETTY-PRINTER. */ 1462 /* Set PREFIX for PRETTY-PRINTER. */
602 void 1463 void
603 pp_base_set_prefix (pretty_printer *pp, const char *prefix) 1464 pp_set_prefix (pretty_printer *pp, const char *prefix)
604 { 1465 {
605 pp->prefix = prefix; 1466 pp->prefix = prefix;
606 pp_set_real_maximum_length (pp); 1467 pp_set_real_maximum_length (pp);
607 pp->emitted_prefix = false; 1468 pp->emitted_prefix = false;
608 pp_indentation (pp) = 0; 1469 pp_indentation (pp) = 0;
609 } 1470 }
610 1471
611 /* Free PRETTY-PRINTER's prefix, a previously malloc()'d string. */ 1472 /* Free PRETTY-PRINTER's prefix, a previously malloc()'d string. */
612 void 1473 void
613 pp_base_destroy_prefix (pretty_printer *pp) 1474 pp_destroy_prefix (pretty_printer *pp)
614 { 1475 {
615 if (pp->prefix != NULL) 1476 if (pp->prefix != NULL)
616 { 1477 {
617 free (CONST_CAST (char *, pp->prefix)); 1478 free (CONST_CAST (char *, pp->prefix));
618 pp->prefix = NULL; 1479 pp->prefix = NULL;
619 } 1480 }
620 } 1481 }
621 1482
622 /* Write out PRETTY-PRINTER's prefix. */ 1483 /* Write out PRETTY-PRINTER's prefix. */
623 void 1484 void
624 pp_base_emit_prefix (pretty_printer *pp) 1485 pp_emit_prefix (pretty_printer *pp)
625 { 1486 {
626 if (pp->prefix != NULL) 1487 if (pp->prefix != NULL)
627 { 1488 {
628 switch (pp_prefixing_rule (pp)) 1489 switch (pp_prefixing_rule (pp))
629 { 1490 {
632 break; 1493 break;
633 1494
634 case DIAGNOSTICS_SHOW_PREFIX_ONCE: 1495 case DIAGNOSTICS_SHOW_PREFIX_ONCE:
635 if (pp->emitted_prefix) 1496 if (pp->emitted_prefix)
636 { 1497 {
637 pp_base_indent (pp); 1498 pp_indent (pp);
638 break; 1499 break;
639 } 1500 }
640 pp_indentation (pp) += 3; 1501 pp_indentation (pp) += 3;
641 /* Fall through. */ 1502 /* Fall through. */
642 1503
651 } 1512 }
652 } 1513 }
653 1514
654 /* Construct a PRETTY-PRINTER with PREFIX and of MAXIMUM_LENGTH 1515 /* Construct a PRETTY-PRINTER with PREFIX and of MAXIMUM_LENGTH
655 characters per line. */ 1516 characters per line. */
656 void 1517
657 pp_construct (pretty_printer *pp, const char *prefix, int maximum_length) 1518 pretty_printer::pretty_printer (const char *p, int l)
658 { 1519 : buffer (new (XCNEW (output_buffer)) output_buffer ()),
659 memset (pp, 0, sizeof (pretty_printer)); 1520 prefix (),
660 pp->buffer = XCNEW (output_buffer); 1521 padding (pp_none),
661 obstack_init (&pp->buffer->chunk_obstack); 1522 maximum_length (),
662 obstack_init (&pp->buffer->formatted_obstack); 1523 indent_skip (),
663 pp->buffer->obstack = &pp->buffer->formatted_obstack; 1524 wrapping (),
664 pp->buffer->stream = stderr; 1525 format_decoder (),
665 pp_line_cutoff (pp) = maximum_length; 1526 m_format_postprocessor (NULL),
666 pp_prefixing_rule (pp) = DIAGNOSTICS_SHOW_PREFIX_ONCE; 1527 emitted_prefix (),
667 pp_set_prefix (pp, prefix); 1528 need_newline (),
668 pp_translate_identifiers (pp) = true; 1529 translate_identifiers (true),
1530 show_color ()
1531 {
1532 pp_line_cutoff (this) = l;
1533 /* By default, we emit prefixes once per message. */
1534 pp_prefixing_rule (this) = DIAGNOSTICS_SHOW_PREFIX_ONCE;
1535 pp_set_prefix (this, p);
1536 }
1537
1538 pretty_printer::~pretty_printer ()
1539 {
1540 if (m_format_postprocessor)
1541 delete m_format_postprocessor;
1542 buffer->~output_buffer ();
1543 XDELETE (buffer);
669 } 1544 }
670 1545
671 /* Append a string delimited by START and END to the output area of 1546 /* Append a string delimited by START and END to the output area of
672 PRETTY-PRINTER. No line wrapping is done. However, if beginning a 1547 PRETTY-PRINTER. No line wrapping is done. However, if beginning a
673 new line then emit PRETTY-PRINTER's prefix and skip any leading 1548 new line then emit PRETTY-PRINTER's prefix and skip any leading
674 whitespace if appropriate. The caller must ensure that it is 1549 whitespace if appropriate. The caller must ensure that it is
675 safe to do so. */ 1550 safe to do so. */
676 void 1551 void
677 pp_base_append_text (pretty_printer *pp, const char *start, const char *end) 1552 pp_append_text (pretty_printer *pp, const char *start, const char *end)
678 { 1553 {
679 /* Emit prefix and skip whitespace if we're starting a new line. */ 1554 /* Emit prefix and skip whitespace if we're starting a new line. */
680 if (pp->buffer->line_length == 0) 1555 if (pp_buffer (pp)->line_length == 0)
681 { 1556 {
682 pp_emit_prefix (pp); 1557 pp_emit_prefix (pp);
683 if (pp_is_wrapping_line (pp)) 1558 if (pp_is_wrapping_line (pp))
684 while (start != end && *start == ' ') 1559 while (start != end && *start == ' ')
685 ++start; 1560 ++start;
688 } 1563 }
689 1564
690 /* Finishes constructing a NULL-terminated character string representing 1565 /* Finishes constructing a NULL-terminated character string representing
691 the PRETTY-PRINTED text. */ 1566 the PRETTY-PRINTED text. */
692 const char * 1567 const char *
693 pp_base_formatted_text (pretty_printer *pp) 1568 pp_formatted_text (pretty_printer *pp)
694 { 1569 {
695 obstack_1grow (pp->buffer->obstack, '\0'); 1570 return output_buffer_formatted_text (pp_buffer (pp));
696 return pp_formatted_text_data (pp);
697 } 1571 }
698 1572
699 /* Return a pointer to the last character emitted in PRETTY-PRINTER's 1573 /* Return a pointer to the last character emitted in PRETTY-PRINTER's
700 output area. A NULL pointer means no character available. */ 1574 output area. A NULL pointer means no character available. */
701 const char * 1575 const char *
702 pp_base_last_position_in_text (const pretty_printer *pp) 1576 pp_last_position_in_text (const pretty_printer *pp)
703 { 1577 {
704 const char *p = NULL; 1578 return output_buffer_last_position_in_text (pp_buffer (pp));
705 struct obstack *text = pp->buffer->obstack;
706
707 if (obstack_base (text) != obstack_next_free (text))
708 p = ((const char *) obstack_next_free (text)) - 1;
709 return p;
710 } 1579 }
711 1580
712 /* Return the amount of characters PRETTY-PRINTER can accept to 1581 /* Return the amount of characters PRETTY-PRINTER can accept to
713 make a full line. Meaningful only in line-wrapping mode. */ 1582 make a full line. Meaningful only in line-wrapping mode. */
714 int 1583 int
715 pp_base_remaining_character_count_for_line (pretty_printer *pp) 1584 pp_remaining_character_count_for_line (pretty_printer *pp)
716 { 1585 {
717 return pp->maximum_length - pp->buffer->line_length; 1586 return pp->maximum_length - pp_buffer (pp)->line_length;
718 } 1587 }
719 1588
720 1589
721 /* Format a message into BUFFER a la printf. */ 1590 /* Format a message into BUFFER a la printf. */
722 void 1591 void
727 1596
728 va_start (ap, msg); 1597 va_start (ap, msg);
729 text.err_no = errno; 1598 text.err_no = errno;
730 text.args_ptr = &ap; 1599 text.args_ptr = &ap;
731 text.format_spec = msg; 1600 text.format_spec = msg;
732 text.locus = NULL;
733 pp_format (pp, &text); 1601 pp_format (pp, &text);
734 pp_output_formatted_text (pp); 1602 pp_output_formatted_text (pp);
735 va_end (ap); 1603 va_end (ap);
736 } 1604 }
737 1605
745 1613
746 va_start (ap, msg); 1614 va_start (ap, msg);
747 text.err_no = errno; 1615 text.err_no = errno;
748 text.args_ptr = &ap; 1616 text.args_ptr = &ap;
749 text.format_spec = msg; 1617 text.format_spec = msg;
750 text.locus = NULL;
751 pp_format_verbatim (pp, &text); 1618 pp_format_verbatim (pp, &text);
752 va_end (ap); 1619 va_end (ap);
753 } 1620 }
754 1621
755 1622
756 1623
757 /* Have PRETTY-PRINTER start a new line. */ 1624 /* Have PRETTY-PRINTER start a new line. */
758 void 1625 void
759 pp_base_newline (pretty_printer *pp) 1626 pp_newline (pretty_printer *pp)
760 { 1627 {
761 obstack_1grow (pp->buffer->obstack, '\n'); 1628 obstack_1grow (pp_buffer (pp)->obstack, '\n');
762 pp->buffer->line_length = 0; 1629 pp_needs_newline (pp) = false;
1630 pp_buffer (pp)->line_length = 0;
763 } 1631 }
764 1632
765 /* Have PRETTY-PRINTER add a CHARACTER. */ 1633 /* Have PRETTY-PRINTER add a CHARACTER. */
766 void 1634 void
767 pp_base_character (pretty_printer *pp, int c) 1635 pp_character (pretty_printer *pp, int c)
768 { 1636 {
769 if (pp_is_wrapping_line (pp) 1637 if (pp_is_wrapping_line (pp)
770 && pp_remaining_character_count_for_line (pp) <= 0) 1638 && pp_remaining_character_count_for_line (pp) <= 0)
771 { 1639 {
772 pp_newline (pp); 1640 pp_newline (pp);
773 if (ISSPACE (c)) 1641 if (ISSPACE (c))
774 return; 1642 return;
775 } 1643 }
776 obstack_1grow (pp->buffer->obstack, c); 1644 obstack_1grow (pp_buffer (pp)->obstack, c);
777 ++pp->buffer->line_length; 1645 ++pp_buffer (pp)->line_length;
778 } 1646 }
779 1647
780 /* Append a STRING to the output area of PRETTY-PRINTER; the STRING may 1648 /* Append a STRING to the output area of PRETTY-PRINTER; the STRING may
781 be line-wrapped if in appropriate mode. */ 1649 be line-wrapped if in appropriate mode. */
782 void 1650 void
783 pp_base_string (pretty_printer *pp, const char *str) 1651 pp_string (pretty_printer *pp, const char *str)
784 { 1652 {
785 pp_maybe_wrap_text (pp, str, str + (str ? strlen (str) : 0)); 1653 gcc_checking_assert (str);
1654 pp_maybe_wrap_text (pp, str, str + strlen (str));
1655 }
1656
1657 /* Append the leading N characters of STRING to the output area of
1658 PRETTY-PRINTER, quoting in hexadecimal non-printable characters.
1659 Setting N = -1 is as if N were set to strlen (STRING). The STRING
1660 may be line-wrapped if in appropriate mode. */
1661 static void
1662 pp_quoted_string (pretty_printer *pp, const char *str, size_t n /* = -1 */)
1663 {
1664 gcc_checking_assert (str);
1665
1666 const char *last = str;
1667 const char *ps;
1668
1669 /* Compute the length if not specified. */
1670 if (n == (size_t) -1)
1671 n = strlen (str);
1672
1673 for (ps = str; n; ++ps, --n)
1674 {
1675 if (ISPRINT (*ps))
1676 continue;
1677
1678 if (last < ps)
1679 pp_maybe_wrap_text (pp, last, ps - 1);
1680
1681 /* Append the hexadecimal value of the character. Allocate a buffer
1682 that's large enough for a 32-bit char plus the hex prefix. */
1683 char buf [11];
1684 int n = sprintf (buf, "\\x%02x", (unsigned char)*ps);
1685 pp_maybe_wrap_text (pp, buf, buf + n);
1686 last = ps + 1;
1687 }
1688
1689 pp_maybe_wrap_text (pp, last, ps);
786 } 1690 }
787 1691
788 /* Maybe print out a whitespace if needed. */ 1692 /* Maybe print out a whitespace if needed. */
789 1693
790 void 1694 void
791 pp_base_maybe_space (pretty_printer *pp) 1695 pp_maybe_space (pretty_printer *pp)
792 { 1696 {
793 if (pp_base (pp)->padding != pp_none) 1697 if (pp->padding != pp_none)
794 { 1698 {
795 pp_space (pp); 1699 pp_space (pp);
796 pp_base (pp)->padding = pp_none; 1700 pp->padding = pp_none;
797 } 1701 }
798 } 1702 }
1703
1704 // Add a newline to the pretty printer PP and flush formatted text.
1705
1706 void
1707 pp_newline_and_flush (pretty_printer *pp)
1708 {
1709 pp_newline (pp);
1710 pp_flush (pp);
1711 pp_needs_newline (pp) = false;
1712 }
1713
1714 // Add a newline to the pretty printer PP, followed by indentation.
1715
1716 void
1717 pp_newline_and_indent (pretty_printer *pp, int n)
1718 {
1719 pp_indentation (pp) += n;
1720 pp_newline (pp);
1721 pp_indent (pp);
1722 pp_needs_newline (pp) = false;
1723 }
1724
1725 // Add separator C, followed by a single whitespace.
1726
1727 void
1728 pp_separate_with (pretty_printer *pp, char c)
1729 {
1730 pp_character (pp, c);
1731 pp_space (pp);
1732 }
1733
799 1734
800 /* The string starting at P has LEN (at least 1) bytes left; if they 1735 /* The string starting at P has LEN (at least 1) bytes left; if they
801 start with a valid UTF-8 sequence, return the length of that 1736 start with a valid UTF-8 sequence, return the length of that
802 sequence and set *VALUE to the value of that sequence, and 1737 sequence and set *VALUE to the value of that sequence, and
803 otherwise return 0 and set *VALUE to (unsigned int) -1. */ 1738 otherwise return 0 and set *VALUE to (unsigned int) -1. */
1017 } 1952 }
1018 *p = 0; 1953 *p = 0;
1019 return ret; 1954 return ret;
1020 } 1955 }
1021 } 1956 }
1957
1958 #if CHECKING_P
1959
1960 namespace selftest {
1961
1962 /* Smoketest for pretty_printer. */
1963
1964 static void
1965 test_basic_printing ()
1966 {
1967 pretty_printer pp;
1968 pp_string (&pp, "hello");
1969 pp_space (&pp);
1970 pp_string (&pp, "world");
1971
1972 ASSERT_STREQ ("hello world", pp_formatted_text (&pp));
1973 }
1974
1975 /* Helper function for testing pp_format.
1976 Verify that pp_format (FMT, ...) followed by pp_output_formatted_text
1977 prints EXPECTED, assuming that pp_show_color is SHOW_COLOR. */
1978
1979 static void
1980 assert_pp_format_va (const location &loc, const char *expected,
1981 bool show_color, const char *fmt, va_list *ap)
1982 {
1983 pretty_printer pp;
1984 text_info ti;
1985 rich_location rich_loc (line_table, UNKNOWN_LOCATION);
1986
1987 ti.format_spec = fmt;
1988 ti.args_ptr = ap;
1989 ti.err_no = 0;
1990 ti.x_data = NULL;
1991 ti.m_richloc = &rich_loc;
1992
1993 pp_show_color (&pp) = show_color;
1994 pp_format (&pp, &ti);
1995 pp_output_formatted_text (&pp);
1996 ASSERT_STREQ_AT (loc, expected, pp_formatted_text (&pp));
1997 }
1998
1999 /* Verify that pp_format (FMT, ...) followed by pp_output_formatted_text
2000 prints EXPECTED, with show_color disabled. */
2001
2002 static void
2003 assert_pp_format (const location &loc, const char *expected,
2004 const char *fmt, ...)
2005 {
2006 va_list ap;
2007
2008 va_start (ap, fmt);
2009 assert_pp_format_va (loc, expected, false, fmt, &ap);
2010 va_end (ap);
2011 }
2012
2013 /* As above, but with colorization enabled. */
2014
2015 static void
2016 assert_pp_format_colored (const location &loc, const char *expected,
2017 const char *fmt, ...)
2018 {
2019 /* The tests of colorization assume the default color scheme.
2020 If GCC_COLORS is set, then the colors have potentially been
2021 overridden; skip the test. */
2022 if (getenv ("GCC_COLORS"))
2023 return;
2024
2025 va_list ap;
2026
2027 va_start (ap, fmt);
2028 assert_pp_format_va (loc, expected, true, fmt, &ap);
2029 va_end (ap);
2030 }
2031
2032 /* Helper function for calling testing pp_format,
2033 by calling assert_pp_format with various numbers of arguments.
2034 These exist mostly to avoid having to write SELFTEST_LOCATION
2035 throughout test_pp_format. */
2036
2037 #define ASSERT_PP_FORMAT_1(EXPECTED, FMT, ARG1) \
2038 SELFTEST_BEGIN_STMT \
2039 assert_pp_format ((SELFTEST_LOCATION), (EXPECTED), (FMT), \
2040 (ARG1)); \
2041 SELFTEST_END_STMT
2042
2043 #define ASSERT_PP_FORMAT_2(EXPECTED, FMT, ARG1, ARG2) \
2044 SELFTEST_BEGIN_STMT \
2045 assert_pp_format ((SELFTEST_LOCATION), (EXPECTED), (FMT), \
2046 (ARG1), (ARG2)); \
2047 SELFTEST_END_STMT
2048
2049 #define ASSERT_PP_FORMAT_3(EXPECTED, FMT, ARG1, ARG2, ARG3) \
2050 SELFTEST_BEGIN_STMT \
2051 assert_pp_format ((SELFTEST_LOCATION), (EXPECTED), (FMT), \
2052 (ARG1), (ARG2), (ARG3)); \
2053 SELFTEST_END_STMT
2054
2055 /* Verify that pp_format works, for various format codes. */
2056
2057 static void
2058 test_pp_format ()
2059 {
2060 /* Avoid introducing locale-specific differences in the results
2061 by hardcoding open_quote and close_quote. */
2062 const char *old_open_quote = open_quote;
2063 const char *old_close_quote = close_quote;
2064 open_quote = "`";
2065 close_quote = "'";
2066
2067 /* Verify that plain text is passed through unchanged. */
2068 assert_pp_format (SELFTEST_LOCATION, "unformatted", "unformatted");
2069
2070 /* Verify various individual format codes, in the order listed in the
2071 comment for pp_format above. For each code, we append a second
2072 argument with a known bit pattern (0x12345678), to ensure that we
2073 are consuming arguments correctly. */
2074 ASSERT_PP_FORMAT_2 ("-27 12345678", "%d %x", -27, 0x12345678);
2075 ASSERT_PP_FORMAT_2 ("-5 12345678", "%i %x", -5, 0x12345678);
2076 ASSERT_PP_FORMAT_2 ("10 12345678", "%u %x", 10, 0x12345678);
2077 ASSERT_PP_FORMAT_2 ("17 12345678", "%o %x", 15, 0x12345678);
2078 ASSERT_PP_FORMAT_2 ("cafebabe 12345678", "%x %x", 0xcafebabe, 0x12345678);
2079 ASSERT_PP_FORMAT_2 ("-27 12345678", "%ld %x", (long)-27, 0x12345678);
2080 ASSERT_PP_FORMAT_2 ("-5 12345678", "%li %x", (long)-5, 0x12345678);
2081 ASSERT_PP_FORMAT_2 ("10 12345678", "%lu %x", (long)10, 0x12345678);
2082 ASSERT_PP_FORMAT_2 ("17 12345678", "%lo %x", (long)15, 0x12345678);
2083 ASSERT_PP_FORMAT_2 ("cafebabe 12345678", "%lx %x", (long)0xcafebabe,
2084 0x12345678);
2085 ASSERT_PP_FORMAT_2 ("-27 12345678", "%lld %x", (long long)-27, 0x12345678);
2086 ASSERT_PP_FORMAT_2 ("-5 12345678", "%lli %x", (long long)-5, 0x12345678);
2087 ASSERT_PP_FORMAT_2 ("10 12345678", "%llu %x", (long long)10, 0x12345678);
2088 ASSERT_PP_FORMAT_2 ("17 12345678", "%llo %x", (long long)15, 0x12345678);
2089 ASSERT_PP_FORMAT_2 ("cafebabe 12345678", "%llx %x", (long long)0xcafebabe,
2090 0x12345678);
2091 ASSERT_PP_FORMAT_2 ("-27 12345678", "%wd %x", (HOST_WIDE_INT)-27, 0x12345678);
2092 ASSERT_PP_FORMAT_2 ("-5 12345678", "%wi %x", (HOST_WIDE_INT)-5, 0x12345678);
2093 ASSERT_PP_FORMAT_2 ("10 12345678", "%wu %x", (unsigned HOST_WIDE_INT)10,
2094 0x12345678);
2095 ASSERT_PP_FORMAT_2 ("17 12345678", "%wo %x", (HOST_WIDE_INT)15, 0x12345678);
2096 ASSERT_PP_FORMAT_2 ("0xcafebabe 12345678", "%wx %x", (HOST_WIDE_INT)0xcafebabe,
2097 0x12345678);
2098 ASSERT_PP_FORMAT_2 ("A 12345678", "%c %x", 'A', 0x12345678);
2099 ASSERT_PP_FORMAT_2 ("hello world 12345678", "%s %x", "hello world",
2100 0x12345678);
2101
2102 /* Not nul-terminated. */
2103 char arr[5] = { '1', '2', '3', '4', '5' };
2104 ASSERT_PP_FORMAT_3 ("123 12345678", "%.*s %x", 3, arr, 0x12345678);
2105 ASSERT_PP_FORMAT_3 ("1234 12345678", "%.*s %x", -1, "1234", 0x12345678);
2106 ASSERT_PP_FORMAT_3 ("12345 12345678", "%.*s %x", 7, "12345", 0x12345678);
2107
2108 /* We can't test for %p; the pointer is printed in an implementation-defined
2109 manner. */
2110 ASSERT_PP_FORMAT_2 ("normal colored normal 12345678",
2111 "normal %rcolored%R normal %x",
2112 "error", 0x12345678);
2113 assert_pp_format_colored
2114 (SELFTEST_LOCATION,
2115 "normal \33[01;31m\33[Kcolored\33[m\33[K normal 12345678",
2116 "normal %rcolored%R normal %x", "error", 0x12345678);
2117 /* TODO:
2118 %m: strerror(text->err_no) - does not consume a value from args_ptr. */
2119 ASSERT_PP_FORMAT_1 ("% 12345678", "%% %x", 0x12345678);
2120 ASSERT_PP_FORMAT_1 ("` 12345678", "%< %x", 0x12345678);
2121 ASSERT_PP_FORMAT_1 ("' 12345678", "%> %x", 0x12345678);
2122 ASSERT_PP_FORMAT_1 ("' 12345678", "%' %x", 0x12345678);
2123 ASSERT_PP_FORMAT_3 ("abc 12345678", "%.*s %x", 3, "abcdef", 0x12345678);
2124 ASSERT_PP_FORMAT_2 ("abc 12345678", "%.3s %x", "abcdef", 0x12345678);
2125
2126 /* Verify flag 'q'. */
2127 ASSERT_PP_FORMAT_2 ("`foo' 12345678", "%qs %x", "foo", 0x12345678);
2128 assert_pp_format_colored (SELFTEST_LOCATION,
2129 "`\33[01m\33[Kfoo\33[m\33[K' 12345678", "%qs %x",
2130 "foo", 0x12345678);
2131
2132 /* Verify %Z. */
2133 int v[] = { 1, 2, 3 };
2134 ASSERT_PP_FORMAT_3 ("1, 2, 3 12345678", "%Z %x", v, 3, 0x12345678);
2135
2136 int v2[] = { 0 };
2137 ASSERT_PP_FORMAT_3 ("0 12345678", "%Z %x", v2, 1, 0x12345678);
2138
2139 /* Verify that combinations work, along with unformatted text. */
2140 assert_pp_format (SELFTEST_LOCATION,
2141 "the quick brown fox jumps over the lazy dog",
2142 "the %s %s %s jumps over the %s %s",
2143 "quick", "brown", "fox", "lazy", "dog");
2144 assert_pp_format (SELFTEST_LOCATION, "item 3 of 7", "item %i of %i", 3, 7);
2145 assert_pp_format (SELFTEST_LOCATION, "problem with `bar' at line 10",
2146 "problem with %qs at line %i", "bar", 10);
2147
2148 /* Restore old values of open_quote and close_quote. */
2149 open_quote = old_open_quote;
2150 close_quote = old_close_quote;
2151 }
2152
2153 /* Run all of the selftests within this file. */
2154
2155 void
2156 pretty_print_c_tests ()
2157 {
2158 test_basic_printing ();
2159 test_pp_format ();
2160 }
2161
2162 } // namespace selftest
2163
2164 #endif /* CHECKING_P */