Update copyright dates.
[gcc.git] / gcc / fortran / error.c
1 /* Handle errors.
2 Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005 Free Software Foundation,
3 Inc.
4 Contributed by Andy Vaught & Niels Kristian Bech Jensen
5
6 This file is part of GCC.
7
8 GCC is free software; you can redistribute it and/or modify it under
9 the terms of the GNU General Public License as published by the Free
10 Software Foundation; either version 2, or (at your option) any later
11 version.
12
13 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
14 WARRANTY; without even the implied warranty of MERCHANTABILITY or
15 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with GCC; see the file COPYING. If not, write to the Free
20 Software Foundation, 59 Temple Place - Suite 330, Boston, MA
21 02111-1307, USA. */
22
23 /* Handle the inevitable errors. A major catch here is that things
24 flagged as errors in one match subroutine can conceivably be legal
25 elsewhere. This means that error messages are recorded and saved
26 for possible use later. If a line does not match a legal
27 construction, then the saved error message is reported. */
28
29 #include "config.h"
30 #include "system.h"
31 #include "flags.h"
32 #include "gfortran.h"
33
34 int gfc_suppress_error = 0;
35
36 static int terminal_width, buffer_flag, errors,
37 use_warning_buffer, warnings;
38
39 static char *error_ptr, *warning_ptr;
40
41 static gfc_error_buf error_buffer, warning_buffer;
42
43
44 /* Per-file error initialization. */
45
46 void
47 gfc_error_init_1 (void)
48 {
49 terminal_width = gfc_terminal_width ();
50 errors = 0;
51 warnings = 0;
52 buffer_flag = 0;
53 }
54
55
56 /* Set the flag for buffering errors or not. */
57
58 void
59 gfc_buffer_error (int flag)
60 {
61 buffer_flag = flag;
62 }
63
64
65 /* Add a single character to the error buffer or output depending on
66 buffer_flag. */
67
68 static void
69 error_char (char c)
70 {
71 if (buffer_flag)
72 {
73 if (use_warning_buffer)
74 {
75 *warning_ptr++ = c;
76 if (warning_ptr - warning_buffer.message >= MAX_ERROR_MESSAGE)
77 gfc_internal_error ("error_char(): Warning buffer overflow");
78 }
79 else
80 {
81 *error_ptr++ = c;
82 if (error_ptr - error_buffer.message >= MAX_ERROR_MESSAGE)
83 gfc_internal_error ("error_char(): Error buffer overflow");
84 }
85 }
86 else
87 {
88 if (c != 0)
89 {
90 /* We build up complete lines before handing things
91 over to the library in order to speed up error printing. */
92 static char line[MAX_ERROR_MESSAGE + 1];
93 static int index = 0;
94
95 line[index++] = c;
96 if (c == '\n' || index == MAX_ERROR_MESSAGE)
97 {
98 line[index] = '\0';
99 fputs (line, stderr);
100 index = 0;
101 }
102 }
103 }
104 }
105
106
107 /* Copy a string to wherever it needs to go. */
108
109 static void
110 error_string (const char *p)
111 {
112 while (*p)
113 error_char (*p++);
114 }
115
116
117 /* Show the file, where it was included and the source line, give a
118 locus. Calls error_printf() recursively, but the recursion is at
119 most one level deep. */
120
121 static void error_printf (const char *, ...) ATTRIBUTE_PRINTF_1;
122
123 static void
124 show_locus (int offset, locus * loc)
125 {
126 gfc_linebuf *lb;
127 gfc_file *f;
128 char c, *p;
129 int i, m;
130
131 /* TODO: Either limit the total length and number of included files
132 displayed or add buffering of arbitrary number of characters in
133 error messages. */
134
135 lb = loc->lb;
136 f = lb->file;
137 error_printf ("In file %s:%d\n", f->filename,
138 #ifdef USE_MAPPED_LOCATION
139 LOCATION_LINE (lb->location)
140 #else
141 lb->linenum
142 #endif
143 );
144
145 for (;;)
146 {
147 i = f->inclusion_line;
148
149 f = f->included_by;
150 if (f == NULL) break;
151
152 error_printf (" Included at %s:%d\n", f->filename, i);
153 }
154
155 /* Show the line itself, taking care not to print more than what can
156 show up on the terminal. Tabs are converted to spaces. */
157
158 p = lb->line + offset;
159 i = strlen (p);
160 if (i > terminal_width)
161 i = terminal_width - 1;
162
163 for (; i > 0; i--)
164 {
165 c = *p++;
166 if (c == '\t')
167 c = ' ';
168
169 if (ISPRINT (c))
170 error_char (c);
171 else
172 {
173 error_char ('\\');
174 error_char ('x');
175
176 m = ((c >> 4) & 0x0F) + '0';
177 if (m > '9')
178 m += 'A' - '9' - 1;
179 error_char (m);
180
181 m = (c & 0x0F) + '0';
182 if (m > '9')
183 m += 'A' - '9' - 1;
184 error_char (m);
185 }
186 }
187
188 error_char ('\n');
189 }
190
191
192 /* As part of printing an error, we show the source lines that caused
193 the problem. We show at least one, possibly two loci. If we're
194 showing two loci and they both refer to the same file and line, we
195 only print the line once. */
196
197 static void
198 show_loci (locus * l1, locus * l2)
199 {
200 int offset, flag, i, m, c1, c2, cmax;
201
202 if (l1 == NULL)
203 {
204 error_printf ("<During initialization>\n");
205 return;
206 }
207
208 c1 = l1->nextc - l1->lb->line;
209 c2 = 0;
210 if (l2 == NULL)
211 goto separate;
212
213 c2 = l2->nextc - l2->lb->line;
214
215 if (c1 < c2)
216 m = c2 - c1;
217 else
218 m = c1 - c2;
219
220
221 if (l1->lb != l2->lb || m > terminal_width - 10)
222 goto separate;
223
224 offset = 0;
225 cmax = (c1 < c2) ? c2 : c1;
226 if (cmax > terminal_width - 5)
227 offset = cmax - terminal_width + 5;
228
229 if (offset < 0)
230 offset = 0;
231
232 c1 -= offset;
233 c2 -= offset;
234
235 show_locus (offset, l1);
236
237 /* Arrange that '1' and '2' will show up even if the two columns are equal. */
238 for (i = 1; i <= cmax; i++)
239 {
240 flag = 0;
241 if (i == c1)
242 {
243 error_char ('1');
244 flag = 1;
245 }
246 if (i == c2)
247 {
248 error_char ('2');
249 flag = 1;
250 }
251 if (flag == 0)
252 error_char (' ');
253 }
254
255 error_char ('\n');
256
257 return;
258
259 separate:
260 offset = 0;
261
262 if (c1 > terminal_width - 5)
263 {
264 offset = c1 - 5;
265 if (offset < 0)
266 offset = 0;
267 c1 = c1 - offset;
268 }
269
270 show_locus (offset, l1);
271 for (i = 1; i < c1; i++)
272 error_char (' ');
273
274 error_char ('1');
275 error_char ('\n');
276
277 if (l2 != NULL)
278 {
279 offset = 0;
280
281 if (c2 > terminal_width - 20)
282 {
283 offset = c2 - 20;
284 if (offset < 0)
285 offset = 0;
286 c2 = c2 - offset;
287 }
288
289 show_locus (offset, l2);
290
291 for (i = 1; i < c2; i++)
292 error_char (' ');
293
294 error_char ('2');
295 error_char ('\n');
296 }
297 }
298
299
300 /* Workhorse for the error printing subroutines. This subroutine is
301 inspired by g77's error handling and is similar to printf() with
302 the following %-codes:
303
304 %c Character, %d Integer, %s String, %% Percent
305 %L Takes locus argument
306 %C Current locus (no argument)
307
308 If a locus pointer is given, the actual source line is printed out
309 and the column is indicated. Since we want the error message at
310 the bottom of any source file information, we must scan the
311 argument list twice. A maximum of two locus arguments are
312 permitted. */
313
314 #define IBUF_LEN 30
315 #define MAX_ARGS 10
316
317 static void
318 error_print (const char *type, const char *format0, va_list argp)
319 {
320 char c, *p, int_buf[IBUF_LEN], c_arg[MAX_ARGS], *cp_arg[MAX_ARGS];
321 int i, n, have_l1, i_arg[MAX_ARGS];
322 locus *l1, *l2, *loc;
323 const char *format;
324
325 l1 = l2 = loc = NULL;
326
327 have_l1 = 0;
328
329 n = 0;
330 format = format0;
331
332 while (*format)
333 {
334 c = *format++;
335 if (c == '%')
336 {
337 c = *format++;
338
339 switch (c)
340 {
341 case '%':
342 break;
343
344 case 'L':
345 loc = va_arg (argp, locus *);
346 /* Fall through */
347
348 case 'C':
349 if (c == 'C')
350 loc = &gfc_current_locus;
351
352 if (have_l1)
353 {
354 l2 = loc;
355 }
356 else
357 {
358 l1 = loc;
359 have_l1 = 1;
360 }
361 break;
362
363 case 'd':
364 case 'i':
365 i_arg[n++] = va_arg (argp, int);
366 break;
367
368 case 'c':
369 c_arg[n++] = va_arg (argp, int);
370 break;
371
372 case 's':
373 cp_arg[n++] = va_arg (argp, char *);
374 break;
375 }
376 }
377 }
378
379 /* Show the current loci if we have to. */
380 if (have_l1)
381 show_loci (l1, l2);
382 error_string (type);
383 error_char (' ');
384
385 have_l1 = 0;
386 format = format0;
387 n = 0;
388
389 for (; *format; format++)
390 {
391 if (*format != '%')
392 {
393 error_char (*format);
394 continue;
395 }
396
397 format++;
398 switch (*format)
399 {
400 case '%':
401 error_char ('%');
402 break;
403
404 case 'c':
405 error_char (c_arg[n++]);
406 break;
407
408 case 's':
409 error_string (cp_arg[n++]);
410 break;
411
412 case 'i':
413 case 'd':
414 i = i_arg[n++];
415
416 if (i < 0)
417 {
418 i = -i;
419 error_char ('-');
420 }
421
422 p = int_buf + IBUF_LEN - 1;
423 *p-- = '\0';
424
425 if (i == 0)
426 *p-- = '0';
427
428 while (i > 0)
429 {
430 *p-- = i % 10 + '0';
431 i = i / 10;
432 }
433
434 error_string (p + 1);
435 break;
436
437 case 'C': /* Current locus */
438 case 'L': /* Specified locus */
439 error_string (have_l1 ? "(2)" : "(1)");
440 have_l1 = 1;
441 break;
442 }
443 }
444
445 error_char ('\n');
446 }
447
448
449 /* Wrapper for error_print(). */
450
451 static void
452 error_printf (const char *format, ...)
453 {
454 va_list argp;
455
456 va_start (argp, format);
457 error_print ("", format, argp);
458 va_end (argp);
459 }
460
461
462 /* Issue a warning. */
463
464 void
465 gfc_warning (const char *format, ...)
466 {
467 va_list argp;
468
469 if (inhibit_warnings)
470 return;
471
472 warning_buffer.flag = 1;
473 warning_ptr = warning_buffer.message;
474 use_warning_buffer = 1;
475
476 va_start (argp, format);
477 if (buffer_flag == 0)
478 warnings++;
479 error_print ("Warning:", format, argp);
480 va_end (argp);
481
482 error_char ('\0');
483 }
484
485
486 /* Possibly issue a warning/error about use of a nonstandard (or deleted)
487 feature. An error/warning will be issued if the currently selected
488 standard does not contain the requested bits. Return FAILURE if
489 and error is generated. */
490
491 try
492 gfc_notify_std (int std, const char *format, ...)
493 {
494 va_list argp;
495 bool warning;
496
497 warning = ((gfc_option.warn_std & std) != 0)
498 && !inhibit_warnings;
499 if ((gfc_option.allow_std & std) != 0
500 && !warning)
501 return SUCCESS;
502
503 if (gfc_suppress_error)
504 return warning ? SUCCESS : FAILURE;
505
506 if (warning)
507 {
508 warning_buffer.flag = 1;
509 warning_ptr = warning_buffer.message;
510 use_warning_buffer = 1;
511 }
512 else
513 {
514 error_buffer.flag = 1;
515 error_ptr = error_buffer.message;
516 use_warning_buffer = 0;
517 }
518
519 if (buffer_flag == 0)
520 {
521 if (warning)
522 warnings++;
523 else
524 errors++;
525 }
526 va_start (argp, format);
527 if (warning)
528 error_print ("Warning:", format, argp);
529 else
530 error_print ("Error:", format, argp);
531 va_end (argp);
532
533 error_char ('\0');
534 return warning ? SUCCESS : FAILURE;
535 }
536
537
538 /* Immediate warning (i.e. do not buffer the warning). */
539
540 void
541 gfc_warning_now (const char *format, ...)
542 {
543 va_list argp;
544 int i;
545
546 if (inhibit_warnings)
547 return;
548
549 i = buffer_flag;
550 buffer_flag = 0;
551 warnings++;
552
553 va_start (argp, format);
554 error_print ("Warning:", format, argp);
555 va_end (argp);
556
557 error_char ('\0');
558 buffer_flag = i;
559 }
560
561
562 /* Clear the warning flag. */
563
564 void
565 gfc_clear_warning (void)
566 {
567 warning_buffer.flag = 0;
568 }
569
570
571 /* Check to see if any warnings have been saved.
572 If so, print the warning. */
573
574 void
575 gfc_warning_check (void)
576 {
577 if (warning_buffer.flag)
578 {
579 warnings++;
580 fputs (warning_buffer.message, stderr);
581 warning_buffer.flag = 0;
582 }
583 }
584
585
586 /* Issue an error. */
587
588 void
589 gfc_error (const char *format, ...)
590 {
591 va_list argp;
592
593 if (gfc_suppress_error)
594 return;
595
596 error_buffer.flag = 1;
597 error_ptr = error_buffer.message;
598 use_warning_buffer = 0;
599
600 va_start (argp, format);
601 if (buffer_flag == 0)
602 errors++;
603 error_print ("Error:", format, argp);
604 va_end (argp);
605
606 error_char ('\0');
607 }
608
609
610 /* Immediate error. */
611
612 void
613 gfc_error_now (const char *format, ...)
614 {
615 va_list argp;
616 int i;
617
618 error_buffer.flag = 1;
619 error_ptr = error_buffer.message;
620
621 i = buffer_flag;
622 buffer_flag = 0;
623 errors++;
624
625 va_start (argp, format);
626 error_print ("Error:", format, argp);
627 va_end (argp);
628
629 error_char ('\0');
630 buffer_flag = i;
631 }
632
633
634 /* Fatal error, never returns. */
635
636 void
637 gfc_fatal_error (const char *format, ...)
638 {
639 va_list argp;
640
641 buffer_flag = 0;
642
643 va_start (argp, format);
644 error_print ("Fatal Error:", format, argp);
645 va_end (argp);
646
647 exit (3);
648 }
649
650
651 /* This shouldn't happen... but sometimes does. */
652
653 void
654 gfc_internal_error (const char *format, ...)
655 {
656 va_list argp;
657
658 buffer_flag = 0;
659
660 va_start (argp, format);
661
662 show_loci (&gfc_current_locus, NULL);
663 error_printf ("Internal Error at (1):");
664
665 error_print ("", format, argp);
666 va_end (argp);
667
668 exit (4);
669 }
670
671
672 /* Clear the error flag when we start to compile a source line. */
673
674 void
675 gfc_clear_error (void)
676 {
677 error_buffer.flag = 0;
678 }
679
680
681 /* Check to see if any errors have been saved.
682 If so, print the error. Returns the state of error_flag. */
683
684 int
685 gfc_error_check (void)
686 {
687 int rc;
688
689 rc = error_buffer.flag;
690
691 if (error_buffer.flag)
692 {
693 errors++;
694 fputs (error_buffer.message, stderr);
695 error_buffer.flag = 0;
696 }
697
698 return rc;
699 }
700
701
702 /* Save the existing error state. */
703
704 void
705 gfc_push_error (gfc_error_buf * err)
706 {
707 err->flag = error_buffer.flag;
708 if (error_buffer.flag)
709 strcpy (err->message, error_buffer.message);
710
711 error_buffer.flag = 0;
712 }
713
714
715 /* Restore a previous pushed error state. */
716
717 void
718 gfc_pop_error (gfc_error_buf * err)
719 {
720 error_buffer.flag = err->flag;
721 if (error_buffer.flag)
722 strcpy (error_buffer.message, err->message);
723 }
724
725
726 /* Debug wrapper for printf. */
727
728 void
729 gfc_status (const char *format, ...)
730 {
731 va_list argp;
732
733 va_start (argp, format);
734
735 vprintf (format, argp);
736
737 va_end (argp);
738 }
739
740
741 /* Subroutine for outputting a single char so that we don't have to go
742 around creating a lot of 1-character strings. */
743
744 void
745 gfc_status_char (char c)
746 {
747 putchar (c);
748 }
749
750
751 /* Report the number of warnings and errors that occurred to the caller. */
752
753 void
754 gfc_get_errors (int *w, int *e)
755 {
756 if (w != NULL)
757 *w = warnings;
758 if (e != NULL)
759 *e = errors;
760 }