From 1897ad44326bb7761dcda46132ae303f7288aba9 Mon Sep 17 00:00:00 2001 From: Joseph Myers Date: Mon, 19 Mar 2012 20:13:10 +0000 Subject: Fix clog overflow/underflow (bug 13629). --- math/s_clogl.c | 27 +++++++++++++++++++++++---- 1 file changed, 23 insertions(+), 4 deletions(-) (limited to 'math/s_clogl.c') diff --git a/math/s_clogl.c b/math/s_clogl.c index 11d4878252..8968eefee3 100644 --- a/math/s_clogl.c +++ b/math/s_clogl.c @@ -1,5 +1,5 @@ /* Compute complex natural logarithm. - Copyright (C) 1997, 1998, 2011 Free Software Foundation, Inc. + Copyright (C) 1997-2012 Free Software Foundation, Inc. This file is part of the GNU C Library. Contributed by Ulrich Drepper , 1997. @@ -20,7 +20,7 @@ #include #include #include - +#include __complex__ long double __clogl (__complex__ long double x) @@ -40,8 +40,27 @@ __clogl (__complex__ long double x) else if (__builtin_expect (rcls != FP_NAN && icls != FP_NAN, 1)) { /* Neither real nor imaginary part is NaN. */ - __real__ result = __ieee754_logl (__ieee754_hypotl (__real__ x, - __imag__ x)); + long double d; + int scale = 0; + + if (fabsl (__real__ x) > LDBL_MAX / 2.0L + || fabsl (__imag__ x) > LDBL_MAX / 2.0L) + { + scale = -1; + __real__ x = __scalbnl (__real__ x, scale); + __imag__ x = __scalbnl (__imag__ x, scale); + } + else if (fabsl (__real__ x) < LDBL_MIN + && fabsl (__imag__ x) < LDBL_MIN) + { + scale = LDBL_MANT_DIG; + __real__ x = __scalbnl (__real__ x, scale); + __imag__ x = __scalbnl (__imag__ x, scale); + } + + d = __ieee754_hypotl (__real__ x, __imag__ x); + + __real__ result = __ieee754_logl (d) - scale * M_LN2l; __imag__ result = __ieee754_atan2l (__imag__ x, __real__ x); } else -- cgit v1.2.1