Mercurial > hg > xemacs-beta
comparison src/number.c @ 4802:2fc0e2f18322
Don't create any bignums before pdumping. Add bignum, ratio, and bigfloat
finalizers so we don't leak memory with NEW_GC. See xemacs-patches message
with ID <870180fe1001060900o46fa2b7o26b58850fadf9aba@mail.gmail.com>.
author | Jerry James <james@xemacs.org> |
---|---|
date | Wed, 06 Jan 2010 10:01:14 -0700 |
parents | b5e1d4f6b66f |
children | f730384b8ddf 6772ce4d982b |
comparison
equal
deleted
inserted
replaced
4801:591091481f20 | 4802:2fc0e2f18322 |
---|---|
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | 13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License |
14 for more details. | 14 for more details. |
15 | 15 |
16 You should have received a copy of the GNU General Public License | 16 You should have received a copy of the GNU General Public License |
17 along with XEmacs; see the file COPYING. If not, write to | 17 along with XEmacs; see the file COPYING. If not, write to |
18 the Free Software Foundation, Inc., 59 Temple Place - Suite 330, | 18 the Free Software Foundation, Inc., 51 Franklin St - Fifth Floor, |
19 Boston, MA 02111-1307, USA. */ | 19 Boston, MA 02111-1301, USA. */ |
20 | 20 |
21 /* Synched up with: Not in FSF. */ | 21 /* Synched up with: Not in FSF. */ |
22 | 22 |
23 #include <config.h> | 23 #include <config.h> |
24 #include <limits.h> | 24 #include <limits.h> |
56 CIbyte *bstr = bignum_to_string (XBIGNUM_DATA (obj), 10); | 56 CIbyte *bstr = bignum_to_string (XBIGNUM_DATA (obj), 10); |
57 write_c_string (printcharfun, bstr); | 57 write_c_string (printcharfun, bstr); |
58 xfree (bstr, CIbyte *); | 58 xfree (bstr, CIbyte *); |
59 } | 59 } |
60 | 60 |
61 #ifdef NEW_GC | |
62 static void | |
63 bignum_finalize (void *header, int for_disksave) | |
64 { | |
65 if (!for_disksave) | |
66 { | |
67 struct Lisp_Bignum *num = (struct Lisp_Bignum *) header; | |
68 bignum_fini (num->data); | |
69 } | |
70 } | |
71 #define BIGNUM_FINALIZE bignum_finalize | |
72 #else | |
73 #define BIGNUM_FINALIZE 0 | |
74 #endif | |
75 | |
61 static int | 76 static int |
62 bignum_equal (Lisp_Object obj1, Lisp_Object obj2, int UNUSED (depth)) | 77 bignum_equal (Lisp_Object obj1, Lisp_Object obj2, int UNUSED (depth)) |
63 { | 78 { |
64 return bignum_eql (XBIGNUM_DATA (obj1), XBIGNUM_DATA (obj2)); | 79 return bignum_eql (XBIGNUM_DATA (obj1), XBIGNUM_DATA (obj2)); |
65 } | 80 } |
105 0, { &bignum_opc }, XD_FLAG_NO_KKCC }, | 120 0, { &bignum_opc }, XD_FLAG_NO_KKCC }, |
106 { XD_END } | 121 { XD_END } |
107 }; | 122 }; |
108 | 123 |
109 DEFINE_BASIC_LRECORD_IMPLEMENTATION ("bignum", bignum, 1, 0, bignum_print, | 124 DEFINE_BASIC_LRECORD_IMPLEMENTATION ("bignum", bignum, 1, 0, bignum_print, |
110 0, bignum_equal, bignum_hash, | 125 BIGNUM_FINALIZE, bignum_equal, |
111 bignum_description, Lisp_Bignum); | 126 bignum_hash, bignum_description, |
127 Lisp_Bignum); | |
112 | 128 |
113 #endif /* HAVE_BIGNUM */ | 129 #endif /* HAVE_BIGNUM */ |
114 | 130 |
115 Lisp_Object Qbignump; | 131 Lisp_Object Qbignump; |
116 | 132 |
164 CIbyte *rstr = ratio_to_string (XRATIO_DATA (obj), 10); | 180 CIbyte *rstr = ratio_to_string (XRATIO_DATA (obj), 10); |
165 write_c_string (printcharfun, rstr); | 181 write_c_string (printcharfun, rstr); |
166 xfree (rstr, CIbyte *); | 182 xfree (rstr, CIbyte *); |
167 } | 183 } |
168 | 184 |
185 #ifdef NEW_GC | |
186 static void | |
187 ratio_finalize (void *header, int for_disksave) | |
188 { | |
189 if (!for_disksave) | |
190 { | |
191 struct Lisp_Ratio *num = (struct Lisp_Ratio *) header; | |
192 ratio_fini (num->data); | |
193 } | |
194 } | |
195 #define RATIO_FINALIZE ratio_finalize | |
196 #else | |
197 #define RATIO_FINALIZE 0 | |
198 #endif | |
199 | |
169 static int | 200 static int |
170 ratio_equal (Lisp_Object obj1, Lisp_Object obj2, int UNUSED (depth)) | 201 ratio_equal (Lisp_Object obj1, Lisp_Object obj2, int UNUSED (depth)) |
171 { | 202 { |
172 return ratio_eql (XRATIO_DATA (obj1), XRATIO_DATA (obj2)); | 203 return ratio_eql (XRATIO_DATA (obj1), XRATIO_DATA (obj2)); |
173 } | 204 } |
182 { XD_OPAQUE_PTR, offsetof (Lisp_Ratio, data) }, | 213 { XD_OPAQUE_PTR, offsetof (Lisp_Ratio, data) }, |
183 { XD_END } | 214 { XD_END } |
184 }; | 215 }; |
185 | 216 |
186 DEFINE_BASIC_LRECORD_IMPLEMENTATION ("ratio", ratio, 0, 0, ratio_print, | 217 DEFINE_BASIC_LRECORD_IMPLEMENTATION ("ratio", ratio, 0, 0, ratio_print, |
187 0, ratio_equal, ratio_hash, | 218 RATIO_FINALIZE, ratio_equal, ratio_hash, |
188 ratio_description, Lisp_Ratio); | 219 ratio_description, Lisp_Ratio); |
189 | 220 |
190 #endif /* HAVE_RATIO */ | 221 #endif /* HAVE_RATIO */ |
191 | 222 |
192 Lisp_Object Qratiop; | 223 Lisp_Object Qratiop; |
251 CIbyte *fstr = bigfloat_to_string (XBIGFLOAT_DATA (obj), 10); | 282 CIbyte *fstr = bigfloat_to_string (XBIGFLOAT_DATA (obj), 10); |
252 write_c_string (printcharfun, fstr); | 283 write_c_string (printcharfun, fstr); |
253 xfree (fstr, CIbyte *); | 284 xfree (fstr, CIbyte *); |
254 } | 285 } |
255 | 286 |
287 #ifdef NEW_GC | |
288 static void | |
289 bigfloat_finalize (void *header, int for_disksave) | |
290 { | |
291 if (!for_disksave) | |
292 { | |
293 struct Lisp_Bigfloat *num = (struct Lisp_Bigfloat *) header; | |
294 bigfloat_fini (num->bf); | |
295 } | |
296 } | |
297 #define BIGFLOAT_FINALIZE bigfloat_finalize | |
298 #else | |
299 #define BIGFLOAT_FINALIZE 0 | |
300 #endif | |
301 | |
256 static int | 302 static int |
257 bigfloat_equal (Lisp_Object obj1, Lisp_Object obj2, int UNUSED (depth)) | 303 bigfloat_equal (Lisp_Object obj1, Lisp_Object obj2, int UNUSED (depth)) |
258 { | 304 { |
259 return bigfloat_eql (XBIGFLOAT_DATA (obj1), XBIGFLOAT_DATA (obj2)); | 305 return bigfloat_eql (XBIGFLOAT_DATA (obj1), XBIGFLOAT_DATA (obj2)); |
260 } | 306 } |
269 { XD_OPAQUE_PTR, offsetof (Lisp_Bigfloat, bf) }, | 315 { XD_OPAQUE_PTR, offsetof (Lisp_Bigfloat, bf) }, |
270 { XD_END } | 316 { XD_END } |
271 }; | 317 }; |
272 | 318 |
273 DEFINE_BASIC_LRECORD_IMPLEMENTATION ("bigfloat", bigfloat, 1, 0, | 319 DEFINE_BASIC_LRECORD_IMPLEMENTATION ("bigfloat", bigfloat, 1, 0, |
274 bigfloat_print, 0, | 320 bigfloat_print, BIGFLOAT_FINALIZE, |
275 bigfloat_equal, bigfloat_hash, | 321 bigfloat_equal, bigfloat_hash, |
276 bigfloat_description, Lisp_Bigfloat); | 322 bigfloat_description, Lisp_Bigfloat); |
277 | 323 |
278 #endif /* HAVE_BIGFLOAT */ | 324 #endif /* HAVE_BIGFLOAT */ |
279 | 325 |
343 | 389 |
344 CONCHECK_INTEGER (*val); | 390 CONCHECK_INTEGER (*val); |
345 #ifdef HAVE_BIGFLOAT | 391 #ifdef HAVE_BIGFLOAT |
346 if (INTP (*val)) | 392 if (INTP (*val)) |
347 prec = XINT (*val); | 393 prec = XINT (*val); |
348 else | 394 else |
349 { | 395 { |
350 if (!bignum_fits_ulong_p (XBIGNUM_DATA (*val))) | 396 if (!bignum_fits_ulong_p (XBIGNUM_DATA (*val))) |
351 args_out_of_range_3 (*val, Qzero, Vbigfloat_max_prec); | 397 args_out_of_range_3 (*val, Qzero, Vbigfloat_max_prec); |
352 prec = bignum_to_ulong (XBIGNUM_DATA (*val)); | 398 prec = bignum_to_ulong (XBIGNUM_DATA (*val)); |
353 } | 399 } |
653 ? XBIGFLOAT_GET_PREC (*arg2) : | 699 ? XBIGFLOAT_GET_PREC (*arg2) : |
654 #endif | 700 #endif |
655 0UL); | 701 0UL); |
656 return type2; | 702 return type2; |
657 } | 703 } |
658 | 704 |
659 if (type2 < type1) | 705 if (type2 < type1) |
660 { | 706 { |
661 *arg2 = internal_coerce_number (*arg2, type1, | 707 *arg2 = internal_coerce_number (*arg2, type1, |
662 #ifdef HAVE_BIGFLOAT | 708 #ifdef HAVE_BIGFLOAT |
663 type1 == BIGFLOAT_T | 709 type1 == BIGFLOAT_T |
798 The maximum number of bits of precision a bigfloat can have. | 844 The maximum number of bits of precision a bigfloat can have. |
799 This is determined by the underlying library used to implement bigfloats. | 845 This is determined by the underlying library used to implement bigfloats. |
800 */); | 846 */); |
801 | 847 |
802 #ifdef HAVE_BIGFLOAT | 848 #ifdef HAVE_BIGFLOAT |
803 #ifdef HAVE_BIGNUM | 849 /* Don't create a bignum here. Otherwise, we lose with NEW_GC + pdump. |
804 Vbigfloat_max_prec = make_bignum (0L); | 850 See reinit_vars_of_number(). */ |
805 bignum_set_ulong (XBIGNUM_DATA (Vbigfloat_max_prec), ULONG_MAX); | |
806 #else | |
807 Vbigfloat_max_prec = make_int (EMACS_INT_MAX); | 851 Vbigfloat_max_prec = make_int (EMACS_INT_MAX); |
808 #endif | |
809 #else | 852 #else |
810 Vbigfloat_max_prec = make_int (0); | 853 Vbigfloat_max_prec = make_int (0); |
811 #endif /* HAVE_BIGFLOAT */ | 854 #endif /* HAVE_BIGFLOAT */ |
812 | 855 |
813 DEFVAR_CONST_INT ("most-negative-fixnum", &Vmost_negative_fixnum /* | 856 DEFVAR_CONST_INT ("most-negative-fixnum", &Vmost_negative_fixnum /* |
831 Fprovide (intern ("bigfloat")); | 874 Fprovide (intern ("bigfloat")); |
832 #endif | 875 #endif |
833 } | 876 } |
834 | 877 |
835 void | 878 void |
879 reinit_vars_of_number (void) | |
880 { | |
881 #if defined(HAVE_BIGFLOAT) && defined(HAVE_BIGNUM) | |
882 Vbigfloat_max_prec = make_bignum (0L); | |
883 bignum_set_ulong (XBIGNUM_DATA (Vbigfloat_max_prec), ULONG_MAX); | |
884 #endif | |
885 } | |
886 | |
887 void | |
836 init_number (void) | 888 init_number (void) |
837 { | 889 { |
838 if (!number_initialized) | 890 if (!number_initialized) |
839 { | 891 { |
840 number_initialized = 1; | 892 number_initialized = 1; |
858 | 910 |
859 #ifdef HAVE_BIGFLOAT | 911 #ifdef HAVE_BIGFLOAT |
860 bigfloat_init (scratch_bigfloat); | 912 bigfloat_init (scratch_bigfloat); |
861 bigfloat_init (scratch_bigfloat2); | 913 bigfloat_init (scratch_bigfloat2); |
862 #endif | 914 #endif |
863 } | 915 |
864 } | 916 #ifndef PDUMP |
917 reinit_vars_of_number (); | |
918 #endif | |
919 } | |
920 } |