X-Git-Url: http://nsz.repo.hu/git/?p=musl;a=blobdiff_plain;f=src%2Finternal%2Ffloatscan.c;h=bba5753b997b27619d2c3fa2d8629f6764ec2f9f;hp=da209e278e14e5abe0a39aa5cf59854696207df8;hb=11458e5b098319cf3e2d05c8cbaa74d58db740e3;hpb=dad40407705801c8bb597d5bc9a4eda562cae890 diff --git a/src/internal/floatscan.c b/src/internal/floatscan.c index da209e27..bba5753b 100644 --- a/src/internal/floatscan.c +++ b/src/internal/floatscan.c @@ -24,6 +24,8 @@ #define MASK (KMAX-1) +#define CONCAT2(x,y) x ## y +#define CONCAT(x,y) CONCAT2(x,y) static long long scanexp(FILE *f, int pok) { @@ -44,7 +46,7 @@ static long long scanexp(FILE *f, int pok) } for (x=0; c-'0'<10U && x LDBL_MANT_DIG+e2-emin) { bits = LDBL_MANT_DIG+e2-emin; if (bits<0) bits=0; + denormal = 1; } /* Calculate bias term to force rounding, move out lower bits */ @@ -275,11 +285,18 @@ static long double decfloat(FILE *f, int c, int bits, int emin, int sign, int po y += frac; y -= bias; - y = scalbnl(y, e2); - - if (!y) errno = ERANGE; + if ((e2+LDBL_MANT_DIG & INT_MAX) > emax-5) { + if (fabs(y) >= CONCAT(0x1p, LDBL_MANT_DIG)) { + if (denormal && bits==LDBL_MANT_DIG+e2-emin) + denormal = 0; + y *= 0.5; + e2++; + } + if (e2+LDBL_MANT_DIG>emax || (denormal && frac)) + errno = ERANGE; + } - return y; + return scalbnl(y, e2); } static long double hexfloat(FILE *f, int bits, int emin, int sign, int pok) @@ -335,7 +352,7 @@ static long double hexfloat(FILE *f, int bits, int emin, int sign, int pok) } else { shlim(f, 0); } - return 0; + return sign * 0.0; } if (!gotrad) rp = dc; while (dc<8) x *= 16, dc++; @@ -394,12 +411,13 @@ static long double hexfloat(FILE *f, int bits, int emin, int sign, int pok) return scalbnl(y, e2); } -long double __floatscan(FILE *f, int c, int prec, int pok) +long double __floatscan(FILE *f, int prec, int pok) { int sign = 1; int i; int bits; int emin; + int c; switch (prec) { case 0: @@ -418,7 +436,7 @@ long double __floatscan(FILE *f, int c, int prec, int pok) return 0; } - if (c<0) c = shgetc(f); + while (isspace((c=shgetc(f)))); if (c=='+' || c=='-') { sign -= 2*(c=='-'); @@ -435,7 +453,7 @@ long double __floatscan(FILE *f, int c, int prec, int pok) return sign * INFINITY; } if (!i) for (i=0; i<3 && (c|32)=="nan"[i]; i++) - if (i<3) c = shgetc(f); + if (i<2) c = shgetc(f); if (i==3) { return NAN; }