aboutsummaryrefslogtreecommitdiffstats
path: root/src/eval.c
diff options
context:
space:
mode:
authorPaul Eggert2020-05-19 23:22:40 -0700
committerPaul Eggert2020-05-19 23:25:16 -0700
commitf0b0105d913a94c66f230874c9269b19dbbc83bd (patch)
tree21180d9cd9266d18187e8dd4de487eed950efa14 /src/eval.c
parent5352bda4eeb7415ad2bda5d74e007b4f36021e68 (diff)
downloademacs-f0b0105d913a94c66f230874c9269b19dbbc83bd.tar.gz
emacs-f0b0105d913a94c66f230874c9269b19dbbc83bd.zip
Hoist some byte-code checking out of eval
Check Lisp_Compiled objects better as they’re created, so that the byte-code interpreter needn’t do the checks each time it executes them. This improved performance of ‘make compile-always’ by 1.5% on my platform. Also, improve the quality of the (still-incomplete) checks, as this is more practical now that they’re done less often. * src/alloc.c (make_byte_code): Remove. All uses removed. (Fmake_byte_code): Put a better (though still incomplete) check here instead. Simplify by using Fvector instead of make_uninit_vector followed by memcpy, and by using XSETPVECTYPE instead of make_byte_code followed by XSETCOMPILED. * src/bytecode.c (Fbyte_code): Do sanity check and conditional translation to unibyte here instead of each time the function is executed. (exec_byte_code): Omit no-longer-necessary sanity and unibyte checking. Use SCHARS instead of SBYTES where either will do, as SCHARS is faster. * src/eval.c (fetch_and_exec_byte_code): New function. (funcall_lambda): Use it. (funcall_lambda, lambda_arity, Ffetch_bytecode): Omit no-longer-necessary sanity checks. (Ffetch_bytecode): Add sanity check if actually fetching. * src/lisp.h (XSETCOMPILED): Remove. All uses removed. * src/lread.c (read1): Check byte-code objects more thoroughly, albeit still incompletely, and do translation to unibyte here instead of each time the function is executed. (read1): Use XSETPVECYPE instead of make_byte_code. (read_vector): Omit no-longer-necessary sanity check.
Diffstat (limited to 'src/eval.c')
-rw-r--r--src/eval.c48
1 files changed, 19 insertions, 29 deletions
diff --git a/src/eval.c b/src/eval.c
index 014905ce6df..be2af2d041b 100644
--- a/src/eval.c
+++ b/src/eval.c
@@ -2904,6 +2904,21 @@ funcall_subr (struct Lisp_Subr *subr, ptrdiff_t numargs, Lisp_Object *args)
2904 } 2904 }
2905} 2905}
2906 2906
2907/* Call the compiled Lisp function FUN. If we have not yet read FUN's
2908 bytecode string and constants vector, fetch them from the file first. */
2909
2910static Lisp_Object
2911fetch_and_exec_byte_code (Lisp_Object fun, Lisp_Object syms_left,
2912 ptrdiff_t nargs, Lisp_Object *args)
2913{
2914 if (CONSP (AREF (fun, COMPILED_BYTECODE)))
2915 Ffetch_bytecode (fun);
2916 return exec_byte_code (AREF (fun, COMPILED_BYTECODE),
2917 AREF (fun, COMPILED_CONSTANTS),
2918 AREF (fun, COMPILED_STACK_DEPTH),
2919 syms_left, nargs, args);
2920}
2921
2907static Lisp_Object 2922static Lisp_Object
2908apply_lambda (Lisp_Object fun, Lisp_Object args, ptrdiff_t count) 2923apply_lambda (Lisp_Object fun, Lisp_Object args, ptrdiff_t count)
2909{ 2924{
@@ -2968,9 +2983,6 @@ funcall_lambda (Lisp_Object fun, ptrdiff_t nargs,
2968 } 2983 }
2969 else if (COMPILEDP (fun)) 2984 else if (COMPILEDP (fun))
2970 { 2985 {
2971 ptrdiff_t size = PVSIZE (fun);
2972 if (size <= COMPILED_STACK_DEPTH)
2973 xsignal1 (Qinvalid_function, fun);
2974 syms_left = AREF (fun, COMPILED_ARGLIST); 2986 syms_left = AREF (fun, COMPILED_ARGLIST);
2975 if (FIXNUMP (syms_left)) 2987 if (FIXNUMP (syms_left))
2976 /* A byte-code object with an integer args template means we 2988 /* A byte-code object with an integer args template means we
@@ -2982,15 +2994,7 @@ funcall_lambda (Lisp_Object fun, ptrdiff_t nargs,
2982 argument-binding code below instead (as do all interpreted 2994 argument-binding code below instead (as do all interpreted
2983 functions, even lexically bound ones). */ 2995 functions, even lexically bound ones). */
2984 { 2996 {
2985 /* If we have not actually read the bytecode string 2997 return fetch_and_exec_byte_code (fun, syms_left, nargs, arg_vector);
2986 and constants vector yet, fetch them from the file. */
2987 if (CONSP (AREF (fun, COMPILED_BYTECODE)))
2988 Ffetch_bytecode (fun);
2989 return exec_byte_code (AREF (fun, COMPILED_BYTECODE),
2990 AREF (fun, COMPILED_CONSTANTS),
2991 AREF (fun, COMPILED_STACK_DEPTH),
2992 syms_left,
2993 nargs, arg_vector);
2994 } 2998 }
2995 lexenv = Qnil; 2999 lexenv = Qnil;
2996 } 3000 }
@@ -3059,16 +3063,7 @@ funcall_lambda (Lisp_Object fun, ptrdiff_t nargs,
3059 if (CONSP (fun)) 3063 if (CONSP (fun))
3060 val = Fprogn (XCDR (XCDR (fun))); 3064 val = Fprogn (XCDR (XCDR (fun)));
3061 else 3065 else
3062 { 3066 val = fetch_and_exec_byte_code (fun, Qnil, 0, NULL);
3063 /* If we have not actually read the bytecode string
3064 and constants vector yet, fetch them from the file. */
3065 if (CONSP (AREF (fun, COMPILED_BYTECODE)))
3066 Ffetch_bytecode (fun);
3067 val = exec_byte_code (AREF (fun, COMPILED_BYTECODE),
3068 AREF (fun, COMPILED_CONSTANTS),
3069 AREF (fun, COMPILED_STACK_DEPTH),
3070 Qnil, 0, 0);
3071 }
3072 3067
3073 return unbind_to (count, val); 3068 return unbind_to (count, val);
3074} 3069}
@@ -3153,9 +3148,6 @@ lambda_arity (Lisp_Object fun)
3153 } 3148 }
3154 else if (COMPILEDP (fun)) 3149 else if (COMPILEDP (fun))
3155 { 3150 {
3156 ptrdiff_t size = PVSIZE (fun);
3157 if (size <= COMPILED_STACK_DEPTH)
3158 xsignal1 (Qinvalid_function, fun);
3159 syms_left = AREF (fun, COMPILED_ARGLIST); 3151 syms_left = AREF (fun, COMPILED_ARGLIST);
3160 if (FIXNUMP (syms_left)) 3152 if (FIXNUMP (syms_left))
3161 return get_byte_code_arity (syms_left); 3153 return get_byte_code_arity (syms_left);
@@ -3198,13 +3190,11 @@ DEFUN ("fetch-bytecode", Ffetch_bytecode, Sfetch_bytecode,
3198 3190
3199 if (COMPILEDP (object)) 3191 if (COMPILEDP (object))
3200 { 3192 {
3201 ptrdiff_t size = PVSIZE (object);
3202 if (size <= COMPILED_STACK_DEPTH)
3203 xsignal1 (Qinvalid_function, object);
3204 if (CONSP (AREF (object, COMPILED_BYTECODE))) 3193 if (CONSP (AREF (object, COMPILED_BYTECODE)))
3205 { 3194 {
3206 tem = read_doc_string (AREF (object, COMPILED_BYTECODE)); 3195 tem = read_doc_string (AREF (object, COMPILED_BYTECODE));
3207 if (!CONSP (tem)) 3196 if (! (CONSP (tem) && STRINGP (XCAR (tem))
3197 && VECTORP (XCDR (tem))))
3208 { 3198 {
3209 tem = AREF (object, COMPILED_BYTECODE); 3199 tem = AREF (object, COMPILED_BYTECODE);
3210 if (CONSP (tem) && STRINGP (XCAR (tem))) 3200 if (CONSP (tem) && STRINGP (XCAR (tem)))