commit 4ef1dabaea247b73f87767e529e87b5bb865b5b7
parent 1fec6d764b22c61919708f5fc874198937fc4645
Author: Andres Navarro <canavarro82@gmail.com>
Date: Sun, 1 May 2011 00:08:34 -0300
Bugfix in kbigint_to_double there was an infinite loop caused by an unsigned var that couldn't get below 0.
Diffstat:
2 files changed, 10 insertions(+), 7 deletions(-)
diff --git a/src/kreal.c b/src/kreal.c
@@ -33,15 +33,16 @@
double kbigint_to_double(Bigint *bigint)
{
double radix = (double) UINT32_MAX + 1.0;
- uint32_t ndigits = bigint->used - 1;
- double accum = 0;
+ uint32_t ndigits = bigint->used;
+ double accum = 0.0;
/* bigint is in little endian format, but we traverse in
big endian */
- while(ndigits >= 0) {
- accum = accum * radix + (double) bigint->digits[ndigits];
+ do {
--ndigits;
- }
+ accum = accum * radix + (double) bigint->digits[ndigits];
+ } while (ndigits > 0); /* have to compare like this, it's unsigned */
+ return mp_int_compare_zero(bigint) < 0? -accum : accum;
}
TValue kexact_to_inexact(klisp_State *K, TValue n)
@@ -50,7 +51,8 @@ TValue kexact_to_inexact(klisp_State *K, TValue n)
case K_TFIXINT:
return d2tv((double) ivalue(n));
case K_TBIGINT: {
- double d = kbigint_to_double(tv2bigint(n));
+ Bigint *bigint = tv2bigint(n);
+ double d = kbigint_to_double(bigint);
/* d may be inf, ktag_double will handle it */
/* MAYBE should throw an exception if strict is on */
return ktag_double(d);
diff --git a/src/kwrite.c b/src/kwrite.c
@@ -289,7 +289,8 @@ void kwrite_simple(klisp_State *K, TValue obj)
break;
case K_TDOUBLE:
/* TODO investigate this further */
- kw_printf(K, "%17.e", dvalue(obj));
+ /* LOCALE, significant digits, etc */
+ kw_printf(K, "%f", dvalue(obj));
break;
case K_TRWNPV:
/* ASK John/TEMP: until John tells me what should this be... */