diff options
author | Jeff Johnston <jjohnstn@redhat.com> | 2000-12-06 23:50:11 +0000 |
---|---|---|
committer | Jeff Johnston <jjohnstn@redhat.com> | 2000-12-06 23:50:11 +0000 |
commit | 6bdac416e9e1aecfb94cd3ae383889cc7b7e62e3 (patch) | |
tree | 0871ae257bee23aa786ad2ac43aeb3470d340f5f /newlib/libc/stdio/vfscanf.c | |
parent | 81e615de9818b0094abea875b60ca955edfcec9c (diff) | |
download | cygnal-6bdac416e9e1aecfb94cd3ae383889cc7b7e62e3.tar.gz cygnal-6bdac416e9e1aecfb94cd3ae383889cc7b7e62e3.tar.bz2 cygnal-6bdac416e9e1aecfb94cd3ae383889cc7b7e62e3.zip |
2000-12-06 Jeff Johnston <jjohnstn@redhat.com>
* libc/stdlib/Makefile.am: Added ldtoa.c to list of sources.
* libc/stdlib/Makefile.in: Regenerated.
* libc/stdio/floatio.h: Added suitable MAXEXP for long double.
* libc/stdio/vfieeefp.h: Added long double bit structures.
* libc/stdio/vfprintf.c[WANT_IO_LONG_DBL]: Added long double support.
[WANT_IO_LONG_DBL](isinfl, isnanl): New static long double routines.
(exponent): Changed expbuf to reasonable maximum instead of MAXEXP.
* libc/stdio/vfscanf.c[WANT_IO_LONG_DBL]: Added long double support.
* libc/stdlib/ldtoa.c: New file containing _ldtoa_r and
_strtold routines used for conversions between character
and long double.
Diffstat (limited to 'newlib/libc/stdio/vfscanf.c')
-rw-r--r-- | newlib/libc/stdio/vfscanf.c | 28 |
1 files changed, 24 insertions, 4 deletions
diff --git a/newlib/libc/stdio/vfscanf.c b/newlib/libc/stdio/vfscanf.c index 7e88f1202..cc0f26d3c 100644 --- a/newlib/libc/stdio/vfscanf.c +++ b/newlib/libc/stdio/vfscanf.c @@ -34,6 +34,17 @@ #endif #ifdef FLOATING_POINT +#include <float.h> + +/* Currently a test is made to see if long double processing is warranted. + This could be changed in the future should the _ldtoa_r code be + preferred over _dtoa_r. */ +#define _NO_LONGDBL +#if defined WANT_IO_LONG_DBL && (LDBL_MANT_DIG > DBL_MANT_DIG) +#undef _NO_LONGDBL +extern _LONG_DOUBLE _strtold _PARAMS((char *s, char **sptr)); +#endif + #include "floatio.h" #define BUF (MAXEXP+MAXFRACT+3) /* 3 = sign + decimal point + NUL */ /* An upper bound for how long a long prints in decimal. 4 / 13 approximates @@ -48,7 +59,7 @@ */ #define LONG 0x01 /* l: long or double */ -#define LONGDBL 0x02 /* L: long double; unimplemented */ +#define LONGDBL 0x02 /* L: long double */ #define SHORT 0x04 /* h: short */ #define SUPPRESS 0x08 /* suppress assignment */ #define POINTER 0x10 /* weird %p pointer (`fake hex') */ @@ -372,7 +383,7 @@ __svfscanf (fp, fmt0, ap) for (;;) { - if ((n = fp->_r) < width) + if ((n = fp->_r) < (int)width) { sum += n; width -= n; @@ -683,8 +694,9 @@ __svfscanf (fp, fmt0, ap) However, ANSI / ISO C makes no such stipulation; we have to get exact results even when there is an unreasonable amount of leading zeroes. */ - long leading_zeroes, zeroes, exp_adjust; - char *exp_start; + long leading_zeroes = 0; + long zeroes, exp_adjust; + char *exp_start = NULL; #ifdef hardway if (width == 0 || width > sizeof (buf) - 1) width = sizeof (buf) - 1; @@ -808,7 +820,11 @@ __svfscanf (fp, fmt0, ap) } if ((flags & SUPPRESS) == 0) { +#ifdef _NO_LONGDBL double res; +#else /* !_NO_LONG_DBL */ + long double res; +#endif /* !_NO_LONG_DBL */ long new_exp; *p = 0; @@ -829,7 +845,11 @@ __svfscanf (fp, fmt0, ap) exp_start = buf + sizeof (buf) - MAX_LONG_LEN - 1; sprintf (exp_start, "e%ld", new_exp); } +#ifdef _NO_LONG_DBL res = atof (buf); +#else /* !_NO_LONG_DBL */ + res = _strtold (buf, NULL); +#endif /* !_NO_LONG_DBL */ if (flags & LONG) { dp = va_arg (ap, double *); |