diff options
author | pelissip <pelissip@280ebfd0-de03-0410-8827-d642c229c3f4> | 2004-09-28 09:26:34 +0000 |
---|---|---|
committer | pelissip <pelissip@280ebfd0-de03-0410-8827-d642c229c3f4> | 2004-09-28 09:26:34 +0000 |
commit | 49755dfe798eafade73ad324123e87ac9abf94b6 (patch) | |
tree | d8513c29600c2d61d0acc658ca3394ea00ce0e42 /mpn_exp.c | |
parent | 6ad38b945a6b11db9d516dc4a0c9c57a0c1175ed (diff) | |
download | mpfr-49755dfe798eafade73ad324123e87ac9abf94b6.tar.gz |
Fix how to detect overflow so that it can be build with GCC -ftrapv
option without any bugs (In the previous code, the overflow was
detected afterwards, whereas, now, it is detected before).
Fix also another real problem of overflow (Addition of two signed integers).
git-svn-id: svn://scm.gforge.inria.fr/svn/mpfr/trunk@3002 280ebfd0-de03-0410-8827-d642c229c3f4
Diffstat (limited to 'mpn_exp.c')
-rw-r--r-- | mpn_exp.c | 22 |
1 files changed, 12 insertions, 10 deletions
@@ -95,16 +95,18 @@ mpfr_mpn_exp (mp_limb_t *a, mp_exp_t *exp_r, int b, mp_exp_t e, size_t n) /* set {c+n, 2n1-n} to 0 : {c, n} = {a, n}^2*K^n */ /* check overflow on f */ - { - mp_exp_t oldf = f; - f = 2 * f; - if (f / 2 != oldf) - { - TMP_FREE(marker); - return -2; - } - } - f += n * BITS_PER_MP_LIMB; + if (MPFR_UNLIKELY(f < MPFR_EXP_MIN/2 || f > MPFR_EXP_MAX/2)) + { + overflow: + TMP_FREE(marker); + return -2; + } + /* FIXME: Could f = 2*f + n * BITS_PER_MP_LIMB be used? */ + f = 2*f; + MPFR_SADD_OVERFLOW (f, f, n * BITS_PER_MP_LIMB, + mp_exp_t, mp_exp_unsigned_t, + MPFR_EXP_MIN, MPFR_EXP_MAX, + goto overflow, goto overflow); if ((c[2*n - 1] & MPFR_LIMB_HIGHBIT) == 0) { /* shift A by one bit to the left */ |