aboutsummaryrefslogtreecommitdiffstats
path: root/src/lisp.h
diff options
context:
space:
mode:
authorStefan Monnier2009-11-06 18:47:48 +0000
committerStefan Monnier2009-11-06 18:47:48 +0000
commit2de9f71c22f9def6adaa6782eea25bc569cb8561 (patch)
tree399507700b025f007803c590ef825f5eea3f989d /src/lisp.h
parent7ac65b38938cdee2916350bc0b16f21a00dca444 (diff)
downloademacs-2de9f71c22f9def6adaa6782eea25bc569cb8561.tar.gz
emacs-2de9f71c22f9def6adaa6782eea25bc569cb8561.zip
Let integers use up 2 tags to give them one extra bit and double their range.
* lisp.h (USE_2_TAGS_FOR_INTS): New macro. (LISP_INT_TAG, case_Lisp_Int, LISP_STRING_TAG, LISP_INT_TAG_P): New macros. (enum Lisp_Type): Use them. Give explicit values. (Lisp_Type_Limit): Remove. (XINT, XUINT, make_number) [!USE_LISP_UNION_TYPE]: (MOST_NEGATIVE_FIXNUM, MOST_POSITIVE_FIXNUM, INTMASK): Pay attention to USE_2_TAGS_FOR_INTS. (INTEGERP): Use LISP_INT_TAG_P. * fns.c (internal_equal): Simplify the default case. (sxhash): Use case_Lisp_Int. * data.c (wrong_type_argument): Don't check against Lisp_Type_Limit any more. (Ftype_of): Use case_Lisp_Int. (store_symval_forwarding): Take into account the fact that Ints can now have more than one tag. * buffer.c (syms_of_buffer): Use LISP_INT_TAG. buffer_slot_type_mismatch): * xfaces.c (face_attr_equal_p): * print.c (print_object): * alloc.c (mark_maybe_object, mark_object, survives_gc_p): Use case_Lisp_Int.
Diffstat (limited to 'src/lisp.h')
-rw-r--r--src/lisp.h117
1 files changed, 82 insertions, 35 deletions
diff --git a/src/lisp.h b/src/lisp.h
index 95759c18f51..65c88dcfab7 100644
--- a/src/lisp.h
+++ b/src/lisp.h
@@ -150,37 +150,68 @@ extern void die P_((const char *, const char *, int)) NO_RETURN;
150 150
151/* Define the fundamental Lisp data structures. */ 151/* Define the fundamental Lisp data structures. */
152 152
153/* If USE_2_TAGBITS_FOR_INTS is defined, then Lisp integers use
154 2 tags, to give them one extra bit, thus extending their range from
155 e.g -2^28..2^28-1 to -2^29..2^29-1. */
156#define USE_2_TAGS_FOR_INTS
157
158/* Making it work for the union case is too much trouble. */
159#ifdef USE_LISP_UNION_TYPE
160# undef USE_2_TAGS_FOR_INTS
161#endif
162
153/* This is the set of Lisp data types. */ 163/* This is the set of Lisp data types. */
154 164
165#if !defined USE_2_TAGS_FOR_INTS
166# define LISP_INT_TAG Lisp_Int
167# define case_Lisp_Int case Lisp_Int
168# define LISP_STRING_TAG 4
169# define LISP_INT_TAG_P(x) ((x) == Lisp_Int)
170#else
171# define LISP_INT_TAG Lisp_Int0
172# define case_Lisp_Int case Lisp_Int0: case Lisp_Int1
173# ifdef USE_LSB_TAG
174# define LISP_INT1_TAG 4
175# define LISP_STRING_TAG 1
176# define LISP_INT_TAG_P(x) (((x) & 3) == 0)
177# else
178# define LISP_INT1_TAG 1
179# define LISP_STRING_TAG 4
180# define LISP_INT_TAG_P(x) (((x) & 6) == 0)
181# endif
182#endif
183
155enum Lisp_Type 184enum Lisp_Type
156 { 185 {
157 /* Integer. XINT (obj) is the integer value. */ 186 /* Integer. XINT (obj) is the integer value. */
158 Lisp_Int, 187#ifdef USE_2_TAGS_FOR_INTS
188 Lisp_Int0 = 0,
189 Lisp_Int1 = LISP_INT1_TAG,
190#else
191 Lisp_Int = 0,
192#endif
159 193
160 /* Symbol. XSYMBOL (object) points to a struct Lisp_Symbol. */ 194 /* Symbol. XSYMBOL (object) points to a struct Lisp_Symbol. */
161 Lisp_Symbol, 195 Lisp_Symbol = 2,
162 196
163 /* Miscellaneous. XMISC (object) points to a union Lisp_Misc, 197 /* Miscellaneous. XMISC (object) points to a union Lisp_Misc,
164 whose first member indicates the subtype. */ 198 whose first member indicates the subtype. */
165 Lisp_Misc, 199 Lisp_Misc = 3,
166 200
167 /* String. XSTRING (object) points to a struct Lisp_String. 201 /* String. XSTRING (object) points to a struct Lisp_String.
168 The length of the string, and its contents, are stored therein. */ 202 The length of the string, and its contents, are stored therein. */
169 Lisp_String, 203 Lisp_String = LISP_STRING_TAG,
170 204
171 /* Vector of Lisp objects, or something resembling it. 205 /* Vector of Lisp objects, or something resembling it.
172 XVECTOR (object) points to a struct Lisp_Vector, which contains 206 XVECTOR (object) points to a struct Lisp_Vector, which contains
173 the size and contents. The size field also contains the type 207 the size and contents. The size field also contains the type
174 information, if it's not a real vector object. */ 208 information, if it's not a real vector object. */
175 Lisp_Vectorlike, 209 Lisp_Vectorlike = 5,
176 210
177 /* Cons. XCONS (object) points to a struct Lisp_Cons. */ 211 /* Cons. XCONS (object) points to a struct Lisp_Cons. */
178 Lisp_Cons, 212 Lisp_Cons = 6,
179
180 Lisp_Float,
181 213
182 /* This is not a type code. It is for range checking. */ 214 Lisp_Float = 7,
183 Lisp_Type_Limit
184 }; 215 };
185 216
186/* This is the set of data types that share a common structure. 217/* This is the set of data types that share a common structure.
@@ -353,12 +384,18 @@ enum pvec_type
353 384
354#define TYPEMASK ((((EMACS_INT) 1) << GCTYPEBITS) - 1) 385#define TYPEMASK ((((EMACS_INT) 1) << GCTYPEBITS) - 1)
355#define XTYPE(a) ((enum Lisp_Type) (((EMACS_UINT) (a)) & TYPEMASK)) 386#define XTYPE(a) ((enum Lisp_Type) (((EMACS_UINT) (a)) & TYPEMASK))
356#define XINT(a) (((EMACS_INT) (a)) >> GCTYPEBITS) 387#ifdef USE_2_TAGS_FOR_INTS
357#define XUINT(a) (((EMACS_UINT) (a)) >> GCTYPEBITS) 388# define XINT(a) (((EMACS_INT) (a)) >> (GCTYPEBITS - 1))
389# define XUINT(a) (((EMACS_UINT) (a)) >> (GCTYPEBITS - 1))
390# define make_number(N) (((EMACS_INT) (N)) << (GCTYPEBITS - 1))
391#else
392# define XINT(a) (((EMACS_INT) (a)) >> GCTYPEBITS)
393# define XUINT(a) (((EMACS_UINT) (a)) >> GCTYPEBITS)
394# define make_number(N) (((EMACS_INT) (N)) << GCTYPEBITS)
395#endif
358#define XSET(var, type, ptr) \ 396#define XSET(var, type, ptr) \
359 (eassert (XTYPE (ptr) == 0), /* Check alignment. */ \ 397 (eassert (XTYPE (ptr) == 0), /* Check alignment. */ \
360 (var) = ((EMACS_INT) (type)) | ((EMACS_INT) (ptr))) 398 (var) = ((EMACS_INT) (type)) | ((EMACS_INT) (ptr)))
361#define make_number(N) (((EMACS_INT) (N)) << GCTYPEBITS)
362 399
363#define XPNTR(a) ((EMACS_INT) ((a) & ~TYPEMASK)) 400#define XPNTR(a) ((EMACS_INT) ((a) & ~TYPEMASK))
364 401
@@ -378,41 +415,43 @@ enum pvec_type
378#define XFASTINT(a) ((a) + 0) 415#define XFASTINT(a) ((a) + 0)
379#define XSETFASTINT(a, b) ((a) = (b)) 416#define XSETFASTINT(a, b) ((a) = (b))
380 417
381/* Extract the value of a Lisp_Object as a signed integer. */ 418/* Extract the value of a Lisp_Object as a (un)signed integer. */
382 419
383#ifndef XINT /* Some machines need to do this differently. */ 420#ifdef USE_2_TAGS_FOR_INTS
384#define XINT(a) ((((EMACS_INT) (a)) << (BITS_PER_EMACS_INT - VALBITS)) \ 421# define XINT(a) ((((EMACS_INT) (a)) << (GCTYPEBITS - 1)) >> (GCTYPEBITS - 1))
422# define XUINT(a) ((EMACS_UINT) ((a) & (1 + (VALMASK << 1))))
423# define make_number(N) ((((EMACS_INT) (N)) & (1 + (VALMASK << 1))))
424#else
425# define XINT(a) ((((EMACS_INT) (a)) << (BITS_PER_EMACS_INT - VALBITS)) \
385 >> (BITS_PER_EMACS_INT - VALBITS)) 426 >> (BITS_PER_EMACS_INT - VALBITS))
427# define XUINT(a) ((EMACS_UINT) ((a) & VALMASK))
428# define make_number(N) \
429 ((((EMACS_INT) (N)) & VALMASK) | ((EMACS_INT) Lisp_Int) << VALBITS)
386#endif 430#endif
387 431
388/* Extract the value as an unsigned integer. This is a basis
389 for extracting it as a pointer to a structure in storage. */
390
391#ifndef XUINT
392#define XUINT(a) ((EMACS_UINT) ((a) & VALMASK))
393#endif
394
395#ifndef XSET
396#define XSET(var, type, ptr) \ 432#define XSET(var, type, ptr) \
397 ((var) = ((EMACS_INT)(type) << VALBITS) + ((EMACS_INT) (ptr) & VALMASK)) 433 ((var) = ((EMACS_INT)(type) << VALBITS) + ((EMACS_INT) (ptr) & VALMASK))
398#endif
399
400/* Convert a C integer into a Lisp_Object integer. */
401 434
402#define make_number(N) \ 435#define XPNTR(a) ((EMACS_UINT) ((a) & VALMASK))
403 ((((EMACS_INT) (N)) & VALMASK) | ((EMACS_INT) Lisp_Int) << VALBITS)
404 436
405#endif /* not USE_LSB_TAG */ 437#endif /* not USE_LSB_TAG */
406 438
407#else /* USE_LISP_UNION_TYPE */ 439#else /* USE_LISP_UNION_TYPE */
408 440
441#ifdef USE_2_TAGS_FOR_INTS
442# error "USE_2_TAGS_FOR_INTS is not supported with USE_LISP_UNION_TYPE"
443#endif
444
409#define XHASH(a) ((a).i) 445#define XHASH(a) ((a).i)
410 446
411#define XTYPE(a) ((enum Lisp_Type) (a).u.type) 447#define XTYPE(a) ((enum Lisp_Type) (a).u.type)
412 448
413#ifdef EXPLICIT_SIGN_EXTEND 449#ifdef EXPLICIT_SIGN_EXTEND
414/* Make sure we sign-extend; compilers have been known to fail to do so. */ 450/* Make sure we sign-extend; compilers have been known to fail to do so.
415#define XINT(a) (((a).s.val << (BITS_PER_EMACS_INT - VALBITS)) \ 451 We additionally cast to EMACS_INT since it seems that some compilers
452 have been known to fail to do so, even though the bitfield is declared
453 as EMACS_INT already. */
454#define XINT(a) ((((EMACS_INT) (a).s.val) << (BITS_PER_EMACS_INT - VALBITS)) \
416 >> (BITS_PER_EMACS_INT - VALBITS)) 455 >> (BITS_PER_EMACS_INT - VALBITS))
417#else 456#else
418#define XINT(a) ((a).s.val) 457#define XINT(a) ((a).s.val)
@@ -491,11 +530,19 @@ extern size_t pure_size;
491/* Largest and smallest representable fixnum values. These are the C 530/* Largest and smallest representable fixnum values. These are the C
492 values. */ 531 values. */
493 532
494#define MOST_NEGATIVE_FIXNUM - ((EMACS_INT) 1 << (VALBITS - 1)) 533#ifdef USE_2_TAGS_FOR_INTS
495#define MOST_POSITIVE_FIXNUM (((EMACS_INT) 1 << (VALBITS - 1)) - 1) 534# define MOST_NEGATIVE_FIXNUM - ((EMACS_INT) 1 << VALBITS)
535# define MOST_POSITIVE_FIXNUM (((EMACS_INT) 1 << VALBITS) - 1)
496/* Mask indicating the significant bits of a Lisp_Int. 536/* Mask indicating the significant bits of a Lisp_Int.
497 I.e. (x & INTMASK) == XUINT (make_number (x)). */ 537 I.e. (x & INTMASK) == XUINT (make_number (x)). */
498#define INTMASK ((((EMACS_INT) 1) << VALBITS) - 1) 538# define INTMASK ((((EMACS_INT) 1) << (VALBITS + 1)) - 1)
539#else
540# define MOST_NEGATIVE_FIXNUM - ((EMACS_INT) 1 << (VALBITS - 1))
541# define MOST_POSITIVE_FIXNUM (((EMACS_INT) 1 << (VALBITS - 1)) - 1)
542/* Mask indicating the significant bits of a Lisp_Int.
543 I.e. (x & INTMASK) == XUINT (make_number (x)). */
544# define INTMASK ((((EMACS_INT) 1) << VALBITS) - 1)
545#endif
499 546
500/* Value is non-zero if I doesn't fit into a Lisp fixnum. It is 547/* Value is non-zero if I doesn't fit into a Lisp fixnum. It is
501 written this way so that it also works if I is of unsigned 548 written this way so that it also works if I is of unsigned
@@ -1506,7 +1553,7 @@ typedef struct {
1506#define NUMBERP(x) (INTEGERP (x) || FLOATP (x)) 1553#define NUMBERP(x) (INTEGERP (x) || FLOATP (x))
1507#define NATNUMP(x) (INTEGERP (x) && XINT (x) >= 0) 1554#define NATNUMP(x) (INTEGERP (x) && XINT (x) >= 0)
1508 1555
1509#define INTEGERP(x) (XTYPE ((x)) == Lisp_Int) 1556#define INTEGERP(x) (LISP_INT_TAG_P (XTYPE ((x))))
1510#define SYMBOLP(x) (XTYPE ((x)) == Lisp_Symbol) 1557#define SYMBOLP(x) (XTYPE ((x)) == Lisp_Symbol)
1511#define MISCP(x) (XTYPE ((x)) == Lisp_Misc) 1558#define MISCP(x) (XTYPE ((x)) == Lisp_Misc)
1512#define VECTORLIKEP(x) (XTYPE ((x)) == Lisp_Vectorlike) 1559#define VECTORLIKEP(x) (XTYPE ((x)) == Lisp_Vectorlike)