diff options
author | Bruno Haible <bruno@clisp.org> | 2011-10-15 13:24:29 +0200 |
---|---|---|
committer | Bruno Haible <bruno@clisp.org> | 2011-10-15 13:24:55 +0200 |
commit | 61e3e44b2a49643c05f0f5c0221d5a2ae3d363fd (patch) | |
tree | 1b4f377b2b8b1e7472738f65586341a5fa0ba1a9 /gettext-runtime/libasprintf | |
parent | f17ea2fd4bac7cdb3d934378cbcdce6b1118beb7 (diff) | |
download | external_gettext-61e3e44b2a49643c05f0f5c0221d5a2ae3d363fd.zip external_gettext-61e3e44b2a49643c05f0f5c0221d5a2ae3d363fd.tar.gz external_gettext-61e3e44b2a49643c05f0f5c0221d5a2ae3d363fd.tar.bz2 |
Update from gnulib.
Diffstat (limited to 'gettext-runtime/libasprintf')
-rw-r--r-- | gettext-runtime/libasprintf/ChangeLog | 6 | ||||
-rw-r--r-- | gettext-runtime/libasprintf/vasnprintf.c | 73 |
2 files changed, 57 insertions, 22 deletions
diff --git a/gettext-runtime/libasprintf/ChangeLog b/gettext-runtime/libasprintf/ChangeLog index da626d5..7032d00 100644 --- a/gettext-runtime/libasprintf/ChangeLog +++ b/gettext-runtime/libasprintf/ChangeLog @@ -1,5 +1,11 @@ 2011-10-15 Bruno Haible <bruno@clisp.org> + vasnprintf: Optimize bit search operation. + * vasnprintf.c (divide): Use optimizations from gnulib's + integer_length.c. + +2011-10-15 Bruno Haible <bruno@clisp.org> + vasnprintf: Fix comments. * vasnprintf.c (decode_long_double, decode_double): Fix comments. diff --git a/gettext-runtime/libasprintf/vasnprintf.c b/gettext-runtime/libasprintf/vasnprintf.c index 665d599..c6676c0 100644 --- a/gettext-runtime/libasprintf/vasnprintf.c +++ b/gettext-runtime/libasprintf/vasnprintf.c @@ -552,32 +552,61 @@ divide (mpn_t a, mpn_t b, mpn_t *q) size_t s; { mp_limb_t msd = b_ptr[b_len - 1]; /* = b[n-1], > 0 */ - s = 31; - if (msd >= 0x10000) - { - msd = msd >> 16; - s -= 16; - } - if (msd >= 0x100) - { - msd = msd >> 8; - s -= 8; - } - if (msd >= 0x10) - { - msd = msd >> 4; - s -= 4; - } - if (msd >= 0x4) + /* Determine s = GMP_LIMB_BITS - integer_length (msd). + Code copied from gnulib's integer_length.c. */ +# if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 4) + s = __builtin_clz (msd); +# else +# if defined DBL_EXPBIT0_WORD && defined DBL_EXPBIT0_BIT + if (GMP_LIMB_BITS <= DBL_MANT_BIT) { - msd = msd >> 2; - s -= 2; + /* Use 'double' operations. + Assumes an IEEE 754 'double' implementation. */ +# define DBL_EXP_MASK ((DBL_MAX_EXP - DBL_MIN_EXP) | 7) +# define DBL_EXP_BIAS (DBL_EXP_MASK / 2 - 1) +# define NWORDS \ + ((sizeof (double) + sizeof (unsigned int) - 1) / sizeof (unsigned int)) + union { double value; unsigned int word[NWORDS]; } m; + + /* Use a single integer to floating-point conversion. */ + m.value = msd; + + s = GMP_LIMB_BITS + - (((m.word[DBL_EXPBIT0_WORD] >> DBL_EXPBIT0_BIT) & DBL_EXP_MASK) + - DBL_EXP_BIAS); } - if (msd >= 0x2) + else +# undef NWORDS +# endif { - msd = msd >> 1; - s -= 1; + s = 31; + if (msd >= 0x10000) + { + msd = msd >> 16; + s -= 16; + } + if (msd >= 0x100) + { + msd = msd >> 8; + s -= 8; + } + if (msd >= 0x10) + { + msd = msd >> 4; + s -= 4; + } + if (msd >= 0x4) + { + msd = msd >> 2; + s -= 2; + } + if (msd >= 0x2) + { + msd = msd >> 1; + s -= 1; + } } +# endif } /* 0 <= s < GMP_LIMB_BITS. Copy b, shifting it left by s bits. */ |