Mercurial > emacs
comparison src/alloc.c @ 89909:68c22ea6027c
Sync to HEAD
| author | Kenichi Handa <handa@m17n.org> |
|---|---|
| date | Fri, 16 Apr 2004 12:51:06 +0000 |
| parents | c9f7a2f363ca |
| children | 4c90ffeb71c5 |
comparison
equal
deleted
inserted
replaced
| 89908:ee1402f7b568 | 89909:68c22ea6027c |
|---|---|
| 1 /* Storage allocation and gc for GNU Emacs Lisp interpreter. | 1 /* Storage allocation and gc for GNU Emacs Lisp interpreter. |
| 2 Copyright (C) 1985, 86, 88, 93, 94, 95, 97, 98, 1999, 2000, 2001, 2002, 2003 | 2 Copyright (C) 1985,86,88,93,94,95,97,98,1999,2000,01,02,03,2004 |
| 3 Free Software Foundation, Inc. | 3 Free Software Foundation, Inc. |
| 4 | 4 |
| 5 This file is part of GNU Emacs. | 5 This file is part of GNU Emacs. |
| 6 | 6 |
| 7 GNU Emacs is free software; you can redistribute it and/or modify | 7 GNU Emacs is free software; you can redistribute it and/or modify |
| 28 #endif | 28 #endif |
| 29 | 29 |
| 30 /* Note that this declares bzero on OSF/1. How dumb. */ | 30 /* Note that this declares bzero on OSF/1. How dumb. */ |
| 31 | 31 |
| 32 #include <signal.h> | 32 #include <signal.h> |
| 33 | |
| 34 /* GC_MALLOC_CHECK defined means perform validity checks of malloc'd | |
| 35 memory. Can do this only if using gmalloc.c. */ | |
| 36 | |
| 37 #if defined SYSTEM_MALLOC || defined DOUG_LEA_MALLOC | |
| 38 #undef GC_MALLOC_CHECK | |
| 39 #endif | |
| 40 | 33 |
| 41 /* This file is part of the core Lisp implementation, and thus must | 34 /* This file is part of the core Lisp implementation, and thus must |
| 42 deal with the real data structures. If the Lisp implementation is | 35 deal with the real data structures. If the Lisp implementation is |
| 43 replaced, this file likely will not be used. */ | 36 replaced, this file likely will not be used. */ |
| 44 | 37 |
| 53 #include "frame.h" | 46 #include "frame.h" |
| 54 #include "blockinput.h" | 47 #include "blockinput.h" |
| 55 #include "character.h" | 48 #include "character.h" |
| 56 #include "syssignal.h" | 49 #include "syssignal.h" |
| 57 #include <setjmp.h> | 50 #include <setjmp.h> |
| 51 | |
| 52 /* GC_MALLOC_CHECK defined means perform validity checks of malloc'd | |
| 53 memory. Can do this only if using gmalloc.c. */ | |
| 54 | |
| 55 #if defined SYSTEM_MALLOC || defined DOUG_LEA_MALLOC | |
| 56 #undef GC_MALLOC_CHECK | |
| 57 #endif | |
| 58 | 58 |
| 59 #ifdef HAVE_UNISTD_H | 59 #ifdef HAVE_UNISTD_H |
| 60 #include <unistd.h> | 60 #include <unistd.h> |
| 61 #else | 61 #else |
| 62 extern POINTER_TYPE *sbrk (); | 62 extern POINTER_TYPE *sbrk (); |
| 596 allocated_mem_type = type; | 596 allocated_mem_type = type; |
| 597 #endif | 597 #endif |
| 598 | 598 |
| 599 val = (void *) malloc (nbytes); | 599 val = (void *) malloc (nbytes); |
| 600 | 600 |
| 601 #ifndef USE_LSB_TAG | |
| 601 /* If the memory just allocated cannot be addressed thru a Lisp | 602 /* If the memory just allocated cannot be addressed thru a Lisp |
| 602 object's pointer, and it needs to be, | 603 object's pointer, and it needs to be, |
| 603 that's equivalent to running out of memory. */ | 604 that's equivalent to running out of memory. */ |
| 604 if (val && type != MEM_TYPE_NON_LISP) | 605 if (val && type != MEM_TYPE_NON_LISP) |
| 605 { | 606 { |
| 610 lisp_malloc_loser = val; | 611 lisp_malloc_loser = val; |
| 611 free (val); | 612 free (val); |
| 612 val = 0; | 613 val = 0; |
| 613 } | 614 } |
| 614 } | 615 } |
| 616 #endif | |
| 615 | 617 |
| 616 #if GC_MARK_STACK && !defined GC_MALLOC_CHECK | 618 #if GC_MARK_STACK && !defined GC_MALLOC_CHECK |
| 617 if (val && type != MEM_TYPE_NON_LISP) | 619 if (val && type != MEM_TYPE_NON_LISP) |
| 618 mem_insert (val, (char *) val + nbytes, type); | 620 mem_insert (val, (char *) val + nbytes, type); |
| 619 #endif | 621 #endif |
| 754 abase = err ? (base = NULL) : base; | 756 abase = err ? (base = NULL) : base; |
| 755 } | 757 } |
| 756 #else | 758 #else |
| 757 base = malloc (ABLOCKS_BYTES); | 759 base = malloc (ABLOCKS_BYTES); |
| 758 abase = ALIGN (base, BLOCK_ALIGN); | 760 abase = ALIGN (base, BLOCK_ALIGN); |
| 761 if (base == 0) | |
| 762 { | |
| 763 UNBLOCK_INPUT; | |
| 764 memory_full (); | |
| 765 } | |
| 759 #endif | 766 #endif |
| 760 | 767 |
| 761 aligned = (base == abase); | 768 aligned = (base == abase); |
| 762 if (!aligned) | 769 if (!aligned) |
| 763 ((void**)abase)[-1] = base; | 770 ((void**)abase)[-1] = base; |
| 765 #ifdef DOUG_LEA_MALLOC | 772 #ifdef DOUG_LEA_MALLOC |
| 766 /* Back to a reasonable maximum of mmap'ed areas. */ | 773 /* Back to a reasonable maximum of mmap'ed areas. */ |
| 767 mallopt (M_MMAP_MAX, MMAP_MAX_AREAS); | 774 mallopt (M_MMAP_MAX, MMAP_MAX_AREAS); |
| 768 #endif | 775 #endif |
| 769 | 776 |
| 777 #ifndef USE_LSB_TAG | |
| 770 /* If the memory just allocated cannot be addressed thru a Lisp | 778 /* If the memory just allocated cannot be addressed thru a Lisp |
| 771 object's pointer, and it needs to be, that's equivalent to | 779 object's pointer, and it needs to be, that's equivalent to |
| 772 running out of memory. */ | 780 running out of memory. */ |
| 773 if (type != MEM_TYPE_NON_LISP) | 781 if (type != MEM_TYPE_NON_LISP) |
| 774 { | 782 { |
| 781 free (base); | 789 free (base); |
| 782 UNBLOCK_INPUT; | 790 UNBLOCK_INPUT; |
| 783 memory_full (); | 791 memory_full (); |
| 784 } | 792 } |
| 785 } | 793 } |
| 794 #endif | |
| 786 | 795 |
| 787 /* Initialize the blocks and put them on the free list. | 796 /* Initialize the blocks and put them on the free list. |
| 788 Is `base' was not properly aligned, we can't use the last block. */ | 797 Is `base' was not properly aligned, we can't use the last block. */ |
| 789 for (i = 0; i < (aligned ? ABLOCKS_SIZE : ABLOCKS_SIZE - 1); i++) | 798 for (i = 0; i < (aligned ? ABLOCKS_SIZE : ABLOCKS_SIZE - 1); i++) |
| 790 { | 799 { |
| 1097 /* Intervals are allocated in chunks in form of an interval_block | 1106 /* Intervals are allocated in chunks in form of an interval_block |
| 1098 structure. */ | 1107 structure. */ |
| 1099 | 1108 |
| 1100 struct interval_block | 1109 struct interval_block |
| 1101 { | 1110 { |
| 1111 /* Place `intervals' first, to preserve alignment. */ | |
| 1112 struct interval intervals[INTERVAL_BLOCK_SIZE]; | |
| 1102 struct interval_block *next; | 1113 struct interval_block *next; |
| 1103 struct interval intervals[INTERVAL_BLOCK_SIZE]; | |
| 1104 }; | 1114 }; |
| 1105 | 1115 |
| 1106 /* Current interval block. Its `next' pointer points to older | 1116 /* Current interval block. Its `next' pointer points to older |
| 1107 blocks. */ | 1117 blocks. */ |
| 1108 | 1118 |
| 1336 /* Structure describing a block from which Lisp_String structures | 1346 /* Structure describing a block from which Lisp_String structures |
| 1337 are allocated. */ | 1347 are allocated. */ |
| 1338 | 1348 |
| 1339 struct string_block | 1349 struct string_block |
| 1340 { | 1350 { |
| 1351 /* Place `strings' first, to preserve alignment. */ | |
| 1352 struct Lisp_String strings[STRING_BLOCK_SIZE]; | |
| 1341 struct string_block *next; | 1353 struct string_block *next; |
| 1342 struct Lisp_String strings[STRING_BLOCK_SIZE]; | |
| 1343 }; | 1354 }; |
| 1344 | 1355 |
| 1345 /* Head and tail of the list of sblock structures holding Lisp string | 1356 /* Head and tail of the list of sblock structures holding Lisp string |
| 1346 data. We always allocate from current_sblock. The NEXT pointers | 1357 data. We always allocate from current_sblock. The NEXT pointers |
| 1347 in the sblock structures go from oldest_sblock to current_sblock. */ | 1358 in the sblock structures go from oldest_sblock to current_sblock. */ |
| 2118 /* We store float cells inside of float_blocks, allocating a new | 2129 /* We store float cells inside of float_blocks, allocating a new |
| 2119 float_block with malloc whenever necessary. Float cells reclaimed | 2130 float_block with malloc whenever necessary. Float cells reclaimed |
| 2120 by GC are put on a free list to be reallocated before allocating | 2131 by GC are put on a free list to be reallocated before allocating |
| 2121 any new float cells from the latest float_block. */ | 2132 any new float cells from the latest float_block. */ |
| 2122 | 2133 |
| 2123 #define FLOAT_BLOCK_SIZE \ | 2134 #define FLOAT_BLOCK_SIZE \ |
| 2124 (((BLOCK_BYTES - sizeof (struct float_block *)) * CHAR_BIT) \ | 2135 (((BLOCK_BYTES - sizeof (struct float_block *) \ |
| 2136 /* The compiler might add padding at the end. */ \ | |
| 2137 - (sizeof (struct Lisp_Float) - sizeof (int))) * CHAR_BIT) \ | |
| 2125 / (sizeof (struct Lisp_Float) * CHAR_BIT + 1)) | 2138 / (sizeof (struct Lisp_Float) * CHAR_BIT + 1)) |
| 2126 | 2139 |
| 2127 #define GETMARKBIT(block,n) \ | 2140 #define GETMARKBIT(block,n) \ |
| 2128 (((block)->gcmarkbits[(n) / (sizeof(int) * CHAR_BIT)] \ | 2141 (((block)->gcmarkbits[(n) / (sizeof(int) * CHAR_BIT)] \ |
| 2129 >> ((n) % (sizeof(int) * CHAR_BIT))) \ | 2142 >> ((n) % (sizeof(int) * CHAR_BIT))) \ |
| 2222 register struct float_block *new; | 2235 register struct float_block *new; |
| 2223 | 2236 |
| 2224 new = (struct float_block *) lisp_align_malloc (sizeof *new, | 2237 new = (struct float_block *) lisp_align_malloc (sizeof *new, |
| 2225 MEM_TYPE_FLOAT); | 2238 MEM_TYPE_FLOAT); |
| 2226 new->next = float_block; | 2239 new->next = float_block; |
| 2240 bzero ((char *) new->gcmarkbits, sizeof new->gcmarkbits); | |
| 2227 float_block = new; | 2241 float_block = new; |
| 2228 float_block_index = 0; | 2242 float_block_index = 0; |
| 2229 n_float_blocks++; | 2243 n_float_blocks++; |
| 2230 } | 2244 } |
| 2231 XSETFLOAT (val, &float_block->floats[float_block_index++]); | 2245 XSETFLOAT (val, &float_block->floats[float_block_index]); |
| 2246 float_block_index++; | |
| 2232 } | 2247 } |
| 2233 | 2248 |
| 2234 XFLOAT_DATA (val) = float_value; | 2249 XFLOAT_DATA (val) = float_value; |
| 2235 FLOAT_UNMARK (XFLOAT (val)); | 2250 eassert (!FLOAT_MARKED_P (XFLOAT (val))); |
| 2236 consing_since_gc += sizeof (struct Lisp_Float); | 2251 consing_since_gc += sizeof (struct Lisp_Float); |
| 2237 floats_consed++; | 2252 floats_consed++; |
| 2238 return val; | 2253 return val; |
| 2239 } | 2254 } |
| 2240 | 2255 |
| 2338 if (cons_block_index == CONS_BLOCK_SIZE) | 2353 if (cons_block_index == CONS_BLOCK_SIZE) |
| 2339 { | 2354 { |
| 2340 register struct cons_block *new; | 2355 register struct cons_block *new; |
| 2341 new = (struct cons_block *) lisp_align_malloc (sizeof *new, | 2356 new = (struct cons_block *) lisp_align_malloc (sizeof *new, |
| 2342 MEM_TYPE_CONS); | 2357 MEM_TYPE_CONS); |
| 2358 bzero ((char *) new->gcmarkbits, sizeof new->gcmarkbits); | |
| 2343 new->next = cons_block; | 2359 new->next = cons_block; |
| 2344 cons_block = new; | 2360 cons_block = new; |
| 2345 cons_block_index = 0; | 2361 cons_block_index = 0; |
| 2346 n_cons_blocks++; | 2362 n_cons_blocks++; |
| 2347 } | 2363 } |
| 2348 XSETCONS (val, &cons_block->conses[cons_block_index++]); | 2364 XSETCONS (val, &cons_block->conses[cons_block_index]); |
| 2365 cons_block_index++; | |
| 2349 } | 2366 } |
| 2350 | 2367 |
| 2351 XSETCAR (val, car); | 2368 XSETCAR (val, car); |
| 2352 XSETCDR (val, cdr); | 2369 XSETCDR (val, cdr); |
| 2353 CONS_UNMARK (XCONS (val)); | 2370 eassert (!CONS_MARKED_P (XCONS (val))); |
| 2354 consing_since_gc += sizeof (struct Lisp_Cons); | 2371 consing_since_gc += sizeof (struct Lisp_Cons); |
| 2355 cons_cells_consed++; | 2372 cons_cells_consed++; |
| 2356 return val; | 2373 return val; |
| 2357 } | 2374 } |
| 2358 | 2375 |
| 2487 | 2504 |
| 2488 #ifdef DOUG_LEA_MALLOC | 2505 #ifdef DOUG_LEA_MALLOC |
| 2489 /* Prevent mmap'ing the chunk. Lisp data may not be mmap'ed | 2506 /* Prevent mmap'ing the chunk. Lisp data may not be mmap'ed |
| 2490 because mapped region contents are not preserved in | 2507 because mapped region contents are not preserved in |
| 2491 a dumped Emacs. */ | 2508 a dumped Emacs. */ |
| 2509 BLOCK_INPUT; | |
| 2492 mallopt (M_MMAP_MAX, 0); | 2510 mallopt (M_MMAP_MAX, 0); |
| 2511 UNBLOCK_INPUT; | |
| 2493 #endif | 2512 #endif |
| 2494 | 2513 |
| 2495 nbytes = sizeof *p + (len - 1) * sizeof p->contents[0]; | 2514 nbytes = sizeof *p + (len - 1) * sizeof p->contents[0]; |
| 2496 p = (struct Lisp_Vector *) lisp_malloc (nbytes, type); | 2515 p = (struct Lisp_Vector *) lisp_malloc (nbytes, type); |
| 2497 | 2516 |
| 2498 #ifdef DOUG_LEA_MALLOC | 2517 #ifdef DOUG_LEA_MALLOC |
| 2499 /* Back to a reasonable maximum of mmap'ed areas. */ | 2518 /* Back to a reasonable maximum of mmap'ed areas. */ |
| 2519 BLOCK_INPUT; | |
| 2500 mallopt (M_MMAP_MAX, MMAP_MAX_AREAS); | 2520 mallopt (M_MMAP_MAX, MMAP_MAX_AREAS); |
| 2521 UNBLOCK_INPUT; | |
| 2501 #endif | 2522 #endif |
| 2502 | 2523 |
| 2503 consing_since_gc += nbytes; | 2524 consing_since_gc += nbytes; |
| 2504 vector_cells_consed += len; | 2525 vector_cells_consed += len; |
| 2505 | 2526 |
| 2695 #define SYMBOL_BLOCK_SIZE \ | 2716 #define SYMBOL_BLOCK_SIZE \ |
| 2696 ((1020 - sizeof (struct symbol_block *)) / sizeof (struct Lisp_Symbol)) | 2717 ((1020 - sizeof (struct symbol_block *)) / sizeof (struct Lisp_Symbol)) |
| 2697 | 2718 |
| 2698 struct symbol_block | 2719 struct symbol_block |
| 2699 { | 2720 { |
| 2721 /* Place `symbols' first, to preserve alignment. */ | |
| 2722 struct Lisp_Symbol symbols[SYMBOL_BLOCK_SIZE]; | |
| 2700 struct symbol_block *next; | 2723 struct symbol_block *next; |
| 2701 struct Lisp_Symbol symbols[SYMBOL_BLOCK_SIZE]; | |
| 2702 }; | 2724 }; |
| 2703 | 2725 |
| 2704 /* Current symbol block and index of first unused Lisp_Symbol | 2726 /* Current symbol block and index of first unused Lisp_Symbol |
| 2705 structure in it. */ | 2727 structure in it. */ |
| 2706 | 2728 |
| 2754 new->next = symbol_block; | 2776 new->next = symbol_block; |
| 2755 symbol_block = new; | 2777 symbol_block = new; |
| 2756 symbol_block_index = 0; | 2778 symbol_block_index = 0; |
| 2757 n_symbol_blocks++; | 2779 n_symbol_blocks++; |
| 2758 } | 2780 } |
| 2759 XSETSYMBOL (val, &symbol_block->symbols[symbol_block_index++]); | 2781 XSETSYMBOL (val, &symbol_block->symbols[symbol_block_index]); |
| 2782 symbol_block_index++; | |
| 2760 } | 2783 } |
| 2761 | 2784 |
| 2762 p = XSYMBOL (val); | 2785 p = XSYMBOL (val); |
| 2763 p->xname = name; | 2786 p->xname = name; |
| 2764 p->plist = Qnil; | 2787 p->plist = Qnil; |
| 2786 #define MARKER_BLOCK_SIZE \ | 2809 #define MARKER_BLOCK_SIZE \ |
| 2787 ((1020 - sizeof (struct marker_block *)) / sizeof (union Lisp_Misc)) | 2810 ((1020 - sizeof (struct marker_block *)) / sizeof (union Lisp_Misc)) |
| 2788 | 2811 |
| 2789 struct marker_block | 2812 struct marker_block |
| 2790 { | 2813 { |
| 2814 /* Place `markers' first, to preserve alignment. */ | |
| 2815 union Lisp_Misc markers[MARKER_BLOCK_SIZE]; | |
| 2791 struct marker_block *next; | 2816 struct marker_block *next; |
| 2792 union Lisp_Misc markers[MARKER_BLOCK_SIZE]; | |
| 2793 }; | 2817 }; |
| 2794 | 2818 |
| 2795 struct marker_block *marker_block; | 2819 struct marker_block *marker_block; |
| 2796 int marker_block_index; | 2820 int marker_block_index; |
| 2797 | 2821 |
| 2832 new->next = marker_block; | 2856 new->next = marker_block; |
| 2833 marker_block = new; | 2857 marker_block = new; |
| 2834 marker_block_index = 0; | 2858 marker_block_index = 0; |
| 2835 n_marker_blocks++; | 2859 n_marker_blocks++; |
| 2836 } | 2860 } |
| 2837 XSETMISC (val, &marker_block->markers[marker_block_index++]); | 2861 XSETMISC (val, &marker_block->markers[marker_block_index]); |
| 2862 marker_block_index++; | |
| 2838 } | 2863 } |
| 2839 | 2864 |
| 2840 consing_since_gc += sizeof (union Lisp_Misc); | 2865 consing_since_gc += sizeof (union Lisp_Misc); |
| 2841 misc_objects_consed++; | 2866 misc_objects_consed++; |
| 2842 XMARKER (val)->gcmarkbit = 0; | 2867 XMARKER (val)->gcmarkbit = 0; |
| 3367 | 3392 |
| 3368 /* P must point to the start of a Lisp_String structure, and it | 3393 /* P must point to the start of a Lisp_String structure, and it |
| 3369 must not be on the free-list. */ | 3394 must not be on the free-list. */ |
| 3370 return (offset >= 0 | 3395 return (offset >= 0 |
| 3371 && offset % sizeof b->strings[0] == 0 | 3396 && offset % sizeof b->strings[0] == 0 |
| 3397 && offset < (STRING_BLOCK_SIZE * sizeof b->strings[0]) | |
| 3372 && ((struct Lisp_String *) p)->data != NULL); | 3398 && ((struct Lisp_String *) p)->data != NULL); |
| 3373 } | 3399 } |
| 3374 else | 3400 else |
| 3375 return 0; | 3401 return 0; |
| 3376 } | 3402 } |
| 3391 | 3417 |
| 3392 /* P must point to the start of a Lisp_Cons, not be | 3418 /* P must point to the start of a Lisp_Cons, not be |
| 3393 one of the unused cells in the current cons block, | 3419 one of the unused cells in the current cons block, |
| 3394 and not be on the free-list. */ | 3420 and not be on the free-list. */ |
| 3395 return (offset >= 0 | 3421 return (offset >= 0 |
| 3422 && offset % sizeof b->conses[0] == 0 | |
| 3396 && offset < (CONS_BLOCK_SIZE * sizeof b->conses[0]) | 3423 && offset < (CONS_BLOCK_SIZE * sizeof b->conses[0]) |
| 3397 && offset % sizeof b->conses[0] == 0 | |
| 3398 && (b != cons_block | 3424 && (b != cons_block |
| 3399 || offset / sizeof b->conses[0] < cons_block_index) | 3425 || offset / sizeof b->conses[0] < cons_block_index) |
| 3400 && !EQ (((struct Lisp_Cons *) p)->car, Vdead)); | 3426 && !EQ (((struct Lisp_Cons *) p)->car, Vdead)); |
| 3401 } | 3427 } |
| 3402 else | 3428 else |
| 3420 /* P must point to the start of a Lisp_Symbol, not be | 3446 /* P must point to the start of a Lisp_Symbol, not be |
| 3421 one of the unused cells in the current symbol block, | 3447 one of the unused cells in the current symbol block, |
| 3422 and not be on the free-list. */ | 3448 and not be on the free-list. */ |
| 3423 return (offset >= 0 | 3449 return (offset >= 0 |
| 3424 && offset % sizeof b->symbols[0] == 0 | 3450 && offset % sizeof b->symbols[0] == 0 |
| 3451 && offset < (SYMBOL_BLOCK_SIZE * sizeof b->symbols[0]) | |
| 3425 && (b != symbol_block | 3452 && (b != symbol_block |
| 3426 || offset / sizeof b->symbols[0] < symbol_block_index) | 3453 || offset / sizeof b->symbols[0] < symbol_block_index) |
| 3427 && !EQ (((struct Lisp_Symbol *) p)->function, Vdead)); | 3454 && !EQ (((struct Lisp_Symbol *) p)->function, Vdead)); |
| 3428 } | 3455 } |
| 3429 else | 3456 else |
| 3445 int offset = (char *) p - (char *) &b->floats[0]; | 3472 int offset = (char *) p - (char *) &b->floats[0]; |
| 3446 | 3473 |
| 3447 /* P must point to the start of a Lisp_Float and not be | 3474 /* P must point to the start of a Lisp_Float and not be |
| 3448 one of the unused cells in the current float block. */ | 3475 one of the unused cells in the current float block. */ |
| 3449 return (offset >= 0 | 3476 return (offset >= 0 |
| 3477 && offset % sizeof b->floats[0] == 0 | |
| 3450 && offset < (FLOAT_BLOCK_SIZE * sizeof b->floats[0]) | 3478 && offset < (FLOAT_BLOCK_SIZE * sizeof b->floats[0]) |
| 3451 && offset % sizeof b->floats[0] == 0 | |
| 3452 && (b != float_block | 3479 && (b != float_block |
| 3453 || offset / sizeof b->floats[0] < float_block_index)); | 3480 || offset / sizeof b->floats[0] < float_block_index)); |
| 3454 } | 3481 } |
| 3455 else | 3482 else |
| 3456 return 0; | 3483 return 0; |
| 3473 /* P must point to the start of a Lisp_Misc, not be | 3500 /* P must point to the start of a Lisp_Misc, not be |
| 3474 one of the unused cells in the current misc block, | 3501 one of the unused cells in the current misc block, |
| 3475 and not be on the free-list. */ | 3502 and not be on the free-list. */ |
| 3476 return (offset >= 0 | 3503 return (offset >= 0 |
| 3477 && offset % sizeof b->markers[0] == 0 | 3504 && offset % sizeof b->markers[0] == 0 |
| 3505 && offset < (MARKER_BLOCK_SIZE * sizeof b->markers[0]) | |
| 3478 && (b != marker_block | 3506 && (b != marker_block |
| 3479 || offset / sizeof b->markers[0] < marker_block_index) | 3507 || offset / sizeof b->markers[0] < marker_block_index) |
| 3480 && ((union Lisp_Misc *) p)->u_marker.type != Lisp_Misc_Free); | 3508 && ((union Lisp_Misc *) p)->u_marker.type != Lisp_Misc_Free); |
| 3481 } | 3509 } |
| 3482 else | 3510 else |
| 4007 pure_alloc (size, type) | 4035 pure_alloc (size, type) |
| 4008 size_t size; | 4036 size_t size; |
| 4009 int type; | 4037 int type; |
| 4010 { | 4038 { |
| 4011 POINTER_TYPE *result; | 4039 POINTER_TYPE *result; |
| 4040 #ifdef USE_LSB_TAG | |
| 4041 size_t alignment = (1 << GCTYPEBITS); | |
| 4042 #else | |
| 4012 size_t alignment = sizeof (EMACS_INT); | 4043 size_t alignment = sizeof (EMACS_INT); |
| 4013 | 4044 |
| 4014 /* Give Lisp_Floats an extra alignment. */ | 4045 /* Give Lisp_Floats an extra alignment. */ |
| 4015 if (type == Lisp_Float) | 4046 if (type == Lisp_Float) |
| 4016 { | 4047 { |
| 4018 alignment = __alignof (struct Lisp_Float); | 4049 alignment = __alignof (struct Lisp_Float); |
| 4019 #else | 4050 #else |
| 4020 alignment = sizeof (struct Lisp_Float); | 4051 alignment = sizeof (struct Lisp_Float); |
| 4021 #endif | 4052 #endif |
| 4022 } | 4053 } |
| 4054 #endif | |
| 4023 | 4055 |
| 4024 again: | 4056 again: |
| 4025 result = ALIGN (purebeg + pure_bytes_used, alignment); | 4057 result = ALIGN (purebeg + pure_bytes_used, alignment); |
| 4026 pure_bytes_used = ((char *)result - (char *)purebeg) + size; | 4058 pure_bytes_used = ((char *)result - (char *)purebeg) + size; |
| 4027 | 4059 |
| 4153 SBYTES (obj), | 4185 SBYTES (obj), |
| 4154 STRING_MULTIBYTE (obj)); | 4186 STRING_MULTIBYTE (obj)); |
| 4155 else if (COMPILEDP (obj) || VECTORP (obj)) | 4187 else if (COMPILEDP (obj) || VECTORP (obj)) |
| 4156 { | 4188 { |
| 4157 register struct Lisp_Vector *vec; | 4189 register struct Lisp_Vector *vec; |
| 4158 register int i, size; | 4190 register int i; |
| 4191 EMACS_INT size; | |
| 4159 | 4192 |
| 4160 size = XVECTOR (obj)->size; | 4193 size = XVECTOR (obj)->size; |
| 4161 if (size & PSEUDOVECTOR_FLAG) | 4194 if (size & PSEUDOVECTOR_FLAG) |
| 4162 size &= PSEUDOVECTOR_SIZE_MASK; | 4195 size &= PSEUDOVECTOR_SIZE_MASK; |
| 4163 vec = XVECTOR (make_pure_vector ((EMACS_INT) size)); | 4196 vec = XVECTOR (make_pure_vector (size)); |
| 4164 for (i = 0; i < size; i++) | 4197 for (i = 0; i < size; i++) |
| 4165 vec->contents[i] = Fpurecopy (XVECTOR (obj)->contents[i]); | 4198 vec->contents[i] = Fpurecopy (XVECTOR (obj)->contents[i]); |
| 4166 if (COMPILEDP (obj)) | 4199 if (COMPILEDP (obj)) |
| 4167 XSETCOMPILED (obj, vec); | 4200 XSETCOMPILED (obj, vec); |
| 4168 else | 4201 else |
| 4443 #endif | 4476 #endif |
| 4444 | 4477 |
| 4445 gc_sweep (); | 4478 gc_sweep (); |
| 4446 | 4479 |
| 4447 /* Clear the mark bits that we set in certain root slots. */ | 4480 /* Clear the mark bits that we set in certain root slots. */ |
| 4448 | |
| 4449 #if (GC_MARK_STACK == GC_USE_GCPROS_AS_BEFORE \ | |
| 4450 || GC_MARK_STACK == GC_USE_GCPROS_CHECK_ZOMBIES) | |
| 4451 { | |
| 4452 register struct gcpro *tail; | |
| 4453 } | |
| 4454 #endif | |
| 4455 | 4481 |
| 4456 unmark_byte_stack (); | 4482 unmark_byte_stack (); |
| 4457 VECTOR_UNMARK (&buffer_defaults); | 4483 VECTOR_UNMARK (&buffer_defaults); |
| 4458 VECTOR_UNMARK (&buffer_local_symbols); | 4484 VECTOR_UNMARK (&buffer_local_symbols); |
| 4459 | 4485 |
