aboutsummaryrefslogtreecommitdiffstats
path: root/src/lisp.h
diff options
context:
space:
mode:
authorPaul Eggert2018-08-21 02:16:50 -0700
committerPaul Eggert2018-08-21 02:38:53 -0700
commitd6a497dd887cdbb35c5b4e2929e83962ba708159 (patch)
tree9f0441f9fe88419b71e568b05ef7f7bea0a0ff06 /src/lisp.h
parent77fc2725985b4e5ef977ae6930835c7f0771c61c (diff)
downloademacs-d6a497dd887cdbb35c5b4e2929e83962ba708159.tar.gz
emacs-d6a497dd887cdbb35c5b4e2929e83962ba708159.zip
Avoid libgmp aborts by imposing limits
libgmp calls ‘abort’ when given numbers too big for its internal data structures. The numeric limit is large and platform-dependent; with 64-bit GMP 6.1.2 it is around 2**2**37. Work around the problem by refusing to call libgmp functions with arguments that would cause an abort. With luck libgmp will have a better way to do this in the future. Also, introduce a variable integer-width that lets the user control how large bignums can be. This currently defaults to 2**16, i.e., it allows bignums up to 2**2**16. This should be enough for ordinary computation, and should help Emacs to avoid thrashing or hanging. Problem noted by Pip Cet (Bug#32463#71). * doc/lispref/numbers.texi, etc/NEWS: Document recent bignum changes, including this one. Improve documentation for bitwise operations, in the light of bignums. * src/alloc.c (make_number): Enforce integer-width. (integer_overflow): New function. (xrealloc_for_gmp, xfree_for_gmp): Move here from emacs.c, as it's memory allocation. (init_alloc): Initialize GMP here, rather than in emacs.c. (integer_width): New var. * src/data.c (GMP_NLIMBS_MAX, NLIMBS_LIMIT): New constants. (emacs_mpz_size, emacs_mpz_mul) (emacs_mpz_mul_2exp, emacs_mpz_pow_ui): New functions. (arith_driver, Fash, expt_integer): Use them. (expt_integer): New function, containing integer code that was out of place in floatfns.c. (check_bignum_size, xmalloc_for_gmp): Remove. * src/emacs.c (main): Do not initialize GMP here. * src/floatfns.c (Fexpt): Use expt_integer, which now contains integer code moved from here. * src/lisp.h (GMP_NUMB_BITS): Define if gmp.h doesn’t.
Diffstat (limited to 'src/lisp.h')
-rw-r--r--src/lisp.h11
1 files changed, 10 insertions, 1 deletions
diff --git a/src/lisp.h b/src/lisp.h
index fe384d1844b..8f48a334844 100644
--- a/src/lisp.h
+++ b/src/lisp.h
@@ -996,6 +996,14 @@ enum More_Lisp_Bits
996#define MOST_POSITIVE_FIXNUM (EMACS_INT_MAX >> INTTYPEBITS) 996#define MOST_POSITIVE_FIXNUM (EMACS_INT_MAX >> INTTYPEBITS)
997#define MOST_NEGATIVE_FIXNUM (-1 - MOST_POSITIVE_FIXNUM) 997#define MOST_NEGATIVE_FIXNUM (-1 - MOST_POSITIVE_FIXNUM)
998 998
999
1000/* GMP-related limits. */
1001
1002/* Number of data bits in a limb. */
1003#ifndef GMP_NUMB_BITS
1004enum { GMP_NUMB_BITS = TYPE_WIDTH (mp_limb_t) };
1005#endif
1006
999#if USE_LSB_TAG 1007#if USE_LSB_TAG
1000 1008
1001INLINE Lisp_Object 1009INLINE Lisp_Object
@@ -3338,7 +3346,7 @@ extern void set_internal (Lisp_Object, Lisp_Object, Lisp_Object,
3338 enum Set_Internal_Bind); 3346 enum Set_Internal_Bind);
3339extern void set_default_internal (Lisp_Object, Lisp_Object, 3347extern void set_default_internal (Lisp_Object, Lisp_Object,
3340 enum Set_Internal_Bind bindflag); 3348 enum Set_Internal_Bind bindflag);
3341 3349extern Lisp_Object expt_integer (Lisp_Object, Lisp_Object);
3342extern void syms_of_data (void); 3350extern void syms_of_data (void);
3343extern void swap_in_global_binding (struct Lisp_Symbol *); 3351extern void swap_in_global_binding (struct Lisp_Symbol *);
3344 3352
@@ -3700,6 +3708,7 @@ extern void display_malloc_warning (void);
3700extern ptrdiff_t inhibit_garbage_collection (void); 3708extern ptrdiff_t inhibit_garbage_collection (void);
3701extern Lisp_Object build_overlay (Lisp_Object, Lisp_Object, Lisp_Object); 3709extern Lisp_Object build_overlay (Lisp_Object, Lisp_Object, Lisp_Object);
3702extern void free_cons (struct Lisp_Cons *); 3710extern void free_cons (struct Lisp_Cons *);
3711extern _Noreturn void integer_overflow (void);
3703extern void init_alloc_once (void); 3712extern void init_alloc_once (void);
3704extern void init_alloc (void); 3713extern void init_alloc (void);
3705extern void syms_of_alloc (void); 3714extern void syms_of_alloc (void);