From: Noam Postavsky Date: Fri, 24 Nov 2017 02:57:09 +0000 (-0500) Subject: Fix command repetition with lexical-binding (Bug#29334) X-Git-Tag: emacs-27.0.90~5936 X-Git-Url: http://git.eshelyaron.com/gitweb/?a=commitdiff_plain;h=ce48658191befb7734a7af484e368af5ed8b9447;p=emacs.git Fix command repetition with lexical-binding (Bug#29334) `call-interactively' relies on analyzing the source of `interactive' forms in order to preserve arguments like (region-end) in the command history, rather than just storing the resulting position. However, the byte-compiler does not preserve the source of the interactive form when lexical-binding is in effect, because `call-interactively' would evaluate the form with dynamic binding in that case. To fix this, change `call-interactively' so that it checks compiled functions for lexical-binding as well. Then the byte-compiler can preserve the source of interactive forms regardless of the value of lexical-binding. * src/callint.c (Fcall_interactively): Functions compiled with lexical-binding have their arglist encoded as an integer, use this to choose the right kind of binding for compiled functions too. * lisp/emacs-lisp/bytecomp.el (byte-compile-lambda): Preserve the uncompiled form of the interactive form when lexical-binding is enabled too. --- diff --git a/lisp/emacs-lisp/bytecomp.el b/lisp/emacs-lisp/bytecomp.el index 2f5f9f8c054..564aac2fc6a 100644 --- a/lisp/emacs-lisp/bytecomp.el +++ b/lisp/emacs-lisp/bytecomp.el @@ -2839,11 +2839,7 @@ for symbols generated by the byte compiler itself." (while (consp (cdr form)) (setq form (cdr form))) (setq form (car form))) - (if (and (eq (car-safe form) 'list) - ;; The spec is evalled in callint.c in dynamic-scoping - ;; mode, so just leaving the form unchanged would mean - ;; it won't be eval'd in the right mode. - (not lexical-binding)) + (if (eq (car-safe form) 'list) nil (setq int `(interactive ,newform))))) ((cdr int) diff --git a/src/callint.c b/src/callint.c index c713e08d4d4..dcda0bcf7a0 100644 --- a/src/callint.c +++ b/src/callint.c @@ -357,7 +357,9 @@ invoke it. If KEYS is omitted or nil, the return value of /* Compute the arg values using the user's expression. */ specs = Feval (specs, CONSP (funval) && EQ (Qclosure, XCAR (funval)) - ? CAR_SAFE (XCDR (funval)) : Qnil); + ? CAR_SAFE (XCDR (funval)) + : COMPILEDP (funval) && INTEGERP (AREF (funval, COMPILED_ARGLIST)) + ? Qt : Qnil); if (events != num_input_events || !NILP (record_flag)) { /* We should record this command on the command history. */