diff options
Diffstat (limited to 'src/alloc.c')
| -rw-r--r-- | src/alloc.c | 299 |
1 files changed, 142 insertions, 157 deletions
diff --git a/src/alloc.c b/src/alloc.c index 1a6d4e2d565..62f43669f2a 100644 --- a/src/alloc.c +++ b/src/alloc.c | |||
| @@ -2872,45 +2872,15 @@ usage: (list &rest OBJECTS) */) | |||
| 2872 | 2872 | ||
| 2873 | DEFUN ("make-list", Fmake_list, Smake_list, 2, 2, 0, | 2873 | DEFUN ("make-list", Fmake_list, Smake_list, 2, 2, 0, |
| 2874 | doc: /* Return a newly created list of length LENGTH, with each element being INIT. */) | 2874 | doc: /* Return a newly created list of length LENGTH, with each element being INIT. */) |
| 2875 | (register Lisp_Object length, Lisp_Object init) | 2875 | (Lisp_Object length, Lisp_Object init) |
| 2876 | { | 2876 | { |
| 2877 | register Lisp_Object val; | 2877 | Lisp_Object val = Qnil; |
| 2878 | register EMACS_INT size; | ||
| 2879 | |||
| 2880 | CHECK_NATNUM (length); | 2878 | CHECK_NATNUM (length); |
| 2881 | size = XFASTINT (length); | ||
| 2882 | 2879 | ||
| 2883 | val = Qnil; | 2880 | for (EMACS_INT size = XFASTINT (length); 0 < size; size--) |
| 2884 | while (size > 0) | ||
| 2885 | { | 2881 | { |
| 2886 | val = Fcons (init, val); | 2882 | val = Fcons (init, val); |
| 2887 | --size; | 2883 | rarely_quit (size); |
| 2888 | |||
| 2889 | if (size > 0) | ||
| 2890 | { | ||
| 2891 | val = Fcons (init, val); | ||
| 2892 | --size; | ||
| 2893 | |||
| 2894 | if (size > 0) | ||
| 2895 | { | ||
| 2896 | val = Fcons (init, val); | ||
| 2897 | --size; | ||
| 2898 | |||
| 2899 | if (size > 0) | ||
| 2900 | { | ||
| 2901 | val = Fcons (init, val); | ||
| 2902 | --size; | ||
| 2903 | |||
| 2904 | if (size > 0) | ||
| 2905 | { | ||
| 2906 | val = Fcons (init, val); | ||
| 2907 | --size; | ||
| 2908 | } | ||
| 2909 | } | ||
| 2910 | } | ||
| 2911 | } | ||
| 2912 | |||
| 2913 | QUIT; | ||
| 2914 | } | 2884 | } |
| 2915 | 2885 | ||
| 2916 | return val; | 2886 | return val; |
| @@ -4917,12 +4887,19 @@ mark_memory (void *start, void *end) | |||
| 4917 | } | 4887 | } |
| 4918 | } | 4888 | } |
| 4919 | 4889 | ||
| 4920 | #if !defined GC_SAVE_REGISTERS_ON_STACK && !defined GC_SETJMP_WORKS | 4890 | #ifndef HAVE___BUILTIN_UNWIND_INIT |
| 4891 | |||
| 4892 | # ifdef GC_SETJMP_WORKS | ||
| 4893 | static void | ||
| 4894 | test_setjmp (void) | ||
| 4895 | { | ||
| 4896 | } | ||
| 4897 | # else | ||
| 4921 | 4898 | ||
| 4922 | static bool setjmp_tested_p; | 4899 | static bool setjmp_tested_p; |
| 4923 | static int longjmps_done; | 4900 | static int longjmps_done; |
| 4924 | 4901 | ||
| 4925 | #define SETJMP_WILL_LIKELY_WORK "\ | 4902 | # define SETJMP_WILL_LIKELY_WORK "\ |
| 4926 | \n\ | 4903 | \n\ |
| 4927 | Emacs garbage collector has been changed to use conservative stack\n\ | 4904 | Emacs garbage collector has been changed to use conservative stack\n\ |
| 4928 | marking. Emacs has determined that the method it uses to do the\n\ | 4905 | marking. Emacs has determined that the method it uses to do the\n\ |
| @@ -4935,7 +4912,7 @@ verify that the methods used are appropriate for your system.\n\ | |||
| 4935 | Please mail the result to <emacs-devel@gnu.org>.\n\ | 4912 | Please mail the result to <emacs-devel@gnu.org>.\n\ |
| 4936 | " | 4913 | " |
| 4937 | 4914 | ||
| 4938 | #define SETJMP_WILL_NOT_WORK "\ | 4915 | # define SETJMP_WILL_NOT_WORK "\ |
| 4939 | \n\ | 4916 | \n\ |
| 4940 | Emacs garbage collector has been changed to use conservative stack\n\ | 4917 | Emacs garbage collector has been changed to use conservative stack\n\ |
| 4941 | marking. Emacs has determined that the default method it uses to do the\n\ | 4918 | marking. Emacs has determined that the default method it uses to do the\n\ |
| @@ -4961,6 +4938,9 @@ Please mail the result to <emacs-devel@gnu.org>.\n\ | |||
| 4961 | static void | 4938 | static void |
| 4962 | test_setjmp (void) | 4939 | test_setjmp (void) |
| 4963 | { | 4940 | { |
| 4941 | if (setjmp_tested_p) | ||
| 4942 | return; | ||
| 4943 | setjmp_tested_p = true; | ||
| 4964 | char buf[10]; | 4944 | char buf[10]; |
| 4965 | register int x; | 4945 | register int x; |
| 4966 | sys_jmp_buf jbuf; | 4946 | sys_jmp_buf jbuf; |
| @@ -4997,9 +4977,60 @@ test_setjmp (void) | |||
| 4997 | if (longjmps_done == 1) | 4977 | if (longjmps_done == 1) |
| 4998 | sys_longjmp (jbuf, 1); | 4978 | sys_longjmp (jbuf, 1); |
| 4999 | } | 4979 | } |
| 4980 | # endif /* ! GC_SETJMP_WORKS */ | ||
| 4981 | #endif /* ! HAVE___BUILTIN_UNWIND_INIT */ | ||
| 5000 | 4982 | ||
| 5001 | #endif /* not GC_SAVE_REGISTERS_ON_STACK && not GC_SETJMP_WORKS */ | 4983 | /* The type of an object near the stack top, whose address can be used |
| 4984 | as a stack scan limit. */ | ||
| 4985 | typedef union | ||
| 4986 | { | ||
| 4987 | /* Align the stack top properly. Even if !HAVE___BUILTIN_UNWIND_INIT, | ||
| 4988 | jmp_buf may not be aligned enough on darwin-ppc64. */ | ||
| 4989 | max_align_t o; | ||
| 4990 | #ifndef HAVE___BUILTIN_UNWIND_INIT | ||
| 4991 | sys_jmp_buf j; | ||
| 4992 | char c; | ||
| 4993 | #endif | ||
| 4994 | } stacktop_sentry; | ||
| 4995 | |||
| 4996 | /* Force callee-saved registers and register windows onto the stack. | ||
| 4997 | Use the platform-defined __builtin_unwind_init if available, | ||
| 4998 | obviating the need for machine dependent methods. */ | ||
| 4999 | #ifndef HAVE___BUILTIN_UNWIND_INIT | ||
| 5000 | # ifdef __sparc__ | ||
| 5001 | /* This trick flushes the register windows so that all the state of | ||
| 5002 | the process is contained in the stack. | ||
| 5003 | FreeBSD does not have a ta 3 handler, so handle it specially. | ||
| 5004 | FIXME: Code in the Boehm GC suggests flushing (with 'flushrs') is | ||
| 5005 | needed on ia64 too. See mach_dep.c, where it also says inline | ||
| 5006 | assembler doesn't work with relevant proprietary compilers. */ | ||
| 5007 | # if defined __sparc64__ && defined __FreeBSD__ | ||
| 5008 | # define __builtin_unwind_init() asm ("flushw") | ||
| 5009 | # else | ||
| 5010 | # define __builtin_unwind_init() asm ("ta 3") | ||
| 5011 | # endif | ||
| 5012 | # else | ||
| 5013 | # define __builtin_unwind_init() ((void) 0) | ||
| 5014 | # endif | ||
| 5015 | #endif | ||
| 5002 | 5016 | ||
| 5017 | /* Set *P to the address of the top of the stack. This must be a | ||
| 5018 | macro, not a function, so that it is executed in the caller’s | ||
| 5019 | environment. It is not inside a do-while so that its storage | ||
| 5020 | survives the macro. */ | ||
| 5021 | #ifdef HAVE___BUILTIN_UNWIND_INIT | ||
| 5022 | # define SET_STACK_TOP_ADDRESS(p) \ | ||
| 5023 | stacktop_sentry sentry; \ | ||
| 5024 | __builtin_unwind_init (); \ | ||
| 5025 | *(p) = &sentry | ||
| 5026 | #else | ||
| 5027 | # define SET_STACK_TOP_ADDRESS(p) \ | ||
| 5028 | stacktop_sentry sentry; \ | ||
| 5029 | __builtin_unwind_init (); \ | ||
| 5030 | test_setjmp (); \ | ||
| 5031 | sys_setjmp (sentry.j); \ | ||
| 5032 | *(p) = &sentry + (stack_bottom < &sentry.c) | ||
| 5033 | #endif | ||
| 5003 | 5034 | ||
| 5004 | /* Mark live Lisp objects on the C stack. | 5035 | /* Mark live Lisp objects on the C stack. |
| 5005 | 5036 | ||
| @@ -5011,12 +5042,7 @@ test_setjmp (void) | |||
| 5011 | We have to mark Lisp objects in CPU registers that can hold local | 5042 | We have to mark Lisp objects in CPU registers that can hold local |
| 5012 | variables or are used to pass parameters. | 5043 | variables or are used to pass parameters. |
| 5013 | 5044 | ||
| 5014 | If GC_SAVE_REGISTERS_ON_STACK is defined, it should expand to | 5045 | This code assumes that calling setjmp saves registers we need |
| 5015 | something that either saves relevant registers on the stack, or | ||
| 5016 | calls mark_maybe_object passing it each register's contents. | ||
| 5017 | |||
| 5018 | If GC_SAVE_REGISTERS_ON_STACK is not defined, the current | ||
| 5019 | implementation assumes that calling setjmp saves registers we need | ||
| 5020 | to see in a jmp_buf which itself lies on the stack. This doesn't | 5046 | to see in a jmp_buf which itself lies on the stack. This doesn't |
| 5021 | have to be true! It must be verified for each system, possibly | 5047 | have to be true! It must be verified for each system, possibly |
| 5022 | by taking a look at the source code of setjmp. | 5048 | by taking a look at the source code of setjmp. |
| @@ -5080,62 +5106,9 @@ flush_stack_call_func (void (*func) (void *arg), void *arg) | |||
| 5080 | { | 5106 | { |
| 5081 | void *end; | 5107 | void *end; |
| 5082 | struct thread_state *self = current_thread; | 5108 | struct thread_state *self = current_thread; |
| 5083 | 5109 | SET_STACK_TOP_ADDRESS (&end); | |
| 5084 | #ifdef HAVE___BUILTIN_UNWIND_INIT | ||
| 5085 | /* Force callee-saved registers and register windows onto the stack. | ||
| 5086 | This is the preferred method if available, obviating the need for | ||
| 5087 | machine dependent methods. */ | ||
| 5088 | __builtin_unwind_init (); | ||
| 5089 | end = &end; | ||
| 5090 | #else /* not HAVE___BUILTIN_UNWIND_INIT */ | ||
| 5091 | #ifndef GC_SAVE_REGISTERS_ON_STACK | ||
| 5092 | /* jmp_buf may not be aligned enough on darwin-ppc64 */ | ||
| 5093 | union aligned_jmpbuf { | ||
| 5094 | Lisp_Object o; | ||
| 5095 | sys_jmp_buf j; | ||
| 5096 | } j; | ||
| 5097 | volatile bool stack_grows_down_p = (char *) &j > (char *) stack_bottom; | ||
| 5098 | #endif | ||
| 5099 | /* This trick flushes the register windows so that all the state of | ||
| 5100 | the process is contained in the stack. */ | ||
| 5101 | /* Fixme: Code in the Boehm GC suggests flushing (with `flushrs') is | ||
| 5102 | needed on ia64 too. See mach_dep.c, where it also says inline | ||
| 5103 | assembler doesn't work with relevant proprietary compilers. */ | ||
| 5104 | #ifdef __sparc__ | ||
| 5105 | #if defined (__sparc64__) && defined (__FreeBSD__) | ||
| 5106 | /* FreeBSD does not have a ta 3 handler. */ | ||
| 5107 | asm ("flushw"); | ||
| 5108 | #else | ||
| 5109 | asm ("ta 3"); | ||
| 5110 | #endif | ||
| 5111 | #endif | ||
| 5112 | |||
| 5113 | /* Save registers that we need to see on the stack. We need to see | ||
| 5114 | registers used to hold register variables and registers used to | ||
| 5115 | pass parameters. */ | ||
| 5116 | #ifdef GC_SAVE_REGISTERS_ON_STACK | ||
| 5117 | GC_SAVE_REGISTERS_ON_STACK (end); | ||
| 5118 | #else /* not GC_SAVE_REGISTERS_ON_STACK */ | ||
| 5119 | |||
| 5120 | #ifndef GC_SETJMP_WORKS /* If it hasn't been checked yet that | ||
| 5121 | setjmp will definitely work, test it | ||
| 5122 | and print a message with the result | ||
| 5123 | of the test. */ | ||
| 5124 | if (!setjmp_tested_p) | ||
| 5125 | { | ||
| 5126 | setjmp_tested_p = 1; | ||
| 5127 | test_setjmp (); | ||
| 5128 | } | ||
| 5129 | #endif /* GC_SETJMP_WORKS */ | ||
| 5130 | |||
| 5131 | sys_setjmp (j.j); | ||
| 5132 | end = stack_grows_down_p ? (char *) &j + sizeof j : (char *) &j; | ||
| 5133 | #endif /* not GC_SAVE_REGISTERS_ON_STACK */ | ||
| 5134 | #endif /* not HAVE___BUILTIN_UNWIND_INIT */ | ||
| 5135 | |||
| 5136 | self->stack_top = end; | 5110 | self->stack_top = end; |
| 5137 | (*func) (arg); | 5111 | func (arg); |
| 5138 | |||
| 5139 | eassert (current_thread == self); | 5112 | eassert (current_thread == self); |
| 5140 | } | 5113 | } |
| 5141 | 5114 | ||
| @@ -5464,6 +5437,38 @@ make_pure_vector (ptrdiff_t len) | |||
| 5464 | return new; | 5437 | return new; |
| 5465 | } | 5438 | } |
| 5466 | 5439 | ||
| 5440 | /* Copy all contents and parameters of TABLE to a new table allocated | ||
| 5441 | from pure space, return the purified table. */ | ||
| 5442 | static struct Lisp_Hash_Table * | ||
| 5443 | purecopy_hash_table (struct Lisp_Hash_Table *table) | ||
| 5444 | { | ||
| 5445 | eassert (NILP (table->weak)); | ||
| 5446 | eassert (!NILP (table->pure)); | ||
| 5447 | |||
| 5448 | struct Lisp_Hash_Table *pure = pure_alloc (sizeof *pure, Lisp_Vectorlike); | ||
| 5449 | struct hash_table_test pure_test = table->test; | ||
| 5450 | |||
| 5451 | /* Purecopy the hash table test. */ | ||
| 5452 | pure_test.name = purecopy (table->test.name); | ||
| 5453 | pure_test.user_hash_function = purecopy (table->test.user_hash_function); | ||
| 5454 | pure_test.user_cmp_function = purecopy (table->test.user_cmp_function); | ||
| 5455 | |||
| 5456 | pure->test = pure_test; | ||
| 5457 | pure->header = table->header; | ||
| 5458 | pure->weak = purecopy (Qnil); | ||
| 5459 | pure->rehash_size = purecopy (table->rehash_size); | ||
| 5460 | pure->rehash_threshold = purecopy (table->rehash_threshold); | ||
| 5461 | pure->hash = purecopy (table->hash); | ||
| 5462 | pure->next = purecopy (table->next); | ||
| 5463 | pure->next_free = purecopy (table->next_free); | ||
| 5464 | pure->index = purecopy (table->index); | ||
| 5465 | pure->count = table->count; | ||
| 5466 | pure->key_and_value = purecopy (table->key_and_value); | ||
| 5467 | pure->pure = purecopy (table->pure); | ||
| 5468 | |||
| 5469 | return pure; | ||
| 5470 | } | ||
| 5471 | |||
| 5467 | DEFUN ("purecopy", Fpurecopy, Spurecopy, 1, 1, 0, | 5472 | DEFUN ("purecopy", Fpurecopy, Spurecopy, 1, 1, 0, |
| 5468 | doc: /* Make a copy of object OBJ in pure storage. | 5473 | doc: /* Make a copy of object OBJ in pure storage. |
| 5469 | Recursively copies contents of vectors and cons cells. | 5474 | Recursively copies contents of vectors and cons cells. |
| @@ -5472,14 +5477,20 @@ Does not copy symbols. Copies strings without text properties. */) | |||
| 5472 | { | 5477 | { |
| 5473 | if (NILP (Vpurify_flag)) | 5478 | if (NILP (Vpurify_flag)) |
| 5474 | return obj; | 5479 | return obj; |
| 5475 | else if (MARKERP (obj) || OVERLAYP (obj) | 5480 | else if (MARKERP (obj) || OVERLAYP (obj) || SYMBOLP (obj)) |
| 5476 | || HASH_TABLE_P (obj) || SYMBOLP (obj)) | ||
| 5477 | /* Can't purify those. */ | 5481 | /* Can't purify those. */ |
| 5478 | return obj; | 5482 | return obj; |
| 5479 | else | 5483 | else |
| 5480 | return purecopy (obj); | 5484 | return purecopy (obj); |
| 5481 | } | 5485 | } |
| 5482 | 5486 | ||
| 5487 | /* Pinned objects are marked before every GC cycle. */ | ||
| 5488 | static struct pinned_object | ||
| 5489 | { | ||
| 5490 | Lisp_Object object; | ||
| 5491 | struct pinned_object *next; | ||
| 5492 | } *pinned_objects; | ||
| 5493 | |||
| 5483 | static Lisp_Object | 5494 | static Lisp_Object |
| 5484 | purecopy (Lisp_Object obj) | 5495 | purecopy (Lisp_Object obj) |
| 5485 | { | 5496 | { |
| @@ -5507,7 +5518,27 @@ purecopy (Lisp_Object obj) | |||
| 5507 | obj = make_pure_string (SSDATA (obj), SCHARS (obj), | 5518 | obj = make_pure_string (SSDATA (obj), SCHARS (obj), |
| 5508 | SBYTES (obj), | 5519 | SBYTES (obj), |
| 5509 | STRING_MULTIBYTE (obj)); | 5520 | STRING_MULTIBYTE (obj)); |
| 5510 | else if (COMPILEDP (obj) || VECTORP (obj) || HASH_TABLE_P (obj)) | 5521 | else if (HASH_TABLE_P (obj)) |
| 5522 | { | ||
| 5523 | struct Lisp_Hash_Table *table = XHASH_TABLE (obj); | ||
| 5524 | /* Do not purify hash tables which haven't been defined with | ||
| 5525 | :purecopy as non-nil or are weak - they aren't guaranteed to | ||
| 5526 | not change. */ | ||
| 5527 | if (!NILP (table->weak) || NILP (table->pure)) | ||
| 5528 | { | ||
| 5529 | /* Instead, add the hash table to the list of pinned objects, | ||
| 5530 | so that it will be marked during GC. */ | ||
| 5531 | struct pinned_object *o = xmalloc (sizeof *o); | ||
| 5532 | o->object = obj; | ||
| 5533 | o->next = pinned_objects; | ||
| 5534 | pinned_objects = o; | ||
| 5535 | return obj; /* Don't hash cons it. */ | ||
| 5536 | } | ||
| 5537 | |||
| 5538 | struct Lisp_Hash_Table *h = purecopy_hash_table (table); | ||
| 5539 | XSET_HASH_TABLE (obj, h); | ||
| 5540 | } | ||
| 5541 | else if (COMPILEDP (obj) || VECTORP (obj)) | ||
| 5511 | { | 5542 | { |
| 5512 | struct Lisp_Vector *objp = XVECTOR (obj); | 5543 | struct Lisp_Vector *objp = XVECTOR (obj); |
| 5513 | ptrdiff_t nbytes = vector_nbytes (objp); | 5544 | ptrdiff_t nbytes = vector_nbytes (objp); |
| @@ -5724,6 +5755,13 @@ compact_undo_list (Lisp_Object list) | |||
| 5724 | } | 5755 | } |
| 5725 | 5756 | ||
| 5726 | static void | 5757 | static void |
| 5758 | mark_pinned_objects (void) | ||
| 5759 | { | ||
| 5760 | for (struct pinned_object *pobj = pinned_objects; pobj; pobj = pobj->next) | ||
| 5761 | mark_object (pobj->object); | ||
| 5762 | } | ||
| 5763 | |||
| 5764 | static void | ||
| 5727 | mark_pinned_symbols (void) | 5765 | mark_pinned_symbols (void) |
| 5728 | { | 5766 | { |
| 5729 | struct symbol_block *sblk; | 5767 | struct symbol_block *sblk; |
| @@ -5843,6 +5881,7 @@ garbage_collect_1 (void *end) | |||
| 5843 | for (i = 0; i < staticidx; i++) | 5881 | for (i = 0; i < staticidx; i++) |
| 5844 | mark_object (*staticvec[i]); | 5882 | mark_object (*staticvec[i]); |
| 5845 | 5883 | ||
| 5884 | mark_pinned_objects (); | ||
| 5846 | mark_pinned_symbols (); | 5885 | mark_pinned_symbols (); |
| 5847 | mark_terminals (); | 5886 | mark_terminals (); |
| 5848 | mark_kboards (); | 5887 | mark_kboards (); |
| @@ -6011,58 +6050,7 @@ See Info node `(elisp)Garbage Collection'. */) | |||
| 6011 | (void) | 6050 | (void) |
| 6012 | { | 6051 | { |
| 6013 | void *end; | 6052 | void *end; |
| 6014 | 6053 | SET_STACK_TOP_ADDRESS (&end); | |
| 6015 | #ifdef HAVE___BUILTIN_UNWIND_INIT | ||
| 6016 | /* Force callee-saved registers and register windows onto the stack. | ||
| 6017 | This is the preferred method if available, obviating the need for | ||
| 6018 | machine dependent methods. */ | ||
| 6019 | __builtin_unwind_init (); | ||
| 6020 | end = &end; | ||
| 6021 | #else /* not HAVE___BUILTIN_UNWIND_INIT */ | ||
| 6022 | #ifndef GC_SAVE_REGISTERS_ON_STACK | ||
| 6023 | /* jmp_buf may not be aligned enough on darwin-ppc64 */ | ||
| 6024 | union aligned_jmpbuf { | ||
| 6025 | Lisp_Object o; | ||
| 6026 | sys_jmp_buf j; | ||
| 6027 | } j; | ||
| 6028 | volatile bool stack_grows_down_p = (char *) &j > (char *) stack_base; | ||
| 6029 | #endif | ||
| 6030 | /* This trick flushes the register windows so that all the state of | ||
| 6031 | the process is contained in the stack. */ | ||
| 6032 | /* Fixme: Code in the Boehm GC suggests flushing (with `flushrs') is | ||
| 6033 | needed on ia64 too. See mach_dep.c, where it also says inline | ||
| 6034 | assembler doesn't work with relevant proprietary compilers. */ | ||
| 6035 | #ifdef __sparc__ | ||
| 6036 | #if defined (__sparc64__) && defined (__FreeBSD__) | ||
| 6037 | /* FreeBSD does not have a ta 3 handler. */ | ||
| 6038 | asm ("flushw"); | ||
| 6039 | #else | ||
| 6040 | asm ("ta 3"); | ||
| 6041 | #endif | ||
| 6042 | #endif | ||
| 6043 | |||
| 6044 | /* Save registers that we need to see on the stack. We need to see | ||
| 6045 | registers used to hold register variables and registers used to | ||
| 6046 | pass parameters. */ | ||
| 6047 | #ifdef GC_SAVE_REGISTERS_ON_STACK | ||
| 6048 | GC_SAVE_REGISTERS_ON_STACK (end); | ||
| 6049 | #else /* not GC_SAVE_REGISTERS_ON_STACK */ | ||
| 6050 | |||
| 6051 | #ifndef GC_SETJMP_WORKS /* If it hasn't been checked yet that | ||
| 6052 | setjmp will definitely work, test it | ||
| 6053 | and print a message with the result | ||
| 6054 | of the test. */ | ||
| 6055 | if (!setjmp_tested_p) | ||
| 6056 | { | ||
| 6057 | setjmp_tested_p = 1; | ||
| 6058 | test_setjmp (); | ||
| 6059 | } | ||
| 6060 | #endif /* GC_SETJMP_WORKS */ | ||
| 6061 | |||
| 6062 | sys_setjmp (j.j); | ||
| 6063 | end = stack_grows_down_p ? (char *) &j + sizeof j : (char *) &j; | ||
| 6064 | #endif /* not GC_SAVE_REGISTERS_ON_STACK */ | ||
| 6065 | #endif /* not HAVE___BUILTIN_UNWIND_INIT */ | ||
| 6066 | return garbage_collect_1 (end); | 6054 | return garbage_collect_1 (end); |
| 6067 | } | 6055 | } |
| 6068 | 6056 | ||
| @@ -7372,9 +7360,6 @@ init_alloc_once (void) | |||
| 7372 | void | 7360 | void |
| 7373 | init_alloc (void) | 7361 | init_alloc (void) |
| 7374 | { | 7362 | { |
| 7375 | #if !defined GC_SAVE_REGISTERS_ON_STACK && !defined GC_SETJMP_WORKS | ||
| 7376 | setjmp_tested_p = longjmps_done = 0; | ||
| 7377 | #endif | ||
| 7378 | Vgc_elapsed = make_float (0.0); | 7363 | Vgc_elapsed = make_float (0.0); |
| 7379 | gcs_done = 0; | 7364 | gcs_done = 0; |
| 7380 | 7365 | ||