webservices: Use a long double variable in format_double.

Signed-off-by: Hans Leidekker <hans@codeweavers.com>
Signed-off-by: Sebastian Lackner <sebastian@fds-team.de>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Hans Leidekker 2016-07-11 09:46:16 +02:00 committed by Alexandre Julliard
parent 0e5fdf0e00
commit d3cc9d1ca6
4 changed files with 19 additions and 7 deletions

1
configure vendored
View File

@ -16939,6 +16939,7 @@ for ac_func in \
lrintf \ lrintf \
lround \ lround \
lroundf \ lroundf \
powl \
remainder \ remainder \
remainderf \ remainderf \
rint \ rint \

View File

@ -2535,6 +2535,7 @@ AC_CHECK_FUNCS(\
lrintf \ lrintf \
lround \ lround \
lroundf \ lroundf \
powl \
remainder \ remainder \
remainderf \ remainderf \
rint \ rint \

View File

@ -16,6 +16,7 @@
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/ */
#include "config.h"
#include <stdarg.h> #include <stdarg.h>
#include <stdio.h> #include <stdio.h>
#include <math.h> #include <math.h>
@ -1049,9 +1050,10 @@ static ULONG format_uint64( const UINT64 *ptr, unsigned char *buf )
static ULONG format_double( const double *ptr, unsigned char *buf ) static ULONG format_double( const double *ptr, unsigned char *buf )
{ {
static const double precision = 0.0000000000000001; #ifdef HAVE_POWL
static const long double precision = 0.0000000000000001;
unsigned char *p = buf; unsigned char *p = buf;
double val = *ptr; /* FIXME: use long double */ long double val = *ptr;
int neg, mag, mag2, use_exp; int neg, mag, mag2, use_exp;
if (isnan( val )) if (isnan( val ))
@ -1081,12 +1083,12 @@ static ULONG format_double( const double *ptr, unsigned char *buf )
val = -val; val = -val;
} }
mag = log10( val ); mag = log10l( val );
use_exp = (mag >= 15 || (neg && mag >= 1) || mag <= -1); use_exp = (mag >= 15 || (neg && mag >= 1) || mag <= -1);
if (use_exp) if (use_exp)
{ {
if (mag < 0) mag -= 1; if (mag < 0) mag -= 1;
val = val / pow( 10.0, mag ); val = val / powl( 10.0, mag );
mag2 = mag; mag2 = mag;
mag = 0; mag = 0;
} }
@ -1094,14 +1096,14 @@ static ULONG format_double( const double *ptr, unsigned char *buf )
while (val > precision || mag >= 0) while (val > precision || mag >= 0)
{ {
double weight = pow( 10.0, mag ); long double weight = powl( 10.0, mag );
if (weight > 0 && !isinf( weight )) if (weight > 0 && !isinf( weight ))
{ {
int digit = floor( val / weight ); int digit = floorl( val / weight );
val -= digit * weight; val -= digit * weight;
*(p++) = '0' + digit; *(p++) = '0' + digit;
} }
if (!mag && val > 0) *(p++) = '.'; if (!mag && val > precision) *(p++) = '.';
mag--; mag--;
} }
@ -1131,6 +1133,10 @@ static ULONG format_double( const double *ptr, unsigned char *buf )
} }
return p - buf; return p - buf;
#else
FIXME( "powl not found at build time\n" );
return 0;
#endif
} }
static ULONG format_guid( const GUID *ptr, unsigned char *buf ) static ULONG format_guid( const GUID *ptr, unsigned char *buf )
@ -1212,6 +1218,7 @@ static HRESULT text_to_utf8text( const WS_XML_TEXT *text, WS_XML_UTF8_TEXT **ret
if (!set_fp_rounding( &fpword )) return E_NOTIMPL; if (!set_fp_rounding( &fpword )) return E_NOTIMPL;
len = format_double( &double_text->value, buf ); len = format_double( &double_text->value, buf );
restore_fp_rounding( fpword ); restore_fp_rounding( fpword );
if (!len) return E_NOTIMPL;
if (!(*ret = alloc_utf8_text( buf, len ))) return E_OUTOFMEMORY; if (!(*ret = alloc_utf8_text( buf, len ))) return E_OUTOFMEMORY;
return S_OK; return S_OK;
} }

View File

@ -672,6 +672,9 @@
/* Define to 1 if you have the <port.h> header file. */ /* Define to 1 if you have the <port.h> header file. */
#undef HAVE_PORT_H #undef HAVE_PORT_H
/* Define to 1 if you have the `powl' function. */
#undef HAVE_POWL
/* Define if we can use ppdev.h for parallel port access */ /* Define if we can use ppdev.h for parallel port access */
#undef HAVE_PPDEV #undef HAVE_PPDEV