diff options
| author | Eli Zaretskii | 2013-11-18 18:45:48 +0200 |
|---|---|---|
| committer | Eli Zaretskii | 2013-11-18 18:45:48 +0200 |
| commit | 18b35e2c7a3ff95fb4a07e58c3f57c70c65c0701 (patch) | |
| tree | 7a837a755a7c22d3258408cb384d01479ad88232 /src/eval.c | |
| parent | df87c56cdf6c8c13e8760bdc409e2eb0fda55b0b (diff) | |
| parent | 37c790b38599cc80a16c6a76152abbf8160fe2a1 (diff) | |
| download | emacs-18b35e2c7a3ff95fb4a07e58c3f57c70c65c0701.tar.gz emacs-18b35e2c7a3ff95fb4a07e58c3f57c70c65c0701.zip | |
Merge from mainline.
Diffstat (limited to 'src/eval.c')
| -rw-r--r-- | src/eval.c | 22 |
1 files changed, 19 insertions, 3 deletions
diff --git a/src/eval.c b/src/eval.c index 1e0a63a0ece..d3fcec5aef4 100644 --- a/src/eval.c +++ b/src/eval.c | |||
| @@ -237,11 +237,22 @@ init_eval_once (void) | |||
| 237 | Vrun_hooks = Qnil; | 237 | Vrun_hooks = Qnil; |
| 238 | } | 238 | } |
| 239 | 239 | ||
| 240 | static struct handler handlerlist_sentinel; | ||
| 241 | |||
| 240 | void | 242 | void |
| 241 | init_eval (void) | 243 | init_eval (void) |
| 242 | { | 244 | { |
| 243 | specpdl_ptr = specpdl; | 245 | specpdl_ptr = specpdl; |
| 244 | handlerlist = NULL; | 246 | { /* Put a dummy catcher at top-level so that handlerlist is never NULL. |
| 247 | This is important since handlerlist->nextfree holds the freelist | ||
| 248 | which would otherwise leak every time we unwind back to top-level. */ | ||
| 249 | struct handler *c; | ||
| 250 | handlerlist = handlerlist_sentinel.nextfree = &handlerlist_sentinel; | ||
| 251 | PUSH_HANDLER (c, Qunbound, CATCHER); | ||
| 252 | eassert (c == &handlerlist_sentinel); | ||
| 253 | handlerlist_sentinel.nextfree = NULL; | ||
| 254 | handlerlist_sentinel.next = NULL; | ||
| 255 | } | ||
| 245 | Vquit_flag = Qnil; | 256 | Vquit_flag = Qnil; |
| 246 | debug_on_next_call = 0; | 257 | debug_on_next_call = 0; |
| 247 | lisp_eval_depth = 0; | 258 | lisp_eval_depth = 0; |
| @@ -1129,6 +1140,8 @@ unwind_to_catch (struct handler *catch, Lisp_Object value) | |||
| 1129 | { | 1140 | { |
| 1130 | bool last_time; | 1141 | bool last_time; |
| 1131 | 1142 | ||
| 1143 | eassert (catch->next); | ||
| 1144 | |||
| 1132 | /* Save the value in the tag. */ | 1145 | /* Save the value in the tag. */ |
| 1133 | catch->val = value; | 1146 | catch->val = value; |
| 1134 | 1147 | ||
| @@ -1542,7 +1555,10 @@ See also the function `condition-case'. */) | |||
| 1542 | } | 1555 | } |
| 1543 | else | 1556 | else |
| 1544 | { | 1557 | { |
| 1545 | if (handlerlist != 0) | 1558 | if (handlerlist != &handlerlist_sentinel) |
| 1559 | /* FIXME: This will come right back here if there's no `top-level' | ||
| 1560 | catcher. A better solution would be to abort here, and instead | ||
| 1561 | add a catch-all condition handler so we never come here. */ | ||
| 1546 | Fthrow (Qtop_level, Qt); | 1562 | Fthrow (Qtop_level, Qt); |
| 1547 | } | 1563 | } |
| 1548 | 1564 | ||
| @@ -2479,7 +2495,7 @@ run_hook_with_args (ptrdiff_t nargs, Lisp_Object *args, | |||
| 2479 | 2495 | ||
| 2480 | if (EQ (val, Qunbound) || NILP (val)) | 2496 | if (EQ (val, Qunbound) || NILP (val)) |
| 2481 | return ret; | 2497 | return ret; |
| 2482 | else if (!CONSP (val) || EQ (XCAR (val), Qlambda)) | 2498 | else if (!CONSP (val) || FUNCTIONP (val)) |
| 2483 | { | 2499 | { |
| 2484 | args[0] = val; | 2500 | args[0] = val; |
| 2485 | return funcall (nargs, args); | 2501 | return funcall (nargs, args); |