diff options
author | zimmerma <zimmerma@280ebfd0-de03-0410-8827-d642c229c3f4> | 2016-02-05 09:54:31 +0000 |
---|---|---|
committer | zimmerma <zimmerma@280ebfd0-de03-0410-8827-d642c229c3f4> | 2016-02-05 09:54:31 +0000 |
commit | c54e31c37533c445fc27106d43f53908ac003e03 (patch) | |
tree | 12ae0b5ede52b485e3051ae7be07a43611d5e7d4 /src/fmma.c | |
parent | 967263f222a105307893c48e47c3534148f1e4b7 (diff) | |
download | mpfr-c54e31c37533c445fc27106d43f53908ac003e03.tar.gz |
fixed fmma failure
git-svn-id: svn://scm.gforge.inria.fr/svn/mpfr/trunk@9957 280ebfd0-de03-0410-8827-d642c229c3f4
Diffstat (limited to 'src/fmma.c')
-rw-r--r-- | src/fmma.c | 18 |
1 files changed, 10 insertions, 8 deletions
diff --git a/src/fmma.c b/src/fmma.c index a029376d8..0d37075c0 100644 --- a/src/fmma.c +++ b/src/fmma.c @@ -76,12 +76,16 @@ mpfr_fmma_fast (mpfr_ptr z, mpfr_srcptr a, mpfr_srcptr b, mpfr_srcptr c, if ((up[an + bn - 1] & MPFR_LIMB_HIGHBIT) == 0) { mpn_lshift (up, up, an + bn, 1); - MPFR_SET_EXP (u, MPFR_EXP(a) + MPFR_EXP(b) - 1); - if (MPFR_UNLIKELY(MPFR_EXP(u) == __MPFR_EXP_INF)) - goto failure; + /* EXP(a) and EXP(b) are in [1-2^(n-2), 2^(n-2)-1] where + mpfr_exp_t has is n-bit wide, thus EXP(a)+EXP(b) is in + [2-2^(n-1), 2^(n-1)-2]. We use the fact here that 2*MPFR_EMIN_MIN-1 + is a valid exponent (see mpfr-impl.h). However we don't use + MPFR_SET_EXP() which only allows the restricted exponent range + [1-2^(n-2), 2^(n-2)-1]. */ + MPFR_EXP(u) = MPFR_EXP(a) + MPFR_EXP(b) - 1; } else - MPFR_SET_EXP (u, MPFR_EXP(a) + MPFR_EXP(b)); + MPFR_EXP(u) = MPFR_EXP(a) + MPFR_EXP(b); /* v <- c*d */ if (cn >= dn) @@ -91,12 +95,10 @@ mpfr_fmma_fast (mpfr_ptr z, mpfr_srcptr a, mpfr_srcptr b, mpfr_srcptr c, if ((vp[cn + dn - 1] & MPFR_LIMB_HIGHBIT) == 0) { mpn_lshift (vp, vp, cn + dn, 1); - MPFR_SET_EXP (v, MPFR_EXP(c) + MPFR_EXP(d) - 1); - if (MPFR_UNLIKELY(MPFR_EXP(v) == __MPFR_EXP_INF)) - goto failure; + MPFR_EXP(v) = MPFR_EXP(c) + MPFR_EXP(d) - 1; } else - MPFR_SET_EXP (v, MPFR_EXP(c) + MPFR_EXP(d)); + MPFR_EXP(v) = MPFR_EXP(c) + MPFR_EXP(d); MPFR_PREC(u) = (an + bn) * GMP_NUMB_BITS; MPFR_PREC(v) = (cn + dn) * GMP_NUMB_BITS; |