Mercurial > hg > xemacs-beta
comparison src/number.c @ 5911:48386fd60fd0
GMP functions that take doubles choke on non-finite values, avoid that.
src/ChangeLog addition:
2015-05-10 Aidan Kehoe <kehoea@parhasard.net>
* floatfns.c (double_to_integer):
Rename this from float_to_int to fit our newer, bignum-compatible
terminology.
GMP can signal SIGFPE when asked to turn NaN or infinity into a
bignum, and we're not prepared to handle that signal if the OS float
library routines don't do that, so check for those values
explicitly.
* floatfns.c (ceiling_two_float):
* floatfns.c (ceiling_one_float):
* floatfns.c (floor_two_float):
* floatfns.c (floor_one_float):
* floatfns.c (round_two_float):
* floatfns.c (round_one_float):
* floatfns.c (truncate_two_float):
* floatfns.c (truncate_one_float):
Call double_to_integer() with its new name.
* number.c:
Don't use the {bignum,ratio,bigfloat}_set_double functions
directly here, with GMP they can choke when handed non-finite C
doubles, call Ftruncate() and the new float_to_bigfloat() from
floatfns.c. Maybe we should extend number-gmp.c with GMP-specific
implementations that check for non-finite values.
tests/ChangeLog addition:
2015-05-10 Aidan Kehoe <kehoea@parhasard.net>
* automated/lisp-tests.el:
Backslash a few parentheses in the first column for the sake of
fontification.
* automated/lisp-tests.el:
Check that the rounding functions signal Lisp errors correctly
when handed positive and negative infinity and NaN.
author | Aidan Kehoe <kehoea@parhasard.net> |
---|---|
date | Sun, 10 May 2015 19:07:09 +0100 |
parents | 6174848f3e6c |
children |
comparison
equal
deleted
inserted
replaced
5910:eb1e15c9440b | 5911:48386fd60fd0 |
---|---|
306 DEFINE_DUMPABLE_FROB_BLOCK_LISP_OBJECT ("bigfloat", bigfloat, 0, | 306 DEFINE_DUMPABLE_FROB_BLOCK_LISP_OBJECT ("bigfloat", bigfloat, 0, |
307 bigfloat_print, | 307 bigfloat_print, |
308 IF_NEW_GC (bigfloat_finalize), | 308 IF_NEW_GC (bigfloat_finalize), |
309 bigfloat_equal, bigfloat_hash, | 309 bigfloat_equal, bigfloat_hash, |
310 bigfloat_description, Lisp_Bigfloat); | 310 bigfloat_description, Lisp_Bigfloat); |
311 | |
312 extern Lisp_Object float_to_bigfloat (const Ascbyte *, Lisp_Object, | |
313 unsigned long); | |
311 | 314 |
312 #endif /* HAVE_BIGFLOAT */ | 315 #endif /* HAVE_BIGFLOAT */ |
313 | 316 |
314 Lisp_Object Qbigfloatp; | 317 Lisp_Object Qbigfloatp; |
315 | 318 |
599 { | 602 { |
600 case FIXNUM_T: | 603 case FIXNUM_T: |
601 return Ftruncate (number, Qnil); | 604 return Ftruncate (number, Qnil); |
602 case BIGNUM_T: | 605 case BIGNUM_T: |
603 #ifdef HAVE_BIGNUM | 606 #ifdef HAVE_BIGNUM |
604 bignum_set_double (scratch_bignum, XFLOAT_DATA (number)); | 607 { |
605 return make_bignum_bg (scratch_bignum); | 608 Lisp_Object truncate = Ftruncate (number, Qnil); |
609 return FIXNUMP (truncate) ? | |
610 make_bignum (XREALFIXNUM (truncate)) : truncate; | |
611 } | |
606 #else | 612 #else |
607 ABORT (); | 613 ABORT (); |
608 #endif /* HAVE_BIGNUM */ | 614 #endif /* HAVE_BIGNUM */ |
609 case RATIO_T: | 615 case RATIO_T: |
610 #ifdef HAVE_RATIO | 616 #ifdef HAVE_RATIO |
611 ratio_set_double (scratch_ratio, XFLOAT_DATA (number)); | 617 { |
612 return make_ratio_rt (scratch_ratio); | 618 Lisp_Object truncate = Ftruncate (number, Qnil); |
619 if (FIXNUMP (truncate)) | |
620 { | |
621 return make_ratio (XREALFIXNUM (truncate), 1UL); | |
622 } | |
623 | |
624 bignum_set_long (scratch_bignum, 1L); | |
625 return make_ratio_bg (XBIGNUM_DATA (truncate), scratch_bignum); | |
626 } | |
613 #else | 627 #else |
614 ABORT (); | 628 ABORT (); |
615 #endif /* HAVE_RATIO */ | 629 #endif /* HAVE_RATIO */ |
616 case FLOAT_T: | 630 case FLOAT_T: |
617 return number; | 631 return number; |
618 case BIGFLOAT_T: | 632 case BIGFLOAT_T: |
619 #ifdef HAVE_BIGFLOAT | 633 #ifdef HAVE_BIGFLOAT |
620 bigfloat_set_prec (scratch_bigfloat, precision); | 634 return float_to_bigfloat ("coerce-number", number, precision); |
621 bigfloat_set_double (scratch_bigfloat, XFLOAT_DATA (number)); | |
622 return make_bigfloat_bf (scratch_bigfloat); | |
623 #else | 635 #else |
624 ABORT (); | 636 ABORT (); |
625 #endif /* HAVE_BIGFLOAT */ | 637 #endif /* HAVE_BIGFLOAT */ |
626 } | 638 } |
627 case BIGFLOAT_T: | 639 case BIGFLOAT_T: |