diff options
Diffstat (limited to 'src/eval.c')
| -rw-r--r-- | src/eval.c | 382 |
1 files changed, 305 insertions, 77 deletions
diff --git a/src/eval.c b/src/eval.c index 718e58c693f..948c2e4d158 100644 --- a/src/eval.c +++ b/src/eval.c | |||
| @@ -64,6 +64,8 @@ Lisp_Object Qinhibit_quit; | |||
| 64 | Lisp_Object Qand_rest, Qand_optional; | 64 | Lisp_Object Qand_rest, Qand_optional; |
| 65 | Lisp_Object Qdebug_on_error; | 65 | Lisp_Object Qdebug_on_error; |
| 66 | Lisp_Object Qdeclare; | 66 | Lisp_Object Qdeclare; |
| 67 | Lisp_Object Qinternal_interpreter_environment, Qclosure; | ||
| 68 | |||
| 67 | Lisp_Object Qdebug; | 69 | Lisp_Object Qdebug; |
| 68 | 70 | ||
| 69 | /* This holds either the symbol `run-hooks' or nil. | 71 | /* This holds either the symbol `run-hooks' or nil. |
| @@ -115,10 +117,10 @@ Lisp_Object Vsignaling_function; | |||
| 115 | 117 | ||
| 116 | int handling_signal; | 118 | int handling_signal; |
| 117 | 119 | ||
| 118 | static Lisp_Object funcall_lambda (Lisp_Object, size_t, Lisp_Object*); | 120 | static Lisp_Object funcall_lambda (Lisp_Object, size_t, Lisp_Object *); |
| 119 | static void unwind_to_catch (struct catchtag *, Lisp_Object) NO_RETURN; | 121 | static void unwind_to_catch (struct catchtag *, Lisp_Object) NO_RETURN; |
| 120 | static int interactive_p (int); | 122 | static int interactive_p (int); |
| 121 | static Lisp_Object apply_lambda (Lisp_Object, Lisp_Object, int); | 123 | static Lisp_Object apply_lambda (Lisp_Object fun, Lisp_Object args); |
| 122 | 124 | ||
| 123 | void | 125 | void |
| 124 | init_eval_once (void) | 126 | init_eval_once (void) |
| @@ -127,7 +129,7 @@ init_eval_once (void) | |||
| 127 | specpdl = (struct specbinding *) xmalloc (specpdl_size * sizeof (struct specbinding)); | 129 | specpdl = (struct specbinding *) xmalloc (specpdl_size * sizeof (struct specbinding)); |
| 128 | specpdl_ptr = specpdl; | 130 | specpdl_ptr = specpdl; |
| 129 | /* Don't forget to update docs (lispref node "Local Variables"). */ | 131 | /* Don't forget to update docs (lispref node "Local Variables"). */ |
| 130 | max_specpdl_size = 1000; | 132 | max_specpdl_size = 1300; /* 1000 is not enough for CEDET's c-by.el. */ |
| 131 | max_lisp_eval_depth = 600; | 133 | max_lisp_eval_depth = 600; |
| 132 | 134 | ||
| 133 | Vrun_hooks = Qnil; | 135 | Vrun_hooks = Qnil; |
| @@ -244,7 +246,7 @@ usage: (or CONDITIONS...) */) | |||
| 244 | 246 | ||
| 245 | while (CONSP (args)) | 247 | while (CONSP (args)) |
| 246 | { | 248 | { |
| 247 | val = Feval (XCAR (args)); | 249 | val = eval_sub (XCAR (args)); |
| 248 | if (!NILP (val)) | 250 | if (!NILP (val)) |
| 249 | break; | 251 | break; |
| 250 | args = XCDR (args); | 252 | args = XCDR (args); |
| @@ -268,7 +270,7 @@ usage: (and CONDITIONS...) */) | |||
| 268 | 270 | ||
| 269 | while (CONSP (args)) | 271 | while (CONSP (args)) |
| 270 | { | 272 | { |
| 271 | val = Feval (XCAR (args)); | 273 | val = eval_sub (XCAR (args)); |
| 272 | if (NILP (val)) | 274 | if (NILP (val)) |
| 273 | break; | 275 | break; |
| 274 | args = XCDR (args); | 276 | args = XCDR (args); |
| @@ -290,11 +292,11 @@ usage: (if COND THEN ELSE...) */) | |||
| 290 | struct gcpro gcpro1; | 292 | struct gcpro gcpro1; |
| 291 | 293 | ||
| 292 | GCPRO1 (args); | 294 | GCPRO1 (args); |
| 293 | cond = Feval (Fcar (args)); | 295 | cond = eval_sub (Fcar (args)); |
| 294 | UNGCPRO; | 296 | UNGCPRO; |
| 295 | 297 | ||
| 296 | if (!NILP (cond)) | 298 | if (!NILP (cond)) |
| 297 | return Feval (Fcar (Fcdr (args))); | 299 | return eval_sub (Fcar (Fcdr (args))); |
| 298 | return Fprogn (Fcdr (Fcdr (args))); | 300 | return Fprogn (Fcdr (Fcdr (args))); |
| 299 | } | 301 | } |
| 300 | 302 | ||
| @@ -318,7 +320,7 @@ usage: (cond CLAUSES...) */) | |||
| 318 | while (!NILP (args)) | 320 | while (!NILP (args)) |
| 319 | { | 321 | { |
| 320 | clause = Fcar (args); | 322 | clause = Fcar (args); |
| 321 | val = Feval (Fcar (clause)); | 323 | val = eval_sub (Fcar (clause)); |
| 322 | if (!NILP (val)) | 324 | if (!NILP (val)) |
| 323 | { | 325 | { |
| 324 | if (!EQ (XCDR (clause), Qnil)) | 326 | if (!EQ (XCDR (clause), Qnil)) |
| @@ -344,7 +346,7 @@ usage: (progn BODY...) */) | |||
| 344 | 346 | ||
| 345 | while (CONSP (args)) | 347 | while (CONSP (args)) |
| 346 | { | 348 | { |
| 347 | val = Feval (XCAR (args)); | 349 | val = eval_sub (XCAR (args)); |
| 348 | args = XCDR (args); | 350 | args = XCDR (args); |
| 349 | } | 351 | } |
| 350 | 352 | ||
| @@ -373,13 +375,12 @@ usage: (prog1 FIRST BODY...) */) | |||
| 373 | 375 | ||
| 374 | do | 376 | do |
| 375 | { | 377 | { |
| 378 | Lisp_Object tem = eval_sub (XCAR (args_left)); | ||
| 376 | if (!(argnum++)) | 379 | if (!(argnum++)) |
| 377 | val = Feval (Fcar (args_left)); | 380 | val = tem; |
| 378 | else | 381 | args_left = XCDR (args_left); |
| 379 | Feval (Fcar (args_left)); | ||
| 380 | args_left = Fcdr (args_left); | ||
| 381 | } | 382 | } |
| 382 | while (!NILP(args_left)); | 383 | while (CONSP (args_left)); |
| 383 | 384 | ||
| 384 | UNGCPRO; | 385 | UNGCPRO; |
| 385 | return val; | 386 | return val; |
| @@ -408,13 +409,12 @@ usage: (prog2 FORM1 FORM2 BODY...) */) | |||
| 408 | 409 | ||
| 409 | do | 410 | do |
| 410 | { | 411 | { |
| 412 | Lisp_Object tem = eval_sub (XCAR (args_left)); | ||
| 411 | if (!(argnum++)) | 413 | if (!(argnum++)) |
| 412 | val = Feval (Fcar (args_left)); | 414 | val = tem; |
| 413 | else | 415 | args_left = XCDR (args_left); |
| 414 | Feval (Fcar (args_left)); | ||
| 415 | args_left = Fcdr (args_left); | ||
| 416 | } | 416 | } |
| 417 | while (!NILP (args_left)); | 417 | while (CONSP (args_left)); |
| 418 | 418 | ||
| 419 | UNGCPRO; | 419 | UNGCPRO; |
| 420 | return val; | 420 | return val; |
| @@ -432,7 +432,7 @@ usage: (setq [SYM VAL]...) */) | |||
| 432 | (Lisp_Object args) | 432 | (Lisp_Object args) |
| 433 | { | 433 | { |
| 434 | register Lisp_Object args_left; | 434 | register Lisp_Object args_left; |
| 435 | register Lisp_Object val, sym; | 435 | register Lisp_Object val, sym, lex_binding; |
| 436 | struct gcpro gcpro1; | 436 | struct gcpro gcpro1; |
| 437 | 437 | ||
| 438 | if (NILP (args)) | 438 | if (NILP (args)) |
| @@ -443,9 +443,19 @@ usage: (setq [SYM VAL]...) */) | |||
| 443 | 443 | ||
| 444 | do | 444 | do |
| 445 | { | 445 | { |
| 446 | val = Feval (Fcar (Fcdr (args_left))); | 446 | val = eval_sub (Fcar (Fcdr (args_left))); |
| 447 | sym = Fcar (args_left); | 447 | sym = Fcar (args_left); |
| 448 | Fset (sym, val); | 448 | |
| 449 | /* Like for eval_sub, we do not check declared_special here since | ||
| 450 | it's been done when let-binding. */ | ||
| 451 | if (!NILP (Vinternal_interpreter_environment) /* Mere optimization! */ | ||
| 452 | && SYMBOLP (sym) | ||
| 453 | && !NILP (lex_binding | ||
| 454 | = Fassq (sym, Vinternal_interpreter_environment))) | ||
| 455 | XSETCDR (lex_binding, val); /* SYM is lexically bound. */ | ||
| 456 | else | ||
| 457 | Fset (sym, val); /* SYM is dynamically bound. */ | ||
| 458 | |||
| 449 | args_left = Fcdr (Fcdr (args_left)); | 459 | args_left = Fcdr (Fcdr (args_left)); |
| 450 | } | 460 | } |
| 451 | while (!NILP(args_left)); | 461 | while (!NILP(args_left)); |
| @@ -471,9 +481,21 @@ In byte compilation, `function' causes its argument to be compiled. | |||
| 471 | usage: (function ARG) */) | 481 | usage: (function ARG) */) |
| 472 | (Lisp_Object args) | 482 | (Lisp_Object args) |
| 473 | { | 483 | { |
| 484 | Lisp_Object quoted = XCAR (args); | ||
| 485 | |||
| 474 | if (!NILP (Fcdr (args))) | 486 | if (!NILP (Fcdr (args))) |
| 475 | xsignal2 (Qwrong_number_of_arguments, Qfunction, Flength (args)); | 487 | xsignal2 (Qwrong_number_of_arguments, Qfunction, Flength (args)); |
| 476 | return Fcar (args); | 488 | |
| 489 | if (!NILP (Vinternal_interpreter_environment) | ||
| 490 | && CONSP (quoted) | ||
| 491 | && EQ (XCAR (quoted), Qlambda)) | ||
| 492 | /* This is a lambda expression within a lexical environment; | ||
| 493 | return an interpreted closure instead of a simple lambda. */ | ||
| 494 | return Fcons (Qclosure, Fcons (Vinternal_interpreter_environment, | ||
| 495 | XCDR (quoted))); | ||
| 496 | else | ||
| 497 | /* Simply quote the argument. */ | ||
| 498 | return quoted; | ||
| 477 | } | 499 | } |
| 478 | 500 | ||
| 479 | 501 | ||
| @@ -496,7 +518,7 @@ spec that specifies non-nil unconditionally (such as \"p\"); or (ii) | |||
| 496 | use `called-interactively-p'. */) | 518 | use `called-interactively-p'. */) |
| 497 | (void) | 519 | (void) |
| 498 | { | 520 | { |
| 499 | return (INTERACTIVE && interactive_p (1)) ? Qt : Qnil; | 521 | return interactive_p (1) ? Qt : Qnil; |
| 500 | } | 522 | } |
| 501 | 523 | ||
| 502 | 524 | ||
| @@ -589,6 +611,8 @@ usage: (defun NAME ARGLIST [DOCSTRING] BODY...) */) | |||
| 589 | fn_name = Fcar (args); | 611 | fn_name = Fcar (args); |
| 590 | CHECK_SYMBOL (fn_name); | 612 | CHECK_SYMBOL (fn_name); |
| 591 | defn = Fcons (Qlambda, Fcdr (args)); | 613 | defn = Fcons (Qlambda, Fcdr (args)); |
| 614 | if (!NILP (Vinternal_interpreter_environment)) /* Mere optimization! */ | ||
| 615 | defn = Ffunction (Fcons (defn, Qnil)); | ||
| 592 | if (!NILP (Vpurify_flag)) | 616 | if (!NILP (Vpurify_flag)) |
| 593 | defn = Fpurecopy (defn); | 617 | defn = Fpurecopy (defn); |
| 594 | if (CONSP (XSYMBOL (fn_name)->function) | 618 | if (CONSP (XSYMBOL (fn_name)->function) |
| @@ -660,7 +684,11 @@ usage: (defmacro NAME ARGLIST [DOCSTRING] [DECL] BODY...) */) | |||
| 660 | tail = Fcons (lambda_list, tail); | 684 | tail = Fcons (lambda_list, tail); |
| 661 | else | 685 | else |
| 662 | tail = Fcons (lambda_list, Fcons (doc, tail)); | 686 | tail = Fcons (lambda_list, Fcons (doc, tail)); |
| 663 | defn = Fcons (Qmacro, Fcons (Qlambda, tail)); | 687 | |
| 688 | defn = Fcons (Qlambda, tail); | ||
| 689 | if (!NILP (Vinternal_interpreter_environment)) /* Mere optimization! */ | ||
| 690 | defn = Ffunction (Fcons (defn, Qnil)); | ||
| 691 | defn = Fcons (Qmacro, defn); | ||
| 664 | 692 | ||
| 665 | if (!NILP (Vpurify_flag)) | 693 | if (!NILP (Vpurify_flag)) |
| 666 | defn = Fpurecopy (defn); | 694 | defn = Fpurecopy (defn); |
| @@ -720,6 +748,7 @@ The return value is BASE-VARIABLE. */) | |||
| 720 | error ("Don't know how to make a let-bound variable an alias"); | 748 | error ("Don't know how to make a let-bound variable an alias"); |
| 721 | } | 749 | } |
| 722 | 750 | ||
| 751 | sym->declared_special = 1; | ||
| 723 | sym->redirect = SYMBOL_VARALIAS; | 752 | sym->redirect = SYMBOL_VARALIAS; |
| 724 | SET_SYMBOL_ALIAS (sym, XSYMBOL (base_variable)); | 753 | SET_SYMBOL_ALIAS (sym, XSYMBOL (base_variable)); |
| 725 | sym->constant = SYMBOL_CONSTANT_P (base_variable); | 754 | sym->constant = SYMBOL_CONSTANT_P (base_variable); |
| @@ -765,6 +794,9 @@ usage: (defvar SYMBOL &optional INITVALUE DOCSTRING) */) | |||
| 765 | tem = Fdefault_boundp (sym); | 794 | tem = Fdefault_boundp (sym); |
| 766 | if (!NILP (tail)) | 795 | if (!NILP (tail)) |
| 767 | { | 796 | { |
| 797 | /* Do it before evaluating the initial value, for self-references. */ | ||
| 798 | XSYMBOL (sym)->declared_special = 1; | ||
| 799 | |||
| 768 | if (SYMBOL_CONSTANT_P (sym)) | 800 | if (SYMBOL_CONSTANT_P (sym)) |
| 769 | { | 801 | { |
| 770 | /* For upward compatibility, allow (defvar :foo (quote :foo)). */ | 802 | /* For upward compatibility, allow (defvar :foo (quote :foo)). */ |
| @@ -778,7 +810,7 @@ usage: (defvar SYMBOL &optional INITVALUE DOCSTRING) */) | |||
| 778 | } | 810 | } |
| 779 | 811 | ||
| 780 | if (NILP (tem)) | 812 | if (NILP (tem)) |
| 781 | Fset_default (sym, Feval (Fcar (tail))); | 813 | Fset_default (sym, eval_sub (Fcar (tail))); |
| 782 | else | 814 | else |
| 783 | { /* Check if there is really a global binding rather than just a let | 815 | { /* Check if there is really a global binding rather than just a let |
| 784 | binding that shadows the global unboundness of the var. */ | 816 | binding that shadows the global unboundness of the var. */ |
| @@ -804,6 +836,13 @@ usage: (defvar SYMBOL &optional INITVALUE DOCSTRING) */) | |||
| 804 | } | 836 | } |
| 805 | LOADHIST_ATTACH (sym); | 837 | LOADHIST_ATTACH (sym); |
| 806 | } | 838 | } |
| 839 | else if (!NILP (Vinternal_interpreter_environment) | ||
| 840 | && !XSYMBOL (sym)->declared_special) | ||
| 841 | /* A simple (defvar foo) with lexical scoping does "nothing" except | ||
| 842 | declare that var to be dynamically scoped *locally* (i.e. within | ||
| 843 | the current file or let-block). */ | ||
| 844 | Vinternal_interpreter_environment = | ||
| 845 | Fcons (sym, Vinternal_interpreter_environment); | ||
| 807 | else | 846 | else |
| 808 | { | 847 | { |
| 809 | /* Simple (defvar <var>) should not count as a definition at all. | 848 | /* Simple (defvar <var>) should not count as a definition at all. |
| @@ -834,10 +873,11 @@ usage: (defconst SYMBOL INITVALUE [DOCSTRING]) */) | |||
| 834 | if (!NILP (Fcdr (Fcdr (Fcdr (args))))) | 873 | if (!NILP (Fcdr (Fcdr (Fcdr (args))))) |
| 835 | error ("Too many arguments"); | 874 | error ("Too many arguments"); |
| 836 | 875 | ||
| 837 | tem = Feval (Fcar (Fcdr (args))); | 876 | tem = eval_sub (Fcar (Fcdr (args))); |
| 838 | if (!NILP (Vpurify_flag)) | 877 | if (!NILP (Vpurify_flag)) |
| 839 | tem = Fpurecopy (tem); | 878 | tem = Fpurecopy (tem); |
| 840 | Fset_default (sym, tem); | 879 | Fset_default (sym, tem); |
| 880 | XSYMBOL (sym)->declared_special = 1; | ||
| 841 | tem = Fcar (Fcdr (Fcdr (args))); | 881 | tem = Fcar (Fcdr (Fcdr (args))); |
| 842 | if (!NILP (tem)) | 882 | if (!NILP (tem)) |
| 843 | { | 883 | { |
| @@ -924,27 +964,53 @@ Each VALUEFORM can refer to the symbols already bound by this VARLIST. | |||
| 924 | usage: (let* VARLIST BODY...) */) | 964 | usage: (let* VARLIST BODY...) */) |
| 925 | (Lisp_Object args) | 965 | (Lisp_Object args) |
| 926 | { | 966 | { |
| 927 | Lisp_Object varlist, val, elt; | 967 | Lisp_Object varlist, var, val, elt, lexenv; |
| 928 | int count = SPECPDL_INDEX (); | 968 | int count = SPECPDL_INDEX (); |
| 929 | struct gcpro gcpro1, gcpro2, gcpro3; | 969 | struct gcpro gcpro1, gcpro2, gcpro3; |
| 930 | 970 | ||
| 931 | GCPRO3 (args, elt, varlist); | 971 | GCPRO3 (args, elt, varlist); |
| 932 | 972 | ||
| 973 | lexenv = Vinternal_interpreter_environment; | ||
| 974 | |||
| 933 | varlist = Fcar (args); | 975 | varlist = Fcar (args); |
| 934 | while (!NILP (varlist)) | 976 | while (CONSP (varlist)) |
| 935 | { | 977 | { |
| 936 | QUIT; | 978 | QUIT; |
| 937 | elt = Fcar (varlist); | 979 | |
| 980 | elt = XCAR (varlist); | ||
| 938 | if (SYMBOLP (elt)) | 981 | if (SYMBOLP (elt)) |
| 939 | specbind (elt, Qnil); | 982 | { |
| 983 | var = elt; | ||
| 984 | val = Qnil; | ||
| 985 | } | ||
| 940 | else if (! NILP (Fcdr (Fcdr (elt)))) | 986 | else if (! NILP (Fcdr (Fcdr (elt)))) |
| 941 | signal_error ("`let' bindings can have only one value-form", elt); | 987 | signal_error ("`let' bindings can have only one value-form", elt); |
| 942 | else | 988 | else |
| 943 | { | 989 | { |
| 944 | val = Feval (Fcar (Fcdr (elt))); | 990 | var = Fcar (elt); |
| 945 | specbind (Fcar (elt), val); | 991 | val = eval_sub (Fcar (Fcdr (elt))); |
| 992 | } | ||
| 993 | |||
| 994 | if (!NILP (lexenv) && SYMBOLP (var) | ||
| 995 | && !XSYMBOL (var)->declared_special | ||
| 996 | && NILP (Fmemq (var, Vinternal_interpreter_environment))) | ||
| 997 | /* Lexically bind VAR by adding it to the interpreter's binding | ||
| 998 | alist. */ | ||
| 999 | { | ||
| 1000 | Lisp_Object newenv | ||
| 1001 | = Fcons (Fcons (var, val), Vinternal_interpreter_environment); | ||
| 1002 | if (EQ (Vinternal_interpreter_environment, lexenv)) | ||
| 1003 | /* Save the old lexical environment on the specpdl stack, | ||
| 1004 | but only for the first lexical binding, since we'll never | ||
| 1005 | need to revert to one of the intermediate ones. */ | ||
| 1006 | specbind (Qinternal_interpreter_environment, newenv); | ||
| 1007 | else | ||
| 1008 | Vinternal_interpreter_environment = newenv; | ||
| 946 | } | 1009 | } |
| 947 | varlist = Fcdr (varlist); | 1010 | else |
| 1011 | specbind (var, val); | ||
| 1012 | |||
| 1013 | varlist = XCDR (varlist); | ||
| 948 | } | 1014 | } |
| 949 | UNGCPRO; | 1015 | UNGCPRO; |
| 950 | val = Fprogn (Fcdr (args)); | 1016 | val = Fprogn (Fcdr (args)); |
| @@ -960,7 +1026,7 @@ All the VALUEFORMs are evalled before any symbols are bound. | |||
| 960 | usage: (let VARLIST BODY...) */) | 1026 | usage: (let VARLIST BODY...) */) |
| 961 | (Lisp_Object args) | 1027 | (Lisp_Object args) |
| 962 | { | 1028 | { |
| 963 | Lisp_Object *temps, tem; | 1029 | Lisp_Object *temps, tem, lexenv; |
| 964 | register Lisp_Object elt, varlist; | 1030 | register Lisp_Object elt, varlist; |
| 965 | int count = SPECPDL_INDEX (); | 1031 | int count = SPECPDL_INDEX (); |
| 966 | register size_t argnum; | 1032 | register size_t argnum; |
| @@ -987,22 +1053,36 @@ usage: (let VARLIST BODY...) */) | |||
| 987 | else if (! NILP (Fcdr (Fcdr (elt)))) | 1053 | else if (! NILP (Fcdr (Fcdr (elt)))) |
| 988 | signal_error ("`let' bindings can have only one value-form", elt); | 1054 | signal_error ("`let' bindings can have only one value-form", elt); |
| 989 | else | 1055 | else |
| 990 | temps [argnum++] = Feval (Fcar (Fcdr (elt))); | 1056 | temps [argnum++] = eval_sub (Fcar (Fcdr (elt))); |
| 991 | gcpro2.nvars = argnum; | 1057 | gcpro2.nvars = argnum; |
| 992 | } | 1058 | } |
| 993 | UNGCPRO; | 1059 | UNGCPRO; |
| 994 | 1060 | ||
| 1061 | lexenv = Vinternal_interpreter_environment; | ||
| 1062 | |||
| 995 | varlist = Fcar (args); | 1063 | varlist = Fcar (args); |
| 996 | for (argnum = 0; CONSP (varlist); varlist = XCDR (varlist)) | 1064 | for (argnum = 0; CONSP (varlist); varlist = XCDR (varlist)) |
| 997 | { | 1065 | { |
| 1066 | Lisp_Object var; | ||
| 1067 | |||
| 998 | elt = XCAR (varlist); | 1068 | elt = XCAR (varlist); |
| 1069 | var = SYMBOLP (elt) ? elt : Fcar (elt); | ||
| 999 | tem = temps[argnum++]; | 1070 | tem = temps[argnum++]; |
| 1000 | if (SYMBOLP (elt)) | 1071 | |
| 1001 | specbind (elt, tem); | 1072 | if (!NILP (lexenv) && SYMBOLP (var) |
| 1073 | && !XSYMBOL (var)->declared_special | ||
| 1074 | && NILP (Fmemq (var, Vinternal_interpreter_environment))) | ||
| 1075 | /* Lexically bind VAR by adding it to the lexenv alist. */ | ||
| 1076 | lexenv = Fcons (Fcons (var, tem), lexenv); | ||
| 1002 | else | 1077 | else |
| 1003 | specbind (Fcar (elt), tem); | 1078 | /* Dynamically bind VAR. */ |
| 1079 | specbind (var, tem); | ||
| 1004 | } | 1080 | } |
| 1005 | 1081 | ||
| 1082 | if (!EQ (lexenv, Vinternal_interpreter_environment)) | ||
| 1083 | /* Instantiate a new lexical environment. */ | ||
| 1084 | specbind (Qinternal_interpreter_environment, lexenv); | ||
| 1085 | |||
| 1006 | elt = Fprogn (Fcdr (args)); | 1086 | elt = Fprogn (Fcdr (args)); |
| 1007 | SAFE_FREE (); | 1087 | SAFE_FREE (); |
| 1008 | return unbind_to (count, elt); | 1088 | return unbind_to (count, elt); |
| @@ -1022,7 +1102,7 @@ usage: (while TEST BODY...) */) | |||
| 1022 | 1102 | ||
| 1023 | test = Fcar (args); | 1103 | test = Fcar (args); |
| 1024 | body = Fcdr (args); | 1104 | body = Fcdr (args); |
| 1025 | while (!NILP (Feval (test))) | 1105 | while (!NILP (eval_sub (test))) |
| 1026 | { | 1106 | { |
| 1027 | QUIT; | 1107 | QUIT; |
| 1028 | Fprogn (body); | 1108 | Fprogn (body); |
| @@ -1124,7 +1204,7 @@ usage: (catch TAG BODY...) */) | |||
| 1124 | struct gcpro gcpro1; | 1204 | struct gcpro gcpro1; |
| 1125 | 1205 | ||
| 1126 | GCPRO1 (args); | 1206 | GCPRO1 (args); |
| 1127 | tag = Feval (Fcar (args)); | 1207 | tag = eval_sub (Fcar (args)); |
| 1128 | UNGCPRO; | 1208 | UNGCPRO; |
| 1129 | return internal_catch (tag, Fprogn, Fcdr (args)); | 1209 | return internal_catch (tag, Fprogn, Fcdr (args)); |
| 1130 | } | 1210 | } |
| @@ -1254,7 +1334,7 @@ usage: (unwind-protect BODYFORM UNWINDFORMS...) */) | |||
| 1254 | int count = SPECPDL_INDEX (); | 1334 | int count = SPECPDL_INDEX (); |
| 1255 | 1335 | ||
| 1256 | record_unwind_protect (Fprogn, Fcdr (args)); | 1336 | record_unwind_protect (Fprogn, Fcdr (args)); |
| 1257 | val = Feval (Fcar (args)); | 1337 | val = eval_sub (Fcar (args)); |
| 1258 | return unbind_to (count, val); | 1338 | return unbind_to (count, val); |
| 1259 | } | 1339 | } |
| 1260 | 1340 | ||
| @@ -1355,7 +1435,7 @@ internal_lisp_condition_case (volatile Lisp_Object var, Lisp_Object bodyform, | |||
| 1355 | h.tag = &c; | 1435 | h.tag = &c; |
| 1356 | handlerlist = &h; | 1436 | handlerlist = &h; |
| 1357 | 1437 | ||
| 1358 | val = Feval (bodyform); | 1438 | val = eval_sub (bodyform); |
| 1359 | catchlist = c.next; | 1439 | catchlist = c.next; |
| 1360 | handlerlist = h.next; | 1440 | handlerlist = h.next; |
| 1361 | return val; | 1441 | return val; |
| @@ -1999,9 +2079,12 @@ then strings and vectors are not accepted. */) | |||
| 1999 | if (!CONSP (fun)) | 2079 | if (!CONSP (fun)) |
| 2000 | return Qnil; | 2080 | return Qnil; |
| 2001 | funcar = XCAR (fun); | 2081 | funcar = XCAR (fun); |
| 2002 | if (EQ (funcar, Qlambda)) | 2082 | if (EQ (funcar, Qclosure)) |
| 2083 | return (!NILP (Fassq (Qinteractive, Fcdr (Fcdr (XCDR (fun))))) | ||
| 2084 | ? Qt : if_prop); | ||
| 2085 | else if (EQ (funcar, Qlambda)) | ||
| 2003 | return !NILP (Fassq (Qinteractive, Fcdr (XCDR (fun)))) ? Qt : if_prop; | 2086 | return !NILP (Fassq (Qinteractive, Fcdr (XCDR (fun)))) ? Qt : if_prop; |
| 2004 | if (EQ (funcar, Qautoload)) | 2087 | else if (EQ (funcar, Qautoload)) |
| 2005 | return !NILP (Fcar (Fcdr (Fcdr (XCDR (fun))))) ? Qt : if_prop; | 2088 | return !NILP (Fcar (Fcdr (Fcdr (XCDR (fun))))) ? Qt : if_prop; |
| 2006 | else | 2089 | else |
| 2007 | return Qnil; | 2090 | return Qnil; |
| @@ -2119,9 +2202,21 @@ do_autoload (Lisp_Object fundef, Lisp_Object funname) | |||
| 2119 | } | 2202 | } |
| 2120 | 2203 | ||
| 2121 | 2204 | ||
| 2122 | DEFUN ("eval", Feval, Seval, 1, 1, 0, | 2205 | DEFUN ("eval", Feval, Seval, 1, 2, 0, |
| 2123 | doc: /* Evaluate FORM and return its value. */) | 2206 | doc: /* Evaluate FORM and return its value. |
| 2124 | (Lisp_Object form) | 2207 | If LEXICAL is t, evaluate using lexical scoping. */) |
| 2208 | (Lisp_Object form, Lisp_Object lexical) | ||
| 2209 | { | ||
| 2210 | int count = SPECPDL_INDEX (); | ||
| 2211 | specbind (Qinternal_interpreter_environment, | ||
| 2212 | NILP (lexical) ? Qnil : Fcons (Qt, Qnil)); | ||
| 2213 | return unbind_to (count, eval_sub (form)); | ||
| 2214 | } | ||
| 2215 | |||
| 2216 | /* Eval a sub-expression of the current expression (i.e. in the same | ||
| 2217 | lexical scope). */ | ||
| 2218 | Lisp_Object | ||
| 2219 | eval_sub (Lisp_Object form) | ||
| 2125 | { | 2220 | { |
| 2126 | Lisp_Object fun, val, original_fun, original_args; | 2221 | Lisp_Object fun, val, original_fun, original_args; |
| 2127 | Lisp_Object funcar; | 2222 | Lisp_Object funcar; |
| @@ -2132,7 +2227,20 @@ DEFUN ("eval", Feval, Seval, 1, 1, 0, | |||
| 2132 | abort (); | 2227 | abort (); |
| 2133 | 2228 | ||
| 2134 | if (SYMBOLP (form)) | 2229 | if (SYMBOLP (form)) |
| 2135 | return Fsymbol_value (form); | 2230 | { |
| 2231 | /* Look up its binding in the lexical environment. | ||
| 2232 | We do not pay attention to the declared_special flag here, since we | ||
| 2233 | already did that when let-binding the variable. */ | ||
| 2234 | Lisp_Object lex_binding | ||
| 2235 | = !NILP (Vinternal_interpreter_environment) /* Mere optimization! */ | ||
| 2236 | ? Fassq (form, Vinternal_interpreter_environment) | ||
| 2237 | : Qnil; | ||
| 2238 | if (CONSP (lex_binding)) | ||
| 2239 | return XCDR (lex_binding); | ||
| 2240 | else | ||
| 2241 | return Fsymbol_value (form); | ||
| 2242 | } | ||
| 2243 | |||
| 2136 | if (!CONSP (form)) | 2244 | if (!CONSP (form)) |
| 2137 | return form; | 2245 | return form; |
| 2138 | 2246 | ||
| @@ -2216,7 +2324,7 @@ DEFUN ("eval", Feval, Seval, 1, 1, 0, | |||
| 2216 | 2324 | ||
| 2217 | while (!NILP (args_left)) | 2325 | while (!NILP (args_left)) |
| 2218 | { | 2326 | { |
| 2219 | vals[argnum++] = Feval (Fcar (args_left)); | 2327 | vals[argnum++] = eval_sub (Fcar (args_left)); |
| 2220 | args_left = Fcdr (args_left); | 2328 | args_left = Fcdr (args_left); |
| 2221 | gcpro3.nvars = argnum; | 2329 | gcpro3.nvars = argnum; |
| 2222 | } | 2330 | } |
| @@ -2237,7 +2345,7 @@ DEFUN ("eval", Feval, Seval, 1, 1, 0, | |||
| 2237 | maxargs = XSUBR (fun)->max_args; | 2345 | maxargs = XSUBR (fun)->max_args; |
| 2238 | for (i = 0; i < maxargs; args_left = Fcdr (args_left)) | 2346 | for (i = 0; i < maxargs; args_left = Fcdr (args_left)) |
| 2239 | { | 2347 | { |
| 2240 | argvals[i] = Feval (Fcar (args_left)); | 2348 | argvals[i] = eval_sub (Fcar (args_left)); |
| 2241 | gcpro3.nvars = ++i; | 2349 | gcpro3.nvars = ++i; |
| 2242 | } | 2350 | } |
| 2243 | 2351 | ||
| @@ -2297,7 +2405,7 @@ DEFUN ("eval", Feval, Seval, 1, 1, 0, | |||
| 2297 | } | 2405 | } |
| 2298 | } | 2406 | } |
| 2299 | else if (COMPILEDP (fun)) | 2407 | else if (COMPILEDP (fun)) |
| 2300 | val = apply_lambda (fun, original_args, 1); | 2408 | val = apply_lambda (fun, original_args); |
| 2301 | else | 2409 | else |
| 2302 | { | 2410 | { |
| 2303 | if (EQ (fun, Qunbound)) | 2411 | if (EQ (fun, Qunbound)) |
| @@ -2313,9 +2421,10 @@ DEFUN ("eval", Feval, Seval, 1, 1, 0, | |||
| 2313 | goto retry; | 2421 | goto retry; |
| 2314 | } | 2422 | } |
| 2315 | if (EQ (funcar, Qmacro)) | 2423 | if (EQ (funcar, Qmacro)) |
| 2316 | val = Feval (apply1 (Fcdr (fun), original_args)); | 2424 | val = eval_sub (apply1 (Fcdr (fun), original_args)); |
| 2317 | else if (EQ (funcar, Qlambda)) | 2425 | else if (EQ (funcar, Qlambda) |
| 2318 | val = apply_lambda (fun, original_args, 1); | 2426 | || EQ (funcar, Qclosure)) |
| 2427 | val = apply_lambda (fun, original_args); | ||
| 2319 | else | 2428 | else |
| 2320 | xsignal1 (Qinvalid_function, original_fun); | 2429 | xsignal1 (Qinvalid_function, original_fun); |
| 2321 | } | 2430 | } |
| @@ -2786,6 +2895,39 @@ call7 (Lisp_Object fn, Lisp_Object arg1, Lisp_Object arg2, Lisp_Object arg3, | |||
| 2786 | 2895 | ||
| 2787 | /* The caller should GCPRO all the elements of ARGS. */ | 2896 | /* The caller should GCPRO all the elements of ARGS. */ |
| 2788 | 2897 | ||
| 2898 | DEFUN ("functionp", Ffunctionp, Sfunctionp, 1, 1, 0, | ||
| 2899 | doc: /* Non-nil if OBJECT is a function. */) | ||
| 2900 | (Lisp_Object object) | ||
| 2901 | { | ||
| 2902 | if (SYMBOLP (object) && !NILP (Ffboundp (object))) | ||
| 2903 | { | ||
| 2904 | object = Findirect_function (object, Qt); | ||
| 2905 | |||
| 2906 | if (CONSP (object) && EQ (XCAR (object), Qautoload)) | ||
| 2907 | { | ||
| 2908 | /* Autoloaded symbols are functions, except if they load | ||
| 2909 | macros or keymaps. */ | ||
| 2910 | int i; | ||
| 2911 | for (i = 0; i < 4 && CONSP (object); i++) | ||
| 2912 | object = XCDR (object); | ||
| 2913 | |||
| 2914 | return (CONSP (object) && !NILP (XCAR (object))) ? Qnil : Qt; | ||
| 2915 | } | ||
| 2916 | } | ||
| 2917 | |||
| 2918 | if (SUBRP (object)) | ||
| 2919 | return (XSUBR (object)->max_args != UNEVALLED) ? Qt : Qnil; | ||
| 2920 | else if (COMPILEDP (object)) | ||
| 2921 | return Qt; | ||
| 2922 | else if (CONSP (object)) | ||
| 2923 | { | ||
| 2924 | Lisp_Object car = XCAR (object); | ||
| 2925 | return (EQ (car, Qlambda) || EQ (car, Qclosure)) ? Qt : Qnil; | ||
| 2926 | } | ||
| 2927 | else | ||
| 2928 | return Qnil; | ||
| 2929 | } | ||
| 2930 | |||
| 2789 | DEFUN ("funcall", Ffuncall, Sfuncall, 1, MANY, 0, | 2931 | DEFUN ("funcall", Ffuncall, Sfuncall, 1, MANY, 0, |
| 2790 | doc: /* Call first argument as a function, passing remaining arguments to it. | 2932 | doc: /* Call first argument as a function, passing remaining arguments to it. |
| 2791 | Return the value that function returns. | 2933 | Return the value that function returns. |
| @@ -2930,7 +3072,8 @@ usage: (funcall FUNCTION &rest ARGUMENTS) */) | |||
| 2930 | funcar = XCAR (fun); | 3072 | funcar = XCAR (fun); |
| 2931 | if (!SYMBOLP (funcar)) | 3073 | if (!SYMBOLP (funcar)) |
| 2932 | xsignal1 (Qinvalid_function, original_fun); | 3074 | xsignal1 (Qinvalid_function, original_fun); |
| 2933 | if (EQ (funcar, Qlambda)) | 3075 | if (EQ (funcar, Qlambda) |
| 3076 | || EQ (funcar, Qclosure)) | ||
| 2934 | val = funcall_lambda (fun, numargs, args + 1); | 3077 | val = funcall_lambda (fun, numargs, args + 1); |
| 2935 | else if (EQ (funcar, Qautoload)) | 3078 | else if (EQ (funcar, Qautoload)) |
| 2936 | { | 3079 | { |
| @@ -2950,7 +3093,7 @@ usage: (funcall FUNCTION &rest ARGUMENTS) */) | |||
| 2950 | } | 3093 | } |
| 2951 | 3094 | ||
| 2952 | static Lisp_Object | 3095 | static Lisp_Object |
| 2953 | apply_lambda (Lisp_Object fun, Lisp_Object args, int eval_flag) | 3096 | apply_lambda (Lisp_Object fun, Lisp_Object args) |
| 2954 | { | 3097 | { |
| 2955 | Lisp_Object args_left; | 3098 | Lisp_Object args_left; |
| 2956 | size_t numargs; | 3099 | size_t numargs; |
| @@ -2970,18 +3113,15 @@ apply_lambda (Lisp_Object fun, Lisp_Object args, int eval_flag) | |||
| 2970 | for (i = 0; i < numargs; ) | 3113 | for (i = 0; i < numargs; ) |
| 2971 | { | 3114 | { |
| 2972 | tem = Fcar (args_left), args_left = Fcdr (args_left); | 3115 | tem = Fcar (args_left), args_left = Fcdr (args_left); |
| 2973 | if (eval_flag) tem = Feval (tem); | 3116 | tem = eval_sub (tem); |
| 2974 | arg_vector[i++] = tem; | 3117 | arg_vector[i++] = tem; |
| 2975 | gcpro1.nvars = i; | 3118 | gcpro1.nvars = i; |
| 2976 | } | 3119 | } |
| 2977 | 3120 | ||
| 2978 | UNGCPRO; | 3121 | UNGCPRO; |
| 2979 | 3122 | ||
| 2980 | if (eval_flag) | 3123 | backtrace_list->args = arg_vector; |
| 2981 | { | 3124 | backtrace_list->nargs = i; |
| 2982 | backtrace_list->args = arg_vector; | ||
| 2983 | backtrace_list->nargs = i; | ||
| 2984 | } | ||
| 2985 | backtrace_list->evalargs = 0; | 3125 | backtrace_list->evalargs = 0; |
| 2986 | tem = funcall_lambda (fun, numargs, arg_vector); | 3126 | tem = funcall_lambda (fun, numargs, arg_vector); |
| 2987 | 3127 | ||
| @@ -3002,13 +3142,21 @@ static Lisp_Object | |||
| 3002 | funcall_lambda (Lisp_Object fun, size_t nargs, | 3142 | funcall_lambda (Lisp_Object fun, size_t nargs, |
| 3003 | register Lisp_Object *arg_vector) | 3143 | register Lisp_Object *arg_vector) |
| 3004 | { | 3144 | { |
| 3005 | Lisp_Object val, syms_left, next; | 3145 | Lisp_Object val, syms_left, next, lexenv; |
| 3006 | int count = SPECPDL_INDEX (); | 3146 | int count = SPECPDL_INDEX (); |
| 3007 | size_t i; | 3147 | size_t i; |
| 3008 | int optional, rest; | 3148 | int optional, rest; |
| 3009 | 3149 | ||
| 3010 | if (CONSP (fun)) | 3150 | if (CONSP (fun)) |
| 3011 | { | 3151 | { |
| 3152 | if (EQ (XCAR (fun), Qclosure)) | ||
| 3153 | { | ||
| 3154 | fun = XCDR (fun); /* Drop `closure'. */ | ||
| 3155 | lexenv = XCAR (fun); | ||
| 3156 | CHECK_LIST_CONS (fun, fun); | ||
| 3157 | } | ||
| 3158 | else | ||
| 3159 | lexenv = Qnil; | ||
| 3012 | syms_left = XCDR (fun); | 3160 | syms_left = XCDR (fun); |
| 3013 | if (CONSP (syms_left)) | 3161 | if (CONSP (syms_left)) |
| 3014 | syms_left = XCAR (syms_left); | 3162 | syms_left = XCAR (syms_left); |
| @@ -3016,7 +3164,30 @@ funcall_lambda (Lisp_Object fun, size_t nargs, | |||
| 3016 | xsignal1 (Qinvalid_function, fun); | 3164 | xsignal1 (Qinvalid_function, fun); |
| 3017 | } | 3165 | } |
| 3018 | else if (COMPILEDP (fun)) | 3166 | else if (COMPILEDP (fun)) |
| 3019 | syms_left = AREF (fun, COMPILED_ARGLIST); | 3167 | { |
| 3168 | syms_left = AREF (fun, COMPILED_ARGLIST); | ||
| 3169 | if (INTEGERP (syms_left)) | ||
| 3170 | /* A byte-code object with a non-nil `push args' slot means we | ||
| 3171 | shouldn't bind any arguments, instead just call the byte-code | ||
| 3172 | interpreter directly; it will push arguments as necessary. | ||
| 3173 | |||
| 3174 | Byte-code objects with either a non-existant, or a nil value for | ||
| 3175 | the `push args' slot (the default), have dynamically-bound | ||
| 3176 | arguments, and use the argument-binding code below instead (as do | ||
| 3177 | all interpreted functions, even lexically bound ones). */ | ||
| 3178 | { | ||
| 3179 | /* If we have not actually read the bytecode string | ||
| 3180 | and constants vector yet, fetch them from the file. */ | ||
| 3181 | if (CONSP (AREF (fun, COMPILED_BYTECODE))) | ||
| 3182 | Ffetch_bytecode (fun); | ||
| 3183 | return exec_byte_code (AREF (fun, COMPILED_BYTECODE), | ||
| 3184 | AREF (fun, COMPILED_CONSTANTS), | ||
| 3185 | AREF (fun, COMPILED_STACK_DEPTH), | ||
| 3186 | syms_left, | ||
| 3187 | nargs, arg_vector); | ||
| 3188 | } | ||
| 3189 | lexenv = Qnil; | ||
| 3190 | } | ||
| 3020 | else | 3191 | else |
| 3021 | abort (); | 3192 | abort (); |
| 3022 | 3193 | ||
| @@ -3033,17 +3204,29 @@ funcall_lambda (Lisp_Object fun, size_t nargs, | |||
| 3033 | rest = 1; | 3204 | rest = 1; |
| 3034 | else if (EQ (next, Qand_optional)) | 3205 | else if (EQ (next, Qand_optional)) |
| 3035 | optional = 1; | 3206 | optional = 1; |
| 3036 | else if (rest) | 3207 | else |
| 3037 | { | 3208 | { |
| 3038 | specbind (next, Flist (nargs - i, &arg_vector[i])); | 3209 | Lisp_Object val; |
| 3039 | i = nargs; | 3210 | if (rest) |
| 3211 | { | ||
| 3212 | val = Flist (nargs - i, &arg_vector[i]); | ||
| 3213 | i = nargs; | ||
| 3214 | } | ||
| 3215 | else if (i < nargs) | ||
| 3216 | val = arg_vector[i++]; | ||
| 3217 | else if (!optional) | ||
| 3218 | xsignal2 (Qwrong_number_of_arguments, fun, make_number (nargs)); | ||
| 3219 | else | ||
| 3220 | val = Qnil; | ||
| 3221 | |||
| 3222 | /* Bind the argument. */ | ||
| 3223 | if (!NILP (lexenv) && SYMBOLP (next)) | ||
| 3224 | /* Lexically bind NEXT by adding it to the lexenv alist. */ | ||
| 3225 | lexenv = Fcons (Fcons (next, val), lexenv); | ||
| 3226 | else | ||
| 3227 | /* Dynamically bind NEXT. */ | ||
| 3228 | specbind (next, val); | ||
| 3040 | } | 3229 | } |
| 3041 | else if (i < nargs) | ||
| 3042 | specbind (next, arg_vector[i++]); | ||
| 3043 | else if (!optional) | ||
| 3044 | xsignal2 (Qwrong_number_of_arguments, fun, make_number (nargs)); | ||
| 3045 | else | ||
| 3046 | specbind (next, Qnil); | ||
| 3047 | } | 3230 | } |
| 3048 | 3231 | ||
| 3049 | if (!NILP (syms_left)) | 3232 | if (!NILP (syms_left)) |
| @@ -3051,6 +3234,10 @@ funcall_lambda (Lisp_Object fun, size_t nargs, | |||
| 3051 | else if (i < nargs) | 3234 | else if (i < nargs) |
| 3052 | xsignal2 (Qwrong_number_of_arguments, fun, make_number (nargs)); | 3235 | xsignal2 (Qwrong_number_of_arguments, fun, make_number (nargs)); |
| 3053 | 3236 | ||
| 3237 | if (!EQ (lexenv, Vinternal_interpreter_environment)) | ||
| 3238 | /* Instantiate a new lexical environment. */ | ||
| 3239 | specbind (Qinternal_interpreter_environment, lexenv); | ||
| 3240 | |||
| 3054 | if (CONSP (fun)) | 3241 | if (CONSP (fun)) |
| 3055 | val = Fprogn (XCDR (XCDR (fun))); | 3242 | val = Fprogn (XCDR (XCDR (fun))); |
| 3056 | else | 3243 | else |
| @@ -3059,9 +3246,10 @@ funcall_lambda (Lisp_Object fun, size_t nargs, | |||
| 3059 | and constants vector yet, fetch them from the file. */ | 3246 | and constants vector yet, fetch them from the file. */ |
| 3060 | if (CONSP (AREF (fun, COMPILED_BYTECODE))) | 3247 | if (CONSP (AREF (fun, COMPILED_BYTECODE))) |
| 3061 | Ffetch_bytecode (fun); | 3248 | Ffetch_bytecode (fun); |
| 3062 | val = Fbyte_code (AREF (fun, COMPILED_BYTECODE), | 3249 | val = exec_byte_code (AREF (fun, COMPILED_BYTECODE), |
| 3063 | AREF (fun, COMPILED_CONSTANTS), | 3250 | AREF (fun, COMPILED_CONSTANTS), |
| 3064 | AREF (fun, COMPILED_STACK_DEPTH)); | 3251 | AREF (fun, COMPILED_STACK_DEPTH), |
| 3252 | Qnil, 0, 0); | ||
| 3065 | } | 3253 | } |
| 3066 | 3254 | ||
| 3067 | return unbind_to (count, val); | 3255 | return unbind_to (count, val); |
| @@ -3297,6 +3485,17 @@ unbind_to (int count, Lisp_Object value) | |||
| 3297 | UNGCPRO; | 3485 | UNGCPRO; |
| 3298 | return value; | 3486 | return value; |
| 3299 | } | 3487 | } |
| 3488 | |||
| 3489 | DEFUN ("special-variable-p", Fspecial_variable_p, Sspecial_variable_p, 1, 1, 0, | ||
| 3490 | doc: /* Return non-nil if SYMBOL's global binding has been declared special. | ||
| 3491 | A special variable is one that will be bound dynamically, even in a | ||
| 3492 | context where binding is lexical by default. */) | ||
| 3493 | (Lisp_Object symbol) | ||
| 3494 | { | ||
| 3495 | CHECK_SYMBOL (symbol); | ||
| 3496 | return XSYMBOL (symbol)->declared_special ? Qt : Qnil; | ||
| 3497 | } | ||
| 3498 | |||
| 3300 | 3499 | ||
| 3301 | DEFUN ("backtrace-debug", Fbacktrace_debug, Sbacktrace_debug, 2, 2, 0, | 3500 | DEFUN ("backtrace-debug", Fbacktrace_debug, Sbacktrace_debug, 2, 2, 0, |
| 3302 | doc: /* Set the debug-on-exit flag of eval frame LEVEL levels down to FLAG. | 3501 | doc: /* Set the debug-on-exit flag of eval frame LEVEL levels down to FLAG. |
| @@ -3437,6 +3636,8 @@ mark_backtrace (void) | |||
| 3437 | } | 3636 | } |
| 3438 | } | 3637 | } |
| 3439 | 3638 | ||
| 3639 | EXFUN (Funintern, 2); | ||
| 3640 | |||
| 3440 | void | 3641 | void |
| 3441 | syms_of_eval (void) | 3642 | syms_of_eval (void) |
| 3442 | { | 3643 | { |
| @@ -3509,6 +3710,9 @@ before making `inhibit-quit' nil. */); | |||
| 3509 | Qand_optional = intern_c_string ("&optional"); | 3710 | Qand_optional = intern_c_string ("&optional"); |
| 3510 | staticpro (&Qand_optional); | 3711 | staticpro (&Qand_optional); |
| 3511 | 3712 | ||
| 3713 | Qclosure = intern_c_string ("closure"); | ||
| 3714 | staticpro (&Qclosure); | ||
| 3715 | |||
| 3512 | Qdebug = intern_c_string ("debug"); | 3716 | Qdebug = intern_c_string ("debug"); |
| 3513 | staticpro (&Qdebug); | 3717 | staticpro (&Qdebug); |
| 3514 | 3718 | ||
| @@ -3576,6 +3780,28 @@ DECL is a list `(declare ...)' containing the declarations. | |||
| 3576 | The value the function returns is not used. */); | 3780 | The value the function returns is not used. */); |
| 3577 | Vmacro_declaration_function = Qnil; | 3781 | Vmacro_declaration_function = Qnil; |
| 3578 | 3782 | ||
| 3783 | /* When lexical binding is being used, | ||
| 3784 | vinternal_interpreter_environment is non-nil, and contains an alist | ||
| 3785 | of lexically-bound variable, or (t), indicating an empty | ||
| 3786 | environment. The lisp name of this variable would be | ||
| 3787 | `internal-interpreter-environment' if it weren't hidden. | ||
| 3788 | Every element of this list can be either a cons (VAR . VAL) | ||
| 3789 | specifying a lexical binding, or a single symbol VAR indicating | ||
| 3790 | that this variable should use dynamic scoping. */ | ||
| 3791 | Qinternal_interpreter_environment | ||
| 3792 | = intern_c_string ("internal-interpreter-environment"); | ||
| 3793 | staticpro (&Qinternal_interpreter_environment); | ||
| 3794 | DEFVAR_LISP ("internal-interpreter-environment", | ||
| 3795 | Vinternal_interpreter_environment, | ||
| 3796 | doc: /* If non-nil, the current lexical environment of the lisp interpreter. | ||
| 3797 | When lexical binding is not being used, this variable is nil. | ||
| 3798 | A value of `(t)' indicates an empty environment, otherwise it is an | ||
| 3799 | alist of active lexical bindings. */); | ||
| 3800 | Vinternal_interpreter_environment = Qnil; | ||
| 3801 | /* Don't export this variable to Elisp, so noone can mess with it | ||
| 3802 | (Just imagine if someone makes it buffer-local). */ | ||
| 3803 | Funintern (Qinternal_interpreter_environment, Qnil); | ||
| 3804 | |||
| 3579 | Vrun_hooks = intern_c_string ("run-hooks"); | 3805 | Vrun_hooks = intern_c_string ("run-hooks"); |
| 3580 | staticpro (&Vrun_hooks); | 3806 | staticpro (&Vrun_hooks); |
| 3581 | 3807 | ||
| @@ -3625,4 +3851,6 @@ The value the function returns is not used. */); | |||
| 3625 | defsubr (&Sbacktrace_debug); | 3851 | defsubr (&Sbacktrace_debug); |
| 3626 | defsubr (&Sbacktrace); | 3852 | defsubr (&Sbacktrace); |
| 3627 | defsubr (&Sbacktrace_frame); | 3853 | defsubr (&Sbacktrace_frame); |
| 3854 | defsubr (&Sspecial_variable_p); | ||
| 3855 | defsubr (&Sfunctionp); | ||
| 3628 | } | 3856 | } |