comparison src/alloc.c @ 272:c5d627a313b1 r21-0b34

Import from CVS: tag r21-0b34
author cvs
date Mon, 13 Aug 2007 10:28:48 +0200
parents 8efd647ea9ca
children ca9a9ec9c1c1
comparison
equal deleted inserted replaced
271:c7b7086b0a39 272:c5d627a313b1
1 /* Storage allocation and gc for XEmacs Lisp interpreter. 1 /* Storage allocation and gc for XEmacs Lisp interpreter.
2 Copyright (C) 1985, 1986, 1988, 1992, 1993, 1994 2 Copyright (C) 1985-1998 Free Software Foundation, Inc.
3 Free Software Foundation, Inc.
4 Copyright (C) 1995 Sun Microsystems, Inc. 3 Copyright (C) 1995 Sun Microsystems, Inc.
5 Copyright (C) 1995, 1996 Ben Wing. 4 Copyright (C) 1995, 1996 Ben Wing.
6 5
7 This file is part of XEmacs. 6 This file is part of XEmacs.
8 7
39 Synched Doug Lea malloc support from Emacs 20.2. 38 Synched Doug Lea malloc support from Emacs 20.2.
40 */ 39 */
41 40
42 #include <config.h> 41 #include <config.h>
43 #include "lisp.h" 42 #include "lisp.h"
44 #include "sysdep.h"
45 43
46 #ifndef standalone 44 #ifndef standalone
47 #include "backtrace.h" 45 #include "backtrace.h"
48 #include "buffer.h" 46 #include "buffer.h"
49 #include "bytecode.h" 47 #include "bytecode.h"
54 #include "extents.h" 52 #include "extents.h"
55 #include "frame.h" 53 #include "frame.h"
56 #include "glyphs.h" 54 #include "glyphs.h"
57 #include "redisplay.h" 55 #include "redisplay.h"
58 #include "specifier.h" 56 #include "specifier.h"
57 #include "sysfile.h"
59 #include "window.h" 58 #include "window.h"
60 #endif 59 #endif
61 60
62 #ifdef DOUG_LEA_MALLOC 61 #ifdef DOUG_LEA_MALLOC
63 #include <malloc.h> 62 #include <malloc.h>
64 #endif 63 #endif
64
65 EXFUN (Fgarbage_collect, 0);
65 66
66 /* #define GDB_SUCKS */ 67 /* #define GDB_SUCKS */
67 68
68 #if 0 /* this is _way_ too slow to be part of the standard debug options */ 69 #if 0 /* this is _way_ too slow to be part of the standard debug options */
69 #if defined(DEBUG_XEMACS) && defined(MULE) 70 #if defined(DEBUG_XEMACS) && defined(MULE)
192 193
193 #ifdef HEAP_IN_DATA 194 #ifdef HEAP_IN_DATA
194 extern void sheap_adjust_h(); 195 extern void sheap_adjust_h();
195 #endif 196 #endif
196 197
197 extern Lisp_Object pure[];/* moved to pure.c to speed incremental linking */ 198 #define PUREBEG ((char *) pure)
198
199 #define PUREBEG ((unsigned char *) pure)
200 199
201 #if 0 /* This is breathing_space in XEmacs */ 200 #if 0 /* This is breathing_space in XEmacs */
202 /* Points to memory space allocated as "spare", 201 /* Points to memory space allocated as "spare",
203 to be freed if we run out of memory. */ 202 to be freed if we run out of memory. */
204 static char *spare_memory; 203 static char *spare_memory;
205 204
206 /* Amount of spare memory to keep in reserve. */ 205 /* Amount of spare memory to keep in reserve. */
207 #define SPARE_MEMORY (1 << 14) 206 #define SPARE_MEMORY (1 << 14)
208 #endif 207 #endif
209 208
210 /* Number of extra blocks malloc should get when it needs more core. */
211 static int malloc_hysteresis;
212
213 /* Index in pure at which next pure object will be allocated. */ 209 /* Index in pure at which next pure object will be allocated. */
214 static long pureptr; 210 static size_t pure_bytes_used;
215 211
216 #define PURIFIED(ptr) \ 212 #define PURIFIED(ptr) \
217 ((uintptr_t) (ptr) < \ 213 ((char *) (ptr) >= PUREBEG && \
218 (uintptr_t) (PUREBEG + get_PURESIZE()) && \ 214 (char *) (ptr) < PUREBEG + get_PURESIZE())
219 (uintptr_t) (ptr) >= \ 215
220 (uintptr_t) PUREBEG) 216 /* Non-zero if pure_bytes_used > get_PURESIZE(); accounts for excess purespace needs. */
221 217 static size_t pure_lossage;
222 /* Non-zero if pureptr > get_PURESIZE(); accounts for excess purespace needs. */
223 static long pure_lossage;
224 218
225 #ifdef ERROR_CHECK_TYPECHECK 219 #ifdef ERROR_CHECK_TYPECHECK
226 220
227 Error_behavior ERROR_ME, ERROR_ME_NOT, ERROR_ME_WARN; 221 Error_behavior ERROR_ME, ERROR_ME_NOT, ERROR_ME_WARN;
228 222
229 #endif 223 #endif
230 224
231 int 225 int
232 purified (Lisp_Object obj) 226 purified (Lisp_Object obj)
233 { 227 {
234 return !POINTER_TYPE_P (XGCTYPE (obj)) ? 0 : PURIFIED (XPNTR (obj)); 228 return POINTER_TYPE_P (XGCTYPE (obj)) && PURIFIED (XPNTR (obj));
235 } 229 }
236 230
237 int 231 size_t
238 purespace_usage (void) 232 purespace_usage (void)
239 { 233 {
240 return (int) pureptr; 234 return pure_bytes_used;
241 } 235 }
242 236
243 static int 237 static int
244 check_purespace (EMACS_INT size) 238 check_purespace (size_t size)
245 { 239 {
246 if (pure_lossage) 240 if (pure_lossage)
247 { 241 {
248 pure_lossage += size; 242 pure_lossage += size;
249 return 0; 243 return 0;
250 } 244 }
251 else if (pureptr + size > get_PURESIZE()) 245 else if (pure_bytes_used + size > get_PURESIZE())
252 { 246 {
253 /* This can cause recursive bad behavior, we'll yell at the end */ 247 /* This can cause recursive bad behavior, we'll yell at the end */
254 /* when we're done. */ 248 /* when we're done. */
255 /* message ("\nERROR: Pure Lisp storage exhausted!\n"); */ 249 /* message ("\nERROR: Pure Lisp storage exhausted!\n"); */
256 pure_lossage = size; 250 pure_lossage = size;
262 256
263 257
264 258
265 #ifndef PURESTAT 259 #ifndef PURESTAT
266 260
267 #define bump_purestat(p,b) do {} while (0) /* Do nothing */ 261 #define bump_purestat(p,b) DO_NOTHING
268 262
269 #else /* PURESTAT */ 263 #else /* PURESTAT */
270 264
271 static int purecopying_for_bytecode; 265 static int purecopying_for_bytecode;
272 266
273 static int pure_sizeof (Lisp_Object /*, int recurse */); 267 static size_t pure_sizeof (Lisp_Object /*, int recurse */);
274 268
275 /* Keep statistics on how much of what is in purespace */ 269 /* Keep statistics on how much of what is in purespace */
276 static struct purestat 270 static struct purestat
277 { 271 {
278 int nobjects; 272 int nobjects;
316 &purestat_string_all, 310 &purestat_string_all,
317 &purestat_vector_all 311 &purestat_vector_all
318 }; 312 };
319 313
320 static void 314 static void
321 bump_purestat (struct purestat *purestat, int nbytes) 315 bump_purestat (struct purestat *purestat, size_t nbytes)
322 { 316 {
323 if (pure_lossage) return; 317 if (pure_lossage) return;
324 purestat->nobjects += 1; 318 purestat->nobjects += 1;
325 purestat->nbytes += nbytes; 319 purestat->nbytes += nbytes;
326 } 320 }
330 /* Maximum amount of C stack to save when a GC happens. */ 324 /* Maximum amount of C stack to save when a GC happens. */
331 325
332 #ifndef MAX_SAVE_STACK 326 #ifndef MAX_SAVE_STACK
333 #define MAX_SAVE_STACK 16000 327 #define MAX_SAVE_STACK 16000
334 #endif 328 #endif
335
336 /* Buffer in which we save a copy of the C stack at each GC. */
337
338 static char *stack_copy;
339 static int stack_copy_size;
340 329
341 /* Non-zero means ignore malloc warnings. Set during initialization. */ 330 /* Non-zero means ignore malloc warnings. Set during initialization. */
342 int ignore_malloc_warnings; 331 int ignore_malloc_warnings;
343 332
344 333
446 assert (block); 435 assert (block);
447 #endif /* ERROR_CHECK_MALLOC */ 436 #endif /* ERROR_CHECK_MALLOC */
448 free (block); 437 free (block);
449 } 438 }
450 439
451 #if INTBITS == 32 440 #ifdef ERROR_CHECK_GC
452 # define FOUR_BYTE_TYPE unsigned int 441
453 #elif LONGBITS == 32 442 #if SIZEOF_INT == 4
454 # define FOUR_BYTE_TYPE unsigned long 443 typedef unsigned int four_byte_t;
455 #elif SHORTBITS == 32 444 #elif SIZEOF_LONG == 4
456 # define FOUR_BYTE_TYPE unsigned short 445 typedef unsigned long four_byte_t;
446 #elif SIZEOF_SHORT == 4
447 typedef unsigned short four_byte_t;
457 #else 448 #else
458 What kind of strange-ass system are we running on? 449 What kind of strange-ass system are we running on?
459 #endif 450 #endif
460 451
461 #ifdef ERROR_CHECK_GC
462
463 #ifdef WORDS_BIGENDIAN
464 static unsigned char deadbeef_as_char[] = {0xDE, 0xAD, 0xBE, 0xEF};
465 #else
466 static unsigned char deadbeef_as_char[] = {0xEF, 0xBE, 0xAD, 0xDE};
467 #endif
468
469 static void 452 static void
470 deadbeef_memory (void *ptr, unsigned long size) 453 deadbeef_memory (void *ptr, size_t size)
471 { 454 {
472 unsigned long long_length = size / sizeof (FOUR_BYTE_TYPE); 455 four_byte_t *ptr4 = (four_byte_t *) ptr;
473 unsigned long i; 456 size_t beefs = size >> 2;
474 unsigned long bytes_left_over = size - sizeof (FOUR_BYTE_TYPE) * long_length; 457
475 458 /* In practice, size will always be a multiple of four. */
476 for (i = 0; i < long_length; i++) 459 while (beefs--)
477 ((FOUR_BYTE_TYPE *) ptr)[i] = 0xdeadbeef; 460 (*ptr4++) = 0xDEADBEEF;
478 for (i = i; i < bytes_left_over; i++)
479 ((unsigned char *) ptr + long_length)[i] = deadbeef_as_char[i];
480 } 461 }
481 462
482 #else /* !ERROR_CHECK_GC */ 463 #else /* !ERROR_CHECK_GC */
483 464
484 465
509 } 490 }
510 #endif /* NEED_STRDUP */ 491 #endif /* NEED_STRDUP */
511 492
512 493
513 static void * 494 static void *
514 allocate_lisp_storage (int size) 495 allocate_lisp_storage (size_t size)
515 { 496 {
516 void *p = xmalloc (size); 497 void *p = xmalloc (size);
498 #ifndef USE_MINIMAL_TAGBITS
517 char *lim = ((char *) p) + size; 499 char *lim = ((char *) p) + size;
518 Lisp_Object val = Qnil; 500 Lisp_Object val;
519 501
520 XSETOBJ (val, Lisp_Type_Record, lim); 502 XSETOBJ (val, Lisp_Type_Record, lim);
521 if ((char *) XPNTR (val) != lim) 503 if ((char *) XPNTR (val) != lim)
522 { 504 {
523 xfree (p); 505 xfree (p);
524 memory_full (); 506 memory_full ();
525 } 507 }
508 #endif /* ! USE_MINIMAL_TAGBITS */
526 return p; 509 return p;
527 } 510 }
528 511
529 512
530 /* lrecords are chained together through their "next.v" field. 513 /* lrecords are chained together through their "next.v" field.
531 * After doing the mark phase, the GC will walk this linked 514 * After doing the mark phase, the GC will walk this linked
532 * list and free any record which hasn't been marked 515 * list and free any record which hasn't been marked.
533 */ 516 */
534 static struct lcrecord_header *all_lcrecords; 517 static struct lcrecord_header *all_lcrecords;
535 518
536 void * 519 void *
537 alloc_lcrecord (int size, CONST struct lrecord_implementation *implementation) 520 alloc_lcrecord (size_t size, CONST struct lrecord_implementation *implementation)
538 { 521 {
539 struct lcrecord_header *lcheader; 522 struct lcrecord_header *lcheader;
540 523
541 if (size <= 0) abort (); 524 if (size <= 0) abort ();
542 if (implementation->static_size == 0) 525 if (implementation->static_size == 0)
639 622
640 /* XGCTYPE for records */ 623 /* XGCTYPE for records */
641 int 624 int
642 gc_record_type_p (Lisp_Object frob, CONST struct lrecord_implementation *type) 625 gc_record_type_p (Lisp_Object frob, CONST struct lrecord_implementation *type)
643 { 626 {
627 CONST struct lrecord_implementation *imp;
628
629 if (XGCTYPE (frob) != Lisp_Type_Record)
630 return 0;
631
632 imp = XRECORD_LHEADER_IMPLEMENTATION (frob);
644 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION 633 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION
645 return (XGCTYPE (frob) == Lisp_Type_Record 634 return imp == type;
646 && XRECORD_LHEADER_IMPLEMENTATION (frob) == type);
647 #else 635 #else
648 return (XGCTYPE (frob) == Lisp_Type_Record 636 return imp == type || imp == type + 1;
649 && (XRECORD_LHEADER (frob)->implementation == type || 637 #endif
650 XRECORD_LHEADER (frob)->implementation == type + 1)); 638 }
651 #endif 639
652 } 640
641 /**********************************************************************/
642 /* Debugger support */
643 /**********************************************************************/
644 /* Give gdb/dbx enough information to decode Lisp Objects.
645 We make sure certain symbols are defined, so gdb doesn't complain
646 about expressions in src/gdbinit. Values are randomly chosen.
647 See src/gdbinit or src/dbxrc to see how this is used. */
648
649 enum dbg_constants
650 {
651 #ifdef USE_MINIMAL_TAGBITS
652 dbg_valmask = (EMACS_INT) (((1UL << VALBITS) - 1) << GCBITS),
653 dbg_typemask = (EMACS_INT) ((1UL << GCTYPEBITS) - 1),
654 dbg_USE_MINIMAL_TAGBITS = 1,
655 dbg_Lisp_Type_Int = 100,
656 #else /* ! USE_MIMIMAL_TAGBITS */
657 dbg_valmask = (EMACS_INT) ((1UL << VALBITS) - 1),
658 dbg_typemask = (EMACS_INT) (((1UL << GCTYPEBITS) - 1) << (VALBITS + GCMARKBITS)),
659 dbg_USE_MINIMAL_TAGBITS = 0,
660 dbg_Lisp_Type_Int = Lisp_Type_Int,
661 #endif /* ! USE_MIMIMAL_TAGBITS */
662 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION
663 dbg_USE_INDEXED_LRECORD_IMPLEMENTATION = 1,
664 #else
665 dbg_USE_INDEXED_LRECORD_IMPLEMENTATION = 0,
666 #endif
667 dbg_Lisp_Type_Char = Lisp_Type_Char,
668 dbg_Lisp_Type_Record = Lisp_Type_Record,
669 #ifdef LRECORD_CONS
670 dbg_Lisp_Type_Cons = 101,
671 #else
672 dbg_Lisp_Type_Cons = Lisp_Type_Cons,
673 lrecord_cons = 201,
674 #endif
675 #ifdef LRECORD_STRING
676 dbg_Lisp_Type_String = 102,
677 #else
678 dbg_Lisp_Type_String = Lisp_Type_String,
679 lrecord_string = 202,
680 #endif
681 #ifdef LRECORD_VECTOR
682 dbg_Lisp_Type_Vector = 103,
683 #else
684 dbg_Lisp_Type_Vector = Lisp_Type_Vector,
685 lrecord_vector = 203,
686 #endif
687 #ifdef LRECORD_SYMBOL
688 dbg_Lisp_Type_Symbol = 104,
689 #else
690 dbg_Lisp_Type_Symbol = Lisp_Type_Symbol,
691 lrecord_symbol = 204,
692 #endif
693 #ifndef MULE
694 lrecord_char_table_entry = 205,
695 lrecord_charset = 206,
696 lrecord_coding_system = 207,
697 #endif
698 #ifndef HAVE_TOOLBARS
699 lrecord_toolbar_button = 208,
700 lrecord_toolbar_data = 209,
701 #endif
702 #ifndef HAVE_TOOLTALK
703 lrecord_tooltalk_message = 210,
704 lrecord_tooltalk_pattern = 211,
705 #endif
706 #ifndef HAVE_DATABASE
707 lrecord_database = 212,
708 #endif
709 dbg_valbits = VALBITS,
710 dbg_gctypebits = GCTYPEBITS
711 /* If we don't have an actual object of this enum, pgcc (and perhaps
712 other compilers) might optimize away the entire type declaration :-( */
713 } dbg_dummy;
653 714
654 715
655 /**********************************************************************/ 716 /**********************************************************************/
656 /* Fixed-size type macros */ 717 /* Fixed-size type macros */
657 /**********************************************************************/ 718 /**********************************************************************/
817 /* If we released our reserve (due to running out of memory), 878 /* If we released our reserve (due to running out of memory),
818 and we have a fair amount free once again, 879 and we have a fair amount free once again,
819 try to set aside another reserve in case we run out once more. 880 try to set aside another reserve in case we run out once more.
820 881
821 This is called when a relocatable block is freed in ralloc.c. */ 882 This is called when a relocatable block is freed in ralloc.c. */
822 883 void refill_memory_reserve (void);
823 void 884 void
824 refill_memory_reserve () 885 refill_memory_reserve ()
825 { 886 {
826 if (breathing_space == 0) 887 if (breathing_space == 0)
827 breathing_space = (char *) malloc (4096 - MALLOC_OVERHEAD); 888 breathing_space = (char *) malloc (4096 - MALLOC_OVERHEAD);
1038 static Lisp_Object 1099 static Lisp_Object
1039 mark_cons (Lisp_Object obj, void (*markobj) (Lisp_Object)) 1100 mark_cons (Lisp_Object obj, void (*markobj) (Lisp_Object))
1040 { 1101 {
1041 if (NILP (XCDR (obj))) 1102 if (NILP (XCDR (obj)))
1042 return XCAR (obj); 1103 return XCAR (obj);
1043 else 1104
1044 (markobj) (XCAR (obj)); 1105 (markobj) (XCAR (obj));
1045 return XCDR (obj); 1106 return XCDR (obj);
1046 } 1107 }
1047 1108
1048 static int 1109 static int
1049 cons_equal (Lisp_Object ob1, Lisp_Object ob2, int depth) 1110 cons_equal (Lisp_Object ob1, Lisp_Object ob2, int depth)
1050 { 1111 {
1051 while (internal_equal (XCAR (ob1), XCAR (ob2), depth + 1)) 1112 while (internal_equal (XCAR (ob1), XCAR (ob2), depth + 1))
1052 { 1113 {
1053 ob1 = XCDR(ob1); 1114 ob1 = XCDR (ob1);
1054 ob2 = XCDR(ob2); 1115 ob2 = XCDR (ob2);
1055 if (! CONSP (ob1) || ! CONSP (ob2)) 1116 if (! CONSP (ob1) || ! CONSP (ob2))
1056 return internal_equal (ob1, ob2, depth + 1); 1117 return internal_equal (ob1, ob2, depth + 1);
1057 } 1118 }
1058 return 0; 1119 return 0;
1059 } 1120 }
1074 Create a new cons, give it CAR and CDR as components, and return it. 1135 Create a new cons, give it CAR and CDR as components, and return it.
1075 */ 1136 */
1076 (car, cdr)) 1137 (car, cdr))
1077 { 1138 {
1078 /* This cannot GC. */ 1139 /* This cannot GC. */
1079 Lisp_Object val = Qnil; 1140 Lisp_Object val;
1080 struct Lisp_Cons *c; 1141 struct Lisp_Cons *c;
1081 1142
1082 ALLOCATE_FIXED_TYPE (cons, struct Lisp_Cons, c); 1143 ALLOCATE_FIXED_TYPE (cons, struct Lisp_Cons, c);
1083 #ifdef LRECORD_CONS 1144 #ifdef LRECORD_CONS
1084 set_lheader_implementation (&(c->lheader), lrecord_cons); 1145 set_lheader_implementation (&(c->lheader), lrecord_cons);
1093 going to free later, and is useful when trying to track down 1154 going to free later, and is useful when trying to track down
1094 "real" consing. */ 1155 "real" consing. */
1095 Lisp_Object 1156 Lisp_Object
1096 noseeum_cons (Lisp_Object car, Lisp_Object cdr) 1157 noseeum_cons (Lisp_Object car, Lisp_Object cdr)
1097 { 1158 {
1098 Lisp_Object val = Qnil; 1159 Lisp_Object val;
1099 struct Lisp_Cons *c; 1160 struct Lisp_Cons *c;
1100 1161
1101 NOSEEUM_ALLOCATE_FIXED_TYPE (cons, struct Lisp_Cons, c); 1162 NOSEEUM_ALLOCATE_FIXED_TYPE (cons, struct Lisp_Cons, c);
1102 #ifdef LRECORD_CONS 1163 #ifdef LRECORD_CONS
1103 set_lheader_implementation (&(c->lheader), lrecord_cons); 1164 set_lheader_implementation (&(c->lheader), lrecord_cons);
1131 1192
1132 Lisp_Object 1193 Lisp_Object
1133 list2 (Lisp_Object obj0, Lisp_Object obj1) 1194 list2 (Lisp_Object obj0, Lisp_Object obj1)
1134 { 1195 {
1135 /* This cannot GC. */ 1196 /* This cannot GC. */
1136 return Fcons (obj0, list1 (obj1)); 1197 return Fcons (obj0, Fcons (obj1, Qnil));
1137 } 1198 }
1138 1199
1139 Lisp_Object 1200 Lisp_Object
1140 list3 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2) 1201 list3 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2)
1141 { 1202 {
1142 /* This cannot GC. */ 1203 /* This cannot GC. */
1143 return Fcons (obj0, list2 (obj1, obj2)); 1204 return Fcons (obj0, Fcons (obj1, Fcons (obj2, Qnil)));
1144 } 1205 }
1145 1206
1146 static Lisp_Object 1207 Lisp_Object
1147 cons3 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2) 1208 cons3 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2)
1148 { 1209 {
1149 /* This cannot GC. */ 1210 /* This cannot GC. */
1150 return Fcons (obj0, Fcons (obj1, obj2)); 1211 return Fcons (obj0, Fcons (obj1, obj2));
1151 } 1212 }
1152 1213
1153 Lisp_Object 1214 Lisp_Object
1215 acons (Lisp_Object key, Lisp_Object value, Lisp_Object alist)
1216 {
1217 return Fcons (Fcons (key, value), alist);
1218 }
1219
1220 Lisp_Object
1154 list4 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2, Lisp_Object obj3) 1221 list4 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2, Lisp_Object obj3)
1155 { 1222 {
1156 /* This cannot GC. */ 1223 /* This cannot GC. */
1157 return Fcons (obj0, list3 (obj1, obj2, obj3)); 1224 return Fcons (obj0, Fcons (obj1, Fcons (obj2, Fcons (obj3, Qnil))));
1158 } 1225 }
1159 1226
1160 Lisp_Object 1227 Lisp_Object
1161 list5 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2, Lisp_Object obj3, 1228 list5 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2, Lisp_Object obj3,
1162 Lisp_Object obj4) 1229 Lisp_Object obj4)
1163 { 1230 {
1164 /* This cannot GC. */ 1231 /* This cannot GC. */
1165 return Fcons (obj0, list4 (obj1, obj2, obj3, obj4)); 1232 return Fcons (obj0, Fcons (obj1, Fcons (obj2, Fcons (obj3, Fcons (obj4, Qnil)))));
1166 } 1233 }
1167 1234
1168 Lisp_Object 1235 Lisp_Object
1169 list6 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2, Lisp_Object obj3, 1236 list6 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2, Lisp_Object obj3,
1170 Lisp_Object obj4, Lisp_Object obj5) 1237 Lisp_Object obj4, Lisp_Object obj5)
1171 { 1238 {
1172 /* This cannot GC. */ 1239 /* This cannot GC. */
1173 return Fcons (obj0, list5 (obj1, obj2, obj3, obj4, obj5)); 1240 return Fcons (obj0, Fcons (obj1, Fcons (obj2, Fcons (obj3, Fcons (obj4, Fcons (obj5, Qnil))))));
1174 } 1241 }
1175 1242
1176 DEFUN ("make-list", Fmake_list, 2, 2, 0, /* 1243 DEFUN ("make-list", Fmake_list, 2, 2, 0, /*
1177 Return a newly created list of length LENGTH, with each element being INIT. 1244 Return a new list of length LENGTH, with each element being INIT.
1178 */ 1245 */
1179 (length, init)) 1246 (length, init))
1180 { 1247 {
1181 Lisp_Object val;
1182 int size;
1183
1184 CHECK_NATNUM (length); 1248 CHECK_NATNUM (length);
1185 size = XINT (length); 1249
1186 1250 {
1187 val = Qnil; 1251 Lisp_Object val = Qnil;
1188 while (size-- > 0) 1252 int size = XINT (length);
1189 val = Fcons (init, val); 1253
1190 return val; 1254 while (size-- > 0)
1255 val = Fcons (init, val);
1256 return val;
1257 }
1191 } 1258 }
1192 1259
1193 1260
1194 /**********************************************************************/ 1261 /**********************************************************************/
1195 /* Float allocation */ 1262 /* Float allocation */
1232 for (i = 0; i < len - 1; i++) 1299 for (i = 0; i < len - 1; i++)
1233 (markobj) (ptr->contents[i]); 1300 (markobj) (ptr->contents[i]);
1234 return (len > 0) ? ptr->contents[len - 1] : Qnil; 1301 return (len > 0) ? ptr->contents[len - 1] : Qnil;
1235 } 1302 }
1236 1303
1237 static unsigned int 1304 static size_t
1238 size_vector (CONST void *lheader) 1305 size_vector (CONST void *lheader)
1239 { 1306 {
1240 CONST struct Lisp_Vector *p = lheader; 1307 /* * -1 because struct Lisp_Vector includes 1 slot */
1241 /*
1242 * -1 because struct Lisp_Vector includes 1 slot
1243 */
1244 return sizeof (struct Lisp_Vector) + 1308 return sizeof (struct Lisp_Vector) +
1245 ((p->size - 1) * sizeof (Lisp_Object)) ; 1309 ((((struct Lisp_Vector *) lheader)->size - 1) * sizeof (Lisp_Object));
1246 } 1310 }
1247 1311
1248 static int 1312 static int
1249 vector_equal (Lisp_Object o1, Lisp_Object o2, int depth) 1313 vector_equal (Lisp_Object o1, Lisp_Object o2, int depth)
1250 { 1314 {
1273 0, 1337 0,
1274 size_vector, struct Lisp_Vector); 1338 size_vector, struct Lisp_Vector);
1275 1339
1276 /* #### should allocate `small' vectors from a frob-block */ 1340 /* #### should allocate `small' vectors from a frob-block */
1277 static struct Lisp_Vector * 1341 static struct Lisp_Vector *
1278 make_vector_internal (EMACS_INT sizei) 1342 make_vector_internal (size_t sizei)
1279 { 1343 {
1280 EMACS_INT sizem = (sizeof (struct Lisp_Vector) 1344 size_t sizem = (sizeof (struct Lisp_Vector)
1281 /* -1 because struct Lisp_Vector includes 1 slot */ 1345 /* -1 because struct Lisp_Vector includes 1 slot */
1282 + (sizei - 1) * sizeof (Lisp_Object) 1346 + (sizei - 1) * sizeof (Lisp_Object));
1283 ); 1347 struct Lisp_Vector *p =
1284 struct Lisp_Vector *p = alloc_lcrecord (sizem, lrecord_vector); 1348 (struct Lisp_Vector *) alloc_lcrecord (sizem, lrecord_vector);
1285 1349
1286 p->size = sizei; 1350 p->size = sizei;
1287 return p; 1351 return p;
1288 } 1352 }
1289 1353
1291 1355
1292 static Lisp_Object all_vectors; 1356 static Lisp_Object all_vectors;
1293 1357
1294 /* #### should allocate `small' vectors from a frob-block */ 1358 /* #### should allocate `small' vectors from a frob-block */
1295 static struct Lisp_Vector * 1359 static struct Lisp_Vector *
1296 make_vector_internal (EMACS_INT sizei) 1360 make_vector_internal (size_t sizei)
1297 { 1361 {
1298 EMACS_INT sizem = (sizeof (struct Lisp_Vector) 1362 size_t sizem = (sizeof (struct Lisp_Vector)
1299 /* -1 because struct Lisp_Vector includes 1 slot, 1363 /* -1 because struct Lisp_Vector includes 1 slot,
1300 * +1 to account for vector_next */ 1364 * +1 to account for vector_next */
1301 + (sizei - 1 + 1) * sizeof (Lisp_Object) 1365 + (sizei - 1 + 1) * sizeof (Lisp_Object));
1302 );
1303 struct Lisp_Vector *p = (struct Lisp_Vector *) allocate_lisp_storage (sizem); 1366 struct Lisp_Vector *p = (struct Lisp_Vector *) allocate_lisp_storage (sizem);
1304 1367
1305 INCREMENT_CONS_COUNTER (sizem, "vector"); 1368 INCREMENT_CONS_COUNTER (sizem, "vector");
1306 1369
1307 p->size = sizei; 1370 p->size = sizei;
1313 #endif /* ! LRECORD_VECTOR */ 1376 #endif /* ! LRECORD_VECTOR */
1314 1377
1315 Lisp_Object 1378 Lisp_Object
1316 make_vector (EMACS_INT length, Lisp_Object init) 1379 make_vector (EMACS_INT length, Lisp_Object init)
1317 { 1380 {
1318 EMACS_INT elt; 1381 int elt;
1319 Lisp_Object vector = Qnil; 1382 Lisp_Object vector;
1320 struct Lisp_Vector *p; 1383 struct Lisp_Vector *p;
1321 1384
1322 if (length < 0) 1385 if (length < 0)
1323 length = XINT (wrong_type_argument (Qnatnump, make_int (length))); 1386 length = XINT (wrong_type_argument (Qnatnump, make_int (length)));
1324 1387
1344 1407
1345 return vector; 1408 return vector;
1346 } 1409 }
1347 1410
1348 DEFUN ("make-vector", Fmake_vector, 2, 2, 0, /* 1411 DEFUN ("make-vector", Fmake_vector, 2, 2, 0, /*
1349 Return a newly created vector of length LENGTH, with each element being INIT. 1412 Return a new vector of length LENGTH, with each element being INIT.
1350 See also the function `vector'. 1413 See also the function `vector'.
1351 */ 1414 */
1352 (length, init)) 1415 (length, init))
1353 { 1416 {
1354 if (!INTP (length) || XINT (length) < 0) 1417 CHECK_NATNUM (length);
1355 length = wrong_type_argument (Qnatnump, length);
1356
1357 return make_vector (XINT (length), init); 1418 return make_vector (XINT (length), init);
1358 } 1419 }
1359 1420
1360 DEFUN ("vector", Fvector, 0, MANY, 0, /* 1421 DEFUN ("vector", Fvector, 0, MANY, 0, /*
1361 Return a newly created vector with specified arguments as elements. 1422 Return a newly created vector with specified arguments as elements.
1362 Any number of arguments, even zero arguments, are allowed. 1423 Any number of arguments, even zero arguments, are allowed.
1363 */ 1424 */
1364 (int nargs, Lisp_Object *args)) 1425 (int nargs, Lisp_Object *args))
1365 { 1426 {
1366 Lisp_Object vector = Qnil; 1427 Lisp_Object vector;
1367 int elt; 1428 int elt;
1368 struct Lisp_Vector *p; 1429 struct Lisp_Vector *p = make_vector_internal (nargs);
1369
1370 p = make_vector_internal (nargs);
1371 XSETVECTOR (vector, p);
1372 1430
1373 for (elt = 0; elt < nargs; elt++) 1431 for (elt = 0; elt < nargs; elt++)
1374 vector_data(p)[elt] = args[elt]; 1432 vector_data(p)[elt] = args[elt];
1375 1433
1434 XSETVECTOR (vector, p);
1376 return vector; 1435 return vector;
1377 } 1436 }
1378 1437
1379 Lisp_Object 1438 Lisp_Object
1380 vector1 (Lisp_Object obj0) 1439 vector1 (Lisp_Object obj0)
1398 args[0] = obj0; 1457 args[0] = obj0;
1399 args[1] = obj1; 1458 args[1] = obj1;
1400 args[2] = obj2; 1459 args[2] = obj2;
1401 return Fvector (3, args); 1460 return Fvector (3, args);
1402 } 1461 }
1462
1463 #if 0 /* currently unused */
1403 1464
1404 Lisp_Object 1465 Lisp_Object
1405 vector4 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2, 1466 vector4 (Lisp_Object obj0, Lisp_Object obj1, Lisp_Object obj2,
1406 Lisp_Object obj3) 1467 Lisp_Object obj3)
1407 { 1468 {
1470 args[5] = obj5; 1531 args[5] = obj5;
1471 args[6] = obj6; 1532 args[6] = obj6;
1472 args[7] = obj7; 1533 args[7] = obj7;
1473 return Fvector (8, args); 1534 return Fvector (8, args);
1474 } 1535 }
1536 #endif /* unused */
1475 1537
1476 /**********************************************************************/ 1538 /**********************************************************************/
1477 /* Bit Vector allocation */ 1539 /* Bit Vector allocation */
1478 /**********************************************************************/ 1540 /**********************************************************************/
1479 1541
1480 static Lisp_Object all_bit_vectors; 1542 static Lisp_Object all_bit_vectors;
1481 1543
1482 /* #### should allocate `small' bit vectors from a frob-block */ 1544 /* #### should allocate `small' bit vectors from a frob-block */
1483 static struct Lisp_Bit_Vector * 1545 static struct Lisp_Bit_Vector *
1484 make_bit_vector_internal (EMACS_INT sizei) 1546 make_bit_vector_internal (size_t sizei)
1485 { 1547 {
1486 EMACS_INT sizem = (sizeof (struct Lisp_Bit_Vector) + 1548 size_t sizem = sizeof (struct Lisp_Bit_Vector) +
1487 /* -1 because struct Lisp_Bit_Vector includes 1 slot */ 1549 /* -1 because struct Lisp_Bit_Vector includes 1 slot */
1488 sizeof (long) * (BIT_VECTOR_LONG_STORAGE (sizei) - 1)); 1550 sizeof (long) * (BIT_VECTOR_LONG_STORAGE (sizei) - 1);
1489 struct Lisp_Bit_Vector *p = 1551 struct Lisp_Bit_Vector *p =
1490 (struct Lisp_Bit_Vector *) allocate_lisp_storage (sizem); 1552 (struct Lisp_Bit_Vector *) allocate_lisp_storage (sizem);
1491 set_lheader_implementation (&(p->lheader), lrecord_bit_vector); 1553 set_lheader_implementation (&(p->lheader), lrecord_bit_vector);
1492 1554
1493 INCREMENT_CONS_COUNTER (sizem, "bit-vector"); 1555 INCREMENT_CONS_COUNTER (sizem, "bit-vector");
1502 } 1564 }
1503 1565
1504 Lisp_Object 1566 Lisp_Object
1505 make_bit_vector (EMACS_INT length, Lisp_Object init) 1567 make_bit_vector (EMACS_INT length, Lisp_Object init)
1506 { 1568 {
1507 Lisp_Object bit_vector = Qnil; 1569 Lisp_Object bit_vector;
1508 struct Lisp_Bit_Vector *p; 1570 struct Lisp_Bit_Vector *p;
1509 EMACS_INT num_longs; 1571 EMACS_INT num_longs;
1510
1511 if (length < 0)
1512 length = XINT (wrong_type_argument (Qnatnump, make_int (length)));
1513 1572
1514 CHECK_BIT (init); 1573 CHECK_BIT (init);
1515 1574
1516 num_longs = BIT_VECTOR_LONG_STORAGE (length); 1575 num_longs = BIT_VECTOR_LONG_STORAGE (length);
1517 p = make_bit_vector_internal (length); 1576 p = make_bit_vector_internal (length);
1533 } 1592 }
1534 1593
1535 Lisp_Object 1594 Lisp_Object
1536 make_bit_vector_from_byte_vector (unsigned char *bytevec, EMACS_INT length) 1595 make_bit_vector_from_byte_vector (unsigned char *bytevec, EMACS_INT length)
1537 { 1596 {
1538 Lisp_Object bit_vector = Qnil; 1597 Lisp_Object bit_vector;
1539 struct Lisp_Bit_Vector *p; 1598 struct Lisp_Bit_Vector *p;
1540 EMACS_INT i; 1599 int i;
1541 1600
1542 if (length < 0) 1601 if (length < 0)
1543 length = XINT (wrong_type_argument (Qnatnump, make_int (length))); 1602 length = XINT (wrong_type_argument (Qnatnump, make_int (length)));
1544 1603
1545 p = make_bit_vector_internal (length); 1604 p = make_bit_vector_internal (length);
1550 1609
1551 return bit_vector; 1610 return bit_vector;
1552 } 1611 }
1553 1612
1554 DEFUN ("make-bit-vector", Fmake_bit_vector, 2, 2, 0, /* 1613 DEFUN ("make-bit-vector", Fmake_bit_vector, 2, 2, 0, /*
1555 Return a newly created bit vector of length LENGTH. 1614 Return a new bit vector of length LENGTH. with each bit being INIT.
1556 Each element is set to INIT. See also the function `bit-vector'. 1615 Each element is set to INIT. See also the function `bit-vector'.
1557 */ 1616 */
1558 (length, init)) 1617 (length, init))
1559 { 1618 {
1560 if (!INTP (length) || XINT (length) < 0) 1619 CONCHECK_NATNUM (length);
1561 length = wrong_type_argument (Qnatnump, length);
1562 1620
1563 return make_bit_vector (XINT (length), init); 1621 return make_bit_vector (XINT (length), init);
1564 } 1622 }
1565 1623
1566 DEFUN ("bit-vector", Fbit_vector, 0, MANY, 0, /* 1624 DEFUN ("bit-vector", Fbit_vector, 0, MANY, 0, /*
1567 Return a newly created bit vector with specified arguments as elements. 1625 Return a newly created bit vector with specified arguments as elements.
1568 Any number of arguments, even zero arguments, are allowed. 1626 Any number of arguments, even zero arguments, are allowed.
1569 */ 1627 */
1570 (int nargs, Lisp_Object *args)) 1628 (int nargs, Lisp_Object *args))
1571 { 1629 {
1572 Lisp_Object bit_vector = Qnil; 1630 Lisp_Object bit_vector;
1573 int elt; 1631 int elt;
1574 struct Lisp_Bit_Vector *p; 1632 struct Lisp_Bit_Vector *p;
1575 1633
1576 for (elt = 0; elt < nargs; elt++) 1634 for (elt = 0; elt < nargs; elt++)
1577 CHECK_BIT (args[elt]); 1635 CHECK_BIT (args[elt]);
1578 1636
1579 p = make_bit_vector_internal (nargs); 1637 p = make_bit_vector_internal (nargs);
1580 XSETBIT_VECTOR (bit_vector, p);
1581 1638
1582 for (elt = 0; elt < nargs; elt++) 1639 for (elt = 0; elt < nargs; elt++)
1583 set_bit_vector_bit (p, elt, !ZEROP (args[elt])); 1640 set_bit_vector_bit (p, elt, !ZEROP (args[elt]));
1584 1641
1642 XSETBIT_VECTOR (bit_vector, p);
1585 return bit_vector; 1643 return bit_vector;
1586 } 1644 }
1587 1645
1588 1646
1589 /**********************************************************************/ 1647 /**********************************************************************/
1596 static Lisp_Object 1654 static Lisp_Object
1597 make_compiled_function (int make_pure) 1655 make_compiled_function (int make_pure)
1598 { 1656 {
1599 struct Lisp_Compiled_Function *b; 1657 struct Lisp_Compiled_Function *b;
1600 Lisp_Object new; 1658 Lisp_Object new;
1601 int size = sizeof (struct Lisp_Compiled_Function); 1659 size_t size = sizeof (struct Lisp_Compiled_Function);
1602 1660
1603 if (make_pure && check_purespace (size)) 1661 if (make_pure && check_purespace (size))
1604 { 1662 {
1605 b = (struct Lisp_Compiled_Function *) (PUREBEG + pureptr); 1663 b = (struct Lisp_Compiled_Function *) (PUREBEG + pure_bytes_used);
1606 set_lheader_implementation (&(b->lheader), lrecord_compiled_function); 1664 set_lheader_implementation (&(b->lheader), lrecord_compiled_function);
1607 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION 1665 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION
1608 b->lheader.pure = 1; 1666 b->lheader.pure = 1;
1609 #endif 1667 #endif
1610 pureptr += size; 1668 pure_bytes_used += size;
1611 bump_purestat (&purestat_bytecode, size); 1669 bump_purestat (&purestat_bytecode, size);
1612 } 1670 }
1613 else 1671 else
1614 { 1672 {
1615 ALLOCATE_FIXED_TYPE (compiled_function, struct Lisp_Compiled_Function, 1673 ALLOCATE_FIXED_TYPE (compiled_function, struct Lisp_Compiled_Function,
1630 XSETCOMPILED_FUNCTION (new, b); 1688 XSETCOMPILED_FUNCTION (new, b);
1631 return new; 1689 return new;
1632 } 1690 }
1633 1691
1634 DEFUN ("make-byte-code", Fmake_byte_code, 4, MANY, 0, /* 1692 DEFUN ("make-byte-code", Fmake_byte_code, 4, MANY, 0, /*
1635 Create a compiled-function object. 1693 Return a new compiled-function object.
1636 Usage: (arglist instructions constants stack-size 1694 Usage: (arglist instructions constants stack-size
1637 &optional doc-string interactive-spec) 1695 &optional doc-string interactive-spec)
1638 Note that, unlike all other emacs-lisp functions, calling this with five 1696 Note that, unlike all other emacs-lisp functions, calling this with five
1639 arguments is NOT the same as calling it with six arguments, the last of 1697 arguments is NOT the same as calling it with six arguments, the last of
1640 which is nil. If the INTERACTIVE arg is specified as nil, then that means 1698 which is nil. If the INTERACTIVE arg is specified as nil, then that means
1652 */ 1710 */
1653 Lisp_Object arglist = args[0]; 1711 Lisp_Object arglist = args[0];
1654 Lisp_Object instructions = args[1]; 1712 Lisp_Object instructions = args[1];
1655 Lisp_Object constants = args[2]; 1713 Lisp_Object constants = args[2];
1656 Lisp_Object stack_size = args[3]; 1714 Lisp_Object stack_size = args[3];
1657 Lisp_Object doc_string = ((nargs > 4) ? args[4] : Qnil); 1715 Lisp_Object doc_string = (nargs > 4) ? args[4] : Qnil;
1658 Lisp_Object interactive = ((nargs > 5) ? args[5] : Qunbound); 1716 Lisp_Object interactive = (nargs > 5) ? args[5] : Qunbound;
1659 /* Don't purecopy the doc references in instructions because it's 1717 /* Don't purecopy the doc references in instructions because it's
1660 wasteful; they will get fixed up later. 1718 wasteful; they will get fixed up later.
1661 1719
1662 #### If something goes wrong and they don't get fixed up, 1720 #### If something goes wrong and they don't get fixed up,
1663 we're screwed, because pure stuff isn't marked and thus the 1721 we're screwed, because pure stuff isn't marked and thus the
1844 allocate_extent (void) 1902 allocate_extent (void)
1845 { 1903 {
1846 struct extent *e; 1904 struct extent *e;
1847 1905
1848 ALLOCATE_FIXED_TYPE (extent, struct extent, e); 1906 ALLOCATE_FIXED_TYPE (extent, struct extent, e);
1849 /* memset (e, 0, sizeof (struct extent)); */ 1907 /* xzero (*e); */
1850 set_lheader_implementation (&(e->lheader), lrecord_extent); 1908 set_lheader_implementation (&(e->lheader), lrecord_extent);
1851 extent_object (e) = Qnil; 1909 extent_object (e) = Qnil;
1852 set_extent_start (e, -1); 1910 set_extent_start (e, -1);
1853 set_extent_end (e, -1); 1911 set_extent_end (e, -1);
1854 e->plist = Qnil; 1912 e->plist = Qnil;
1855 1913
1856 memset (&e->flags, 0, sizeof (e->flags)); 1914 xzero (e->flags);
1857 1915
1858 extent_face (e) = Qnil; 1916 extent_face (e) = Qnil;
1859 e->flags.end_open = 1; /* default is for endpoints to behave like markers */ 1917 e->flags.end_open = 1; /* default is for endpoints to behave like markers */
1860 e->flags.detachable = 1; 1918 e->flags.detachable = 1;
1861 1919
1890 1948
1891 DECLARE_FIXED_TYPE_ALLOC (marker, struct Lisp_Marker); 1949 DECLARE_FIXED_TYPE_ALLOC (marker, struct Lisp_Marker);
1892 #define MINIMUM_ALLOWED_FIXED_TYPE_CELLS_marker 1000 1950 #define MINIMUM_ALLOWED_FIXED_TYPE_CELLS_marker 1000
1893 1951
1894 DEFUN ("make-marker", Fmake_marker, 0, 0, 0, /* 1952 DEFUN ("make-marker", Fmake_marker, 0, 0, 0, /*
1895 Return a newly allocated marker which does not point at any place. 1953 Return a new marker which does not point at any place.
1896 */ 1954 */
1897 ()) 1955 ())
1898 { 1956 {
1899 Lisp_Object val; 1957 Lisp_Object val;
1900 struct Lisp_Marker *p; 1958 struct Lisp_Marker *p;
1962 } 2020 }
1963 2021
1964 static int 2022 static int
1965 string_equal (Lisp_Object o1, Lisp_Object o2, int depth) 2023 string_equal (Lisp_Object o1, Lisp_Object o2, int depth)
1966 { 2024 {
1967 Bytecount len = XSTRING_LENGTH (o1); 2025 Bytecount len;
1968 if (len != XSTRING_LENGTH (o2)) 2026 return (((len = XSTRING_LENGTH (o1)) == XSTRING_LENGTH (o2)) &&
1969 return 0; 2027 !memcmp (XSTRING_DATA (o1), XSTRING_DATA (o2), len));
1970 if (memcmp (XSTRING_DATA (o1), XSTRING_DATA (o2), len))
1971 return 0;
1972 return 1;
1973 } 2028 }
1974 2029
1975 DEFINE_BASIC_LRECORD_IMPLEMENTATION ("string", string, 2030 DEFINE_BASIC_LRECORD_IMPLEMENTATION ("string", string,
1976 mark_string, print_string, 2031 mark_string, print_string,
1977 /* 2032 /*
1987 0, string_equal, 0, 2042 0, string_equal, 0,
1988 struct Lisp_String); 2043 struct Lisp_String);
1989 #endif /* LRECORD_STRING */ 2044 #endif /* LRECORD_STRING */
1990 2045
1991 /* String blocks contain this many useful bytes. */ 2046 /* String blocks contain this many useful bytes. */
1992 #define STRING_CHARS_BLOCK_SIZE \ 2047 #define STRING_CHARS_BLOCK_SIZE \
1993 (8192 - MALLOC_OVERHEAD - ((2 * sizeof (struct string_chars_block *)) \ 2048 ((Bytecount) (8192 - MALLOC_OVERHEAD - \
1994 + sizeof (EMACS_INT))) 2049 ((2 * sizeof (struct string_chars_block *)) \
2050 + sizeof (EMACS_INT))))
1995 /* Block header for small strings. */ 2051 /* Block header for small strings. */
1996 struct string_chars_block 2052 struct string_chars_block
1997 { 2053 {
1998 EMACS_INT pos; 2054 EMACS_INT pos;
1999 struct string_chars_block *next; 2055 struct string_chars_block *next;
2155 if (delta == 0) 2211 if (delta == 0)
2156 /* simplest case: no size change. */ 2212 /* simplest case: no size change. */
2157 return; 2213 return;
2158 else 2214 else
2159 { 2215 {
2160 EMACS_INT oldfullsize = STRING_FULLSIZE (string_length (s)); 2216 Bytecount oldfullsize = STRING_FULLSIZE (string_length (s));
2161 EMACS_INT newfullsize = STRING_FULLSIZE (string_length (s) + delta); 2217 Bytecount newfullsize = STRING_FULLSIZE (string_length (s) + delta);
2162 2218
2163 if (oldfullsize == newfullsize) 2219 if (oldfullsize == newfullsize)
2164 { 2220 {
2165 /* next simplest case; size change but the necessary 2221 /* next simplest case; size change but the necessary
2166 allocation size won't change (up or down; code somewhere 2222 allocation size won't change (up or down; code somewhere
2238 Terminate now just to make sure. */ 2294 Terminate now just to make sure. */
2239 string_data (s)[string_length (s)] = '\0'; 2295 string_data (s)[string_length (s)] = '\0';
2240 2296
2241 if (pos >= 0) 2297 if (pos >= 0)
2242 { 2298 {
2243 Lisp_Object string = Qnil; 2299 Lisp_Object string;
2244 2300
2245 XSETSTRING (string, s); 2301 XSETSTRING (string, s);
2246 /* We also have to adjust all of the extent indices after the 2302 /* We also have to adjust all of the extent indices after the
2247 place we did the change. We say "pos - 1" because 2303 place we did the change. We say "pos - 1" because
2248 adjust_extents() is exclusive of the starting position 2304 adjust_extents() is exclusive of the starting position
2276 } 2332 }
2277 2333
2278 #endif /* MULE */ 2334 #endif /* MULE */
2279 2335
2280 DEFUN ("make-string", Fmake_string, 2, 2, 0, /* 2336 DEFUN ("make-string", Fmake_string, 2, 2, 0, /*
2281 Return a newly created string of length LENGTH, with each element being INIT. 2337 Return a new string of length LENGTH, with each character being INIT.
2282 LENGTH must be an integer and INIT must be a character. 2338 LENGTH must be an integer and INIT must be a character.
2283 */ 2339 */
2284 (length, init)) 2340 (length, init))
2285 { 2341 {
2286 Lisp_Object val; 2342 Lisp_Object val;
2308 } 2364 }
2309 return val; 2365 return val;
2310 } 2366 }
2311 2367
2312 /* Take some raw memory, which MUST already be in internal format, 2368 /* Take some raw memory, which MUST already be in internal format,
2313 and package it up it into a Lisp string. */ 2369 and package it up into a Lisp string. */
2314 Lisp_Object 2370 Lisp_Object
2315 make_string (CONST Bufbyte *contents, Bytecount length) 2371 make_string (CONST Bufbyte *contents, Bytecount length)
2316 { 2372 {
2317 Lisp_Object val; 2373 Lisp_Object val;
2318 2374
2330 and convert it into a Lisp string. */ 2386 and convert it into a Lisp string. */
2331 Lisp_Object 2387 Lisp_Object
2332 make_ext_string (CONST Extbyte *contents, EMACS_INT length, 2388 make_ext_string (CONST Extbyte *contents, EMACS_INT length,
2333 enum external_data_format fmt) 2389 enum external_data_format fmt)
2334 { 2390 {
2335 CONST Bufbyte *intstr; 2391 Bufbyte *intstr;
2336 Bytecount intlen; 2392 Bytecount intlen;
2337 2393
2338 GET_CHARPTR_INT_DATA_ALLOCA (contents, length, fmt, intstr, intlen); 2394 GET_CHARPTR_INT_DATA_ALLOCA (contents, length, fmt, intstr, intlen);
2339 return make_string (intstr, intlen); 2395 return make_string (intstr, intlen);
2340 } 2396 }
2348 2404
2349 Lisp_Object 2405 Lisp_Object
2350 build_ext_string (CONST char *str, enum external_data_format fmt) 2406 build_ext_string (CONST char *str, enum external_data_format fmt)
2351 { 2407 {
2352 /* Some strlen's crash and burn if passed null. */ 2408 /* Some strlen's crash and burn if passed null. */
2353 return make_ext_string ((Extbyte *) str, (str ? strlen(str) : 0), fmt); 2409 return make_ext_string ((CONST Extbyte *) str, (str ? strlen(str) : 0), fmt);
2354 } 2410 }
2355 2411
2356 Lisp_Object 2412 Lisp_Object
2357 build_translated_string (CONST char *str) 2413 build_translated_string (CONST char *str)
2358 { 2414 {
2430 2486
2431 DEFINE_LRECORD_IMPLEMENTATION ("lcrecord-list", lcrecord_list, 2487 DEFINE_LRECORD_IMPLEMENTATION ("lcrecord-list", lcrecord_list,
2432 mark_lcrecord_list, internal_object_printer, 2488 mark_lcrecord_list, internal_object_printer,
2433 0, 0, 0, struct lcrecord_list); 2489 0, 0, 0, struct lcrecord_list);
2434 Lisp_Object 2490 Lisp_Object
2435 make_lcrecord_list (int size, 2491 make_lcrecord_list (size_t size,
2436 CONST struct lrecord_implementation *implementation) 2492 CONST struct lrecord_implementation *implementation)
2437 { 2493 {
2438 struct lcrecord_list *p = alloc_lcrecord_type (struct lcrecord_list, 2494 struct lcrecord_list *p = alloc_lcrecord_type (struct lcrecord_list,
2439 lrecord_lcrecord_list); 2495 lrecord_lcrecord_list);
2440 Lisp_Object val = Qnil; 2496 Lisp_Object val;
2441 2497
2442 p->implementation = implementation; 2498 p->implementation = implementation;
2443 p->size = size; 2499 p->size = size;
2444 p->free = Qnil; 2500 p->free = Qnil;
2445 XSETLCRECORD_LIST (val, p); 2501 XSETLCRECORD_LIST (val, p);
2478 free_header->lcheader.free = 0; 2534 free_header->lcheader.free = 0;
2479 return val; 2535 return val;
2480 } 2536 }
2481 else 2537 else
2482 { 2538 {
2483 Lisp_Object val = Qnil; 2539 Lisp_Object val;
2484 2540
2485 XSETOBJ (val, Lisp_Type_Record, 2541 XSETOBJ (val, Lisp_Type_Record,
2486 alloc_lcrecord (list->size, list->implementation)); 2542 alloc_lcrecord (list->size, list->implementation));
2487 return val; 2543 return val;
2488 } 2544 }
2527 make_pure_string (CONST Bufbyte *data, Bytecount length, 2583 make_pure_string (CONST Bufbyte *data, Bytecount length,
2528 Lisp_Object plist, int no_need_to_copy_data) 2584 Lisp_Object plist, int no_need_to_copy_data)
2529 { 2585 {
2530 Lisp_Object new; 2586 Lisp_Object new;
2531 struct Lisp_String *s; 2587 struct Lisp_String *s;
2532 int size = (sizeof (struct Lisp_String) + ((no_need_to_copy_data) 2588 size_t size = sizeof (struct Lisp_String) +
2533 ? 0 2589 (no_need_to_copy_data ? 0 : (length + 1)); /* + 1 for terminating 0 */
2534 /* + 1 for terminating 0 */
2535 : (length + 1)));
2536 size = ALIGN_SIZE (size, ALIGNOF (Lisp_Object)); 2590 size = ALIGN_SIZE (size, ALIGNOF (Lisp_Object));
2537 2591
2538 if (symbols_initialized && !pure_lossage) 2592 if (symbols_initialized && !pure_lossage)
2539 { 2593 {
2540 /* Try to share some names. Saves a few kbytes. */ 2594 /* Try to share some names. Saves a few kbytes. */
2549 } 2603 }
2550 2604
2551 if (!check_purespace (size)) 2605 if (!check_purespace (size))
2552 return make_string (data, length); 2606 return make_string (data, length);
2553 2607
2554 s = (struct Lisp_String *) (PUREBEG + pureptr); 2608 s = (struct Lisp_String *) (PUREBEG + pure_bytes_used);
2555 #ifdef LRECORD_STRING 2609 #ifdef LRECORD_STRING
2556 set_lheader_implementation (&(s->lheader), lrecord_string); 2610 set_lheader_implementation (&(s->lheader), lrecord_string);
2557 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION 2611 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION
2558 s->lheader.pure = 1; 2612 s->lheader.pure = 1;
2559 #endif 2613 #endif
2568 set_string_data (s, (Bufbyte *) s + sizeof (struct Lisp_String)); 2622 set_string_data (s, (Bufbyte *) s + sizeof (struct Lisp_String));
2569 memcpy (string_data (s), data, length); 2623 memcpy (string_data (s), data, length);
2570 set_string_byte (s, length, 0); 2624 set_string_byte (s, length, 0);
2571 } 2625 }
2572 s->plist = Qnil; 2626 s->plist = Qnil;
2573 pureptr += size; 2627 pure_bytes_used += size;
2574 2628
2575 #ifdef PURESTAT 2629 #ifdef PURESTAT
2576 bump_purestat (&purestat_string_all, size); 2630 bump_purestat (&purestat_string_all, size);
2577 if (purecopying_for_bytecode) 2631 if (purecopying_for_bytecode)
2578 bump_purestat (&purestat_string_other_function, size); 2632 bump_purestat (&purestat_string_other_function, size);
2608 struct Lisp_Cons *c; 2662 struct Lisp_Cons *c;
2609 2663
2610 if (!check_purespace (sizeof (struct Lisp_Cons))) 2664 if (!check_purespace (sizeof (struct Lisp_Cons)))
2611 return Fcons (Fpurecopy (car), Fpurecopy (cdr)); 2665 return Fcons (Fpurecopy (car), Fpurecopy (cdr));
2612 2666
2613 c = (struct Lisp_Cons *) (PUREBEG + pureptr); 2667 c = (struct Lisp_Cons *) (PUREBEG + pure_bytes_used);
2614 #ifdef LRECORD_CONS 2668 #ifdef LRECORD_CONS
2615 set_lheader_implementation (&(c->lheader), lrecord_cons); 2669 set_lheader_implementation (&(c->lheader), lrecord_cons);
2616 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION 2670 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION
2617 c->lheader.pure = 1; 2671 c->lheader.pure = 1;
2618 #endif 2672 #endif
2619 #endif 2673 #endif
2620 pureptr += sizeof (struct Lisp_Cons); 2674 pure_bytes_used += sizeof (struct Lisp_Cons);
2621 bump_purestat (&purestat_cons, sizeof (struct Lisp_Cons)); 2675 bump_purestat (&purestat_cons, sizeof (struct Lisp_Cons));
2622 2676
2623 c->car = Fpurecopy (car); 2677 c->car = Fpurecopy (car);
2624 c->cdr = Fpurecopy (cdr); 2678 c->cdr = Fpurecopy (cdr);
2625 XSETCONS (new, c); 2679 XSETCONS (new, c);
2627 } 2681 }
2628 2682
2629 Lisp_Object 2683 Lisp_Object
2630 pure_list (int nargs, Lisp_Object *args) 2684 pure_list (int nargs, Lisp_Object *args)
2631 { 2685 {
2632 Lisp_Object foo = Qnil; 2686 Lisp_Object val = Qnil;
2633 2687
2634 for (--nargs; nargs >= 0; nargs--) 2688 for (--nargs; nargs >= 0; nargs--)
2635 foo = pure_cons (args[nargs], foo); 2689 val = pure_cons (args[nargs], val);
2636 2690
2637 return foo; 2691 return val;
2638 } 2692 }
2639 2693
2640 #ifdef LISP_FLOAT_TYPE 2694 #ifdef LISP_FLOAT_TYPE
2641 2695
2642 Lisp_Object 2696 static Lisp_Object
2643 make_pure_float (double num) 2697 make_pure_float (double num)
2644 { 2698 {
2645 struct Lisp_Float *f; 2699 struct Lisp_Float *f;
2646 Lisp_Object val; 2700 Lisp_Object val;
2647 2701
2648 /* Make sure that PUREBEG + pureptr is aligned on at least a sizeof 2702 /* Make sure that PUREBEG + pure_bytes_used is aligned on at least a sizeof
2649 (double) boundary. Some architectures (like the sparc) require 2703 (double) boundary. Some architectures (like the sparc) require
2650 this, and I suspect that floats are rare enough that it's no 2704 this, and I suspect that floats are rare enough that it's no
2651 tragedy for those that don't. */ 2705 tragedy for those that don't. */
2652 { 2706 {
2653 #if defined (__GNUC__) && (__GNUC__ >= 2) 2707 #if defined (__GNUC__) && (__GNUC__ >= 2)
2663 should be ok because presumably there is padding in the layout 2717 should be ok because presumably there is padding in the layout
2664 of the struct to account for this. 2718 of the struct to account for this.
2665 */ 2719 */
2666 int alignment = sizeof (float_data (f)); 2720 int alignment = sizeof (float_data (f));
2667 #endif /* !GNUC */ 2721 #endif /* !GNUC */
2668 char *p = ((char *) PUREBEG + pureptr); 2722 char *p = ((char *) PUREBEG + pure_bytes_used);
2669 2723
2670 p = (char *) (((unsigned EMACS_INT) p + alignment - 1) & - alignment); 2724 p = (char *) (((EMACS_UINT) p + alignment - 1) & - alignment);
2671 pureptr = p - (char *) PUREBEG; 2725 pure_bytes_used = p - (char *) PUREBEG;
2672 } 2726 }
2673 2727
2674 if (!check_purespace (sizeof (struct Lisp_Float))) 2728 if (!check_purespace (sizeof (struct Lisp_Float)))
2675 return make_float (num); 2729 return make_float (num);
2676 2730
2677 f = (struct Lisp_Float *) (PUREBEG + pureptr); 2731 f = (struct Lisp_Float *) (PUREBEG + pure_bytes_used);
2678 set_lheader_implementation (&(f->lheader), lrecord_float); 2732 set_lheader_implementation (&(f->lheader), lrecord_float);
2679 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION 2733 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION
2680 f->lheader.pure = 1; 2734 f->lheader.pure = 1;
2681 #endif 2735 #endif
2682 pureptr += sizeof (struct Lisp_Float); 2736 pure_bytes_used += sizeof (struct Lisp_Float);
2683 bump_purestat (&purestat_float, sizeof (struct Lisp_Float)); 2737 bump_purestat (&purestat_float, sizeof (struct Lisp_Float));
2684 2738
2685 float_next (f) = ((struct Lisp_Float *) -1); 2739 float_next (f) = ((struct Lisp_Float *) -1);
2686 float_data (f) = num; 2740 float_data (f) = num;
2687 XSETFLOAT (val, f); 2741 XSETFLOAT (val, f);
2689 } 2743 }
2690 2744
2691 #endif /* LISP_FLOAT_TYPE */ 2745 #endif /* LISP_FLOAT_TYPE */
2692 2746
2693 Lisp_Object 2747 Lisp_Object
2694 make_pure_vector (EMACS_INT len, Lisp_Object init) 2748 make_pure_vector (size_t len, Lisp_Object init)
2695 { 2749 {
2696 Lisp_Object new; 2750 Lisp_Object new;
2697 struct Lisp_Vector *v; 2751 struct Lisp_Vector *v;
2698 EMACS_INT size = (sizeof (struct Lisp_Vector) 2752 size_t size = (sizeof (struct Lisp_Vector)
2699 + (len - 1) * sizeof (Lisp_Object)); 2753 + (len - 1) * sizeof (Lisp_Object));
2700 2754
2701 init = Fpurecopy (init); 2755 init = Fpurecopy (init);
2702 2756
2703 if (!check_purespace (size)) 2757 if (!check_purespace (size))
2704 return make_vector (len, init); 2758 return make_vector (len, init);
2705 2759
2706 v = (struct Lisp_Vector *) (PUREBEG + pureptr); 2760 v = (struct Lisp_Vector *) (PUREBEG + pure_bytes_used);
2707 #ifdef LRECORD_VECTOR 2761 #ifdef LRECORD_VECTOR
2708 set_lheader_implementation (&(v->header.lheader), lrecord_vector); 2762 set_lheader_implementation (&(v->header.lheader), lrecord_vector);
2709 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION 2763 #ifdef USE_INDEXED_LRECORD_IMPLEMENTATION
2710 v->header.lheader.pure = 1; 2764 v->header.lheader.pure = 1;
2711 #endif 2765 #endif
2712 #endif 2766 #endif
2713 pureptr += size; 2767 pure_bytes_used += size;
2714 bump_purestat (&purestat_vector_all, size); 2768 bump_purestat (&purestat_vector_all, size);
2715 2769
2716 v->size = len; 2770 v->size = len;
2717 2771
2718 for (size = 0; size < len; size++) 2772 for (size = 0; size < len; size++)
2725 #if 0 2779 #if 0
2726 /* Presently unused */ 2780 /* Presently unused */
2727 void * 2781 void *
2728 alloc_pure_lrecord (int size, struct lrecord_implementation *implementation) 2782 alloc_pure_lrecord (int size, struct lrecord_implementation *implementation)
2729 { 2783 {
2730 struct lrecord_header *header = (void *) (PUREBEG + pureptr); 2784 struct lrecord_header *header = (void *) (PUREBEG + pure_bytes_used);
2731 2785
2732 if (pureptr + size > get_PURESIZE()) 2786 if (pure_bytes_used + size > get_PURESIZE())
2733 pure_storage_exhausted (); 2787 pure_storage_exhausted ();
2734 2788
2735 set_lheader_implementation (header, implementation); 2789 set_lheader_implementation (header, implementation);
2736 header->next = 0; 2790 header->next = 0;
2737 return header; 2791 return header;
2859 } 2913 }
2860 2914
2861 2915
2862 2916
2863 static void 2917 static void
2864 puresize_adjust_h (long int puresize) 2918 puresize_adjust_h (size_t puresize)
2865 { 2919 {
2866 FILE *stream = fopen ("puresize-adjust.h", "w"); 2920 FILE *stream = fopen ("puresize-adjust.h", "w");
2867 2921
2868 if (stream == NULL) 2922 if (stream == NULL)
2869 report_file_error ("Opening puresize adjustment file", 2923 report_file_error ("Opening puresize adjustment file",
2871 2925
2872 fprintf (stream, 2926 fprintf (stream,
2873 "/*\tDo not edit this file!\n" 2927 "/*\tDo not edit this file!\n"
2874 "\tAutomatically generated by XEmacs */\n" 2928 "\tAutomatically generated by XEmacs */\n"
2875 "# define PURESIZE_ADJUSTMENT (%ld)\n", 2929 "# define PURESIZE_ADJUSTMENT (%ld)\n",
2876 puresize - RAW_PURESIZE); 2930 (long) (puresize - RAW_PURESIZE));
2877 fclose (stream); 2931 fclose (stream);
2878 } 2932 }
2879 2933
2880 void 2934 void
2881 report_pure_usage (int report_impurities, 2935 report_pure_usage (int report_impurities,
2886 if (pure_lossage) 2940 if (pure_lossage)
2887 { 2941 {
2888 message ("\n****\tPure Lisp storage exhausted!\n" 2942 message ("\n****\tPure Lisp storage exhausted!\n"
2889 "\tPurespace usage: %ld of %ld\n" 2943 "\tPurespace usage: %ld of %ld\n"
2890 "****", 2944 "****",
2891 get_PURESIZE()+pure_lossage, (long) get_PURESIZE()); 2945 (long) get_PURESIZE() + pure_lossage,
2892 if (die_if_pure_storage_exceeded) { 2946 (long) get_PURESIZE());
2893 puresize_adjust_h (get_PURESIZE() + pure_lossage); 2947 if (die_if_pure_storage_exceeded)
2948 {
2949 puresize_adjust_h (get_PURESIZE() + pure_lossage);
2894 #ifdef HEAP_IN_DATA 2950 #ifdef HEAP_IN_DATA
2895 sheap_adjust_h(); 2951 sheap_adjust_h();
2896 #endif 2952 #endif
2897 rc = -1; 2953 rc = -1;
2898 } 2954 }
2899 } 2955 }
2900 else 2956 else
2901 { 2957 {
2902 int lost = (get_PURESIZE() - pureptr) / 1024; 2958 size_t lost = (get_PURESIZE() - pure_bytes_used) / 1024;
2903 char buf[200]; 2959 char buf[200];
2904 /* extern Lisp_Object Vemacs_beta_version; */ 2960 /* extern Lisp_Object Vemacs_beta_version; */
2905 /* This used to be NILP(Vemacs_beta_version) ? 512 : 4; */ 2961 /* This used to be NILP(Vemacs_beta_version) ? 512 : 4; */
2906 #ifndef PURESIZE_SLOP 2962 #ifndef PURESIZE_SLOP
2907 #define PURESIZE_SLOP 0 2963 #define PURESIZE_SLOP 0
2908 #endif 2964 #endif
2909 int slop = PURESIZE_SLOP; 2965 size_t slop = PURESIZE_SLOP;
2910 2966
2911 sprintf (buf, "Purespace usage: %ld of %ld (%d%%", 2967 sprintf (buf, "Purespace usage: %ld of %ld (%d%%",
2912 pureptr, (long) get_PURESIZE(), 2968 (long) pure_bytes_used,
2913 (int) (pureptr / (get_PURESIZE() / 100.0) + 0.5)); 2969 (long) get_PURESIZE(),
2970 (int) (pure_bytes_used / (get_PURESIZE() / 100.0) + 0.5));
2914 if (lost > ((slop ? slop : 1) / 1024)) { 2971 if (lost > ((slop ? slop : 1) / 1024)) {
2915 sprintf (buf + strlen (buf), " -- %dk wasted", lost); 2972 sprintf (buf + strlen (buf), " -- %dk wasted", lost);
2916 if (die_if_pure_storage_exceeded) { 2973 if (die_if_pure_storage_exceeded) {
2917 puresize_adjust_h (pureptr + slop); 2974 puresize_adjust_h (pure_bytes_used + slop);
2918 #ifdef HEAP_IN_DATA 2975 #ifdef HEAP_IN_DATA
2919 sheap_adjust_h(); 2976 sheap_adjust_h();
2920 #endif 2977 #endif
2921 rc = -1; 2978 rc = -1;
2922 } 2979 }
2971 sprintf(buf, "%s:", purestats[j]->name); 3028 sprintf(buf, "%s:", purestats[j]->name);
2972 message (" %-26s %5d %7d %2d%%", 3029 message (" %-26s %5d %7d %2d%%",
2973 buf, 3030 buf,
2974 purestats[j]->nobjects, 3031 purestats[j]->nobjects,
2975 purestats[j]->nbytes, 3032 purestats[j]->nbytes,
2976 (int) (purestats[j]->nbytes / (pureptr / 100.0) + 0.5)); 3033 (int) (purestats[j]->nbytes / (pure_bytes_used / 100.0) + 0.5));
2977 } 3034 }
2978 } 3035 }
2979 #endif /* PURESTAT */ 3036 #endif /* PURESTAT */
2980 3037
2981 3038
3229 { 3286 {
3230 idiot_c_doesnt_have_closures += pure_sizeof (obj, 1); 3287 idiot_c_doesnt_have_closures += pure_sizeof (obj, 1);
3231 } 3288 }
3232 #endif /* unused */ 3289 #endif /* unused */
3233 3290
3234 static int 3291 static size_t
3235 pure_string_sizeof(Lisp_Object obj) 3292 pure_string_sizeof (Lisp_Object obj)
3236 { 3293 {
3237 struct Lisp_String *ptr = XSTRING (obj); 3294 struct Lisp_String *ptr = XSTRING (obj);
3238 int size = string_length (ptr); 3295
3239 3296 if (string_data (ptr) != (Bufbyte *) ptr + sizeof (*ptr))
3240 if (string_data (ptr) !=
3241 (unsigned char *) ptr + sizeof (struct Lisp_String))
3242 { 3297 {
3243 /* string-data not allocated contiguously. 3298 /* string-data not allocated contiguously.
3244 Probably (better be!!) a pointer constant "C" data. */ 3299 Probably (better be!!) a pointer constant "C" data. */
3245 size = sizeof (struct Lisp_String); 3300 return sizeof (*ptr);
3246 } 3301 }
3247 else 3302 else
3248 { 3303 {
3249 size = sizeof (struct Lisp_String) + size + 1; 3304 size_t size = sizeof (*ptr) + string_length (ptr) + 1;
3250 size = ALIGN_SIZE (size, sizeof (Lisp_Object)); 3305 size = ALIGN_SIZE (size, sizeof (Lisp_Object));
3251 } 3306 return size;
3252 return size; 3307 }
3253 } 3308 }
3254 3309
3255 /* recurse arg isn't actually used */ 3310 /* recurse arg isn't actually used */
3256 static int 3311 static size_t
3257 pure_sizeof (Lisp_Object obj /*, int recurse */) 3312 pure_sizeof (Lisp_Object obj /*, int recurse */)
3258 { 3313 {
3259 int total = 0; 3314 size_t total = 0;
3260 3315
3261 /*tail_recurse: */ 3316 /*tail_recurse: */
3262 if (!POINTER_TYPE_P (XTYPE (obj)) 3317 if (!POINTER_TYPE_P (XTYPE (obj))
3263 || !PURIFIED (XPNTR (obj))) 3318 || !PURIFIED (XPNTR (obj)))
3264 return total; 3319 return total;
3270 switch (XTYPE (obj)) 3325 switch (XTYPE (obj))
3271 { 3326 {
3272 3327
3273 #ifndef LRECORD_STRING 3328 #ifndef LRECORD_STRING
3274 case Lisp_Type_String: 3329 case Lisp_Type_String:
3275 { 3330 total += pure_string_sizeof (obj);
3276 total += pure_string_sizeof (obj);
3277 }
3278 break; 3331 break;
3279 #endif /* ! LRECORD_STRING */ 3332 #endif /* ! LRECORD_STRING */
3280 3333
3281 #ifndef LRECORD_VECTOR 3334 #ifndef LRECORD_VECTOR
3282 case Lisp_Type_Vector: 3335 case Lisp_Type_Vector:
3397 3450
3398 int 3451 int
3399 lrecord_type_index (CONST struct lrecord_implementation *implementation) 3452 lrecord_type_index (CONST struct lrecord_implementation *implementation)
3400 { 3453 {
3401 int type_index = *(implementation->lrecord_type_index); 3454 int type_index = *(implementation->lrecord_type_index);
3402 /* Have to do this circuitous and validation test because of problems 3455 /* Have to do this circuitous validation test because of problems
3403 dumping out initialized variables (ie can't set xxx_type_index to -1 3456 dumping out initialized variables (ie can't set xxx_type_index to -1
3404 because that would make xxx_type_index read-only in a dumped emacs. */ 3457 because that would make xxx_type_index read-only in a dumped emacs. */
3405 if (type_index < 0 || type_index > max_lrecord_type 3458 if (type_index < 0 || type_index > max_lrecord_type
3406 || lrecord_implementations_table[type_index] != implementation) 3459 || lrecord_implementations_table[type_index] != implementation)
3407 { 3460 {
3452 assert (!free_p); 3505 assert (!free_p);
3453 lcrecord_stats[type_index].instances_on_free_list++; 3506 lcrecord_stats[type_index].instances_on_free_list++;
3454 } 3507 }
3455 else 3508 else
3456 { 3509 {
3457 unsigned int sz = (implementation->size_in_bytes_method 3510 size_t sz = (implementation->size_in_bytes_method
3458 ? ((implementation->size_in_bytes_method) (h)) 3511 ? ((implementation->size_in_bytes_method) (h))
3459 : implementation->static_size); 3512 : implementation->static_size);
3460 3513
3461 if (free_p) 3514 if (free_p)
3462 { 3515 {
3463 lcrecord_stats[type_index].instances_freed++; 3516 lcrecord_stats[type_index].instances_freed++;
3464 lcrecord_stats[type_index].bytes_freed += sz; 3517 lcrecord_stats[type_index].bytes_freed += sz;
4236 4289
4237 } 4290 }
4238 4291
4239 /* Clearing for disksave. */ 4292 /* Clearing for disksave. */
4240 4293
4241 extern Lisp_Object Vprocess_environment;
4242 extern Lisp_Object Vdoc_directory;
4243 extern Lisp_Object Vconfigure_info_directory;
4244 extern Lisp_Object Vload_path;
4245 extern Lisp_Object Vload_history;
4246 extern Lisp_Object Vshell_file_name;
4247
4248 void 4294 void
4249 disksave_object_finalization (void) 4295 disksave_object_finalization (void)
4250 { 4296 {
4251 /* It's important that certain information from the environment not get 4297 /* It's important that certain information from the environment not get
4252 dumped with the executable (pathnames, environment variables, etc.). 4298 dumped with the executable (pathnames, environment variables, etc.).
4279 disksave_object_finalization_1 (); 4325 disksave_object_finalization_1 ();
4280 4326
4281 #if 0 /* I don't see any point in this. The purespace starts out all 0's */ 4327 #if 0 /* I don't see any point in this. The purespace starts out all 0's */
4282 /* Zero out the unused portion of purespace */ 4328 /* Zero out the unused portion of purespace */
4283 if (!pure_lossage) 4329 if (!pure_lossage)
4284 memset ( (char *) (PUREBEG + pureptr), 0, 4330 memset ( (char *) (PUREBEG + pure_bytes_used), 0,
4285 (((char *) (PUREBEG + get_PURESIZE())) - 4331 (((char *) (PUREBEG + get_PURESIZE())) -
4286 ((char *) (PUREBEG + pureptr)))); 4332 ((char *) (PUREBEG + pure_bytes_used))));
4287 #endif 4333 #endif
4288 4334
4289 /* Zero out the uninitialized (really, unused) part of the containers 4335 /* Zero out the uninitialized (really, unused) part of the containers
4290 for the live strings. */ 4336 for the live strings. */
4291 { 4337 {
4323 { 4369 {
4324 char stack_top_variable; 4370 char stack_top_variable;
4325 extern char *stack_bottom; 4371 extern char *stack_bottom;
4326 int i; 4372 int i;
4327 struct frame *f; 4373 struct frame *f;
4328 int speccount = specpdl_depth (); 4374 int speccount;
4329 Lisp_Object pre_gc_cursor = Qnil; 4375 int cursor_changed;
4376 Lisp_Object pre_gc_cursor;
4330 struct gcpro gcpro1; 4377 struct gcpro gcpro1;
4331 4378
4332 int cursor_changed = 0; 4379 if (gc_in_progress
4333 4380 || gc_currently_forbidden
4334 if (gc_in_progress != 0) 4381 || in_display
4382 || preparing_for_armageddon)
4335 return; 4383 return;
4336 4384
4337 if (gc_currently_forbidden || in_display) 4385 pre_gc_cursor = Qnil;
4338 return; 4386 cursor_changed = 0;
4339
4340 if (preparing_for_armageddon)
4341 return;
4342 4387
4343 /* This function cannot be called inside GC so we move to after the */ 4388 /* This function cannot be called inside GC so we move to after the */
4344 /* above tests */ 4389 /* above tests */
4345 f = selected_frame (); 4390 f = selected_frame ();
4346 4391
4347 GCPRO1 (pre_gc_cursor); 4392 GCPRO1 (pre_gc_cursor);
4348 4393
4349 /* Very important to prevent GC during any of the following 4394 /* Very important to prevent GC during any of the following
4350 stuff that might run Lisp code; otherwise, we'll likely 4395 stuff that might run Lisp code; otherwise, we'll likely
4351 have infinite GC recursion. */ 4396 have infinite GC recursion. */
4397 speccount = specpdl_depth ();
4352 record_unwind_protect (restore_gc_inhibit, 4398 record_unwind_protect (restore_gc_inhibit,
4353 make_int (gc_currently_forbidden)); 4399 make_int (gc_currently_forbidden));
4354 gc_currently_forbidden = 1; 4400 gc_currently_forbidden = 1;
4355 4401
4356 if (!gc_hooks_inhibited) 4402 if (!gc_hooks_inhibited)
4400 #if MAX_SAVE_STACK > 0 4446 #if MAX_SAVE_STACK > 0
4401 4447
4402 /* Save a copy of the contents of the stack, for debugging. */ 4448 /* Save a copy of the contents of the stack, for debugging. */
4403 if (!purify_flag) 4449 if (!purify_flag)
4404 { 4450 {
4405 i = &stack_top_variable - stack_bottom; 4451 /* Static buffer in which we save a copy of the C stack at each GC. */
4406 if (i < 0) i = -i; 4452 static char *stack_copy;
4407 if (i < MAX_SAVE_STACK) 4453 static size_t stack_copy_size;
4454
4455 ptrdiff_t stack_diff = &stack_top_variable - stack_bottom;
4456 size_t stack_size = (stack_diff > 0 ? stack_diff : -stack_diff);
4457 if (stack_size < MAX_SAVE_STACK)
4408 { 4458 {
4409 if (stack_copy == 0) 4459 if (stack_copy_size < stack_size)
4410 stack_copy = (char *) malloc (stack_copy_size = i);
4411 else if (stack_copy_size < i)
4412 stack_copy = (char *) realloc (stack_copy, (stack_copy_size = i));
4413 if (stack_copy)
4414 { 4460 {
4415 if ((int) (&stack_top_variable - stack_bottom) > 0) 4461 stack_copy = (char *) xrealloc (stack_copy, stack_size);
4416 memcpy (stack_copy, stack_bottom, i); 4462 stack_copy_size = stack_size;
4417 else
4418 memcpy (stack_copy, &stack_top_variable, i);
4419 } 4463 }
4464
4465 memcpy (stack_copy,
4466 stack_diff > 0 ? stack_bottom : &stack_top_variable,
4467 stack_size);
4420 } 4468 }
4421 } 4469 }
4422 #endif /* MAX_SAVE_STACK > 0 */ 4470 #endif /* MAX_SAVE_STACK > 0 */
4423 4471
4424 /* Do some totally ad-hoc resource clearing. */ 4472 /* Do some totally ad-hoc resource clearing. */
4550 /* now stop inhibiting GC */ 4598 /* now stop inhibiting GC */
4551 unbind_to (speccount, Qnil); 4599 unbind_to (speccount, Qnil);
4552 4600
4553 if (!breathing_space) 4601 if (!breathing_space)
4554 { 4602 {
4555 breathing_space = (void *) malloc (4096 - MALLOC_OVERHEAD); 4603 breathing_space = malloc (4096 - MALLOC_OVERHEAD);
4556 } 4604 }
4557 4605
4558 UNGCPRO; 4606 UNGCPRO;
4559 return; 4607 return;
4560 } 4608 }
4587 (pl) = gc_plist_hack ((name), s, (pl)); \ 4635 (pl) = gc_plist_hack ((name), s, (pl)); \
4588 } 4636 }
4589 4637
4590 DEFUN ("garbage-collect", Fgarbage_collect, 0, 0, "", /* 4638 DEFUN ("garbage-collect", Fgarbage_collect, 0, 0, "", /*
4591 Reclaim storage for Lisp objects no longer needed. 4639 Reclaim storage for Lisp objects no longer needed.
4592 Returns info on amount of space in use: 4640 Return info on amount of space in use:
4593 ((USED-CONSES . FREE-CONSES) (USED-SYMS . FREE-SYMS) 4641 ((USED-CONSES . FREE-CONSES) (USED-SYMS . FREE-SYMS)
4594 (USED-MARKERS . FREE-MARKERS) USED-STRING-CHARS USED-VECTOR-SLOTS 4642 (USED-MARKERS . FREE-MARKERS) USED-STRING-CHARS USED-VECTOR-SLOTS
4595 PLIST) 4643 PLIST)
4596 where `PLIST' is a list of alternating keyword/value pairs providing 4644 where `PLIST' is a list of alternating keyword/value pairs providing
4597 more detailed information. 4645 more detailed information.
4599 `gc-cons-threshold' bytes of Lisp data since previous garbage collection. 4647 `gc-cons-threshold' bytes of Lisp data since previous garbage collection.
4600 */ 4648 */
4601 ()) 4649 ())
4602 { 4650 {
4603 Lisp_Object pl = Qnil; 4651 Lisp_Object pl = Qnil;
4604 Lisp_Object ret[6];
4605 int i; 4652 int i;
4606 #ifdef LRECORD_VECTOR 4653 #ifdef LRECORD_VECTOR
4607 int gc_count_vector_total_size = 0; 4654 int gc_count_vector_total_size = 0;
4608 #endif 4655 #endif
4609 4656
4610 if (purify_flag && pure_lossage) 4657 if (purify_flag && pure_lossage)
4611 { 4658 return Qnil;
4612 return Qnil;
4613 }
4614 4659
4615 garbage_collect_1 (); 4660 garbage_collect_1 ();
4616 4661
4617 for (i = 0; i < last_lrecord_type_index_assigned; i++) 4662 for (i = 0; i < last_lrecord_type_index_assigned; i++)
4618 { 4663 {
4706 HACK_O_MATIC (cons, "cons-storage", pl); 4751 HACK_O_MATIC (cons, "cons-storage", pl);
4707 pl = gc_plist_hack ("conses-free", gc_count_num_cons_freelist, pl); 4752 pl = gc_plist_hack ("conses-free", gc_count_num_cons_freelist, pl);
4708 pl = gc_plist_hack ("conses-used", gc_count_num_cons_in_use, pl); 4753 pl = gc_plist_hack ("conses-used", gc_count_num_cons_in_use, pl);
4709 4754
4710 /* The things we do for backwards-compatibility */ 4755 /* The things we do for backwards-compatibility */
4711 ret[0] = Fcons (make_int (gc_count_num_cons_in_use), 4756 return
4712 make_int (gc_count_num_cons_freelist)); 4757 list6 (Fcons (make_int (gc_count_num_cons_in_use),
4713 ret[1] = Fcons (make_int (gc_count_num_symbol_in_use), 4758 make_int (gc_count_num_cons_freelist)),
4714 make_int (gc_count_num_symbol_freelist)); 4759 Fcons (make_int (gc_count_num_symbol_in_use),
4715 ret[2] = Fcons (make_int (gc_count_num_marker_in_use), 4760 make_int (gc_count_num_symbol_freelist)),
4716 make_int (gc_count_num_marker_freelist)); 4761 Fcons (make_int (gc_count_num_marker_in_use),
4717 ret[3] = make_int (gc_count_string_total_size); 4762 make_int (gc_count_num_marker_freelist)),
4718 ret[4] = make_int (gc_count_vector_total_size); 4763 make_int (gc_count_string_total_size),
4719 ret[5] = pl; 4764 make_int (gc_count_vector_total_size),
4720 return Flist (6, ret); 4765 pl);
4721 } 4766 }
4722 #undef HACK_O_MATIC 4767 #undef HACK_O_MATIC
4723 4768
4724 DEFUN ("consing-since-gc", Fconsing_since_gc, 0, 0, "", /* 4769 DEFUN ("consing-since-gc", Fconsing_since_gc, 0, 0, "", /*
4725 Return the number of bytes consed since the last garbage collection. 4770 Return the number of bytes consed since the last garbage collection.
4753 (WINDOWP (obj) && !WINDOW_LIVE_P (XWINDOW (obj))) || 4798 (WINDOWP (obj) && !WINDOW_LIVE_P (XWINDOW (obj))) ||
4754 (DEVICEP (obj) && !DEVICE_LIVE_P (XDEVICE (obj))) || 4799 (DEVICEP (obj) && !DEVICE_LIVE_P (XDEVICE (obj))) ||
4755 (CONSOLEP (obj) && !CONSOLE_LIVE_P (XCONSOLE (obj))) || 4800 (CONSOLEP (obj) && !CONSOLE_LIVE_P (XCONSOLE (obj))) ||
4756 (EVENTP (obj) && !EVENT_LIVE_P (XEVENT (obj))) || 4801 (EVENTP (obj) && !EVENT_LIVE_P (XEVENT (obj))) ||
4757 (EXTENTP (obj) && !EXTENT_LIVE_P (XEXTENT (obj)))); 4802 (EXTENTP (obj) && !EXTENT_LIVE_P (XEXTENT (obj))));
4758
4759 } 4803 }
4760 4804
4761 #ifdef MEMORY_USAGE_STATS 4805 #ifdef MEMORY_USAGE_STATS
4762 4806
4763 /* Attempt to determine the actual amount of space that is used for 4807 /* Attempt to determine the actual amount of space that is used for
4790 for want of better data is that sizeof (void *), or maybe 4834 for want of better data is that sizeof (void *), or maybe
4791 2 * sizeof (void *), is required as overhead and that 4835 2 * sizeof (void *), is required as overhead and that
4792 blocks are allocated in the minimum required size except 4836 blocks are allocated in the minimum required size except
4793 that some minimum block size is imposed (e.g. 16 bytes). */ 4837 that some minimum block size is imposed (e.g. 16 bytes). */
4794 4838
4795 int 4839 size_t
4796 malloced_storage_size (void *ptr, int claimed_size, 4840 malloced_storage_size (void *ptr, size_t claimed_size,
4797 struct overhead_stats *stats) 4841 struct overhead_stats *stats)
4798 { 4842 {
4799 int orig_claimed_size = claimed_size; 4843 size_t orig_claimed_size = claimed_size;
4800 4844
4801 #ifdef GNU_MALLOC 4845 #ifdef GNU_MALLOC
4802 4846
4803 if (claimed_size < 2 * sizeof (void *)) 4847 if (claimed_size < 2 * sizeof (void *))
4804 claimed_size = 2 * sizeof (void *); 4848 claimed_size = 2 * sizeof (void *);
4823 claimed_size *= 2; 4867 claimed_size *= 2;
4824 log--; 4868 log--;
4825 } 4869 }
4826 /* We have to come up with some average about the amount of 4870 /* We have to come up with some average about the amount of
4827 blocks used. */ 4871 blocks used. */
4828 if ((rand () & 4095) < claimed_size) 4872 if ((size_t) (rand () & 4095) < claimed_size)
4829 claimed_size += 3 * sizeof (void *); 4873 claimed_size += 3 * sizeof (void *);
4830 } 4874 }
4831 else 4875 else
4832 { 4876 {
4833 claimed_size += 4095; 4877 claimed_size += 4095;
4874 stats->malloc_overhead += claimed_size - orig_claimed_size; 4918 stats->malloc_overhead += claimed_size - orig_claimed_size;
4875 } 4919 }
4876 return claimed_size; 4920 return claimed_size;
4877 } 4921 }
4878 4922
4879 int 4923 size_t
4880 fixed_type_block_overhead (int size) 4924 fixed_type_block_overhead (size_t size)
4881 { 4925 {
4882 int per_block = TYPE_ALLOC_SIZE (cons, unsigned char); 4926 size_t per_block = TYPE_ALLOC_SIZE (cons, unsigned char);
4883 int overhead = 0; 4927 size_t overhead = 0;
4884 int storage_size = malloced_storage_size (0, per_block, 0); 4928 size_t storage_size = malloced_storage_size (0, per_block, 0);
4885 while (size >= per_block) 4929 while (size >= per_block)
4886 { 4930 {
4887 size -= per_block; 4931 size -= per_block;
4888 overhead += sizeof (void *) + per_block - storage_size; 4932 overhead += sizeof (void *) + per_block - storage_size;
4889
4890 } 4933 }
4891 if (rand () % per_block < size) 4934 if (rand () % per_block < size)
4892 overhead += sizeof (void *) + per_block - storage_size; 4935 overhead += sizeof (void *) + per_block - storage_size;
4893 return overhead; 4936 return overhead;
4894 } 4937 }
4924 * defined subr lrecords were initialized with lheader->type == 0. 4967 * defined subr lrecords were initialized with lheader->type == 0.
4925 * See subr_lheader_initializer in lisp.h. Force type index 0 to be 4968 * See subr_lheader_initializer in lisp.h. Force type index 0 to be
4926 * assigned to lrecord_subr so that those predefined indexes match 4969 * assigned to lrecord_subr so that those predefined indexes match
4927 * reality. 4970 * reality.
4928 */ 4971 */
4929 (void) lrecord_type_index (lrecord_subr); 4972 lrecord_type_index (lrecord_subr);
4930 assert (*(lrecord_subr[0].lrecord_type_index) == 0); 4973 assert (*(lrecord_subr[0].lrecord_type_index) == 0);
4931 /* 4974 /*
4932 * The same is true for symbol_value_forward objects, except the 4975 * The same is true for symbol_value_forward objects, except the
4933 * type is 1. 4976 * type is 1.
4934 */ 4977 */
4935 (void) lrecord_type_index (lrecord_symbol_value_forward); 4978 lrecord_type_index (lrecord_symbol_value_forward);
4936 assert (*(lrecord_symbol_value_forward[0].lrecord_type_index) == 1); 4979 assert (*(lrecord_symbol_value_forward[0].lrecord_type_index) == 1);
4937 #endif 4980 #endif /* USE_INDEXED_LRECORD_IMPLEMENTATION */
4938 4981
4939 symbols_initialized = 0; 4982 symbols_initialized = 0;
4940 4983
4941 gc_generation_number[0] = 0; 4984 gc_generation_number[0] = 0;
4942 /* purify_flag 1 is correct even if CANNOT_DUMP. 4985 /* purify_flag 1 is correct even if CANNOT_DUMP.
4943 * loadup.el will set to nil at end. */ 4986 * loadup.el will set to nil at end. */
4944 purify_flag = 1; 4987 purify_flag = 1;
4945 pureptr = 0; 4988 pure_bytes_used = 0;
4946 pure_lossage = 0; 4989 pure_lossage = 0;
4947 breathing_space = 0; 4990 breathing_space = 0;
4948 #ifndef LRECORD_VECTOR 4991 #ifndef LRECORD_VECTOR
4949 XSETINT (all_vectors, 0); /* Qzero may not be set yet. */ 4992 XSETINT (all_vectors, 0); /* Qzero may not be set yet. */
4950 #endif 4993 #endif
5048 prevent garbage collection during a part of the program. 5091 prevent garbage collection during a part of the program.
5049 5092
5050 See also `consing-since-gc'. 5093 See also `consing-since-gc'.
5051 */ ); 5094 */ );
5052 5095
5053 DEFVAR_INT ("pure-bytes-used", &pureptr /* 5096 DEFVAR_INT ("pure-bytes-used", &pure_bytes_used /*
5054 Number of bytes of sharable Lisp data allocated so far. 5097 Number of bytes of sharable Lisp data allocated so far.
5055 */ ); 5098 */ );
5056 5099
5057 #if 0 5100 #if 0
5058 DEFVAR_INT ("data-bytes-used", &malloc_sbrk_used /* 5101 DEFVAR_INT ("data-bytes-used", &malloc_sbrk_used /*