Bug Summary

File:build/gcc/fortran/error.c
Warning:line 755, column 3
Value stored to 'have_l1' is never read

Annotated Source Code

Press '?' to see keyboard shortcuts

clang -cc1 -cc1 -triple x86_64-unknown-linux-gnu -analyze -disable-free -disable-llvm-verifier -discard-value-names -main-file-name error.c -analyzer-store=region -analyzer-opt-analyze-nested-blocks -analyzer-checker=core -analyzer-checker=apiModeling -analyzer-checker=unix -analyzer-checker=deadcode -analyzer-checker=cplusplus -analyzer-checker=security.insecureAPI.UncheckedReturn -analyzer-checker=security.insecureAPI.getpw -analyzer-checker=security.insecureAPI.gets -analyzer-checker=security.insecureAPI.mktemp -analyzer-checker=security.insecureAPI.mkstemp -analyzer-checker=security.insecureAPI.vfork -analyzer-checker=nullability.NullPassedToNonnull -analyzer-checker=nullability.NullReturnedFromNonnull -analyzer-output plist -w -setup-static-analyzer -analyzer-config-compatibility-mode=true -mrelocation-model static -mframe-pointer=none -fmath-errno -fno-rounding-math -mconstructor-aliases -munwind-tables -target-cpu x86-64 -tune-cpu generic -debugger-tuning=gdb -fcoverage-compilation-dir=/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/objdir/gcc -resource-dir /usr/lib64/clang/13.0.0 -D IN_GCC_FRONTEND -D IN_GCC -D HAVE_CONFIG_H -I . -I fortran -I /home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc -I /home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran -I /home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/../include -I /home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/../libcpp/include -I /home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/../libcody -I /home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/../libdecnumber -I /home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/../libdecnumber/bid -I ../libdecnumber -I /home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/../libbacktrace -internal-isystem /usr/bin/../lib64/gcc/x86_64-suse-linux/11/../../../../include/c++/11 -internal-isystem /usr/bin/../lib64/gcc/x86_64-suse-linux/11/../../../../include/c++/11/x86_64-suse-linux -internal-isystem /usr/bin/../lib64/gcc/x86_64-suse-linux/11/../../../../include/c++/11/backward -internal-isystem /usr/lib64/clang/13.0.0/include -internal-isystem /usr/local/include -internal-isystem /usr/bin/../lib64/gcc/x86_64-suse-linux/11/../../../../x86_64-suse-linux/include -internal-externc-isystem /include -internal-externc-isystem /usr/include -O2 -Wno-narrowing -Wwrite-strings -Wno-error=format-diag -Wno-long-long -Wno-variadic-macros -Wno-overlength-strings -fdeprecated-macro -fdebug-compilation-dir=/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/objdir/gcc -ferror-limit 19 -fno-rtti -fgnuc-version=4.2.1 -vectorize-loops -vectorize-slp -analyzer-output=plist-html -analyzer-config silence-checkers=core.NullDereference -faddrsig -D__GCC_HAVE_DWARF2_CFI_ASM=1 -o /home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/objdir/clang-static-analyzer/2021-11-20-133755-20252-1/report-gXry6Y.plist -x c++ /home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c
1/* Handle errors.
2 Copyright (C) 2000-2021 Free Software Foundation, Inc.
3 Contributed by Andy Vaught & Niels Kristian Bech Jensen
4
5This file is part of GCC.
6
7GCC is free software; you can redistribute it and/or modify it under
8the terms of the GNU General Public License as published by the Free
9Software Foundation; either version 3, or (at your option) any later
10version.
11
12GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13WARRANTY; without even the implied warranty of MERCHANTABILITY or
14FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15for more details.
16
17You should have received a copy of the GNU General Public License
18along with GCC; see the file COPYING3. If not see
19<http://www.gnu.org/licenses/>. */
20
21/* Handle the inevitable errors. A major catch here is that things
22 flagged as errors in one match subroutine can conceivably be legal
23 elsewhere. This means that error messages are recorded and saved
24 for possible use later. If a line does not match a legal
25 construction, then the saved error message is reported. */
26
27#include "config.h"
28#include "system.h"
29#include "coretypes.h"
30#include "options.h"
31#include "gfortran.h"
32
33#include "diagnostic.h"
34#include "diagnostic-color.h"
35#include "tree-diagnostic.h" /* tree_diagnostics_defaults */
36
37static int suppress_errors = 0;
38
39static bool warnings_not_errors = false;
40
41static int terminal_width;
42
43/* True if the error/warnings should be buffered. */
44static bool buffered_p;
45
46static gfc_error_buffer error_buffer;
47/* These are always buffered buffers (.flush_p == false) to be used by
48 the pretty-printer. */
49static output_buffer *pp_error_buffer, *pp_warning_buffer;
50static int warningcount_buffered, werrorcount_buffered;
51
52/* Return true if there output_buffer is empty. */
53
54static bool
55gfc_output_buffer_empty_p (const output_buffer * buf)
56{
57 return output_buffer_last_position_in_text (buf) == NULL__null;
58}
59
60/* Go one level deeper suppressing errors. */
61
62void
63gfc_push_suppress_errors (void)
64{
65 gcc_assert (suppress_errors >= 0)((void)(!(suppress_errors >= 0) ? fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 65, __FUNCTION__), 0 : 0))
;
66 ++suppress_errors;
67}
68
69static void
70gfc_error_opt (int opt, const char *gmsgid, va_list ap) ATTRIBUTE_GCC_GFC(2,0)__attribute__ ((__format__ (__gcc_gfc__, 2, 0))) __attribute__
((__nonnull__ (2)))
;
71
72static bool
73gfc_warning (int opt, const char *gmsgid, va_list ap) ATTRIBUTE_GCC_GFC(2,0)__attribute__ ((__format__ (__gcc_gfc__, 2, 0))) __attribute__
((__nonnull__ (2)))
;
74
75
76/* Leave one level of error suppressing. */
77
78void
79gfc_pop_suppress_errors (void)
80{
81 gcc_assert (suppress_errors > 0)((void)(!(suppress_errors > 0) ? fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 81, __FUNCTION__), 0 : 0))
;
82 --suppress_errors;
83}
84
85
86/* Determine terminal width (for trimming source lines in output). */
87
88static int
89gfc_get_terminal_width (void)
90{
91 return isatty (STDERR_FILENO2) ? get_terminal_width () : INT_MAX2147483647;
92}
93
94
95/* Per-file error initialization. */
96
97void
98gfc_error_init_1 (void)
99{
100 terminal_width = gfc_get_terminal_width ();
101 gfc_buffer_error (false);
102}
103
104
105/* Set the flag for buffering errors or not. */
106
107void
108gfc_buffer_error (bool flag)
109{
110 buffered_p = flag;
111}
112
113
114/* Add a single character to the error buffer or output depending on
115 buffered_p. */
116
117static void
118error_char (char)
119{
120 /* FIXME: Unused function to be removed in a subsequent patch. */
121}
122
123
124/* Copy a string to wherever it needs to go. */
125
126static void
127error_string (const char *p)
128{
129 while (*p)
130 error_char (*p++);
131}
132
133
134/* Print a formatted integer to the error buffer or output. */
135
136#define IBUF_LEN60 60
137
138static void
139error_uinteger (unsigned long long int i)
140{
141 char *p, int_buf[IBUF_LEN60];
142
143 p = int_buf + IBUF_LEN60 - 1;
144 *p-- = '\0';
145
146 if (i == 0)
147 *p-- = '0';
148
149 while (i > 0)
150 {
151 *p-- = i % 10 + '0';
152 i = i / 10;
153 }
154
155 error_string (p + 1);
156}
157
158static void
159error_integer (long long int i)
160{
161 unsigned long long int u;
162
163 if (i < 0)
164 {
165 u = (unsigned long long int) -i;
166 error_char ('-');
167 }
168 else
169 u = i;
170
171 error_uinteger (u);
172}
173
174
175static void
176error_hwuint (unsigned HOST_WIDE_INTlong i)
177{
178 char *p, int_buf[IBUF_LEN60];
179
180 p = int_buf + IBUF_LEN60 - 1;
181 *p-- = '\0';
182
183 if (i == 0)
184 *p-- = '0';
185
186 while (i > 0)
187 {
188 *p-- = i % 10 + '0';
189 i = i / 10;
190 }
191
192 error_string (p + 1);
193}
194
195static void
196error_hwint (HOST_WIDE_INTlong i)
197{
198 unsigned HOST_WIDE_INTlong u;
199
200 if (i < 0)
201 {
202 u = (unsigned HOST_WIDE_INTlong) -i;
203 error_char ('-');
204 }
205 else
206 u = i;
207
208 error_uinteger (u);
209}
210
211
212static size_t
213gfc_widechar_display_length (gfc_char_t c)
214{
215 if (gfc_wide_is_printable (c) || c == '\t')
216 /* Printable ASCII character, or tabulation (output as a space). */
217 return 1;
218 else if (c < ((gfc_char_t) 1 << 8))
219 /* Displayed as \x?? */
220 return 4;
221 else if (c < ((gfc_char_t) 1 << 16))
222 /* Displayed as \u???? */
223 return 6;
224 else
225 /* Displayed as \U???????? */
226 return 10;
227}
228
229
230/* Length of the ASCII representation of the wide string, escaping wide
231 characters as print_wide_char_into_buffer() does. */
232
233static size_t
234gfc_wide_display_length (const gfc_char_t *str)
235{
236 size_t i, len;
237
238 for (i = 0, len = 0; str[i]; i++)
239 len += gfc_widechar_display_length (str[i]);
240
241 return len;
242}
243
244static int
245print_wide_char_into_buffer (gfc_char_t c, char *buf)
246{
247 static const char xdigit[16] = { '0', '1', '2', '3', '4', '5', '6',
248 '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' };
249
250 if (gfc_wide_is_printable (c) || c == '\t')
251 {
252 buf[1] = '\0';
253 /* Tabulation is output as a space. */
254 buf[0] = (unsigned char) (c == '\t' ? ' ' : c);
255 return 1;
256 }
257 else if (c < ((gfc_char_t) 1 << 8))
258 {
259 buf[4] = '\0';
260 buf[3] = xdigit[c & 0x0F];
261 c = c >> 4;
262 buf[2] = xdigit[c & 0x0F];
263
264 buf[1] = 'x';
265 buf[0] = '\\';
266 return 4;
267 }
268 else if (c < ((gfc_char_t) 1 << 16))
269 {
270 buf[6] = '\0';
271 buf[5] = xdigit[c & 0x0F];
272 c = c >> 4;
273 buf[4] = xdigit[c & 0x0F];
274 c = c >> 4;
275 buf[3] = xdigit[c & 0x0F];
276 c = c >> 4;
277 buf[2] = xdigit[c & 0x0F];
278
279 buf[1] = 'u';
280 buf[0] = '\\';
281 return 6;
282 }
283 else
284 {
285 buf[10] = '\0';
286 buf[9] = xdigit[c & 0x0F];
287 c = c >> 4;
288 buf[8] = xdigit[c & 0x0F];
289 c = c >> 4;
290 buf[7] = xdigit[c & 0x0F];
291 c = c >> 4;
292 buf[6] = xdigit[c & 0x0F];
293 c = c >> 4;
294 buf[5] = xdigit[c & 0x0F];
295 c = c >> 4;
296 buf[4] = xdigit[c & 0x0F];
297 c = c >> 4;
298 buf[3] = xdigit[c & 0x0F];
299 c = c >> 4;
300 buf[2] = xdigit[c & 0x0F];
301
302 buf[1] = 'U';
303 buf[0] = '\\';
304 return 10;
305 }
306}
307
308static char wide_char_print_buffer[11];
309
310const char *
311gfc_print_wide_char (gfc_char_t c)
312{
313 print_wide_char_into_buffer (c, wide_char_print_buffer);
314 return wide_char_print_buffer;
315}
316
317
318/* Show the file, where it was included, and the source line, give a
319 locus. Calls error_printf() recursively, but the recursion is at
320 most one level deep. */
321
322static void error_printf (const char *, ...) ATTRIBUTE_GCC_GFC(1,2)__attribute__ ((__format__ (__gcc_gfc__, 1, 2))) __attribute__
((__nonnull__ (1)))
;
323
324static void
325show_locus (locus *loc, int c1, int c2)
326{
327 gfc_linebuf *lb;
328 gfc_file *f;
329 gfc_char_t *p;
330 int i, offset, cmax;
331
332 /* TODO: Either limit the total length and number of included files
333 displayed or add buffering of arbitrary number of characters in
334 error messages. */
335
336 /* Write out the error header line, giving the source file and error
337 location (in GNU standard "[file]:[line].[column]:" format),
338 followed by an "included by" stack and a blank line. This header
339 format is matched by a testsuite parser defined in
340 lib/gfortran-dg.exp. */
341
342 lb = loc->lb;
343 f = lb->file;
344
345 error_string (f->filename);
346 error_char (':');
347
348 error_integer (LOCATION_LINE (lb->location)((expand_location (lb->location)).line));
349
350 if ((c1 > 0) || (c2 > 0))
351 error_char ('.');
352
353 if (c1 > 0)
354 error_integer (c1);
355
356 if ((c1 > 0) && (c2 > 0))
357 error_char ('-');
358
359 if (c2 > 0)
360 error_integer (c2);
361
362 error_char (':');
363 error_char ('\n');
364
365 for (;;)
366 {
367 i = f->inclusion_line;
368
369 f = f->up;
370 if (f == NULL__null) break;
371
372 error_printf (" Included at %s:%d:", f->filename, i);
373 }
374
375 error_char ('\n');
376
377 /* Calculate an appropriate horizontal offset of the source line in
378 order to get the error locus within the visible portion of the
379 line. Note that if the margin of 5 here is changed, the
380 corresponding margin of 10 in show_loci should be changed. */
381
382 offset = 0;
383
384 /* If the two loci would appear in the same column, we shift
385 '2' one column to the right, so as to print '12' rather than
386 just '1'. We do this here so it will be accounted for in the
387 margin calculations. */
388
389 if (c1 == c2)
390 c2 += 1;
391
392 cmax = (c1 < c2) ? c2 : c1;
393 if (cmax > terminal_width - 5)
394 offset = cmax - terminal_width + 5;
395
396 /* Show the line itself, taking care not to print more than what can
397 show up on the terminal. Tabs are converted to spaces, and
398 nonprintable characters are converted to a "\xNN" sequence. */
399
400 p = &(lb->line[offset]);
401 i = gfc_wide_display_length (p);
402 if (i > terminal_width)
403 i = terminal_width - 1;
404
405 while (i > 0)
406 {
407 static char buffer[11];
408 i -= print_wide_char_into_buffer (*p++, buffer);
409 error_string (buffer);
410 }
411
412 error_char ('\n');
413
414 /* Show the '1' and/or '2' corresponding to the column of the error
415 locus. Note that a value of -1 for c1 or c2 will simply cause
416 the relevant number not to be printed. */
417
418 c1 -= offset;
419 c2 -= offset;
420 cmax -= offset;
421
422 p = &(lb->line[offset]);
423 for (i = 0; i < cmax; i++)
424 {
425 int spaces, j;
426 spaces = gfc_widechar_display_length (*p++);
427
428 if (i == c1)
429 error_char ('1'), spaces--;
430 else if (i == c2)
431 error_char ('2'), spaces--;
432
433 for (j = 0; j < spaces; j++)
434 error_char (' ');
435 }
436
437 if (i == c1)
438 error_char ('1');
439 else if (i == c2)
440 error_char ('2');
441
442 error_char ('\n');
443
444}
445
446
447/* As part of printing an error, we show the source lines that caused
448 the problem. We show at least one, and possibly two loci; the two
449 loci may or may not be on the same source line. */
450
451static void
452show_loci (locus *l1, locus *l2)
453{
454 int m, c1, c2;
455
456 if (l1 == NULL__null || l1->lb == NULL__null)
457 {
458 error_printf ("<During initialization>\n");
459 return;
460 }
461
462 /* While calculating parameters for printing the loci, we consider possible
463 reasons for printing one per line. If appropriate, print the loci
464 individually; otherwise we print them both on the same line. */
465
466 c1 = l1->nextc - l1->lb->line;
467 if (l2 == NULL__null)
468 {
469 show_locus (l1, c1, -1);
470 return;
471 }
472
473 c2 = l2->nextc - l2->lb->line;
474
475 if (c1 < c2)
476 m = c2 - c1;
477 else
478 m = c1 - c2;
479
480 /* Note that the margin value of 10 here needs to be less than the
481 margin of 5 used in the calculation of offset in show_locus. */
482
483 if (l1->lb != l2->lb || m > terminal_width - 10)
484 {
485 show_locus (l1, c1, -1);
486 show_locus (l2, -1, c2);
487 return;
488 }
489
490 show_locus (l1, c1, c2);
491
492 return;
493}
494
495
496/* Workhorse for the error printing subroutines. This subroutine is
497 inspired by g77's error handling and is similar to printf() with
498 the following %-codes:
499
500 %c Character, %d or %i Integer, %s String, %% Percent
501 %L Takes locus argument
502 %C Current locus (no argument)
503
504 If a locus pointer is given, the actual source line is printed out
505 and the column is indicated. Since we want the error message at
506 the bottom of any source file information, we must scan the
507 argument list twice -- once to determine whether the loci are
508 present and record this for printing, and once to print the error
509 message after and loci have been printed. A maximum of two locus
510 arguments are permitted.
511
512 This function is also called (recursively) by show_locus in the
513 case of included files; however, as show_locus does not resupply
514 any loci, the recursion is at most one level deep. */
515
516#define MAX_ARGS10 10
517
518static void ATTRIBUTE_GCC_GFC(2,0)__attribute__ ((__format__ (__gcc_gfc__, 2, 0))) __attribute__
((__nonnull__ (2)))
519error_print (const char *type, const char *format0, va_list argp)
520{
521 enum { TYPE_CURRENTLOC, TYPE_LOCUS, TYPE_INTEGER, TYPE_UINTEGER,
522 TYPE_LONGINT, TYPE_ULONGINT, TYPE_LLONGINT, TYPE_ULLONGINT,
523 TYPE_HWINT, TYPE_HWUINT, TYPE_CHAR, TYPE_STRING, NOTYPE };
524 struct
525 {
526 int type;
527 int pos;
528 union
529 {
530 int intval;
531 unsigned int uintval;
532 long int longintval;
533 unsigned long int ulongintval;
534 long long int llongintval;
535 unsigned long long int ullongintval;
536 HOST_WIDE_INTlong hwintval;
537 unsigned HOST_WIDE_INTlong hwuintval;
538 char charval;
539 const char * stringval;
540 } u;
541 } arg[MAX_ARGS10], spec[MAX_ARGS10];
542 /* spec is the array of specifiers, in the same order as they
543 appear in the format string. arg is the array of arguments,
544 in the same order as they appear in the va_list. */
545
546 char c;
547 int i, n, have_l1, pos, maxpos;
548 locus *l1, *l2, *loc;
549 const char *format;
550
551 loc = l1 = l2 = NULL__null;
552
553 have_l1 = 0;
554 pos = -1;
555 maxpos = -1;
556
557 n = 0;
558 format = format0;
559
560 for (i = 0; i < MAX_ARGS10; i++)
561 {
562 arg[i].type = NOTYPE;
563 spec[i].pos = -1;
564 }
565
566 /* First parse the format string for position specifiers. */
567 while (*format)
568 {
569 c = *format++;
570 if (c != '%')
571 continue;
572
573 if (*format == '%')
574 {
575 format++;
576 continue;
577 }
578
579 if (ISDIGIT (*format)(_sch_istable[(*format) & 0xff] & (unsigned short)(_sch_isdigit
))
)
580 {
581 /* This is a position specifier. For example, the number
582 12 in the format string "%12$d", which specifies the third
583 argument of the va_list, formatted in %d format.
584 For details, see "man 3 printf". */
585 pos = atoi(format) - 1;
586 gcc_assert (pos >= 0)((void)(!(pos >= 0) ? fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 586, __FUNCTION__), 0 : 0))
;
587 while (ISDIGIT(*format)(_sch_istable[(*format) & 0xff] & (unsigned short)(_sch_isdigit
))
)
588 format++;
589 gcc_assert (*format == '$')((void)(!(*format == '$') ? fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 589, __FUNCTION__), 0 : 0))
;
590 format++;
591 }
592 else
593 pos++;
594
595 c = *format++;
596
597 if (pos > maxpos)
598 maxpos = pos;
599
600 switch (c)
601 {
602 case 'C':
603 arg[pos].type = TYPE_CURRENTLOC;
604 break;
605
606 case 'L':
607 arg[pos].type = TYPE_LOCUS;
608 break;
609
610 case 'd':
611 case 'i':
612 arg[pos].type = TYPE_INTEGER;
613 break;
614
615 case 'u':
616 arg[pos].type = TYPE_UINTEGER;
617 break;
618
619 case 'l':
620 c = *format++;
621 if (c == 'l')
622 {
623 c = *format++;
624 if (c == 'u')
625 arg[pos].type = TYPE_ULLONGINT;
626 else if (c == 'i' || c == 'd')
627 arg[pos].type = TYPE_LLONGINT;
628 else
629 gcc_unreachable ()(fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 629, __FUNCTION__))
;
630 }
631 else if (c == 'u')
632 arg[pos].type = TYPE_ULONGINT;
633 else if (c == 'i' || c == 'd')
634 arg[pos].type = TYPE_LONGINT;
635 else
636 gcc_unreachable ()(fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 636, __FUNCTION__))
;
637 break;
638
639 case 'w':
640 c = *format++;
641 if (c == 'u')
642 arg[pos].type = TYPE_HWUINT;
643 else if (c == 'i' || c == 'd')
644 arg[pos].type = TYPE_HWINT;
645 else
646 gcc_unreachable ()(fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 646, __FUNCTION__))
;
647 break;
648
649 case 'c':
650 arg[pos].type = TYPE_CHAR;
651 break;
652
653 case 's':
654 arg[pos].type = TYPE_STRING;
655 break;
656
657 default:
658 gcc_unreachable ()(fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 658, __FUNCTION__))
;
659 }
660
661 spec[n++].pos = pos;
662 }
663
664 /* Then convert the values for each %-style argument. */
665 for (pos = 0; pos <= maxpos; pos++)
666 {
667 gcc_assert (arg[pos].type != NOTYPE)((void)(!(arg[pos].type != NOTYPE) ? fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 667, __FUNCTION__), 0 : 0))
;
668 switch (arg[pos].type)
669 {
670 case TYPE_CURRENTLOC:
671 loc = &gfc_current_locus;
672 /* Fall through. */
673
674 case TYPE_LOCUS:
675 if (arg[pos].type == TYPE_LOCUS)
676 loc = va_arg (argp, locus *)__builtin_va_arg(argp, locus *);
677
678 if (have_l1)
679 {
680 l2 = loc;
681 arg[pos].u.stringval = "(2)";
682 /* Point %C first offending character not the last good one. */
683 if (arg[pos].type == TYPE_CURRENTLOC && *l2->nextc != '\0')
684 l2->nextc++;
685 }
686 else
687 {
688 l1 = loc;
689 have_l1 = 1;
690 arg[pos].u.stringval = "(1)";
691 /* Point %C first offending character not the last good one. */
692 if (arg[pos].type == TYPE_CURRENTLOC && *l1->nextc != '\0')
693 l1->nextc++;
694 }
695 break;
696
697 case TYPE_INTEGER:
698 arg[pos].u.intval = va_arg (argp, int)__builtin_va_arg(argp, int);
699 break;
700
701 case TYPE_UINTEGER:
702 arg[pos].u.uintval = va_arg (argp, unsigned int)__builtin_va_arg(argp, unsigned int);
703 break;
704
705 case TYPE_LONGINT:
706 arg[pos].u.longintval = va_arg (argp, long int)__builtin_va_arg(argp, long int);
707 break;
708
709 case TYPE_ULONGINT:
710 arg[pos].u.ulongintval = va_arg (argp, unsigned long int)__builtin_va_arg(argp, unsigned long int);
711 break;
712
713 case TYPE_LLONGINT:
714 arg[pos].u.llongintval = va_arg (argp, long long int)__builtin_va_arg(argp, long long int);
715 break;
716
717 case TYPE_ULLONGINT:
718 arg[pos].u.ullongintval = va_arg (argp, unsigned long long int)__builtin_va_arg(argp, unsigned long long int);
719 break;
720
721 case TYPE_HWINT:
722 arg[pos].u.hwintval = va_arg (argp, HOST_WIDE_INT)__builtin_va_arg(argp, long);
723 break;
724
725 case TYPE_HWUINT:
726 arg[pos].u.hwuintval = va_arg (argp, unsigned HOST_WIDE_INT)__builtin_va_arg(argp, unsigned long);
727 break;
728
729 case TYPE_CHAR:
730 arg[pos].u.charval = (char) va_arg (argp, int)__builtin_va_arg(argp, int);
731 break;
732
733 case TYPE_STRING:
734 arg[pos].u.stringval = (const char *) va_arg (argp, char *)__builtin_va_arg(argp, char *);
735 break;
736
737 default:
738 gcc_unreachable ()(fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 738, __FUNCTION__))
;
739 }
740 }
741
742 for (n = 0; spec[n].pos >= 0; n++)
743 spec[n].u = arg[spec[n].pos].u;
744
745 /* Show the current loci if we have to. */
746 if (have_l1)
747 show_loci (l1, l2);
748
749 if (*type)
750 {
751 error_string (type);
752 error_char (' ');
753 }
754
755 have_l1 = 0;
Value stored to 'have_l1' is never read
756 format = format0;
757 n = 0;
758
759 for (; *format; format++)
760 {
761 if (*format != '%')
762 {
763 error_char (*format);
764 continue;
765 }
766
767 format++;
768 if (ISDIGIT (*format)(_sch_istable[(*format) & 0xff] & (unsigned short)(_sch_isdigit
))
)
769 {
770 /* This is a position specifier. See comment above. */
771 while (ISDIGIT (*format)(_sch_istable[(*format) & 0xff] & (unsigned short)(_sch_isdigit
))
)
772 format++;
773
774 /* Skip over the dollar sign. */
775 format++;
776 }
777
778 switch (*format)
779 {
780 case '%':
781 error_char ('%');
782 break;
783
784 case 'c':
785 error_char (spec[n++].u.charval);
786 break;
787
788 case 's':
789 case 'C': /* Current locus */
790 case 'L': /* Specified locus */
791 error_string (spec[n++].u.stringval);
792 break;
793
794 case 'd':
795 case 'i':
796 error_integer (spec[n++].u.intval);
797 break;
798
799 case 'u':
800 error_uinteger (spec[n++].u.uintval);
801 break;
802
803 case 'l':
804 format++;
805 if (*format == 'l')
806 {
807 format++;
808 if (*format == 'u')
809 error_uinteger (spec[n++].u.ullongintval);
810 else
811 error_integer (spec[n++].u.llongintval);
812 }
813 if (*format == 'u')
814 error_uinteger (spec[n++].u.ulongintval);
815 else
816 error_integer (spec[n++].u.longintval);
817 break;
818
819 case 'w':
820 format++;
821 if (*format == 'u')
822 error_hwuint (spec[n++].u.hwintval);
823 else
824 error_hwint (spec[n++].u.hwuintval);
825 break;
826 }
827 }
828
829 error_char ('\n');
830}
831
832
833/* Wrapper for error_print(). */
834
835static void
836error_printf (const char *gmsgid, ...)
837{
838 va_list argp;
839
840 va_start (argp, gmsgid)__builtin_va_start(argp, gmsgid);
841 error_print ("", _(gmsgid)gettext (gmsgid), argp);
842 va_end (argp)__builtin_va_end(argp);
843}
844
845
846/* Clear any output buffered in a pretty-print output_buffer. */
847
848static void
849gfc_clear_pp_buffer (output_buffer *this_buffer)
850{
851 pretty_printer *pp = global_dc->printer;
852 output_buffer *tmp_buffer = pp->buffer;
853 pp->buffer = this_buffer;
854 pp_clear_output_area (pp);
855 pp->buffer = tmp_buffer;
856 /* We need to reset last_location, otherwise we may skip caret lines
857 when we actually give a diagnostic. */
858 global_dc->last_location = UNKNOWN_LOCATION((location_t) 0);
859}
860
861/* The currently-printing diagnostic, for use by gfc_format_decoder,
862 for colorizing %C and %L. */
863
864static diagnostic_info *curr_diagnostic;
865
866/* A helper function to call diagnostic_report_diagnostic, while setting
867 curr_diagnostic for the duration of the call. */
868
869static bool
870gfc_report_diagnostic (diagnostic_info *diagnostic)
871{
872 gcc_assert (diagnostic != NULL)((void)(!(diagnostic != __null) ? fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 872, __FUNCTION__), 0 : 0))
;
873 curr_diagnostic = diagnostic;
874 bool ret = diagnostic_report_diagnostic (global_dc, diagnostic);
875 curr_diagnostic = NULL__null;
876 return ret;
877}
878
879/* This is just a helper function to avoid duplicating the logic of
880 gfc_warning. */
881
882static bool
883gfc_warning (int opt, const char *gmsgid, va_list ap)
884{
885 va_list argp;
886 va_copy (argp, ap)__builtin_va_copy(argp, ap);
887
888 diagnostic_info diagnostic;
889 rich_location rich_loc (line_table, UNKNOWN_LOCATION((location_t) 0));
890 bool fatal_errors = global_dc->fatal_errors;
891 pretty_printer *pp = global_dc->printer;
892 output_buffer *tmp_buffer = pp->buffer;
893
894 gfc_clear_pp_buffer (pp_warning_buffer);
895
896 if (buffered_p)
897 {
898 pp->buffer = pp_warning_buffer;
899 global_dc->fatal_errors = false;
900 /* To prevent -fmax-errors= triggering. */
901 --werrorcount(global_dc)->diagnostic_count[(int) (DK_WERROR)];
902 }
903
904 diagnostic_set_info (&diagnostic, gmsgid, &argp, &rich_loc,
905 DK_WARNING);
906 diagnostic.option_index = opt;
907 bool ret = gfc_report_diagnostic (&diagnostic);
908
909 if (buffered_p)
910 {
911 pp->buffer = tmp_buffer;
912 global_dc->fatal_errors = fatal_errors;
913
914 warningcount_buffered = 0;
915 werrorcount_buffered = 0;
916 /* Undo the above --werrorcount if not Werror, otherwise
917 werrorcount is correct already. */
918 if (!ret)
919 ++werrorcount(global_dc)->diagnostic_count[(int) (DK_WERROR)];
920 else if (diagnostic.kind == DK_ERROR)
921 ++werrorcount_buffered;
922 else
923 ++werrorcount(global_dc)->diagnostic_count[(int) (DK_WERROR)], --warningcount(global_dc)->diagnostic_count[(int) (DK_WARNING)], ++warningcount_buffered;
924 }
925
926 va_end (argp)__builtin_va_end(argp);
927 return ret;
928}
929
930/* Issue a warning. */
931
932bool
933gfc_warning (int opt, const char *gmsgid, ...)
934{
935 va_list argp;
936
937 va_start (argp, gmsgid)__builtin_va_start(argp, gmsgid);
938 bool ret = gfc_warning (opt, gmsgid, argp);
939 va_end (argp)__builtin_va_end(argp);
940 return ret;
941}
942
943
944/* Whether, for a feature included in a given standard set (GFC_STD_*),
945 we should issue an error or a warning, or be quiet. */
946
947notification
948gfc_notification_std (int std)
949{
950 bool warning;
951
952 warning = ((gfc_option.warn_std & std) != 0) && !inhibit_warningsglobal_options.x_inhibit_warnings;
953 if ((gfc_option.allow_std & std) != 0 && !warning)
954 return SILENT;
955
956 return warning ? WARNING : ERROR;
957}
958
959
960/* Return a string describing the nature of a standard violation
961 * and/or the relevant version of the standard. */
962
963char const*
964notify_std_msg(int std)
965{
966
967 if (std & GFC_STD_F2018_DEL(1<<11))
968 return _("Fortran 2018 deleted feature:")gettext ("Fortran 2018 deleted feature:");
969 else if (std & GFC_STD_F2018_OBS(1<<10))
970 return _("Fortran 2018 obsolescent feature:")gettext ("Fortran 2018 obsolescent feature:");
971 else if (std & GFC_STD_F2018(1<<9))
972 return _("Fortran 2018:")gettext ("Fortran 2018:");
973 else if (std & GFC_STD_F2008_OBS(1<<8))
974 return _("Fortran 2008 obsolescent feature:")gettext ("Fortran 2008 obsolescent feature:");
975 else if (std & GFC_STD_F2008(1<<7))
976 return "Fortran 2008:";
977 else if (std & GFC_STD_F2003(1<<4))
978 return "Fortran 2003:";
979 else if (std & GFC_STD_GNU(1<<5))
980 return _("GNU Extension:")gettext ("GNU Extension:");
981 else if (std & GFC_STD_LEGACY(1<<6))
982 return _("Legacy Extension:")gettext ("Legacy Extension:");
983 else if (std & GFC_STD_F95_OBS(1<<1))
984 return _("Obsolescent feature:")gettext ("Obsolescent feature:");
985 else if (std & GFC_STD_F95_DEL(1<<2))
986 return _("Deleted feature:")gettext ("Deleted feature:");
987 else
988 gcc_unreachable ()(fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 988, __FUNCTION__))
;
989}
990
991
992/* Possibly issue a warning/error about use of a nonstandard (or deleted)
993 feature. An error/warning will be issued if the currently selected
994 standard does not contain the requested bits. Return false if
995 an error is generated. */
996
997bool
998gfc_notify_std (int std, const char *gmsgid, ...)
999{
1000 va_list argp;
1001 const char *msg, *msg2;
1002 char *buffer;
1003
1004 /* Determine whether an error or a warning is needed. */
1005 const int wstd = std & gfc_option.warn_std; /* Standard to warn about. */
1006 const int estd = std & ~gfc_option.allow_std; /* Standard to error about. */
1007 const bool warning = (wstd != 0) && !inhibit_warningsglobal_options.x_inhibit_warnings;
1008 const bool error = (estd != 0);
1009
1010 if (!error && !warning)
1011 return true;
1012 if (suppress_errors)
1013 return !error;
1014
1015 if (error)
1016 msg = notify_std_msg (estd);
1017 else
1018 msg = notify_std_msg (wstd);
1019
1020 msg2 = _(gmsgid)gettext (gmsgid);
1021 buffer = (char *) alloca (strlen (msg) + strlen (msg2) + 2)__builtin_alloca(strlen (msg) + strlen (msg2) + 2);
1022 strcpy (buffer, msg);
1023 strcat (buffer, " ");
1024 strcat (buffer, msg2);
1025
1026 va_start (argp, gmsgid)__builtin_va_start(argp, gmsgid);
1027 if (error)
1028 gfc_error_opt (0, buffer, argp);
1029 else
1030 gfc_warning (0, buffer, argp);
1031 va_end (argp)__builtin_va_end(argp);
1032
1033 if (error)
1034 return false;
1035 else
1036 return (warning && !warnings_are_errorsglobal_options.x_warnings_are_errors);
1037}
1038
1039
1040/* Called from output_format -- during diagnostic message processing
1041 to handle Fortran specific format specifiers with the following meanings:
1042
1043 %C Current locus (no argument)
1044 %L Takes locus argument
1045*/
1046static bool
1047gfc_format_decoder (pretty_printer *pp, text_info *text, const char *spec,
1048 int precision, bool wide, bool set_locus, bool hash,
1049 bool *quoted, const char **buffer_ptr)
1050{
1051 switch (*spec)
1052 {
1053 case 'C':
1054 case 'L':
1055 {
1056 static const char *result[2] = { "(1)", "(2)" };
1057 locus *loc;
1058 if (*spec == 'C')
1059 loc = &gfc_current_locus;
1060 else
1061 loc = va_arg (*text->args_ptr, locus *)__builtin_va_arg(*text->args_ptr, locus *);
1062 gcc_assert (loc->nextc - loc->lb->line >= 0)((void)(!(loc->nextc - loc->lb->line >= 0) ? fancy_abort
("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 1062, __FUNCTION__), 0 : 0))
;
1063 unsigned int offset = loc->nextc - loc->lb->line;
1064 if (*spec == 'C' && *loc->nextc != '\0')
1065 /* Point %C first offending character not the last good one. */
1066 offset++;
1067 /* If location[0] != UNKNOWN_LOCATION means that we already
1068 processed one of %C/%L. */
1069 int loc_num = text->get_location (0) == UNKNOWN_LOCATION((location_t) 0) ? 0 : 1;
1070 location_t src_loc
1071 = linemap_position_for_loc_and_offset (line_table,
1072 loc->lb->location,
1073 offset);
1074 text->set_location (loc_num, src_loc, SHOW_RANGE_WITH_CARET);
1075 /* Colorize the markers to match the color choices of
1076 diagnostic_show_locus (the initial location has a color given
1077 by the "kind" of the diagnostic, the secondary location has
1078 color "range1"). */
1079 gcc_assert (curr_diagnostic != NULL)((void)(!(curr_diagnostic != __null) ? fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 1079, __FUNCTION__), 0 : 0))
;
1080 const char *color
1081 = (loc_num
1082 ? "range1"
1083 : diagnostic_get_color_for_kind (curr_diagnostic->kind));
1084 pp_string (pp, colorize_start (pp_show_color (pp)(pp)->show_color, color));
1085 pp_string (pp, result[loc_num]);
1086 pp_string (pp, colorize_stop (pp_show_color (pp)(pp)->show_color));
1087 return true;
1088 }
1089 default:
1090 /* Fall through info the middle-end decoder, as e.g. stor-layout.c
1091 etc. diagnostics can use the FE printer while the FE is still
1092 active. */
1093 return default_tree_printer (pp, text, spec, precision, wide,
1094 set_locus, hash, quoted, buffer_ptr);
1095 }
1096}
1097
1098/* Return a malloc'd string describing the kind of diagnostic. The
1099 caller is responsible for freeing the memory. */
1100static char *
1101gfc_diagnostic_build_kind_prefix (diagnostic_context *context,
1102 const diagnostic_info *diagnostic)
1103{
1104 static const char *const diagnostic_kind_text[] = {
1105#define DEFINE_DIAGNOSTIC_KIND(K, T, C) (T),
1106#include "gfc-diagnostic.def"
1107#undef DEFINE_DIAGNOSTIC_KIND
1108 "must-not-happen"
1109 };
1110 static const char *const diagnostic_kind_color[] = {
1111#define DEFINE_DIAGNOSTIC_KIND(K, T, C) (C),
1112#include "gfc-diagnostic.def"
1113#undef DEFINE_DIAGNOSTIC_KIND
1114 NULL__null
1115 };
1116 gcc_assert (diagnostic->kind < DK_LAST_DIAGNOSTIC_KIND)((void)(!(diagnostic->kind < DK_LAST_DIAGNOSTIC_KIND) ?
fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 1116, __FUNCTION__), 0 : 0))
;
1117 const char *text = _(diagnostic_kind_text[diagnostic->kind])gettext (diagnostic_kind_text[diagnostic->kind]);
1118 const char *text_cs = "", *text_ce = "";
1119 pretty_printer *pp = context->printer;
1120
1121 if (diagnostic_kind_color[diagnostic->kind])
1122 {
1123 text_cs = colorize_start (pp_show_color (pp)(pp)->show_color,
1124 diagnostic_kind_color[diagnostic->kind]);
1125 text_ce = colorize_stop (pp_show_color (pp)(pp)->show_color);
1126 }
1127 return build_message_string ("%s%s:%s ", text_cs, text, text_ce);
1128}
1129
1130/* Return a malloc'd string describing a location. The caller is
1131 responsible for freeing the memory. */
1132static char *
1133gfc_diagnostic_build_locus_prefix (diagnostic_context *context,
1134 expanded_location s)
1135{
1136 pretty_printer *pp = context->printer;
1137 const char *locus_cs = colorize_start (pp_show_color (pp)(pp)->show_color, "locus");
1138 const char *locus_ce = colorize_stop (pp_show_color (pp)(pp)->show_color);
1139 return (s.file == NULL__null
1140 ? build_message_string ("%s%s:%s", locus_cs, progname, locus_ce )
1141 : !strcmp (s.file, N_("<built-in>")"<built-in>")
1142 ? build_message_string ("%s%s:%s", locus_cs, s.file, locus_ce)
1143 : context->show_column
1144 ? build_message_string ("%s%s:%d:%d:%s", locus_cs, s.file, s.line,
1145 s.column, locus_ce)
1146 : build_message_string ("%s%s:%d:%s", locus_cs, s.file, s.line, locus_ce));
1147}
1148
1149/* Return a malloc'd string describing two locations. The caller is
1150 responsible for freeing the memory. */
1151static char *
1152gfc_diagnostic_build_locus_prefix (diagnostic_context *context,
1153 expanded_location s, expanded_location s2)
1154{
1155 pretty_printer *pp = context->printer;
1156 const char *locus_cs = colorize_start (pp_show_color (pp)(pp)->show_color, "locus");
1157 const char *locus_ce = colorize_stop (pp_show_color (pp)(pp)->show_color);
1158
1159 return (s.file == NULL__null
1160 ? build_message_string ("%s%s:%s", locus_cs, progname, locus_ce )
1161 : !strcmp (s.file, N_("<built-in>")"<built-in>")
1162 ? build_message_string ("%s%s:%s", locus_cs, s.file, locus_ce)
1163 : context->show_column
1164 ? build_message_string ("%s%s:%d:%d-%d:%s", locus_cs, s.file, s.line,
1165 MIN (s.column, s2.column)((s.column) < (s2.column) ? (s.column) : (s2.column)),
1166 MAX (s.column, s2.column)((s.column) > (s2.column) ? (s.column) : (s2.column)), locus_ce)
1167 : build_message_string ("%s%s:%d:%s", locus_cs, s.file, s.line,
1168 locus_ce));
1169}
1170
1171/* This function prints the locus (file:line:column), the diagnostic kind
1172 (Error, Warning) and (optionally) the relevant lines of code with
1173 annotation lines with '1' and/or '2' below them.
1174
1175 With -fdiagnostic-show-caret (the default) it prints:
1176
1177 [locus of primary range]:
1178
1179 some code
1180 1
1181 Error: Some error at (1)
1182
1183 With -fno-diagnostic-show-caret or if the primary range is not
1184 valid, it prints:
1185
1186 [locus of primary range]: Error: Some error at (1) and (2)
1187*/
1188static void
1189gfc_diagnostic_starter (diagnostic_context *context,
1190 diagnostic_info *diagnostic)
1191{
1192 char * kind_prefix = gfc_diagnostic_build_kind_prefix (context, diagnostic);
1193
1194 expanded_location s1 = diagnostic_expand_location (diagnostic);
1195 expanded_location s2;
1196 bool one_locus = diagnostic->richloc->get_num_locations () < 2;
1197 bool same_locus = false;
1198
1199 if (!one_locus)
1200 {
1201 s2 = diagnostic_expand_location (diagnostic, 1);
1202 same_locus = diagnostic_same_line (context, s1, s2);
1203 }
1204
1205 char * locus_prefix = (one_locus || !same_locus)
1206 ? gfc_diagnostic_build_locus_prefix (context, s1)
1207 : gfc_diagnostic_build_locus_prefix (context, s1, s2);
1208
1209 if (!context->show_caret
1210 || diagnostic_location (diagnostic, 0) <= BUILTINS_LOCATION((location_t) 1)
1211 || diagnostic_location (diagnostic, 0) == context->last_location)
1212 {
1213 pp_set_prefix (context->printer,
1214 concat (locus_prefix, " ", kind_prefix, NULL__null));
1215 free (locus_prefix);
1216
1217 if (one_locus || same_locus)
1218 {
1219 free (kind_prefix);
1220 return;
1221 }
1222 /* In this case, we print the previous locus and prefix as:
1223
1224 [locus]:[prefix]: (1)
1225
1226 and we flush with a new line before setting the new prefix. */
1227 pp_string (context->printer, "(1)");
1228 pp_newline (context->printer);
1229 locus_prefix = gfc_diagnostic_build_locus_prefix (context, s2);
1230 pp_set_prefix (context->printer,
1231 concat (locus_prefix, " ", kind_prefix, NULL__null));
1232 free (kind_prefix);
1233 free (locus_prefix);
1234 }
1235 else
1236 {
1237 pp_verbatim (context->printer, "%s", locus_prefix);
1238 free (locus_prefix);
1239 /* Fortran uses an empty line between locus and caret line. */
1240 pp_newline (context->printer);
1241 pp_set_prefix (context->printer, NULL__null);
1242 pp_newline (context->printer);
1243 diagnostic_show_locus (context, diagnostic->richloc, diagnostic->kind);
1244 /* If the caret line was shown, the prefix does not contain the
1245 locus. */
1246 pp_set_prefix (context->printer, kind_prefix);
1247 }
1248}
1249
1250static void
1251gfc_diagnostic_start_span (diagnostic_context *context,
1252 expanded_location exploc)
1253{
1254 char *locus_prefix;
1255 locus_prefix = gfc_diagnostic_build_locus_prefix (context, exploc);
1256 pp_verbatim (context->printer, "%s", locus_prefix);
1257 free (locus_prefix);
1258 pp_newline (context->printer);
1259 /* Fortran uses an empty line between locus and caret line. */
1260 pp_newline (context->printer);
1261}
1262
1263
1264static void
1265gfc_diagnostic_finalizer (diagnostic_context *context,
1266 diagnostic_info *diagnostic ATTRIBUTE_UNUSED__attribute__ ((__unused__)),
1267 diagnostic_t orig_diag_kind ATTRIBUTE_UNUSED__attribute__ ((__unused__)))
1268{
1269 pp_destroy_prefix (context->printer);
1270 pp_newline_and_flush (context->printer);
1271}
1272
1273/* Immediate warning (i.e. do not buffer the warning) with an explicit
1274 location. */
1275
1276bool
1277gfc_warning_now_at (location_t loc, int opt, const char *gmsgid, ...)
1278{
1279 va_list argp;
1280 diagnostic_info diagnostic;
1281 rich_location rich_loc (line_table, loc);
1282 bool ret;
1283
1284 va_start (argp, gmsgid)__builtin_va_start(argp, gmsgid);
1285 diagnostic_set_info (&diagnostic, gmsgid, &argp, &rich_loc, DK_WARNING);
1286 diagnostic.option_index = opt;
1287 ret = gfc_report_diagnostic (&diagnostic);
1288 va_end (argp)__builtin_va_end(argp);
1289 return ret;
1290}
1291
1292/* Immediate warning (i.e. do not buffer the warning). */
1293
1294bool
1295gfc_warning_now (int opt, const char *gmsgid, ...)
1296{
1297 va_list argp;
1298 diagnostic_info diagnostic;
1299 rich_location rich_loc (line_table, UNKNOWN_LOCATION((location_t) 0));
1300 bool ret;
1301
1302 va_start (argp, gmsgid)__builtin_va_start(argp, gmsgid);
1303 diagnostic_set_info (&diagnostic, gmsgid, &argp, &rich_loc,
1304 DK_WARNING);
1305 diagnostic.option_index = opt;
1306 ret = gfc_report_diagnostic (&diagnostic);
1307 va_end (argp)__builtin_va_end(argp);
1308 return ret;
1309}
1310
1311/* Internal warning, do not buffer. */
1312
1313bool
1314gfc_warning_internal (int opt, const char *gmsgid, ...)
1315{
1316 va_list argp;
1317 diagnostic_info diagnostic;
1318 rich_location rich_loc (line_table, UNKNOWN_LOCATION((location_t) 0));
1319 bool ret;
1320
1321 va_start (argp, gmsgid)__builtin_va_start(argp, gmsgid);
1322 diagnostic_set_info (&diagnostic, gmsgid, &argp, &rich_loc,
1323 DK_WARNING);
1324 diagnostic.option_index = opt;
1325 ret = gfc_report_diagnostic (&diagnostic);
1326 va_end (argp)__builtin_va_end(argp);
1327 return ret;
1328}
1329
1330/* Immediate error (i.e. do not buffer). */
1331
1332void
1333gfc_error_now (const char *gmsgid, ...)
1334{
1335 va_list argp;
1336 diagnostic_info diagnostic;
1337 rich_location rich_loc (line_table, UNKNOWN_LOCATION((location_t) 0));
1338
1339 error_buffer.flag = true;
1340
1341 va_start (argp, gmsgid)__builtin_va_start(argp, gmsgid);
1342 diagnostic_set_info (&diagnostic, gmsgid, &argp, &rich_loc, DK_ERROR);
1343 gfc_report_diagnostic (&diagnostic);
1344 va_end (argp)__builtin_va_end(argp);
1345}
1346
1347
1348/* Fatal error, never returns. */
1349
1350void
1351gfc_fatal_error (const char *gmsgid, ...)
1352{
1353 va_list argp;
1354 diagnostic_info diagnostic;
1355 rich_location rich_loc (line_table, UNKNOWN_LOCATION((location_t) 0));
1356
1357 va_start (argp, gmsgid)__builtin_va_start(argp, gmsgid);
1358 diagnostic_set_info (&diagnostic, gmsgid, &argp, &rich_loc, DK_FATAL);
1359 gfc_report_diagnostic (&diagnostic);
1360 va_end (argp)__builtin_va_end(argp);
1361
1362 gcc_unreachable ()(fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 1362, __FUNCTION__))
;
1363}
1364
1365/* Clear the warning flag. */
1366
1367void
1368gfc_clear_warning (void)
1369{
1370 gfc_clear_pp_buffer (pp_warning_buffer);
1371 warningcount_buffered = 0;
1372 werrorcount_buffered = 0;
1373}
1374
1375
1376/* Check to see if any warnings have been saved.
1377 If so, print the warning. */
1378
1379void
1380gfc_warning_check (void)
1381{
1382 if (! gfc_output_buffer_empty_p (pp_warning_buffer))
1383 {
1384 pretty_printer *pp = global_dc->printer;
1385 output_buffer *tmp_buffer = pp->buffer;
1386 pp->buffer = pp_warning_buffer;
1387 pp_really_flush (pp);
1388 warningcount(global_dc)->diagnostic_count[(int) (DK_WARNING)] += warningcount_buffered;
1389 werrorcount(global_dc)->diagnostic_count[(int) (DK_WERROR)] += werrorcount_buffered;
1390 gcc_assert (warningcount_buffered + werrorcount_buffered == 1)((void)(!(warningcount_buffered + werrorcount_buffered == 1) ?
fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 1390, __FUNCTION__), 0 : 0))
;
1391 pp->buffer = tmp_buffer;
1392 diagnostic_action_after_output (global_dc,
1393 warningcount_buffered
1394 ? DK_WARNING : DK_ERROR);
1395 diagnostic_check_max_errors (global_dc, true);
1396 }
1397}
1398
1399
1400/* Issue an error. */
1401
1402static void
1403gfc_error_opt (int opt, const char *gmsgid, va_list ap)
1404{
1405 va_list argp;
1406 va_copy (argp, ap)__builtin_va_copy(argp, ap);
1407 bool saved_abort_on_error = false;
1408
1409 if (warnings_not_errors)
1410 {
1411 gfc_warning (opt, gmsgid, argp);
1412 va_end (argp)__builtin_va_end(argp);
1413 return;
1414 }
1415
1416 if (suppress_errors)
1417 {
1418 va_end (argp)__builtin_va_end(argp);
1419 return;
1420 }
1421
1422 diagnostic_info diagnostic;
1423 rich_location richloc (line_table, UNKNOWN_LOCATION((location_t) 0));
1424 bool fatal_errors = global_dc->fatal_errors;
1425 pretty_printer *pp = global_dc->printer;
1426 output_buffer *tmp_buffer = pp->buffer;
1427
1428 gfc_clear_pp_buffer (pp_error_buffer);
1429
1430 if (buffered_p)
1431 {
1432 /* To prevent -dH from triggering an abort on a buffered error,
1433 save abort_on_error and restore it below. */
1434 saved_abort_on_error = global_dc->abort_on_error;
1435 global_dc->abort_on_error = false;
1436 pp->buffer = pp_error_buffer;
1437 global_dc->fatal_errors = false;
1438 /* To prevent -fmax-errors= triggering, we decrease it before
1439 report_diagnostic increases it. */
1440 --errorcount(global_dc)->diagnostic_count[(int) (DK_ERROR)];
1441 }
1442
1443 diagnostic_set_info (&diagnostic, gmsgid, &argp, &richloc, DK_ERROR);
1444 gfc_report_diagnostic (&diagnostic);
1445
1446 if (buffered_p)
1447 {
1448 pp->buffer = tmp_buffer;
1449 global_dc->fatal_errors = fatal_errors;
1450 global_dc->abort_on_error = saved_abort_on_error;
1451
1452 }
1453
1454 va_end (argp)__builtin_va_end(argp);
1455}
1456
1457
1458void
1459gfc_error_opt (int opt, const char *gmsgid, ...)
1460{
1461 va_list argp;
1462 va_start (argp, gmsgid)__builtin_va_start(argp, gmsgid);
1463 gfc_error_opt (opt, gmsgid, argp);
1464 va_end (argp)__builtin_va_end(argp);
1465}
1466
1467
1468void
1469gfc_error (const char *gmsgid, ...)
1470{
1471 va_list argp;
1472 va_start (argp, gmsgid)__builtin_va_start(argp, gmsgid);
1473 gfc_error_opt (0, gmsgid, argp);
1474 va_end (argp)__builtin_va_end(argp);
1475}
1476
1477
1478/* This shouldn't happen... but sometimes does. */
1479
1480void
1481gfc_internal_error (const char *gmsgid, ...)
1482{
1483 int e, w;
1484 va_list argp;
1485 diagnostic_info diagnostic;
1486 rich_location rich_loc (line_table, UNKNOWN_LOCATION((location_t) 0));
1487
1488 gfc_get_errors (&w, &e);
1489 if (e > 0)
1490 exit(EXIT_FAILURE1);
1491
1492 va_start (argp, gmsgid)__builtin_va_start(argp, gmsgid);
1493 diagnostic_set_info (&diagnostic, gmsgid, &argp, &rich_loc, DK_ICE);
1494 gfc_report_diagnostic (&diagnostic);
1495 va_end (argp)__builtin_va_end(argp);
1496
1497 gcc_unreachable ()(fancy_abort ("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 1497, __FUNCTION__))
;
1498}
1499
1500
1501/* Clear the error flag when we start to compile a source line. */
1502
1503void
1504gfc_clear_error (void)
1505{
1506 error_buffer.flag = false;
1507 warnings_not_errors = false;
1508 gfc_clear_pp_buffer (pp_error_buffer);
1509}
1510
1511
1512/* Tests the state of error_flag. */
1513
1514bool
1515gfc_error_flag_test (void)
1516{
1517 return error_buffer.flag
1518 || !gfc_output_buffer_empty_p (pp_error_buffer);
1519}
1520
1521
1522/* Check to see if any errors have been saved.
1523 If so, print the error. Returns the state of error_flag. */
1524
1525bool
1526gfc_error_check (void)
1527{
1528 if (error_buffer.flag
1529 || ! gfc_output_buffer_empty_p (pp_error_buffer))
1530 {
1531 error_buffer.flag = false;
1532 pretty_printer *pp = global_dc->printer;
1533 output_buffer *tmp_buffer = pp->buffer;
1534 pp->buffer = pp_error_buffer;
1535 pp_really_flush (pp);
1536 ++errorcount(global_dc)->diagnostic_count[(int) (DK_ERROR)];
1537 gcc_assert (gfc_output_buffer_empty_p (pp_error_buffer))((void)(!(gfc_output_buffer_empty_p (pp_error_buffer)) ? fancy_abort
("/home/marxin/BIG/buildbot/buildworker/marxinbox-gcc-clang-static-analyzer/build/gcc/fortran/error.c"
, 1537, __FUNCTION__), 0 : 0))
;
1538 pp->buffer = tmp_buffer;
1539 diagnostic_action_after_output (global_dc, DK_ERROR);
1540 diagnostic_check_max_errors (global_dc, true);
1541 return true;
1542 }
1543
1544 return false;
1545}
1546
1547/* Move the text buffered from FROM to TO, then clear
1548 FROM. Independently if there was text in FROM, TO is also
1549 cleared. */
1550
1551static void
1552gfc_move_error_buffer_from_to (gfc_error_buffer * buffer_from,
1553 gfc_error_buffer * buffer_to)
1554{
1555 output_buffer * from = &(buffer_from->buffer);
1556 output_buffer * to = &(buffer_to->buffer);
1557
1558 buffer_to->flag = buffer_from->flag;
1559 buffer_from->flag = false;
1560
1561 gfc_clear_pp_buffer (to);
1562 /* We make sure this is always buffered. */
1563 to->flush_p = false;
1564
1565 if (! gfc_output_buffer_empty_p (from))
1566 {
1567 const char *str = output_buffer_formatted_text (from);
1568 output_buffer_append_r (to, str, strlen (str));
1569 gfc_clear_pp_buffer (from);
1570 }
1571}
1572
1573/* Save the existing error state. */
1574
1575void
1576gfc_push_error (gfc_error_buffer *err)
1577{
1578 gfc_move_error_buffer_from_to (&error_buffer, err);
1579}
1580
1581
1582/* Restore a previous pushed error state. */
1583
1584void
1585gfc_pop_error (gfc_error_buffer *err)
1586{
1587 gfc_move_error_buffer_from_to (err, &error_buffer);
1588}
1589
1590
1591/* Free a pushed error state, but keep the current error state. */
1592
1593void
1594gfc_free_error (gfc_error_buffer *err)
1595{
1596 gfc_clear_pp_buffer (&(err->buffer));
1597}
1598
1599
1600/* Report the number of warnings and errors that occurred to the caller. */
1601
1602void
1603gfc_get_errors (int *w, int *e)
1604{
1605 if (w != NULL__null)
1606 *w = warningcount(global_dc)->diagnostic_count[(int) (DK_WARNING)] + werrorcount(global_dc)->diagnostic_count[(int) (DK_WERROR)];
1607 if (e != NULL__null)
1608 *e = errorcount(global_dc)->diagnostic_count[(int) (DK_ERROR)] + sorrycount(global_dc)->diagnostic_count[(int) (DK_SORRY)] + werrorcount(global_dc)->diagnostic_count[(int) (DK_WERROR)];
1609}
1610
1611
1612/* Switch errors into warnings. */
1613
1614void
1615gfc_errors_to_warnings (bool f)
1616{
1617 warnings_not_errors = f;
1618}
1619
1620void
1621gfc_diagnostics_init (void)
1622{
1623 diagnostic_starter (global_dc)(global_dc)->begin_diagnostic = gfc_diagnostic_starter;
1624 global_dc->start_span = gfc_diagnostic_start_span;
1625 diagnostic_finalizer (global_dc)(global_dc)->end_diagnostic = gfc_diagnostic_finalizer;
1626 diagnostic_format_decoder (global_dc)((global_dc)->printer->format_decoder) = gfc_format_decoder;
1627 global_dc->caret_chars[0] = '1';
1628 global_dc->caret_chars[1] = '2';
1629 pp_warning_buffer = new (XNEW (output_buffer)((output_buffer *) xmalloc (sizeof (output_buffer)))) output_buffer ();
1630 pp_warning_buffer->flush_p = false;
1631 /* pp_error_buffer is statically allocated. This simplifies memory
1632 management when using gfc_push/pop_error. */
1633 pp_error_buffer = &(error_buffer.buffer);
1634 pp_error_buffer->flush_p = false;
1635}
1636
1637void
1638gfc_diagnostics_finish (void)
1639{
1640 tree_diagnostics_defaults (global_dc);
1641 /* We still want to use the gfc starter and finalizer, not the tree
1642 defaults. */
1643 diagnostic_starter (global_dc)(global_dc)->begin_diagnostic = gfc_diagnostic_starter;
1644 diagnostic_finalizer (global_dc)(global_dc)->end_diagnostic = gfc_diagnostic_finalizer;
1645 global_dc->caret_chars[0] = '^';
1646 global_dc->caret_chars[1] = '^';
1647}