1 /* Language-independent diagnostic subroutines for the GNU Compiler Collection
2 Copyright (C) 1999-2021 Free Software Foundation, Inc.
3 Contributed by Gabriel Dos Reis <gdr@codesourcery.com>
5 This file is part of GCC.
7 GCC is free software; you can redistribute it and/or modify it under
8 the terms of the GNU General Public License as published by the Free
9 Software Foundation; either version 3, or (at your option) any later
12 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13 WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
17 You should have received a copy of the GNU General Public License
18 along with GCC; see the file COPYING3. If not see
19 <http://www.gnu.org/licenses/>. */
22 /* This file implements the language independent aspect of diagnostic
27 #include "coretypes.h"
31 #include "backtrace.h"
32 #include "diagnostic.h"
33 #include "diagnostic-color.h"
34 #include "diagnostic-url.h"
35 #include "diagnostic-metadata.h"
36 #include "diagnostic-path.h"
37 #include "edit-context.h"
39 #include "selftest-diagnostic.h"
47 #ifdef GWINSZ_IN_SYS_IOCTL
48 # include <sys/ioctl.h>
51 /* Disable warnings about quoting issues in the pp_xxx calls below
52 that (intentionally) don't follow GCC diagnostic conventions. */
54 # pragma GCC diagnostic push
55 # pragma GCC diagnostic ignored "-Wformat-diag"
58 #define pedantic_warning_kind(DC) \
59 ((DC)->pedantic_errors ? DK_ERROR : DK_WARNING)
60 #define permissive_error_kind(DC) ((DC)->permissive ? DK_WARNING : DK_ERROR)
61 #define permissive_error_option(DC) ((DC)->opt_permissive)
64 static bool diagnostic_impl (rich_location
*, const diagnostic_metadata
*,
66 va_list *, diagnostic_t
) ATTRIBUTE_GCC_DIAG(4,0);
67 static bool diagnostic_n_impl (rich_location
*, const diagnostic_metadata
*,
68 int, unsigned HOST_WIDE_INT
,
69 const char *, const char *, va_list *,
70 diagnostic_t
) ATTRIBUTE_GCC_DIAG(6,0);
72 static void error_recursion (diagnostic_context
*) ATTRIBUTE_NORETURN
;
73 static void real_abort (void) ATTRIBUTE_NORETURN
;
75 /* Name of program invoked, sans directories. */
79 /* A diagnostic_context surrogate for stderr. */
80 static diagnostic_context global_diagnostic_context
;
81 diagnostic_context
*global_dc
= &global_diagnostic_context
;
83 /* Return a malloc'd string containing MSG formatted a la printf. The
84 caller is responsible for freeing the memory. */
86 build_message_string (const char *msg
, ...)
92 str
= xvasprintf (msg
, ap
);
98 /* Same as diagnostic_build_prefix, but only the source FILE is given. */
100 file_name_as_prefix (diagnostic_context
*context
, const char *f
)
103 = colorize_start (pp_show_color (context
->printer
), "locus");
104 const char *locus_ce
= colorize_stop (pp_show_color (context
->printer
));
105 return build_message_string ("%s%s:%s ", locus_cs
, f
, locus_ce
);
110 /* Return the value of the getenv("COLUMNS") as an integer. If the
111 value is not set to a positive integer, use ioctl to get the
112 terminal width. If it fails, return INT_MAX. */
114 get_terminal_width (void)
116 const char * s
= getenv ("COLUMNS");
126 if (ioctl (0, TIOCGWINSZ
, &w
) == 0 && w
.ws_col
> 0)
133 /* Set caret_max_width to value. */
135 diagnostic_set_caret_max_width (diagnostic_context
*context
, int value
)
137 /* One minus to account for the leading empty space. */
138 value
= value
? value
- 1
139 : (isatty (fileno (pp_buffer (context
->printer
)->stream
))
140 ? get_terminal_width () - 1: INT_MAX
);
145 context
->caret_max_width
= value
;
148 /* Default implementation of final_cb. */
151 default_diagnostic_final_cb (diagnostic_context
*context
)
153 /* Some of the errors may actually have been warnings. */
154 if (diagnostic_kind_count (context
, DK_WERROR
))
156 /* -Werror was given. */
157 if (context
->warning_as_error_requested
)
158 pp_verbatim (context
->printer
,
159 _("%s: all warnings being treated as errors"),
161 /* At least one -Werror= was given. */
163 pp_verbatim (context
->printer
,
164 _("%s: some warnings being treated as errors"),
166 pp_newline_and_flush (context
->printer
);
170 /* Initialize the diagnostic message outputting machinery. */
172 diagnostic_initialize (diagnostic_context
*context
, int n_opts
)
176 /* Allocate a basic pretty-printer. Clients will replace this a
177 much more elaborated pretty-printer if they wish. */
178 context
->printer
= XNEW (pretty_printer
);
179 new (context
->printer
) pretty_printer ();
181 memset (context
->diagnostic_count
, 0, sizeof context
->diagnostic_count
);
182 context
->warning_as_error_requested
= false;
183 context
->n_opts
= n_opts
;
184 context
->classify_diagnostic
= XNEWVEC (diagnostic_t
, n_opts
);
185 for (i
= 0; i
< n_opts
; i
++)
186 context
->classify_diagnostic
[i
] = DK_UNSPECIFIED
;
187 context
->show_caret
= false;
188 diagnostic_set_caret_max_width (context
, pp_line_cutoff (context
->printer
));
189 for (i
= 0; i
< rich_location::STATICALLY_ALLOCATED_RANGES
; i
++)
190 context
->caret_chars
[i
] = '^';
191 context
->show_cwe
= false;
192 context
->path_format
= DPF_NONE
;
193 context
->show_path_depths
= false;
194 context
->show_option_requested
= false;
195 context
->abort_on_error
= false;
196 context
->show_column
= false;
197 context
->pedantic_errors
= false;
198 context
->permissive
= false;
199 context
->opt_permissive
= 0;
200 context
->fatal_errors
= false;
201 context
->dc_inhibit_warnings
= false;
202 context
->dc_warn_system_headers
= false;
203 context
->max_errors
= 0;
204 context
->internal_error
= NULL
;
205 diagnostic_starter (context
) = default_diagnostic_starter
;
206 context
->start_span
= default_diagnostic_start_span_fn
;
207 diagnostic_finalizer (context
) = default_diagnostic_finalizer
;
208 context
->option_enabled
= NULL
;
209 context
->option_state
= NULL
;
210 context
->option_name
= NULL
;
211 context
->get_option_url
= NULL
;
212 context
->last_location
= UNKNOWN_LOCATION
;
213 context
->last_module
= 0;
214 context
->x_data
= NULL
;
216 context
->inhibit_notes_p
= false;
217 context
->colorize_source_p
= false;
218 context
->show_labels_p
= false;
219 context
->show_line_numbers_p
= false;
220 context
->min_margin_width
= 0;
221 context
->show_ruler_p
= false;
222 if (const char *var
= getenv ("GCC_EXTRA_DIAGNOSTIC_OUTPUT"))
224 if (!strcmp (var
, "fixits-v1"))
225 context
->extra_output_kind
= EXTRA_DIAGNOSTIC_OUTPUT_fixits_v1
;
226 else if (!strcmp (var
, "fixits-v2"))
227 context
->extra_output_kind
= EXTRA_DIAGNOSTIC_OUTPUT_fixits_v2
;
228 /* Silently ignore unrecognized values. */
230 context
->column_unit
= DIAGNOSTICS_COLUMN_UNIT_DISPLAY
;
231 context
->column_origin
= 1;
232 context
->tabstop
= 8;
233 context
->edit_context_ptr
= NULL
;
234 context
->diagnostic_group_nesting_depth
= 0;
235 context
->diagnostic_group_emission_count
= 0;
236 context
->begin_group_cb
= NULL
;
237 context
->end_group_cb
= NULL
;
238 context
->final_cb
= default_diagnostic_final_cb
;
241 /* Maybe initialize the color support. We require clients to do this
242 explicitly, since most clients don't want color. When called
243 without a VALUE, it initializes with DIAGNOSTICS_COLOR_DEFAULT. */
246 diagnostic_color_init (diagnostic_context
*context
, int value
/*= -1 */)
248 /* value == -1 is the default value. */
251 /* If DIAGNOSTICS_COLOR_DEFAULT is -1, default to
252 -fdiagnostics-color=auto if GCC_COLORS is in the environment,
253 otherwise default to -fdiagnostics-color=never, for other
254 values default to that
255 -fdiagnostics-color={never,auto,always}. */
256 if (DIAGNOSTICS_COLOR_DEFAULT
== -1)
258 if (!getenv ("GCC_COLORS"))
260 value
= DIAGNOSTICS_COLOR_AUTO
;
263 value
= DIAGNOSTICS_COLOR_DEFAULT
;
265 pp_show_color (context
->printer
)
266 = colorize_init ((diagnostic_color_rule_t
) value
);
269 /* Initialize URL support within CONTEXT based on VALUE, handling "auto". */
272 diagnostic_urls_init (diagnostic_context
*context
, int value
/*= -1 */)
274 /* value == -1 is the default value. */
277 /* If DIAGNOSTICS_URLS_DEFAULT is -1, default to
278 -fdiagnostics-urls=auto if GCC_URLS or TERM_URLS is in the
279 environment, otherwise default to -fdiagnostics-urls=never,
280 for other values default to that
281 -fdiagnostics-urls={never,auto,always}. */
282 if (DIAGNOSTICS_URLS_DEFAULT
== -1)
284 if (!getenv ("GCC_URLS") && !getenv ("TERM_URLS"))
286 value
= DIAGNOSTICS_URL_AUTO
;
289 value
= DIAGNOSTICS_URLS_DEFAULT
;
292 context
->printer
->url_format
293 = determine_url_format ((diagnostic_url_rule_t
) value
);
296 /* Do any cleaning up required after the last diagnostic is emitted. */
299 diagnostic_finish (diagnostic_context
*context
)
301 if (context
->final_cb
)
302 context
->final_cb (context
);
304 diagnostic_file_cache_fini ();
306 XDELETEVEC (context
->classify_diagnostic
);
307 context
->classify_diagnostic
= NULL
;
309 /* diagnostic_initialize allocates context->printer using XNEW
310 and placement-new. */
311 context
->printer
->~pretty_printer ();
312 XDELETE (context
->printer
);
313 context
->printer
= NULL
;
315 if (context
->edit_context_ptr
)
317 delete context
->edit_context_ptr
;
318 context
->edit_context_ptr
= NULL
;
322 /* Initialize DIAGNOSTIC, where the message MSG has already been
325 diagnostic_set_info_translated (diagnostic_info
*diagnostic
, const char *msg
,
326 va_list *args
, rich_location
*richloc
,
329 gcc_assert (richloc
);
330 diagnostic
->message
.err_no
= errno
;
331 diagnostic
->message
.args_ptr
= args
;
332 diagnostic
->message
.format_spec
= msg
;
333 diagnostic
->message
.m_richloc
= richloc
;
334 diagnostic
->richloc
= richloc
;
335 diagnostic
->metadata
= NULL
;
336 diagnostic
->kind
= kind
;
337 diagnostic
->option_index
= 0;
340 /* Initialize DIAGNOSTIC, where the message GMSGID has not yet been
343 diagnostic_set_info (diagnostic_info
*diagnostic
, const char *gmsgid
,
344 va_list *args
, rich_location
*richloc
,
347 gcc_assert (richloc
);
348 diagnostic_set_info_translated (diagnostic
, _(gmsgid
), args
, richloc
, kind
);
351 static const char *const diagnostic_kind_color
[] = {
352 #define DEFINE_DIAGNOSTIC_KIND(K, T, C) (C),
353 #include "diagnostic.def"
354 #undef DEFINE_DIAGNOSTIC_KIND
358 /* Get a color name for diagnostics of type KIND
359 Result could be NULL. */
362 diagnostic_get_color_for_kind (diagnostic_t kind
)
364 return diagnostic_kind_color
[kind
];
367 /* Given an expanded_location, convert the column (which is in 1-based bytes)
368 to the requested units, without converting the origin.
369 Return -1 if the column is invalid (<= 0). */
372 convert_column_unit (enum diagnostics_column_unit column_unit
,
384 case DIAGNOSTICS_COLUMN_UNIT_DISPLAY
:
385 return location_compute_display_column (s
, tabstop
);
387 case DIAGNOSTICS_COLUMN_UNIT_BYTE
:
392 /* Given an expanded_location, convert the column (which is in 1-based bytes)
393 to the requested units and origin. Return -1 if the column is
396 diagnostic_converted_column (diagnostic_context
*context
, expanded_location s
)
399 = convert_column_unit (context
->column_unit
, context
->tabstop
, s
);
400 if (one_based_col
<= 0)
402 return one_based_col
+ (context
->column_origin
- 1);
405 /* Return a formatted line and column ':%line:%column'. Elided if
406 line == 0 or col < 0. (A column of 0 may be valid due to the
407 -fdiagnostics-column-origin option.)
408 The result is a statically allocated buffer. */
411 maybe_line_and_column (int line
, int col
)
413 static char result
[32];
418 = snprintf (result
, sizeof (result
),
419 col
>= 0 ? ":%d:%d" : ":%d", line
, col
);
420 gcc_checking_assert (l
< sizeof (result
));
427 /* Return a malloc'd string describing a location e.g. "foo.c:42:10".
428 The caller is responsible for freeing the memory. */
431 diagnostic_get_location_text (diagnostic_context
*context
,
434 pretty_printer
*pp
= context
->printer
;
435 const char *locus_cs
= colorize_start (pp_show_color (pp
), "locus");
436 const char *locus_ce
= colorize_stop (pp_show_color (pp
));
437 const char *file
= s
.file
? s
.file
: progname
;
440 if (strcmp (file
, N_("<built-in>")))
443 if (context
->show_column
)
444 col
= diagnostic_converted_column (context
, s
);
447 const char *line_col
= maybe_line_and_column (line
, col
);
448 return build_message_string ("%s%s%s:%s", locus_cs
, file
,
452 static const char *const diagnostic_kind_text
[] = {
453 #define DEFINE_DIAGNOSTIC_KIND(K, T, C) (T),
454 #include "diagnostic.def"
455 #undef DEFINE_DIAGNOSTIC_KIND
459 /* Return a malloc'd string describing a location and the severity of the
460 diagnostic, e.g. "foo.c:42:10: error: ". The caller is responsible for
461 freeing the memory. */
463 diagnostic_build_prefix (diagnostic_context
*context
,
464 const diagnostic_info
*diagnostic
)
466 gcc_assert (diagnostic
->kind
< DK_LAST_DIAGNOSTIC_KIND
);
468 const char *text
= _(diagnostic_kind_text
[diagnostic
->kind
]);
469 const char *text_cs
= "", *text_ce
= "";
470 pretty_printer
*pp
= context
->printer
;
472 if (diagnostic_kind_color
[diagnostic
->kind
])
474 text_cs
= colorize_start (pp_show_color (pp
),
475 diagnostic_kind_color
[diagnostic
->kind
]);
476 text_ce
= colorize_stop (pp_show_color (pp
));
479 expanded_location s
= diagnostic_expand_location (diagnostic
);
480 char *location_text
= diagnostic_get_location_text (context
, s
);
482 char *result
= build_message_string ("%s %s%s%s", location_text
,
483 text_cs
, text
, text_ce
);
484 free (location_text
);
488 /* Functions at which to stop the backtrace print. It's not
489 particularly helpful to print the callers of these functions. */
491 static const char * const bt_stop
[] =
499 /* A callback function passed to the backtrace_full function. */
502 bt_callback (void *data
, uintptr_t pc
, const char *filename
, int lineno
,
503 const char *function
)
505 int *pcount
= (int *) data
;
507 /* If we don't have any useful information, don't print
509 if (filename
== NULL
&& function
== NULL
)
512 /* Skip functions in diagnostic.c. */
515 && strcmp (lbasename (filename
), "diagnostic.c") == 0)
518 /* Print up to 20 functions. We could make this a --param, but
519 since this is only for debugging just use a constant for now. */
522 /* Returning a non-zero value stops the backtrace. */
528 if (function
!= NULL
)
530 char *str
= cplus_demangle_v3 (function
,
531 (DMGL_VERBOSE
| DMGL_ANSI
532 | DMGL_GNU_V3
| DMGL_PARAMS
));
539 for (size_t i
= 0; i
< ARRAY_SIZE (bt_stop
); ++i
)
541 size_t len
= strlen (bt_stop
[i
]);
542 if (strncmp (function
, bt_stop
[i
], len
) == 0
543 && (function
[len
] == '\0' || function
[len
] == '('))
547 /* Returning a non-zero value stops the backtrace. */
553 fprintf (stderr
, "0x%lx %s\n\t%s:%d\n",
555 function
== NULL
? "???" : function
,
556 filename
== NULL
? "???" : filename
,
565 /* A callback function passed to the backtrace_full function. This is
566 called if backtrace_full has an error. */
569 bt_err_callback (void *data ATTRIBUTE_UNUSED
, const char *msg
, int errnum
)
573 /* This means that no debug info was available. Just quietly
574 skip printing backtrace info. */
577 fprintf (stderr
, "%s%s%s\n", msg
, errnum
== 0 ? "" : ": ",
578 errnum
== 0 ? "" : xstrerror (errnum
));
581 /* Check if we've met the maximum error limit, and if so fatally exit
582 with a message. CONTEXT is the context to check, and FLUSH
583 indicates whether a diagnostic_finish call is needed. */
586 diagnostic_check_max_errors (diagnostic_context
*context
, bool flush
)
588 if (!context
->max_errors
)
591 int count
= (diagnostic_kind_count (context
, DK_ERROR
)
592 + diagnostic_kind_count (context
, DK_SORRY
)
593 + diagnostic_kind_count (context
, DK_WERROR
));
595 if (count
>= context
->max_errors
)
598 "compilation terminated due to -fmax-errors=%u.\n",
599 context
->max_errors
);
601 diagnostic_finish (context
);
602 exit (FATAL_EXIT_CODE
);
606 /* Take any action which is expected to happen after the diagnostic
607 is written out. This function does not always return. */
609 diagnostic_action_after_output (diagnostic_context
*context
,
610 diagnostic_t diag_kind
)
622 if (context
->abort_on_error
)
624 if (context
->fatal_errors
)
626 fnotice (stderr
, "compilation terminated due to -Wfatal-errors.\n");
627 diagnostic_finish (context
);
628 exit (FATAL_EXIT_CODE
);
635 struct backtrace_state
*state
= NULL
;
636 if (diag_kind
== DK_ICE
)
637 state
= backtrace_create_state (NULL
, 0, bt_err_callback
, NULL
);
640 backtrace_full (state
, 2, bt_callback
, bt_err_callback
,
643 if (context
->abort_on_error
)
646 fnotice (stderr
, "Please submit a full bug report,\n"
647 "with preprocessed source if appropriate.\n");
650 ("Please include the complete backtrace "
651 "with any bug report.\n"));
652 fnotice (stderr
, "See %s for instructions.\n", bug_report_url
);
654 exit (ICE_EXIT_CODE
);
658 if (context
->abort_on_error
)
660 diagnostic_finish (context
);
661 fnotice (stderr
, "compilation terminated.\n");
662 exit (FATAL_EXIT_CODE
);
669 /* True if the last module or file in which a diagnostic was reported is
670 different from the current one. */
673 last_module_changed_p (diagnostic_context
*context
,
674 const line_map_ordinary
*map
)
676 return context
->last_module
!= map
;
679 /* Remember the current module or file as being the last one in which we
680 report a diagnostic. */
683 set_last_module (diagnostic_context
*context
, const line_map_ordinary
*map
)
685 context
->last_module
= map
;
689 diagnostic_report_current_module (diagnostic_context
*context
, location_t where
)
691 const line_map_ordinary
*map
= NULL
;
693 if (pp_needs_newline (context
->printer
))
695 pp_newline (context
->printer
);
696 pp_needs_newline (context
->printer
) = false;
699 if (where
<= BUILTINS_LOCATION
)
702 linemap_resolve_location (line_table
, where
,
703 LRK_MACRO_DEFINITION_LOCATION
,
706 if (map
&& last_module_changed_p (context
, map
))
708 set_last_module (context
, map
);
709 if (! MAIN_FILE_P (map
))
711 bool first
= true, need_inc
= true, was_module
= MAP_MODULE_P (map
);
712 expanded_location s
= {};
715 where
= linemap_included_from (map
);
716 map
= linemap_included_from_linemap (line_table
, map
);
717 bool is_module
= MAP_MODULE_P (map
);
718 s
.file
= LINEMAP_FILE (map
);
719 s
.line
= SOURCE_LINE (map
, where
);
721 if (first
&& context
->show_column
)
723 s
.column
= SOURCE_COLUMN (map
, where
);
724 col
= diagnostic_converted_column (context
, s
);
726 const char *line_col
= maybe_line_and_column (s
.line
, col
);
727 static const char *const msgs
[] =
731 N_("In file included from"), /* 2 */
732 N_(" included from"),
733 N_("In module"), /* 4 */
735 N_("In module imported at"), /* 6 */
739 unsigned index
= (was_module
? 6 : is_module
? 4
740 : need_inc
? 2 : 0) + !first
;
742 pp_verbatim (context
->printer
, "%s%s %r%s%s%R",
743 first
? "" : was_module
? ", " : ",\n",
745 "locus", s
.file
, line_col
);
746 first
= false, need_inc
= was_module
, was_module
= is_module
;
748 while (! MAIN_FILE_P (map
));
749 pp_verbatim (context
->printer
, ":");
750 pp_newline (context
->printer
);
755 /* If DIAGNOSTIC has a diagnostic_path and CONTEXT supports printing paths,
759 diagnostic_show_any_path (diagnostic_context
*context
,
760 diagnostic_info
*diagnostic
)
762 const diagnostic_path
*path
= diagnostic
->richloc
->get_path ();
766 if (context
->print_path
)
767 context
->print_path (context
, path
);
770 /* Return true if the events in this path involve more than one
771 function, or false if it is purely intraprocedural. */
774 diagnostic_path::interprocedural_p () const
776 const unsigned num
= num_events ();
777 for (unsigned i
= 0; i
< num
; i
++)
779 if (get_event (i
).get_fndecl () != get_event (0).get_fndecl ())
781 if (get_event (i
).get_stack_depth () != get_event (0).get_stack_depth ())
788 default_diagnostic_starter (diagnostic_context
*context
,
789 diagnostic_info
*diagnostic
)
791 diagnostic_report_current_module (context
, diagnostic_location (diagnostic
));
792 pp_set_prefix (context
->printer
, diagnostic_build_prefix (context
,
797 default_diagnostic_start_span_fn (diagnostic_context
*context
,
798 expanded_location exploc
)
800 char *text
= diagnostic_get_location_text (context
, exploc
);
801 pp_string (context
->printer
, text
);
803 pp_newline (context
->printer
);
807 default_diagnostic_finalizer (diagnostic_context
*context
,
808 diagnostic_info
*diagnostic
,
811 char *saved_prefix
= pp_take_prefix (context
->printer
);
812 pp_set_prefix (context
->printer
, NULL
);
813 pp_newline (context
->printer
);
814 diagnostic_show_locus (context
, diagnostic
->richloc
, diagnostic
->kind
);
815 pp_set_prefix (context
->printer
, saved_prefix
);
816 pp_flush (context
->printer
);
819 /* Interface to specify diagnostic kind overrides. Returns the
820 previous setting, or DK_UNSPECIFIED if the parameters are out of
821 range. If OPTION_INDEX is zero, the new setting is for all the
824 diagnostic_classify_diagnostic (diagnostic_context
*context
,
826 diagnostic_t new_kind
,
829 diagnostic_t old_kind
;
832 || option_index
>= context
->n_opts
833 || new_kind
>= DK_LAST_DIAGNOSTIC_KIND
)
834 return DK_UNSPECIFIED
;
836 old_kind
= context
->classify_diagnostic
[option_index
];
838 /* Handle pragmas separately, since we need to keep track of *where*
840 if (where
!= UNKNOWN_LOCATION
)
844 /* Record the command-line status, so we can reset it back on DK_POP. */
845 if (old_kind
== DK_UNSPECIFIED
)
847 old_kind
= !context
->option_enabled (option_index
,
849 context
->option_state
)
850 ? DK_IGNORED
: (context
->warning_as_error_requested
851 ? DK_ERROR
: DK_WARNING
);
852 context
->classify_diagnostic
[option_index
] = old_kind
;
855 for (i
= context
->n_classification_history
- 1; i
>= 0; i
--)
856 if (context
->classification_history
[i
].option
== option_index
)
858 old_kind
= context
->classification_history
[i
].kind
;
862 i
= context
->n_classification_history
;
863 context
->classification_history
=
864 (diagnostic_classification_change_t
*) xrealloc (context
->classification_history
, (i
+ 1)
865 * sizeof (diagnostic_classification_change_t
));
866 context
->classification_history
[i
].location
= where
;
867 context
->classification_history
[i
].option
= option_index
;
868 context
->classification_history
[i
].kind
= new_kind
;
869 context
->n_classification_history
++;
872 context
->classify_diagnostic
[option_index
] = new_kind
;
877 /* Save all diagnostic classifications in a stack. */
879 diagnostic_push_diagnostics (diagnostic_context
*context
, location_t where ATTRIBUTE_UNUSED
)
881 context
->push_list
= (int *) xrealloc (context
->push_list
, (context
->n_push
+ 1) * sizeof (int));
882 context
->push_list
[context
->n_push
++] = context
->n_classification_history
;
885 /* Restore the topmost classification set off the stack. If the stack
886 is empty, revert to the state based on command line parameters. */
888 diagnostic_pop_diagnostics (diagnostic_context
*context
, location_t where
)
894 jump_to
= context
->push_list
[-- context
->n_push
];
898 i
= context
->n_classification_history
;
899 context
->classification_history
=
900 (diagnostic_classification_change_t
*) xrealloc (context
->classification_history
, (i
+ 1)
901 * sizeof (diagnostic_classification_change_t
));
902 context
->classification_history
[i
].location
= where
;
903 context
->classification_history
[i
].option
= jump_to
;
904 context
->classification_history
[i
].kind
= DK_POP
;
905 context
->n_classification_history
++;
908 /* Helper function for print_parseable_fixits. Print TEXT to PP, obeying the
909 escaping rules for -fdiagnostics-parseable-fixits. */
912 print_escaped_string (pretty_printer
*pp
, const char *text
)
917 pp_character (pp
, '"');
918 for (const char *ch
= text
; *ch
; ch
++)
923 /* Escape backslash as two backslashes. */
924 pp_string (pp
, "\\\\");
927 /* Escape tab as "\t". */
928 pp_string (pp
, "\\t");
931 /* Escape newline as "\n". */
932 pp_string (pp
, "\\n");
935 /* Escape doublequotes as \". */
936 pp_string (pp
, "\\\"");
940 pp_character (pp
, *ch
);
942 /* Use octal for non-printable chars. */
944 unsigned char c
= (*ch
& 0xff);
945 pp_printf (pp
, "\\%o%o%o", (c
/ 64), (c
/ 8) & 007, c
& 007);
950 pp_character (pp
, '"');
953 /* Implementation of -fdiagnostics-parseable-fixits and
954 GCC_EXTRA_DIAGNOSTIC_OUTPUT.
955 Print a machine-parseable version of all fixits in RICHLOC to PP,
956 using COLUMN_UNIT to express columns.
957 Use TABSTOP when handling DIAGNOSTICS_COLUMN_UNIT_DISPLAY. */
960 print_parseable_fixits (pretty_printer
*pp
, rich_location
*richloc
,
961 enum diagnostics_column_unit column_unit
,
965 gcc_assert (richloc
);
967 char *saved_prefix
= pp_take_prefix (pp
);
968 pp_set_prefix (pp
, NULL
);
970 for (unsigned i
= 0; i
< richloc
->get_num_fixit_hints (); i
++)
972 const fixit_hint
*hint
= richloc
->get_fixit_hint (i
);
973 location_t start_loc
= hint
->get_start_loc ();
974 expanded_location start_exploc
= expand_location (start_loc
);
975 pp_string (pp
, "fix-it:");
976 print_escaped_string (pp
, start_exploc
.file
);
977 /* For compatibility with clang, print as a half-open range. */
978 location_t next_loc
= hint
->get_next_loc ();
979 expanded_location next_exploc
= expand_location (next_loc
);
981 = convert_column_unit (column_unit
, tabstop
, start_exploc
);
983 = convert_column_unit (column_unit
, tabstop
, next_exploc
);
984 pp_printf (pp
, ":{%i:%i-%i:%i}:",
985 start_exploc
.line
, start_col
,
986 next_exploc
.line
, next_col
);
987 print_escaped_string (pp
, hint
->get_string ());
991 pp_set_prefix (pp
, saved_prefix
);
994 /* Update the diag_class of DIAGNOSTIC based on its location
996 #pragma GCC diagnostic
997 directives recorded within CONTEXT.
999 Return the new diag_class of DIAGNOSTIC if it was updated, or
1000 DK_UNSPECIFIED otherwise. */
1003 update_effective_level_from_pragmas (diagnostic_context
*context
,
1004 diagnostic_info
*diagnostic
)
1006 diagnostic_t diag_class
= DK_UNSPECIFIED
;
1008 if (context
->n_classification_history
> 0)
1010 location_t location
= diagnostic_location (diagnostic
);
1012 /* FIXME: Stupid search. Optimize later. */
1013 for (int i
= context
->n_classification_history
- 1; i
>= 0; i
--)
1015 if (linemap_location_before_p
1017 context
->classification_history
[i
].location
,
1020 if (context
->classification_history
[i
].kind
== (int) DK_POP
)
1022 i
= context
->classification_history
[i
].option
;
1025 int option
= context
->classification_history
[i
].option
;
1026 /* The option 0 is for all the diagnostics. */
1027 if (option
== 0 || option
== diagnostic
->option_index
)
1029 diag_class
= context
->classification_history
[i
].kind
;
1030 if (diag_class
!= DK_UNSPECIFIED
)
1031 diagnostic
->kind
= diag_class
;
1041 /* Generate a URL string describing CWE. The caller is responsible for
1042 freeing the string. */
1045 get_cwe_url (int cwe
)
1047 return xasprintf ("https://cwe.mitre.org/data/definitions/%i.html", cwe
);
1050 /* If DIAGNOSTIC has a CWE identifier, print it.
1052 For example, if the diagnostic metadata associates it with CWE-119,
1053 " [CWE-119]" will be printed, suitably colorized, and with a URL of a
1054 description of the security issue. */
1057 print_any_cwe (diagnostic_context
*context
,
1058 const diagnostic_info
*diagnostic
)
1060 if (diagnostic
->metadata
== NULL
)
1063 int cwe
= diagnostic
->metadata
->get_cwe ();
1066 pretty_printer
*pp
= context
->printer
;
1067 char *saved_prefix
= pp_take_prefix (context
->printer
);
1068 pp_string (pp
, " [");
1069 pp_string (pp
, colorize_start (pp_show_color (pp
),
1070 diagnostic_kind_color
[diagnostic
->kind
]));
1071 if (pp
->url_format
!= URL_FORMAT_NONE
)
1073 char *cwe_url
= get_cwe_url (cwe
);
1074 pp_begin_url (pp
, cwe_url
);
1077 pp_printf (pp
, "CWE-%i", cwe
);
1078 pp_set_prefix (context
->printer
, saved_prefix
);
1079 if (pp
->url_format
!= URL_FORMAT_NONE
)
1081 pp_string (pp
, colorize_stop (pp_show_color (pp
)));
1082 pp_character (pp
, ']');
1086 /* Print any metadata about the option used to control DIAGNOSTIC to CONTEXT's
1087 printer, e.g. " [-Werror=uninitialized]".
1088 Subroutine of diagnostic_report_diagnostic. */
1091 print_option_information (diagnostic_context
*context
,
1092 const diagnostic_info
*diagnostic
,
1093 diagnostic_t orig_diag_kind
)
1097 option_text
= context
->option_name (context
, diagnostic
->option_index
,
1098 orig_diag_kind
, diagnostic
->kind
);
1102 char *option_url
= NULL
;
1103 if (context
->get_option_url
1104 && context
->printer
->url_format
!= URL_FORMAT_NONE
)
1105 option_url
= context
->get_option_url (context
,
1106 diagnostic
->option_index
);
1107 pretty_printer
*pp
= context
->printer
;
1108 pp_string (pp
, " [");
1109 pp_string (pp
, colorize_start (pp_show_color (pp
),
1110 diagnostic_kind_color
[diagnostic
->kind
]));
1112 pp_begin_url (pp
, option_url
);
1113 pp_string (pp
, option_text
);
1119 pp_string (pp
, colorize_stop (pp_show_color (pp
)));
1120 pp_character (pp
, ']');
1125 /* Report a diagnostic message (an error or a warning) as specified by
1126 DC. This function is *the* subroutine in terms of which front-ends
1127 should implement their specific diagnostic handling modules. The
1128 front-end independent format specifiers are exactly those described
1129 in the documentation of output_format.
1130 Return true if a diagnostic was printed, false otherwise. */
1133 diagnostic_report_diagnostic (diagnostic_context
*context
,
1134 diagnostic_info
*diagnostic
)
1136 location_t location
= diagnostic_location (diagnostic
);
1137 diagnostic_t orig_diag_kind
= diagnostic
->kind
;
1139 /* Give preference to being able to inhibit warnings, before they
1140 get reclassified to something else. */
1141 if ((diagnostic
->kind
== DK_WARNING
|| diagnostic
->kind
== DK_PEDWARN
)
1142 && !diagnostic_report_warnings_p (context
, location
))
1145 if (diagnostic
->kind
== DK_PEDWARN
)
1147 diagnostic
->kind
= pedantic_warning_kind (context
);
1148 /* We do this to avoid giving the message for -pedantic-errors. */
1149 orig_diag_kind
= diagnostic
->kind
;
1152 if (diagnostic
->kind
== DK_NOTE
&& context
->inhibit_notes_p
)
1155 if (context
->lock
> 0)
1157 /* If we're reporting an ICE in the middle of some other error,
1158 try to flush out the previous error, then let this one
1159 through. Don't do this more than once. */
1160 if ((diagnostic
->kind
== DK_ICE
|| diagnostic
->kind
== DK_ICE_NOBT
)
1161 && context
->lock
== 1)
1162 pp_newline_and_flush (context
->printer
);
1164 error_recursion (context
);
1167 /* If the user requested that warnings be treated as errors, so be
1168 it. Note that we do this before the next block so that
1169 individual warnings can be overridden back to warnings with
1171 if (context
->warning_as_error_requested
1172 && diagnostic
->kind
== DK_WARNING
)
1173 diagnostic
->kind
= DK_ERROR
;
1175 if (diagnostic
->option_index
1176 && diagnostic
->option_index
!= permissive_error_option (context
))
1178 /* This tests if the user provided the appropriate -Wfoo or
1180 if (! context
->option_enabled (diagnostic
->option_index
,
1182 context
->option_state
))
1185 /* This tests for #pragma diagnostic changes. */
1186 diagnostic_t diag_class
1187 = update_effective_level_from_pragmas (context
, diagnostic
);
1189 /* This tests if the user provided the appropriate -Werror=foo
1191 if (diag_class
== DK_UNSPECIFIED
1192 && (context
->classify_diagnostic
[diagnostic
->option_index
]
1195 = context
->classify_diagnostic
[diagnostic
->option_index
];
1197 /* This allows for future extensions, like temporarily disabling
1198 warnings for ranges of source code. */
1199 if (diagnostic
->kind
== DK_IGNORED
)
1203 if (diagnostic
->kind
!= DK_NOTE
&& diagnostic
->kind
!= DK_ICE
)
1204 diagnostic_check_max_errors (context
);
1208 if (diagnostic
->kind
== DK_ICE
|| diagnostic
->kind
== DK_ICE_NOBT
)
1210 /* When not checking, ICEs are converted to fatal errors when an
1211 error has already occurred. This is counteracted by
1214 && (diagnostic_kind_count (context
, DK_ERROR
) > 0
1215 || diagnostic_kind_count (context
, DK_SORRY
) > 0)
1216 && !context
->abort_on_error
)
1219 = expand_location (diagnostic_location (diagnostic
));
1220 fnotice (stderr
, "%s:%d: confused by earlier errors, bailing out\n",
1222 exit (ICE_EXIT_CODE
);
1224 if (context
->internal_error
)
1225 (*context
->internal_error
) (context
,
1226 diagnostic
->message
.format_spec
,
1227 diagnostic
->message
.args_ptr
);
1229 if (diagnostic
->kind
== DK_ERROR
&& orig_diag_kind
== DK_WARNING
)
1230 ++diagnostic_kind_count (context
, DK_WERROR
);
1232 ++diagnostic_kind_count (context
, diagnostic
->kind
);
1234 /* Is this the initial diagnostic within the stack of groups? */
1235 if (context
->diagnostic_group_emission_count
== 0)
1237 if (context
->begin_group_cb
)
1238 context
->begin_group_cb (context
);
1240 context
->diagnostic_group_emission_count
++;
1242 diagnostic
->message
.x_data
= &diagnostic
->x_data
;
1243 diagnostic
->x_data
= NULL
;
1244 pp_format (context
->printer
, &diagnostic
->message
);
1245 (*diagnostic_starter (context
)) (context
, diagnostic
);
1246 pp_output_formatted_text (context
->printer
);
1247 if (context
->show_cwe
)
1248 print_any_cwe (context
, diagnostic
);
1249 if (context
->show_option_requested
)
1250 print_option_information (context
, diagnostic
, orig_diag_kind
);
1251 (*diagnostic_finalizer (context
)) (context
, diagnostic
, orig_diag_kind
);
1252 switch (context
->extra_output_kind
)
1256 case EXTRA_DIAGNOSTIC_OUTPUT_fixits_v1
:
1257 print_parseable_fixits (context
->printer
, diagnostic
->richloc
,
1258 DIAGNOSTICS_COLUMN_UNIT_BYTE
,
1260 pp_flush (context
->printer
);
1262 case EXTRA_DIAGNOSTIC_OUTPUT_fixits_v2
:
1263 print_parseable_fixits (context
->printer
, diagnostic
->richloc
,
1264 DIAGNOSTICS_COLUMN_UNIT_DISPLAY
,
1266 pp_flush (context
->printer
);
1269 diagnostic_action_after_output (context
, diagnostic
->kind
);
1270 diagnostic
->x_data
= NULL
;
1272 if (context
->edit_context_ptr
)
1273 if (diagnostic
->richloc
->fixits_can_be_auto_applied_p ())
1274 context
->edit_context_ptr
->add_fixits (diagnostic
->richloc
);
1278 diagnostic_show_any_path (context
, diagnostic
);
1283 /* Get the number of digits in the decimal representation of VALUE. */
1286 num_digits (int value
)
1288 /* Perhaps simpler to use log10 for this, but doing it this way avoids
1289 using floating point. */
1290 gcc_assert (value
>= 0);
1304 /* Given a partial pathname as input, return another pathname that
1305 shares no directory elements with the pathname of __FILE__. This
1306 is used by fancy_abort() to print `Internal compiler error in expr.c'
1307 instead of `Internal compiler error in ../../GCC/gcc/expr.c'. */
1310 trim_filename (const char *name
)
1312 static const char this_file
[] = __FILE__
;
1313 const char *p
= name
, *q
= this_file
;
1315 /* First skip any "../" in each filename. This allows us to give a proper
1316 reference to a file in a subdirectory. */
1317 while (p
[0] == '.' && p
[1] == '.' && IS_DIR_SEPARATOR (p
[2]))
1320 while (q
[0] == '.' && q
[1] == '.' && IS_DIR_SEPARATOR (q
[2]))
1323 /* Now skip any parts the two filenames have in common. */
1324 while (*p
== *q
&& *p
!= 0 && *q
!= 0)
1327 /* Now go backwards until the previous directory separator. */
1328 while (p
> name
&& !IS_DIR_SEPARATOR (p
[-1]))
1334 /* Standard error reporting routines in increasing order of severity.
1335 All of these take arguments like printf. */
1337 /* Text to be emitted verbatim to the error message stream; this
1338 produces no prefix and disables line-wrapping. Use rarely. */
1340 verbatim (const char *gmsgid
, ...)
1345 va_start (ap
, gmsgid
);
1346 text
.err_no
= errno
;
1347 text
.args_ptr
= &ap
;
1348 text
.format_spec
= _(gmsgid
);
1350 pp_format_verbatim (global_dc
->printer
, &text
);
1351 pp_newline_and_flush (global_dc
->printer
);
1355 /* Add a note with text GMSGID and with LOCATION to the diagnostic CONTEXT. */
1357 diagnostic_append_note (diagnostic_context
*context
,
1358 location_t location
,
1359 const char * gmsgid
, ...)
1361 diagnostic_info diagnostic
;
1363 rich_location
richloc (line_table
, location
);
1365 va_start (ap
, gmsgid
);
1366 diagnostic_set_info (&diagnostic
, gmsgid
, &ap
, &richloc
, DK_NOTE
);
1367 if (context
->inhibit_notes_p
)
1372 char *saved_prefix
= pp_take_prefix (context
->printer
);
1373 pp_set_prefix (context
->printer
,
1374 diagnostic_build_prefix (context
, &diagnostic
));
1375 pp_format (context
->printer
, &diagnostic
.message
);
1376 pp_output_formatted_text (context
->printer
);
1377 pp_destroy_prefix (context
->printer
);
1378 pp_set_prefix (context
->printer
, saved_prefix
);
1379 pp_newline (context
->printer
);
1380 diagnostic_show_locus (context
, &richloc
, DK_NOTE
);
1384 /* Implement emit_diagnostic, inform, warning, warning_at, pedwarn,
1385 permerror, error, error_at, error_at, sorry, fatal_error, internal_error,
1386 and internal_error_no_backtrace, as documented and defined below. */
1388 diagnostic_impl (rich_location
*richloc
, const diagnostic_metadata
*metadata
,
1389 int opt
, const char *gmsgid
,
1390 va_list *ap
, diagnostic_t kind
)
1392 diagnostic_info diagnostic
;
1393 if (kind
== DK_PERMERROR
)
1395 diagnostic_set_info (&diagnostic
, gmsgid
, ap
, richloc
,
1396 permissive_error_kind (global_dc
));
1397 diagnostic
.option_index
= permissive_error_option (global_dc
);
1401 diagnostic_set_info (&diagnostic
, gmsgid
, ap
, richloc
, kind
);
1402 if (kind
== DK_WARNING
|| kind
== DK_PEDWARN
)
1403 diagnostic
.option_index
= opt
;
1405 diagnostic
.metadata
= metadata
;
1406 return diagnostic_report_diagnostic (global_dc
, &diagnostic
);
1409 /* Implement inform_n, warning_n, and error_n, as documented and
1412 diagnostic_n_impl (rich_location
*richloc
, const diagnostic_metadata
*metadata
,
1413 int opt
, unsigned HOST_WIDE_INT n
,
1414 const char *singular_gmsgid
,
1415 const char *plural_gmsgid
,
1416 va_list *ap
, diagnostic_t kind
)
1418 diagnostic_info diagnostic
;
1421 if (sizeof n
<= sizeof gtn
)
1424 /* Use the largest number ngettext can handle, otherwise
1425 preserve the six least significant decimal digits for
1426 languages where the plural form depends on them. */
1427 gtn
= n
<= ULONG_MAX
? n
: n
% 1000000LU + 1000000LU;
1429 const char *text
= ngettext (singular_gmsgid
, plural_gmsgid
, gtn
);
1430 diagnostic_set_info_translated (&diagnostic
, text
, ap
, richloc
, kind
);
1431 if (kind
== DK_WARNING
)
1432 diagnostic
.option_index
= opt
;
1433 diagnostic
.metadata
= metadata
;
1434 return diagnostic_report_diagnostic (global_dc
, &diagnostic
);
1437 /* Wrapper around diagnostic_impl taking a variable argument list. */
1440 emit_diagnostic (diagnostic_t kind
, location_t location
, int opt
,
1441 const char *gmsgid
, ...)
1443 auto_diagnostic_group d
;
1445 va_start (ap
, gmsgid
);
1446 rich_location
richloc (line_table
, location
);
1447 bool ret
= diagnostic_impl (&richloc
, NULL
, opt
, gmsgid
, &ap
, kind
);
1452 /* As above, but for rich_location *. */
1455 emit_diagnostic (diagnostic_t kind
, rich_location
*richloc
, int opt
,
1456 const char *gmsgid
, ...)
1458 auto_diagnostic_group d
;
1460 va_start (ap
, gmsgid
);
1461 bool ret
= diagnostic_impl (richloc
, NULL
, opt
, gmsgid
, &ap
, kind
);
1466 /* Wrapper around diagnostic_impl taking a va_list parameter. */
1469 emit_diagnostic_valist (diagnostic_t kind
, location_t location
, int opt
,
1470 const char *gmsgid
, va_list *ap
)
1472 rich_location
richloc (line_table
, location
);
1473 return diagnostic_impl (&richloc
, NULL
, opt
, gmsgid
, ap
, kind
);
1476 /* An informative note at LOCATION. Use this for additional details on an error
1479 inform (location_t location
, const char *gmsgid
, ...)
1481 auto_diagnostic_group d
;
1483 va_start (ap
, gmsgid
);
1484 rich_location
richloc (line_table
, location
);
1485 diagnostic_impl (&richloc
, NULL
, -1, gmsgid
, &ap
, DK_NOTE
);
1489 /* Same as "inform" above, but at RICHLOC. */
1491 inform (rich_location
*richloc
, const char *gmsgid
, ...)
1493 gcc_assert (richloc
);
1495 auto_diagnostic_group d
;
1497 va_start (ap
, gmsgid
);
1498 diagnostic_impl (richloc
, NULL
, -1, gmsgid
, &ap
, DK_NOTE
);
1502 /* An informative note at LOCATION. Use this for additional details on an
1505 inform_n (location_t location
, unsigned HOST_WIDE_INT n
,
1506 const char *singular_gmsgid
, const char *plural_gmsgid
, ...)
1509 va_start (ap
, plural_gmsgid
);
1510 auto_diagnostic_group d
;
1511 rich_location
richloc (line_table
, location
);
1512 diagnostic_n_impl (&richloc
, NULL
, -1, n
, singular_gmsgid
, plural_gmsgid
,
1517 /* A warning at INPUT_LOCATION. Use this for code which is correct according
1518 to the relevant language specification but is likely to be buggy anyway.
1519 Returns true if the warning was printed, false if it was inhibited. */
1521 warning (int opt
, const char *gmsgid
, ...)
1523 auto_diagnostic_group d
;
1525 va_start (ap
, gmsgid
);
1526 rich_location
richloc (line_table
, input_location
);
1527 bool ret
= diagnostic_impl (&richloc
, NULL
, opt
, gmsgid
, &ap
, DK_WARNING
);
1532 /* A warning at LOCATION. Use this for code which is correct according to the
1533 relevant language specification but is likely to be buggy anyway.
1534 Returns true if the warning was printed, false if it was inhibited. */
1537 warning_at (location_t location
, int opt
, const char *gmsgid
, ...)
1539 auto_diagnostic_group d
;
1541 va_start (ap
, gmsgid
);
1542 rich_location
richloc (line_table
, location
);
1543 bool ret
= diagnostic_impl (&richloc
, NULL
, opt
, gmsgid
, &ap
, DK_WARNING
);
1548 /* Same as "warning at" above, but using RICHLOC. */
1551 warning_at (rich_location
*richloc
, int opt
, const char *gmsgid
, ...)
1553 gcc_assert (richloc
);
1555 auto_diagnostic_group d
;
1557 va_start (ap
, gmsgid
);
1558 bool ret
= diagnostic_impl (richloc
, NULL
, opt
, gmsgid
, &ap
, DK_WARNING
);
1563 /* Same as "warning at" above, but using METADATA. */
1566 warning_meta (rich_location
*richloc
,
1567 const diagnostic_metadata
&metadata
,
1568 int opt
, const char *gmsgid
, ...)
1570 gcc_assert (richloc
);
1572 auto_diagnostic_group d
;
1574 va_start (ap
, gmsgid
);
1576 = diagnostic_impl (richloc
, &metadata
, opt
, gmsgid
, &ap
,
1582 /* Same as warning_n plural variant below, but using RICHLOC. */
1585 warning_n (rich_location
*richloc
, int opt
, unsigned HOST_WIDE_INT n
,
1586 const char *singular_gmsgid
, const char *plural_gmsgid
, ...)
1588 gcc_assert (richloc
);
1590 auto_diagnostic_group d
;
1592 va_start (ap
, plural_gmsgid
);
1593 bool ret
= diagnostic_n_impl (richloc
, NULL
, opt
, n
,
1594 singular_gmsgid
, plural_gmsgid
,
1600 /* A warning at LOCATION. Use this for code which is correct according to the
1601 relevant language specification but is likely to be buggy anyway.
1602 Returns true if the warning was printed, false if it was inhibited. */
1605 warning_n (location_t location
, int opt
, unsigned HOST_WIDE_INT n
,
1606 const char *singular_gmsgid
, const char *plural_gmsgid
, ...)
1608 auto_diagnostic_group d
;
1610 va_start (ap
, plural_gmsgid
);
1611 rich_location
richloc (line_table
, location
);
1612 bool ret
= diagnostic_n_impl (&richloc
, NULL
, opt
, n
,
1613 singular_gmsgid
, plural_gmsgid
,
1619 /* A "pedantic" warning at LOCATION: issues a warning unless
1620 -pedantic-errors was given on the command line, in which case it
1621 issues an error. Use this for diagnostics required by the relevant
1622 language standard, if you have chosen not to make them errors.
1624 Note that these diagnostics are issued independent of the setting
1625 of the -Wpedantic command-line switch. To get a warning enabled
1626 only with that switch, use either "if (pedantic) pedwarn
1627 (OPT_Wpedantic,...)" or just "pedwarn (OPT_Wpedantic,..)". To get a
1628 pedwarn independently of the -Wpedantic switch use "pedwarn (0,...)".
1630 Returns true if the warning was printed, false if it was inhibited. */
1633 pedwarn (location_t location
, int opt
, const char *gmsgid
, ...)
1635 auto_diagnostic_group d
;
1637 va_start (ap
, gmsgid
);
1638 rich_location
richloc (line_table
, location
);
1639 bool ret
= diagnostic_impl (&richloc
, NULL
, opt
, gmsgid
, &ap
, DK_PEDWARN
);
1644 /* Same as pedwarn above, but using RICHLOC. */
1647 pedwarn (rich_location
*richloc
, int opt
, const char *gmsgid
, ...)
1649 gcc_assert (richloc
);
1651 auto_diagnostic_group d
;
1653 va_start (ap
, gmsgid
);
1654 bool ret
= diagnostic_impl (richloc
, NULL
, opt
, gmsgid
, &ap
, DK_PEDWARN
);
1659 /* A "permissive" error at LOCATION: issues an error unless
1660 -fpermissive was given on the command line, in which case it issues
1661 a warning. Use this for things that really should be errors but we
1662 want to support legacy code.
1664 Returns true if the warning was printed, false if it was inhibited. */
1667 permerror (location_t location
, const char *gmsgid
, ...)
1669 auto_diagnostic_group d
;
1671 va_start (ap
, gmsgid
);
1672 rich_location
richloc (line_table
, location
);
1673 bool ret
= diagnostic_impl (&richloc
, NULL
, -1, gmsgid
, &ap
, DK_PERMERROR
);
1678 /* Same as "permerror" above, but at RICHLOC. */
1681 permerror (rich_location
*richloc
, const char *gmsgid
, ...)
1683 gcc_assert (richloc
);
1685 auto_diagnostic_group d
;
1687 va_start (ap
, gmsgid
);
1688 bool ret
= diagnostic_impl (richloc
, NULL
, -1, gmsgid
, &ap
, DK_PERMERROR
);
1693 /* A hard error: the code is definitely ill-formed, and an object file
1694 will not be produced. */
1696 error (const char *gmsgid
, ...)
1698 auto_diagnostic_group d
;
1700 va_start (ap
, gmsgid
);
1701 rich_location
richloc (line_table
, input_location
);
1702 diagnostic_impl (&richloc
, NULL
, -1, gmsgid
, &ap
, DK_ERROR
);
1706 /* A hard error: the code is definitely ill-formed, and an object file
1707 will not be produced. */
1709 error_n (location_t location
, unsigned HOST_WIDE_INT n
,
1710 const char *singular_gmsgid
, const char *plural_gmsgid
, ...)
1712 auto_diagnostic_group d
;
1714 va_start (ap
, plural_gmsgid
);
1715 rich_location
richloc (line_table
, location
);
1716 diagnostic_n_impl (&richloc
, NULL
, -1, n
, singular_gmsgid
, plural_gmsgid
,
1721 /* Same as above, but use location LOC instead of input_location. */
1723 error_at (location_t loc
, const char *gmsgid
, ...)
1725 auto_diagnostic_group d
;
1727 va_start (ap
, gmsgid
);
1728 rich_location
richloc (line_table
, loc
);
1729 diagnostic_impl (&richloc
, NULL
, -1, gmsgid
, &ap
, DK_ERROR
);
1733 /* Same as above, but use RICH_LOC. */
1736 error_at (rich_location
*richloc
, const char *gmsgid
, ...)
1738 gcc_assert (richloc
);
1740 auto_diagnostic_group d
;
1742 va_start (ap
, gmsgid
);
1743 diagnostic_impl (richloc
, NULL
, -1, gmsgid
, &ap
, DK_ERROR
);
1747 /* "Sorry, not implemented." Use for a language feature which is
1748 required by the relevant specification but not implemented by GCC.
1749 An object file will not be produced. */
1751 sorry (const char *gmsgid
, ...)
1753 auto_diagnostic_group d
;
1755 va_start (ap
, gmsgid
);
1756 rich_location
richloc (line_table
, input_location
);
1757 diagnostic_impl (&richloc
, NULL
, -1, gmsgid
, &ap
, DK_SORRY
);
1761 /* Same as above, but use location LOC instead of input_location. */
1763 sorry_at (location_t loc
, const char *gmsgid
, ...)
1765 auto_diagnostic_group d
;
1767 va_start (ap
, gmsgid
);
1768 rich_location
richloc (line_table
, loc
);
1769 diagnostic_impl (&richloc
, NULL
, -1, gmsgid
, &ap
, DK_SORRY
);
1773 /* Return true if an error or a "sorry" has been seen. Various
1774 processing is disabled after errors. */
1778 return errorcount
|| sorrycount
;
1781 /* An error which is severe enough that we make no attempt to
1782 continue. Do not use this for internal consistency checks; that's
1783 internal_error. Use of this function should be rare. */
1785 fatal_error (location_t loc
, const char *gmsgid
, ...)
1787 auto_diagnostic_group d
;
1789 va_start (ap
, gmsgid
);
1790 rich_location
richloc (line_table
, loc
);
1791 diagnostic_impl (&richloc
, NULL
, -1, gmsgid
, &ap
, DK_FATAL
);
1797 /* An internal consistency check has failed. We make no attempt to
1798 continue. Note that unless there is debugging value to be had from
1799 a more specific message, or some other good reason, you should use
1800 abort () instead of calling this function directly. */
1802 internal_error (const char *gmsgid
, ...)
1804 auto_diagnostic_group d
;
1806 va_start (ap
, gmsgid
);
1807 rich_location
richloc (line_table
, input_location
);
1808 diagnostic_impl (&richloc
, NULL
, -1, gmsgid
, &ap
, DK_ICE
);
1814 /* Like internal_error, but no backtrace will be printed. Used when
1815 the internal error does not happen at the current location, but happened
1818 internal_error_no_backtrace (const char *gmsgid
, ...)
1820 auto_diagnostic_group d
;
1822 va_start (ap
, gmsgid
);
1823 rich_location
richloc (line_table
, input_location
);
1824 diagnostic_impl (&richloc
, NULL
, -1, gmsgid
, &ap
, DK_ICE_NOBT
);
1830 /* Special case error functions. Most are implemented in terms of the
1831 above, or should be. */
1833 /* Print a diagnostic MSGID on FILE. This is just fprintf, except it
1834 runs its second argument through gettext. */
1836 fnotice (FILE *file
, const char *cmsgid
, ...)
1840 va_start (ap
, cmsgid
);
1841 vfprintf (file
, _(cmsgid
), ap
);
1845 /* Inform the user that an error occurred while trying to report some
1846 other error. This indicates catastrophic internal inconsistencies,
1847 so give up now. But do try to flush out the previous error.
1848 This mustn't use internal_error, that will cause infinite recursion. */
1851 error_recursion (diagnostic_context
*context
)
1853 if (context
->lock
< 3)
1854 pp_newline_and_flush (context
->printer
);
1857 "Internal compiler error: Error reporting routines re-entered.\n");
1859 /* Call diagnostic_action_after_output to get the "please submit a bug
1861 diagnostic_action_after_output (context
, DK_ICE
);
1863 /* Do not use gcc_unreachable here; that goes through internal_error
1864 and therefore would cause infinite recursion. */
1868 /* Report an internal compiler error in a friendly manner. This is
1869 the function that gets called upon use of abort() in the source
1870 code generally, thanks to a special macro. */
1873 fancy_abort (const char *file
, int line
, const char *function
)
1875 /* If fancy_abort is called before the diagnostic subsystem is initialized,
1876 internal_error will crash internally in a way that prevents a
1877 useful message reaching the user.
1878 This can happen with libgccjit in the case of gcc_assert failures
1879 that occur outside of the libgccjit mutex that guards the rest of
1880 gcc's state, including global_dc (when global_dc may not be
1881 initialized yet, or might be in use by another thread).
1882 Handle such cases as gracefully as possible by falling back to a
1883 minimal abort handler that only relies on i18n. */
1884 if (global_dc
->printer
== NULL
)
1886 /* Print the error message. */
1887 fnotice (stderr
, diagnostic_kind_text
[DK_ICE
]);
1888 fnotice (stderr
, "in %s, at %s:%d", function
, trim_filename (file
), line
);
1889 fputc ('\n', stderr
);
1891 /* Attempt to print a backtrace. */
1892 struct backtrace_state
*state
1893 = backtrace_create_state (NULL
, 0, bt_err_callback
, NULL
);
1896 backtrace_full (state
, 2, bt_callback
, bt_err_callback
,
1899 /* We can't call warn_if_plugins or emergency_dump_function as these
1900 rely on GCC state that might not be initialized, or might be in
1901 use by another thread. */
1903 /* Abort the process. */
1907 internal_error ("in %s, at %s:%d", function
, trim_filename (file
), line
);
1910 /* class auto_diagnostic_group. */
1912 /* Constructor: "push" this group into global_dc. */
1914 auto_diagnostic_group::auto_diagnostic_group ()
1916 global_dc
->diagnostic_group_nesting_depth
++;
1919 /* Destructor: "pop" this group from global_dc. */
1921 auto_diagnostic_group::~auto_diagnostic_group ()
1923 if (--global_dc
->diagnostic_group_nesting_depth
== 0)
1925 /* Handle the case where we've popped the final diagnostic group.
1926 If any diagnostics were emitted, give the context a chance
1928 if (global_dc
->diagnostic_group_emission_count
> 0)
1930 if (global_dc
->end_group_cb
)
1931 global_dc
->end_group_cb (global_dc
);
1933 global_dc
->diagnostic_group_emission_count
= 0;
1937 /* Implementation of diagnostic_path::num_events vfunc for
1938 simple_diagnostic_path: simply get the number of events in the vec. */
1941 simple_diagnostic_path::num_events () const
1943 return m_events
.length ();
1946 /* Implementation of diagnostic_path::get_event vfunc for
1947 simple_diagnostic_path: simply return the event in the vec. */
1949 const diagnostic_event
&
1950 simple_diagnostic_path::get_event (int idx
) const
1952 return *m_events
[idx
];
1955 /* Add an event to this path at LOC within function FNDECL at
1958 Use m_context's printer to format FMT, as the text of the new
1961 Return the id of the new event. */
1963 diagnostic_event_id_t
1964 simple_diagnostic_path::add_event (location_t loc
, tree fndecl
, int depth
,
1965 const char *fmt
, ...)
1967 pretty_printer
*pp
= m_event_pp
;
1968 pp_clear_output_area (pp
);
1971 rich_location
rich_loc (line_table
, UNKNOWN_LOCATION
);
1977 ti
.format_spec
= _(fmt
);
1981 ti
.m_richloc
= &rich_loc
;
1983 pp_format (pp
, &ti
);
1984 pp_output_formatted_text (pp
);
1988 simple_diagnostic_event
*new_event
1989 = new simple_diagnostic_event (loc
, fndecl
, depth
, pp_formatted_text (pp
));
1990 m_events
.safe_push (new_event
);
1992 pp_clear_output_area (pp
);
1994 return diagnostic_event_id_t (m_events
.length () - 1);
1997 /* struct simple_diagnostic_event. */
1999 /* simple_diagnostic_event's ctor. */
2001 simple_diagnostic_event::simple_diagnostic_event (location_t loc
,
2005 : m_loc (loc
), m_fndecl (fndecl
), m_depth (depth
), m_desc (xstrdup (desc
))
2009 /* simple_diagnostic_event's dtor. */
2011 simple_diagnostic_event::~simple_diagnostic_event ()
2016 /* Print PATH by emitting a dummy "note" associated with it. */
2019 void debug (diagnostic_path
*path
)
2021 rich_location
richloc (line_table
, UNKNOWN_LOCATION
);
2022 richloc
.set_path (path
);
2023 inform (&richloc
, "debug path");
2026 /* Really call the system 'abort'. This has to go right at the end of
2027 this file, so that there are no functions after it that call abort
2028 and get the system abort instead of our macro. */
2038 namespace selftest
{
2040 /* Helper function for test_print_escaped_string. */
2043 assert_print_escaped_string (const location
&loc
, const char *expected_output
,
2047 print_escaped_string (&pp
, input
);
2048 ASSERT_STREQ_AT (loc
, expected_output
, pp_formatted_text (&pp
));
2051 #define ASSERT_PRINT_ESCAPED_STRING_STREQ(EXPECTED_OUTPUT, INPUT) \
2052 assert_print_escaped_string (SELFTEST_LOCATION, EXPECTED_OUTPUT, INPUT)
2054 /* Tests of print_escaped_string. */
2057 test_print_escaped_string ()
2060 ASSERT_PRINT_ESCAPED_STRING_STREQ ("\"\"", "");
2062 /* Non-empty string. */
2063 ASSERT_PRINT_ESCAPED_STRING_STREQ ("\"hello world\"", "hello world");
2065 /* Various things that need to be escaped: */
2067 ASSERT_PRINT_ESCAPED_STRING_STREQ ("\"before\\\\after\"",
2070 ASSERT_PRINT_ESCAPED_STRING_STREQ ("\"before\\tafter\"",
2073 ASSERT_PRINT_ESCAPED_STRING_STREQ ("\"before\\nafter\"",
2076 ASSERT_PRINT_ESCAPED_STRING_STREQ ("\"before\\\"after\"",
2079 /* Non-printable characters: BEL: '\a': 0x07 */
2080 ASSERT_PRINT_ESCAPED_STRING_STREQ ("\"before\\007after\"",
2082 /* Non-printable characters: vertical tab: '\v': 0x0b */
2083 ASSERT_PRINT_ESCAPED_STRING_STREQ ("\"before\\013after\"",
2087 /* Tests of print_parseable_fixits. */
2089 /* Verify that print_parseable_fixits emits the empty string if there
2093 test_print_parseable_fixits_none ()
2096 rich_location
richloc (line_table
, UNKNOWN_LOCATION
);
2098 print_parseable_fixits (&pp
, &richloc
, DIAGNOSTICS_COLUMN_UNIT_BYTE
, 8);
2099 ASSERT_STREQ ("", pp_formatted_text (&pp
));
2102 /* Verify that print_parseable_fixits does the right thing if there
2103 is an insertion fixit hint. */
2106 test_print_parseable_fixits_insert ()
2109 rich_location
richloc (line_table
, UNKNOWN_LOCATION
);
2111 linemap_add (line_table
, LC_ENTER
, false, "test.c", 0);
2112 linemap_line_start (line_table
, 5, 100);
2113 linemap_add (line_table
, LC_LEAVE
, false, NULL
, 0);
2114 location_t where
= linemap_position_for_column (line_table
, 10);
2115 richloc
.add_fixit_insert_before (where
, "added content");
2117 print_parseable_fixits (&pp
, &richloc
, DIAGNOSTICS_COLUMN_UNIT_BYTE
, 8);
2118 ASSERT_STREQ ("fix-it:\"test.c\":{5:10-5:10}:\"added content\"\n",
2119 pp_formatted_text (&pp
));
2122 /* Verify that print_parseable_fixits does the right thing if there
2123 is an removal fixit hint. */
2126 test_print_parseable_fixits_remove ()
2129 rich_location
richloc (line_table
, UNKNOWN_LOCATION
);
2131 linemap_add (line_table
, LC_ENTER
, false, "test.c", 0);
2132 linemap_line_start (line_table
, 5, 100);
2133 linemap_add (line_table
, LC_LEAVE
, false, NULL
, 0);
2135 where
.m_start
= linemap_position_for_column (line_table
, 10);
2136 where
.m_finish
= linemap_position_for_column (line_table
, 20);
2137 richloc
.add_fixit_remove (where
);
2139 print_parseable_fixits (&pp
, &richloc
, DIAGNOSTICS_COLUMN_UNIT_BYTE
, 8);
2140 ASSERT_STREQ ("fix-it:\"test.c\":{5:10-5:21}:\"\"\n",
2141 pp_formatted_text (&pp
));
2144 /* Verify that print_parseable_fixits does the right thing if there
2145 is an replacement fixit hint. */
2148 test_print_parseable_fixits_replace ()
2151 rich_location
richloc (line_table
, UNKNOWN_LOCATION
);
2153 linemap_add (line_table
, LC_ENTER
, false, "test.c", 0);
2154 linemap_line_start (line_table
, 5, 100);
2155 linemap_add (line_table
, LC_LEAVE
, false, NULL
, 0);
2157 where
.m_start
= linemap_position_for_column (line_table
, 10);
2158 where
.m_finish
= linemap_position_for_column (line_table
, 20);
2159 richloc
.add_fixit_replace (where
, "replacement");
2161 print_parseable_fixits (&pp
, &richloc
, DIAGNOSTICS_COLUMN_UNIT_BYTE
, 8);
2162 ASSERT_STREQ ("fix-it:\"test.c\":{5:10-5:21}:\"replacement\"\n",
2163 pp_formatted_text (&pp
));
2166 /* Verify that print_parseable_fixits correctly handles
2167 DIAGNOSTICS_COLUMN_UNIT_BYTE vs DIAGNOSTICS_COLUMN_UNIT_COLUMN. */
2170 test_print_parseable_fixits_bytes_vs_display_columns ()
2172 line_table_test ltt
;
2173 rich_location
richloc (line_table
, UNKNOWN_LOCATION
);
2175 /* 1-based byte offsets: 12345677778888999900001234567. */
2176 const char *const content
= "smile \xf0\x9f\x98\x82 colour\n";
2177 /* 1-based display cols: 123456[......7-8.....]9012345. */
2178 const int tabstop
= 8;
2180 temp_source_file
tmp (SELFTEST_LOCATION
, ".c", content
);
2181 const char *const fname
= tmp
.get_filename ();
2183 linemap_add (line_table
, LC_ENTER
, false, fname
, 0);
2184 linemap_line_start (line_table
, 1, 100);
2185 linemap_add (line_table
, LC_LEAVE
, false, NULL
, 0);
2187 where
.m_start
= linemap_position_for_column (line_table
, 12);
2188 where
.m_finish
= linemap_position_for_column (line_table
, 17);
2189 richloc
.add_fixit_replace (where
, "color");
2192 pretty_printer tmp_pp
;
2193 print_escaped_string (&tmp_pp
, fname
);
2194 char *escaped_fname
= xstrdup (pp_formatted_text (&tmp_pp
));
2196 const int buf_len
= strlen (escaped_fname
) + 100;
2197 char *const expected
= XNEWVEC (char, buf_len
);
2201 print_parseable_fixits (&pp
, &richloc
, DIAGNOSTICS_COLUMN_UNIT_BYTE
,
2203 snprintf (expected
, buf_len
,
2204 "fix-it:%s:{1:12-1:18}:\"color\"\n", escaped_fname
);
2205 ASSERT_STREQ (expected
, pp_formatted_text (&pp
));
2209 print_parseable_fixits (&pp
, &richloc
, DIAGNOSTICS_COLUMN_UNIT_DISPLAY
,
2211 snprintf (expected
, buf_len
,
2212 "fix-it:%s:{1:10-1:16}:\"color\"\n", escaped_fname
);
2213 ASSERT_STREQ (expected
, pp_formatted_text (&pp
));
2216 XDELETEVEC (expected
);
2217 free (escaped_fname
);
2221 diagnostic_get_location_text (..., SHOW_COLUMN)
2222 generates EXPECTED_LOC_TEXT, given FILENAME, LINE, COLUMN, with
2223 colorization disabled. */
2226 assert_location_text (const char *expected_loc_text
,
2227 const char *filename
, int line
, int column
,
2230 enum diagnostics_column_unit column_unit
2231 = DIAGNOSTICS_COLUMN_UNIT_BYTE
)
2233 test_diagnostic_context dc
;
2234 dc
.show_column
= show_column
;
2235 dc
.column_unit
= column_unit
;
2236 dc
.column_origin
= origin
;
2238 expanded_location xloc
;
2239 xloc
.file
= filename
;
2241 xloc
.column
= column
;
2245 char *actual_loc_text
= diagnostic_get_location_text (&dc
, xloc
);
2246 ASSERT_STREQ (expected_loc_text
, actual_loc_text
);
2247 free (actual_loc_text
);
2250 /* Verify that diagnostic_get_location_text works as expected. */
2253 test_diagnostic_get_location_text ()
2255 const char *old_progname
= progname
;
2256 progname
= "PROGNAME";
2257 assert_location_text ("PROGNAME:", NULL
, 0, 0, true);
2258 assert_location_text ("<built-in>:", "<built-in>", 42, 10, true);
2259 assert_location_text ("foo.c:42:10:", "foo.c", 42, 10, true);
2260 assert_location_text ("foo.c:42:9:", "foo.c", 42, 10, true, 0);
2261 assert_location_text ("foo.c:42:1010:", "foo.c", 42, 10, true, 1001);
2262 for (int origin
= 0; origin
!= 2; ++origin
)
2263 assert_location_text ("foo.c:42:", "foo.c", 42, 0, true, origin
);
2264 assert_location_text ("foo.c:", "foo.c", 0, 10, true);
2265 assert_location_text ("foo.c:42:", "foo.c", 42, 10, false);
2266 assert_location_text ("foo.c:", "foo.c", 0, 10, false);
2268 maybe_line_and_column (INT_MAX
, INT_MAX
);
2269 maybe_line_and_column (INT_MIN
, INT_MIN
);
2272 /* In order to test display columns vs byte columns, we need to create a
2273 file for location_get_source_line() to read. */
2275 const char *const content
= "smile \xf0\x9f\x98\x82\n";
2276 const int line_bytes
= strlen (content
) - 1;
2277 const int def_tabstop
= 8;
2278 const int display_width
= cpp_display_width (content
, line_bytes
,
2280 ASSERT_EQ (line_bytes
- 2, display_width
);
2281 temp_source_file
tmp (SELFTEST_LOCATION
, ".c", content
);
2282 const char *const fname
= tmp
.get_filename ();
2283 const int buf_len
= strlen (fname
) + 16;
2284 char *const expected
= XNEWVEC (char, buf_len
);
2286 snprintf (expected
, buf_len
, "%s:1:%d:", fname
, line_bytes
);
2287 assert_location_text (expected
, fname
, 1, line_bytes
, true,
2288 1, DIAGNOSTICS_COLUMN_UNIT_BYTE
);
2290 snprintf (expected
, buf_len
, "%s:1:%d:", fname
, line_bytes
- 1);
2291 assert_location_text (expected
, fname
, 1, line_bytes
, true,
2292 0, DIAGNOSTICS_COLUMN_UNIT_BYTE
);
2294 snprintf (expected
, buf_len
, "%s:1:%d:", fname
, display_width
);
2295 assert_location_text (expected
, fname
, 1, line_bytes
, true,
2296 1, DIAGNOSTICS_COLUMN_UNIT_DISPLAY
);
2298 snprintf (expected
, buf_len
, "%s:1:%d:", fname
, display_width
- 1);
2299 assert_location_text (expected
, fname
, 1, line_bytes
, true,
2300 0, DIAGNOSTICS_COLUMN_UNIT_DISPLAY
);
2302 XDELETEVEC (expected
);
2306 progname
= old_progname
;
2309 /* Selftest for num_digits. */
2314 ASSERT_EQ (1, num_digits (0));
2315 ASSERT_EQ (1, num_digits (9));
2316 ASSERT_EQ (2, num_digits (10));
2317 ASSERT_EQ (2, num_digits (99));
2318 ASSERT_EQ (3, num_digits (100));
2319 ASSERT_EQ (3, num_digits (999));
2320 ASSERT_EQ (4, num_digits (1000));
2321 ASSERT_EQ (4, num_digits (9999));
2322 ASSERT_EQ (5, num_digits (10000));
2323 ASSERT_EQ (5, num_digits (99999));
2324 ASSERT_EQ (6, num_digits (100000));
2325 ASSERT_EQ (6, num_digits (999999));
2326 ASSERT_EQ (7, num_digits (1000000));
2327 ASSERT_EQ (7, num_digits (9999999));
2328 ASSERT_EQ (8, num_digits (10000000));
2329 ASSERT_EQ (8, num_digits (99999999));
2332 /* Run all of the selftests within this file. */
2335 diagnostic_c_tests ()
2337 test_print_escaped_string ();
2338 test_print_parseable_fixits_none ();
2339 test_print_parseable_fixits_insert ();
2340 test_print_parseable_fixits_remove ();
2341 test_print_parseable_fixits_replace ();
2342 test_print_parseable_fixits_bytes_vs_display_columns ();
2343 test_diagnostic_get_location_text ();
2348 } // namespace selftest
2350 #endif /* #if CHECKING_P */
2353 # pragma GCC diagnostic pop