Add PR number in:
[official-gcc.git] / libgfortran / io / read.c
blob3ce9f1d3a1afc29431fed7815fb3cf55cfc468d3
1 /* Copyright (C) 2002-2003 Free Software Foundation, Inc.
2 Contributed by Andy Vaught
4 This file is part of the GNU Fortran 95 runtime library (libgfortran).
6 Libgfortran is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2, or (at your option)
9 any later version.
11 Libgfortran is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with Libgfortran; see the file COPYING. If not, write to
18 the Free Software Foundation, 59 Temple Place - Suite 330,
19 Boston, MA 02111-1307, USA. */
22 #include "config.h"
23 #include <string.h>
24 #include <errno.h>
25 #include <ctype.h>
26 #include <stdlib.h>
27 #include "libgfortran.h"
28 #include "io.h"
30 /* read.c -- Deal with formatted reads */
32 /* set_integer()-- All of the integer assignments come here to
33 * actually place the value into memory. */
35 void
36 set_integer (void *dest, int64_t value, int length)
39 switch (length)
41 case 8:
42 *((int64_t *) dest) = value;
43 break;
44 case 4:
45 *((int32_t *) dest) = value;
46 break;
47 case 2:
48 *((int16_t *) dest) = value;
49 break;
50 case 1:
51 *((int8_t *) dest) = value;
52 break;
53 default:
54 internal_error ("Bad integer kind");
59 /* max_value()-- Given a length (kind), return the maximum signed or
60 * unsigned value */
62 uint64_t
63 max_value (int length, int signed_flag)
65 uint64_t value;
67 switch (length)
69 case 8:
70 value = signed_flag ? 0x7fffffffffffffff : 0xffffffffffffffff;
71 break;
72 case 4:
73 value = signed_flag ? 0x7fffffff : 0xffffffff;
74 break;
75 case 2:
76 value = signed_flag ? 0x7fff : 0xffff;
77 break;
78 case 1:
79 value = signed_flag ? 0x7f : 0xff;
80 break;
81 default:
82 internal_error ("Bad integer kind");
85 return value;
89 /* convert_real()-- Convert a character representation of a floating
90 * point number to the machine number. Returns nonzero if there is a
91 * range problem during conversion. TODO: handle not-a-numbers and
92 * infinities. Handling of kind 4 is probably wrong because of double
93 * rounding. */
95 int
96 convert_real (void *dest, const char *buffer, int length)
99 errno = 0;
101 switch (length)
103 case 4:
104 *((float *) dest) = (float) strtod (buffer, NULL);
105 break;
106 case 8:
107 *((double *) dest) = strtod (buffer, NULL);
108 break;
109 default:
110 internal_error ("Bad real number kind");
113 if (errno != 0)
115 generate_error (ERROR_READ_VALUE,
116 "Range error during floating point read");
117 return 1;
120 return 0;
123 static int
124 convert_precision_real (void *dest, int sign,
125 char *buffer, int length, int exponent)
127 int w, new_dp_pos, i, slen, k, dp;
128 char * p, c;
129 double fval;
130 float tf;
132 fval =0.0;
133 tf = 0.0;
134 dp = 0;
135 new_dp_pos = 0;
137 slen = strlen (buffer);
138 w = slen;
139 p = buffer;
141 /* for (i = w - 1; i > 0; i --)
143 if (buffer[i] == '0' || buffer[i] == 0)
144 buffer[i] = 0;
145 else
146 break;
149 for (i = 0; i < w; i++)
151 if (buffer[i] == '.')
152 break;
155 new_dp_pos = i;
156 new_dp_pos += exponent;
158 while (w > 0)
160 c = *p;
161 switch (c)
163 case '0':
164 case '1':
165 case '2':
166 case '3':
167 case '4':
168 case '5':
169 case '6':
170 case '7':
171 case '8':
172 case '9':
173 fval = fval * 10.0 + c - '0';
174 p++;
175 w--;
176 break;
178 case '.':
179 dp = 1;
180 p++;
181 w--;
182 break;
184 default:
185 p++;
186 w--;
187 break;
191 if (sign)
192 fval = - fval;
194 i = new_dp_pos - slen + dp;
195 k = abs(i);
196 tf = 1.0;
198 while (k > 0)
200 tf *= 10.0 ;
201 k -- ;
204 if (fval != 0.0)
206 if (i < 0)
208 fval = fval / tf;
210 else
212 fval = fval * tf;
216 switch (length)
218 case 4:
219 *((float *) dest) = (float)fval;
220 break;
221 case 8:
222 *((double *) dest) = fval;
223 break;
224 default:
225 internal_error ("Bad real number kind");
228 return 0;
232 /* read_l()-- Read a logical value */
234 void
235 read_l (fnode * f, char *dest, int length)
237 char *p;
238 int w;
240 w = f->u.w;
241 p = read_block (&w);
242 if (p == NULL)
243 return;
245 while (*p == ' ')
247 if (--w == 0)
248 goto bad;
249 p++;
252 if (*p == '.')
254 if (--w == 0)
255 goto bad;
256 p++;
259 switch (*p)
261 case 't':
262 case 'T':
263 set_integer (dest, 1, length);
264 break;
265 case 'f':
266 case 'F':
267 set_integer (dest, 0, length);
268 break;
269 default:
270 bad:
271 generate_error (ERROR_READ_VALUE, "Bad value on logical read");
272 break;
277 /* read_a()-- Read a character record. This one is pretty easy. */
279 void
280 read_a (fnode * f, char *p, int length)
282 char *source;
283 int w, m, n;
285 w = f->u.w;
286 if (w == -1) /* '(A)' edit descriptor */
287 w = length;
289 source = read_block (&w);
290 if (source == NULL)
291 return;
292 if (w > length)
293 source += (w - length);
295 m = (w > length) ? length : w;
296 memcpy (p, source, m);
298 n = length - w;
299 if (n > 0)
300 memset (p + m, ' ', n);
304 /* eat_leading_spaces()-- Given a character pointer and a width,
305 * ignore the leading spaces. */
307 static char *
308 eat_leading_spaces (int *width, char *p)
311 for (;;)
313 if (*width == 0 || *p != ' ')
314 break;
316 (*width)--;
317 p++;
320 return p;
324 static char
325 next_char (char **p, int *w)
327 char c, *q;
329 if (*w == 0)
330 return '\0';
332 q = *p;
333 c = *q++;
334 *p = q;
336 (*w)--;
338 if (c != ' ')
339 return c;
340 if (g.blank_status == BLANK_ZERO)
341 return '0';
343 /* At this point, the rest of the field has to be trailing blanks */
345 while (*w > 0)
347 if (*q++ != ' ')
348 return '?';
349 (*w)--;
352 *p = q;
353 return '\0';
357 /* read_decimal()-- Read a decimal integer value. The values here are
358 * signed values. */
360 void
361 read_decimal (fnode * f, char *dest, int length)
363 unsigned value, maxv, maxv_10;
364 int v, w, negative;
365 char c, *p;
367 w = f->u.w;
368 p = read_block (&w);
369 if (p == NULL)
370 return;
372 p = eat_leading_spaces (&w, p);
373 if (w == 0)
375 set_integer (dest, 0, length);
376 return;
379 maxv = max_value (length, 1);
380 maxv_10 = maxv / 10;
382 negative = 0;
383 value = 0;
385 switch (*p)
387 case '-':
388 negative = 1;
389 /* Fall through */
391 case '+':
392 p++;
393 if (--w == 0)
394 goto bad;
395 /* Fall through */
397 default:
398 break;
401 /* At this point we have a digit-string */
402 value = 0;
404 for (;;)
406 c = next_char (&p, &w);
407 if (c == '\0')
408 break;
410 if (c < '0' || c > '9')
411 goto bad;
413 if (value > maxv_10)
414 goto overflow;
416 c -= '0';
417 value = 10 * value;
419 if (value > maxv - c)
420 goto overflow;
421 value += c;
424 v = (signed int) value;
425 if (negative)
426 v = -v;
428 set_integer (dest, v, length);
429 return;
431 bad:
432 generate_error (ERROR_READ_VALUE, "Bad value during integer read");
433 return;
435 overflow:
436 generate_error (ERROR_READ_OVERFLOW,
437 "Value overflowed during integer read");
438 return;
442 /* read_radix()-- This function reads values for non-decimal radixes.
443 * The difference here is that we treat the values here as unsigned
444 * values for the purposes of overflow. If minus sign is present and
445 * the top bit is set, the value will be incorrect. */
447 void
448 read_radix (fnode * f, char *dest, int length, int radix)
450 unsigned value, maxv, maxv_r;
451 int v, w, negative;
452 char c, *p;
454 w = f->u.w;
455 p = read_block (&w);
456 if (p == NULL)
457 return;
459 p = eat_leading_spaces (&w, p);
460 if (w == 0)
462 set_integer (dest, 0, length);
463 return;
466 maxv = max_value (length, 0);
467 maxv_r = maxv / radix;
469 negative = 0;
470 value = 0;
472 switch (*p)
474 case '-':
475 negative = 1;
476 /* Fall through */
478 case '+':
479 p++;
480 if (--w == 0)
481 goto bad;
482 /* Fall through */
484 default:
485 break;
488 /* At this point we have a digit-string */
489 value = 0;
491 for (;;)
493 c = next_char (&p, &w);
494 if (c == '\0')
495 break;
497 switch (radix)
499 case 2:
500 if (c < '0' || c > '1')
501 goto bad;
502 break;
504 case 8:
505 if (c < '0' || c > '7')
506 goto bad;
507 break;
509 case 16:
510 switch (c)
512 case '0':
513 case '1':
514 case '2':
515 case '3':
516 case '4':
517 case '5':
518 case '6':
519 case '7':
520 case '8':
521 case '9':
522 break;
524 case 'a':
525 case 'b':
526 case 'c':
527 case 'd':
528 case 'e':
529 c = c - 'a' + '9' + 1;
530 break;
532 case 'A':
533 case 'B':
534 case 'C':
535 case 'D':
536 case 'E':
537 c = c - 'A' + '9' + 1;
538 break;
540 default:
541 goto bad;
544 break;
547 if (value > maxv_r)
548 goto overflow;
550 c -= '0';
551 value = radix * value;
553 if (maxv - c < value)
554 goto overflow;
555 value += c;
558 v = (signed int) value;
559 if (negative)
560 v = -v;
562 set_integer (dest, v, length);
563 return;
565 bad:
566 generate_error (ERROR_READ_VALUE, "Bad value during integer read");
567 return;
569 overflow:
570 generate_error (ERROR_READ_OVERFLOW,
571 "Value overflowed during integer read");
572 return;
576 /* read_f()-- Read a floating point number with F-style editing, which
577 * is what all of the other floating point descriptors behave as. The
578 * tricky part is that optional spaces are allowed after an E or D,
579 * and the implicit decimal point if a decimal point is not present in
580 * the input. */
582 void
583 read_f (fnode * f, char *dest, int length)
585 int w, seen_dp, exponent;
586 int exponent_sign, val_sign;
587 char *p, *buffer, *n;
589 val_sign = 0;
590 seen_dp = 0;
591 w = f->u.w;
592 p = read_block (&w);
593 if (p == NULL)
594 return;
596 p = eat_leading_spaces (&w, p);
597 if (w == 0)
599 switch (length)
601 case 4:
602 *((float *) dest) = 0.0;
603 break;
605 case 8:
606 *((double *) dest) = 0.0;
607 break;
610 return;
613 if (w + 2 < SCRATCH_SIZE)
614 buffer = scratch;
615 else
616 buffer = get_mem (w + 2);
618 memset(buffer, 0, w + 2);
620 n = buffer;
622 /* Optional sign */
624 if (*p == '-' || *p == '+')
626 if (*p == '-')
627 val_sign = 1;
628 p++;
630 if (--w == 0)
631 goto bad_float;
634 exponent_sign = 1;
636 /* A digit (or a '.') is required at this point */
638 if (!isdigit (*p) && *p != '.')
639 goto bad_float;
641 while (w > 0)
643 switch (*p)
645 case '0':
646 case '1':
647 case '2':
648 case '3':
649 case '4':
650 case '5':
651 case '6':
652 case '7':
653 case '8':
654 case '9':
655 *n++ = *p++;
656 w--;
657 break;
659 case '.':
660 if (seen_dp)
661 goto bad_float;
662 seen_dp = 1;
664 *n++ = *p++;
665 w--;
666 break;
668 case ' ':
669 if (g.blank_status == BLANK_ZERO)
670 *n++ = '0';
671 p++;
672 w--;
673 break;
675 case '-':
676 exponent_sign = -1;
677 /* Fall through */
679 case '+':
680 p++;
681 w--;
682 goto exp2;
684 case 'd':
685 case 'e':
686 case 'D':
687 case 'E':
688 p++;
689 w--;
690 goto exp1;
692 default:
693 goto bad_float;
697 /* No exponent has been seen, so we use the current scale factor */
699 exponent = -g.scale_factor;
700 goto done;
702 bad_float:
703 generate_error (ERROR_READ_VALUE, "Bad value during floating point read");
704 if (buffer != scratch)
705 free_mem (buffer);
706 return;
708 /* At this point the start of an exponent has been found */
710 exp1:
711 while (w > 0 && *p == ' ')
713 w--;
714 p++;
717 switch (*p)
719 case '-':
720 exponent_sign = -1;
721 /* Fall through */
723 case '+':
724 p++;
725 w--;
726 break;
729 if (w == 0)
730 goto bad_float;
732 /* At this point a digit string is required. We calculate the value
733 * of the exponent in order to take account of the scale factor and
734 * the d parameter before explict conversion takes place. */
736 exp2:
737 if (!isdigit (*p))
738 goto bad_float;
740 exponent = *p - '0';
741 p++;
742 w--;
744 while (w > 0 && isdigit (*p))
746 exponent = 10 * exponent + *p - '0';
747 if (exponent > 999999)
748 goto bad_float;
750 p++;
751 w--;
754 /* Only allow trailing blanks */
756 while (w > 0)
758 if (*p != ' ')
759 goto bad_float;
760 p++;
761 w--;
764 exponent = exponent * exponent_sign;
766 done:
767 if (!seen_dp)
768 exponent -= f->u.real.d;
770 /* The number is syntactically correct and ready for conversion.
771 * The only thing that can go wrong at this point is overflow or
772 * underflow. */
774 convert_precision_real (dest, val_sign, buffer, length, exponent);
776 if (buffer != scratch)
777 free_mem (buffer);
779 return;
783 /* read_x()-- Deal with the X/TR descriptor. We just read some data
784 * and never look at it. */
786 void
787 read_x (fnode * f)
789 int n;
791 n = f->u.n;
792 read_block (&n);