aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorStefan Monnier2012-07-25 21:27:33 -0400
committerStefan Monnier2012-07-25 21:27:33 -0400
commit7abaf5ccc9f11e657b6671e7a6d5a7533bba5f31 (patch)
tree26a250aef4c762d2128fb99c7442d01cedbd208b
parentb1364986cb927ca113b0447a66a5274221ad9100 (diff)
downloademacs-7abaf5ccc9f11e657b6671e7a6d5a7533bba5f31.tar.gz
emacs-7abaf5ccc9f11e657b6671e7a6d5a7533bba5f31.zip
Autoload more carefully from Lisp. Follow aliases for function properties.
* lisp/subr.el (autoloadp): New function. (symbol-file): Use it. (function-get): New function. * lisp/emacs-lisp/macroexp.el (macroexp--expand-all): Use function-get and autoload-do-load. * lisp/emacs-lisp/lisp-mode.el (lisp-font-lock-syntactic-face-function) (lisp-indent-function): * lisp/emacs-lisp/gv.el (gv-get): * lisp/emacs-lisp/edebug.el (get-edebug-spec, edebug-basic-spec): * lisp/emacs-lisp/byte-opt.el (byte-optimize-form): * lisp/emacs-lisp/bytecomp.el (byte-compile-arglist-warn): * lisp/emacs-lisp/autoload.el (make-autoload, autoload-print-form): Use function-get. * lisp/emacs-lisp/cl.el: Don't propagate function properties any more. * src/eval.c (Fautoload_do_load): Rename from do_autoload, export to Lisp, add argument, tune behavior, and adjust all callers. * lisp/speedbar.el (speedbar-add-localized-speedbar-support): * lisp/emacs-lisp/disass.el (disassemble-internal): * lisp/desktop.el (desktop-load-file): * lisp/help-fns.el (help-function-arglist, find-lisp-object-file-name) (describe-function-1): * lisp/emacs-lisp/find-func.el (find-function-noselect): * lisp/emacs-lisp/elp.el (elp-instrument-function): * lisp/emacs-lisp/advice.el (ad-has-proper-definition): * lisp/apropos.el (apropos-safe-documentation, apropos-macrop): * lisp/emacs-lisp/debug.el (debug-on-entry): * lisp/emacs-lisp/cl-macs.el (cl-compiler-macroexpand): * lisp/emacs-lisp/byte-opt.el (byte-compile-inline-expand): * lisp/calc/calc.el (name): Use autoloadp & autoload-do-load.
-rw-r--r--etc/NEWS4
-rw-r--r--lisp/ChangeLog34
-rw-r--r--lisp/apropos.el4
-rw-r--r--lisp/calc/calc.el2
-rw-r--r--lisp/desktop.el7
-rw-r--r--lisp/emacs-lisp/advice.el2
-rw-r--r--lisp/emacs-lisp/autoload.el28
-rw-r--r--lisp/emacs-lisp/byte-opt.el13
-rw-r--r--lisp/emacs-lisp/bytecomp.el2
-rw-r--r--lisp/emacs-lisp/cl-macs.el4
-rw-r--r--lisp/emacs-lisp/cl.el11
-rw-r--r--lisp/emacs-lisp/debug.el4
-rw-r--r--lisp/emacs-lisp/disass.el8
-rw-r--r--lisp/emacs-lisp/edebug.el13
-rw-r--r--lisp/emacs-lisp/elp.el2
-rw-r--r--lisp/emacs-lisp/find-func.el3
-rw-r--r--lisp/emacs-lisp/gv.el9
-rw-r--r--lisp/emacs-lisp/lisp-mode.el6
-rw-r--r--lisp/emacs-lisp/macroexp.el14
-rw-r--r--lisp/emacs-lisp/pcase.el3
-rw-r--r--lisp/help-fns.el8
-rw-r--r--lisp/speedbar.el4
-rw-r--r--lisp/subr.el33
-rw-r--r--src/ChangeLog5
-rw-r--r--src/data.c4
-rw-r--r--src/eval.c78
-rw-r--r--src/keyboard.c10
-rw-r--r--src/keymap.c4
-rw-r--r--src/lisp.h7
29 files changed, 190 insertions, 136 deletions
diff --git a/etc/NEWS b/etc/NEWS
index 0f903c790c2..ce44a530e26 100644
--- a/etc/NEWS
+++ b/etc/NEWS
@@ -498,6 +498,10 @@ still be supported for Emacs 24.x.
498 498
499* Lisp changes in Emacs 24.2 499* Lisp changes in Emacs 24.2
500 500
501** New functions `autoloadp' and `autoload-do-load'.
502
503** `function-get' fetches the property of a function, following aliases.
504
501** `toggle-read-only' accepts a second argument specifying whether to 505** `toggle-read-only' accepts a second argument specifying whether to
502print a message, if called from Lisp. 506print a message, if called from Lisp.
503 507
diff --git a/lisp/ChangeLog b/lisp/ChangeLog
index 1d4baa8b054..40cded6f9cc 100644
--- a/lisp/ChangeLog
+++ b/lisp/ChangeLog
@@ -1,3 +1,37 @@
12012-07-26 Stefan Monnier <monnier@iro.umontreal.ca>
2
3 Autoload from Lisp with more care. Follow aliases when looking for
4 function properties.
5 * subr.el (autoloadp): New function.
6 (symbol-file): Use it.
7 (function-get): New function.
8 * emacs-lisp/macroexp.el (macroexp--expand-all): Use function-get and
9 autoload-do-load.
10 * emacs-lisp/lisp-mode.el (lisp-font-lock-syntactic-face-function)
11 (lisp-indent-function):
12 * emacs-lisp/gv.el (gv-get):
13 * emacs-lisp/edebug.el (get-edebug-spec, edebug-basic-spec):
14 * emacs-lisp/byte-opt.el (byte-optimize-form):
15 * emacs-lisp/bytecomp.el (byte-compile-arglist-warn):
16 * emacs-lisp/autoload.el (make-autoload, autoload-print-form):
17 Use function-get.
18 * emacs-lisp/cl.el: Don't propagate function properties any more.
19
20 * speedbar.el (speedbar-add-localized-speedbar-support):
21 * emacs-lisp/disass.el (disassemble-internal):
22 * desktop.el (desktop-load-file):
23 * help-fns.el (help-function-arglist, find-lisp-object-file-name)
24 (describe-function-1):
25 * emacs-lisp/find-func.el (find-function-noselect):
26 * emacs-lisp/elp.el (elp-instrument-function):
27 * emacs-lisp/advice.el (ad-has-proper-definition):
28 * apropos.el (apropos-safe-documentation, apropos-macrop):
29 * emacs-lisp/debug.el (debug-on-entry):
30 * emacs-lisp/cl-macs.el (cl-compiler-macroexpand):
31 * emacs-lisp/byte-opt.el (byte-compile-inline-expand):
32 * calc/calc.el (name): Use autoloadp & autoload-do-load.
33
34
12012-07-25 Alp Aker <alp.tekin.aker@gmail.com> 352012-07-25 Alp Aker <alp.tekin.aker@gmail.com>
2 36
3 * international/mule-cmds.el (ucs-insert): Mark it as an obsolete 37 * international/mule-cmds.el (ucs-insert): Mark it as an obsolete
diff --git a/lisp/apropos.el b/lisp/apropos.el
index e1c3e06752d..6c6e3b325e8 100644
--- a/lisp/apropos.el
+++ b/lisp/apropos.el
@@ -980,7 +980,7 @@ Will return nil instead."
980 (setq function (if (byte-code-function-p function) 980 (setq function (if (byte-code-function-p function)
981 (if (> (length function) 4) 981 (if (> (length function) 4)
982 (aref function 4)) 982 (aref function 4))
983 (if (eq (car-safe function) 'autoload) 983 (if (autoloadp function)
984 (nth 2 function) 984 (nth 2 function)
985 (if (eq (car-safe function) 'lambda) 985 (if (eq (car-safe function) 'lambda)
986 (if (stringp (nth 2 function)) 986 (if (stringp (nth 2 function))
@@ -1114,7 +1114,7 @@ If non-nil TEXT is a string that will be printed as a heading."
1114 (consp (setq symbol 1114 (consp (setq symbol
1115 (symbol-function symbol))) 1115 (symbol-function symbol)))
1116 (or (eq (car symbol) 'macro) 1116 (or (eq (car symbol) 'macro)
1117 (if (eq (car symbol) 'autoload) 1117 (if (autoloadp symbol)
1118 (memq (nth 4 symbol) 1118 (memq (nth 4 symbol)
1119 '(macro t)))))) 1119 '(macro t))))))
1120 1120
diff --git a/lisp/calc/calc.el b/lisp/calc/calc.el
index 4d64209dd36..7fb9148535a 100644
--- a/lisp/calc/calc.el
+++ b/lisp/calc/calc.el
@@ -914,7 +914,7 @@ Used by `calc-user-invocation'.")
914 914
915;; Set up the autoloading linkage. 915;; Set up the autoloading linkage.
916(let ((name (and (fboundp 'calc-dispatch) 916(let ((name (and (fboundp 'calc-dispatch)
917 (eq (car-safe (symbol-function 'calc-dispatch)) 'autoload) 917 (autoloadp (symbol-function 'calc-dispatch))
918 (nth 1 (symbol-function 'calc-dispatch)))) 918 (nth 1 (symbol-function 'calc-dispatch))))
919 (p load-path)) 919 (p load-path))
920 920
diff --git a/lisp/desktop.el b/lisp/desktop.el
index 2c2106e18b7..a873a6b63bf 100644
--- a/lisp/desktop.el
+++ b/lisp/desktop.el
@@ -1119,11 +1119,8 @@ directory DIRNAME."
1119 1119
1120(defun desktop-load-file (function) 1120(defun desktop-load-file (function)
1121 "Load the file where auto loaded FUNCTION is defined." 1121 "Load the file where auto loaded FUNCTION is defined."
1122 (when function 1122 (when (fboundp function)
1123 (let ((fcell (and (fboundp function) (symbol-function function)))) 1123 (autoload-do-load (symbol-function function) function)))
1124 (when (and (listp fcell)
1125 (eq 'autoload (car fcell)))
1126 (load (cadr fcell))))))
1127 1124
1128;; ---------------------------------------------------------------------------- 1125;; ----------------------------------------------------------------------------
1129;; Create a buffer, load its file, set its mode, ...; 1126;; Create a buffer, load its file, set its mode, ...;
diff --git a/lisp/emacs-lisp/advice.el b/lisp/emacs-lisp/advice.el
index 09dde2c1c17..cac76d2bce1 100644
--- a/lisp/emacs-lisp/advice.el
+++ b/lisp/emacs-lisp/advice.el
@@ -2542,7 +2542,7 @@ definition (see the code for `documentation')."
2542For that it has to be fbound with a non-autoload definition." 2542For that it has to be fbound with a non-autoload definition."
2543 (and (symbolp function) 2543 (and (symbolp function)
2544 (fboundp function) 2544 (fboundp function)
2545 (not (eq (car-safe (symbol-function function)) 'autoload)))) 2545 (not (autoloadp (symbol-function function)))))
2546 2546
2547;; The following two are necessary for the sake of packages such as 2547;; The following two are necessary for the sake of packages such as
2548;; ange-ftp which redefine functions via fcell indirection: 2548;; ange-ftp which redefine functions via fcell indirection:
diff --git a/lisp/emacs-lisp/autoload.el b/lisp/emacs-lisp/autoload.el
index 1bdd6d8fc4b..3fc185dda25 100644
--- a/lisp/emacs-lisp/autoload.el
+++ b/lisp/emacs-lisp/autoload.el
@@ -163,23 +163,23 @@ expression, in which case we want to handle forms differently."
163 ((or `define-generic-mode `define-derived-mode 163 ((or `define-generic-mode `define-derived-mode
164 `define-compilation-mode) nil) 164 `define-compilation-mode) nil)
165 (_ t))) 165 (_ t)))
166 (body (nthcdr (or (get car 'doc-string-elt) 3) form)) 166 (body (nthcdr (or (function-get car 'doc-string-elt) 3) form))
167 (doc (if (stringp (car body)) (pop body)))) 167 (doc (if (stringp (car body)) (pop body))))
168 ;; Add the usage form at the end where describe-function-1 168 ;; Add the usage form at the end where describe-function-1
169 ;; can recover it. 169 ;; can recover it.
170 (when (listp args) (setq doc (help-add-fundoc-usage doc args))) 170 (when (listp args) (setq doc (help-add-fundoc-usage doc args)))
171 ;; `define-generic-mode' quotes the name, so take care of that 171 ;; `define-generic-mode' quotes the name, so take care of that
172 (list 'autoload (if (listp name) name (list 'quote name)) 172 `(autoload ,(if (listp name) name (list 'quote name))
173 file doc 173 ,file ,doc
174 (or (and (memq car '(define-skeleton define-derived-mode 174 ,(or (and (memq car '(define-skeleton define-derived-mode
175 define-generic-mode 175 define-generic-mode
176 easy-mmode-define-global-mode 176 easy-mmode-define-global-mode
177 define-global-minor-mode 177 define-global-minor-mode
178 define-globalized-minor-mode 178 define-globalized-minor-mode
179 easy-mmode-define-minor-mode 179 easy-mmode-define-minor-mode
180 define-minor-mode)) t) 180 define-minor-mode)) t)
181 (eq (car-safe (car body)) 'interactive)) 181 (eq (car-safe (car body)) 'interactive))
182 (if macrop (list 'quote 'macro) nil)))) 182 ,(if macrop ''macro nil))))
183 183
184 ;; For defclass forms, use `eieio-defclass-autoload'. 184 ;; For defclass forms, use `eieio-defclass-autoload'.
185 ((eq car 'defclass) 185 ((eq car 'defclass)
@@ -277,7 +277,7 @@ put the output in."
277 ;; Symbols at the toplevel are meaningless. 277 ;; Symbols at the toplevel are meaningless.
278 ((symbolp form) nil) 278 ((symbolp form) nil)
279 (t 279 (t
280 (let ((doc-string-elt (get (car-safe form) 'doc-string-elt)) 280 (let ((doc-string-elt (function-get (car-safe form) 'doc-string-elt))
281 (outbuf autoload-print-form-outbuf)) 281 (outbuf autoload-print-form-outbuf))
282 (if (and doc-string-elt (stringp (nth doc-string-elt form))) 282 (if (and doc-string-elt (stringp (nth doc-string-elt form)))
283 ;; We need to hack the printing because the 283 ;; We need to hack the printing because the
@@ -356,7 +356,7 @@ not be relied upon."
356 "Insert the section-header line, 356 "Insert the section-header line,
357which lists the file name and which functions are in it, etc." 357which lists the file name and which functions are in it, etc."
358 (insert generate-autoload-section-header) 358 (insert generate-autoload-section-header)
359 (prin1 (list 'autoloads autoloads load-name file time) 359 (prin1 `(autoloads ,autoloads ,load-name ,file ,time)
360 outbuf) 360 outbuf)
361 (terpri outbuf) 361 (terpri outbuf)
362 ;; Break that line at spaces, to avoid very long lines. 362 ;; Break that line at spaces, to avoid very long lines.
diff --git a/lisp/emacs-lisp/byte-opt.el b/lisp/emacs-lisp/byte-opt.el
index 5a3fd7dddb1..a4c3e8aac4e 100644
--- a/lisp/emacs-lisp/byte-opt.el
+++ b/lisp/emacs-lisp/byte-opt.el
@@ -249,8 +249,8 @@
249 (let* ((name (car form)) 249 (let* ((name (car form))
250 (localfn (cdr (assq name byte-compile-function-environment))) 250 (localfn (cdr (assq name byte-compile-function-environment)))
251 (fn (or localfn (and (fboundp name) (symbol-function name))))) 251 (fn (or localfn (and (fboundp name) (symbol-function name)))))
252 (when (and (consp fn) (eq (car fn) 'autoload)) 252 (when (autoloadp fn)
253 (load (nth 1 fn)) 253 (autoload-do-load fn)
254 (setq fn (or (and (fboundp name) (symbol-function name)) 254 (setq fn (or (and (fboundp name) (symbol-function name))
255 (cdr (assq name byte-compile-function-environment))))) 255 (cdr (assq name byte-compile-function-environment)))))
256 (pcase fn 256 (pcase fn
@@ -586,10 +586,11 @@
586 (let (opt new) 586 (let (opt new)
587 (if (and (consp form) 587 (if (and (consp form)
588 (symbolp (car form)) 588 (symbolp (car form))
589 (or (and for-effect 589 (or ;; (and for-effect
590 ;; we don't have any of these yet, but we might. 590 ;; ;; We don't have any of these yet, but we might.
591 (setq opt (get (car form) 'byte-for-effect-optimizer))) 591 ;; (setq opt (get (car form)
592 (setq opt (get (car form) 'byte-optimizer))) 592 ;; 'byte-for-effect-optimizer)))
593 (setq opt (function-get (car form) 'byte-optimizer)))
593 (not (eq form (setq new (funcall opt form))))) 594 (not (eq form (setq new (funcall opt form)))))
594 (progn 595 (progn
595;; (if (equal form new) (error "bogus optimizer -- %s" opt)) 596;; (if (equal form new) (error "bogus optimizer -- %s" opt))
diff --git a/lisp/emacs-lisp/bytecomp.el b/lisp/emacs-lisp/bytecomp.el
index 97d7ab924ed..e5df8dd112c 100644
--- a/lisp/emacs-lisp/bytecomp.el
+++ b/lisp/emacs-lisp/bytecomp.el
@@ -1355,7 +1355,7 @@ extra args."
1355 nums sig min max) 1355 nums sig min max)
1356 (when calls 1356 (when calls
1357 (when (and (symbolp name) 1357 (when (and (symbolp name)
1358 (eq (get name 'byte-optimizer) 1358 (eq (function-get name 'byte-optimizer)
1359 'byte-compile-inline-expand)) 1359 'byte-compile-inline-expand))
1360 (byte-compile-warn "defsubst `%s' was used before it was defined" 1360 (byte-compile-warn "defsubst `%s' was used before it was defined"
1361 name)) 1361 name))
diff --git a/lisp/emacs-lisp/cl-macs.el b/lisp/emacs-lisp/cl-macs.el
index 70d907a14c1..00ba6b9e0d0 100644
--- a/lisp/emacs-lisp/cl-macs.el
+++ b/lisp/emacs-lisp/cl-macs.el
@@ -2420,8 +2420,8 @@ and then returning foo."
2420 (while (and (symbolp func) 2420 (while (and (symbolp func)
2421 (not (setq handler (get func 'compiler-macro))) 2421 (not (setq handler (get func 'compiler-macro)))
2422 (fboundp func) 2422 (fboundp func)
2423 (or (not (eq (car-safe (symbol-function func)) 'autoload)) 2423 (or (not (autoloadp (symbol-function func)))
2424 (load (nth 1 (symbol-function func))))) 2424 (autoload-do-load (symbol-function func) func)))
2425 (setq func (symbol-function func))) 2425 (setq func (symbol-function func)))
2426 (and handler 2426 (and handler
2427 (not (eq form (setq form (apply handler form (cdr form)))))))) 2427 (not (eq form (setq form (apply handler form (cdr form))))))))
diff --git a/lisp/emacs-lisp/cl.el b/lisp/emacs-lisp/cl.el
index 32cf1670744..8174de786c7 100644
--- a/lisp/emacs-lisp/cl.el
+++ b/lisp/emacs-lisp/cl.el
@@ -320,16 +320,7 @@
320 )) 320 ))
321 (let ((new (if (consp fun) (prog1 (cdr fun) (setq fun (car fun))) 321 (let ((new (if (consp fun) (prog1 (cdr fun) (setq fun (car fun)))
322 (intern (format "cl-%s" fun))))) 322 (intern (format "cl-%s" fun)))))
323 (defalias fun new) 323 (defalias fun new)))
324 ;; If `cl-foo' is declare inline, then make `foo' inline as well, and
325 ;; similarly. Same for edebug specifications, indent rules and
326 ;; doc-string position.
327 ;; FIXME: For most of them, we should instead follow aliases
328 ;; where applicable.
329 (dolist (prop '(byte-optimizer doc-string-elt edebug-form-spec
330 lisp-indent-function))
331 (if (get new prop)
332 (put fun prop (get new prop))))))
333 324
334;;; Features provided a bit differently in Elisp. 325;;; Features provided a bit differently in Elisp.
335 326
diff --git a/lisp/emacs-lisp/debug.el b/lisp/emacs-lisp/debug.el
index b0813aebef6..7bc93a19d1a 100644
--- a/lisp/emacs-lisp/debug.el
+++ b/lisp/emacs-lisp/debug.el
@@ -805,9 +805,9 @@ Redefining FUNCTION also cancels it."
805 ,(interactive-form (symbol-function function)) 805 ,(interactive-form (symbol-function function))
806 (apply ',(symbol-function function) 806 (apply ',(symbol-function function)
807 debug-on-entry-args))) 807 debug-on-entry-args)))
808 (when (eq (car-safe (symbol-function function)) 'autoload) 808 (when (autoloadp (symbol-function function))
809 ;; The function is autoloaded. Load its real definition. 809 ;; The function is autoloaded. Load its real definition.
810 (load (cadr (symbol-function function)) nil noninteractive nil t)) 810 (autoload-do-load (symbol-function function) function))
811 (when (or (not (consp (symbol-function function))) 811 (when (or (not (consp (symbol-function function)))
812 (and (eq (car (symbol-function function)) 'macro) 812 (and (eq (car (symbol-function function)) 'macro)
813 (not (consp (cdr (symbol-function function)))))) 813 (not (consp (cdr (symbol-function function))))))
diff --git a/lisp/emacs-lisp/disass.el b/lisp/emacs-lisp/disass.el
index ba720b42868..206166bc77a 100644
--- a/lisp/emacs-lisp/disass.el
+++ b/lisp/emacs-lisp/disass.el
@@ -80,14 +80,10 @@ redefine OBJECT if it is a symbol."
80 obj (symbol-function obj))) 80 obj (symbol-function obj)))
81 (if (subrp obj) 81 (if (subrp obj)
82 (error "Can't disassemble #<subr %s>" name)) 82 (error "Can't disassemble #<subr %s>" name))
83 (when (and (listp obj) (eq (car obj) 'autoload)) 83 (setq obj (autoload-do-load obj name))
84 (load (nth 1 obj)) 84 (if (eq (car-safe obj) 'macro) ;Handle macros.
85 (setq obj (symbol-function name)))
86 (if (eq (car-safe obj) 'macro) ;handle macros
87 (setq macro t 85 (setq macro t
88 obj (cdr obj))) 86 obj (cdr obj)))
89 (when (and (listp obj) (eq (car obj) 'closure))
90 (error "Don't know how to compile an interpreted closure"))
91 (if (and (listp obj) (eq (car obj) 'byte-code)) 87 (if (and (listp obj) (eq (car obj) 'byte-code))
92 (setq obj (list 'lambda nil obj))) 88 (setq obj (list 'lambda nil obj)))
93 (if (and (listp obj) (not (eq (car obj) 'lambda))) 89 (if (and (listp obj) (not (eq (car obj) 'lambda)))
diff --git a/lisp/emacs-lisp/edebug.el b/lisp/emacs-lisp/edebug.el
index c1c65b6f661..bbf0757c3bc 100644
--- a/lisp/emacs-lisp/edebug.el
+++ b/lisp/emacs-lisp/edebug.el
@@ -242,10 +242,13 @@ If the result is non-nil, then break. Errors are ignored."
242 242
243(defun get-edebug-spec (symbol) 243(defun get-edebug-spec (symbol)
244 ;; Get the spec of symbol resolving all indirection. 244 ;; Get the spec of symbol resolving all indirection.
245 (let ((edebug-form-spec (get symbol 'edebug-form-spec)) 245 (let ((edebug-form-spec nil)
246 indirect) 246 (indirect symbol))
247 (while (and (symbolp edebug-form-spec) 247 (while
248 (setq indirect (get edebug-form-spec 'edebug-form-spec))) 248 (progn
249 (and (symbolp indirect)
250 (setq indirect
251 (function-get indirect 'edebug-form-spec 'autoload))))
249 ;; (edebug-trace "indirection: %s" edebug-form-spec) 252 ;; (edebug-trace "indirection: %s" edebug-form-spec)
250 (setq edebug-form-spec indirect)) 253 (setq edebug-form-spec indirect))
251 edebug-form-spec 254 edebug-form-spec
@@ -263,7 +266,7 @@ An extant spec symbol is a symbol that is not a function and has a
263 (setq spec (cdr spec))) 266 (setq spec (cdr spec)))
264 t)) 267 t))
265 ((symbolp spec) 268 ((symbolp spec)
266 (unless (functionp spec) (get spec 'edebug-form-spec))))) 269 (unless (functionp spec) (function-get spec 'edebug-form-spec)))))
267 270
268;;; Utilities 271;;; Utilities
269 272
diff --git a/lisp/emacs-lisp/elp.el b/lisp/emacs-lisp/elp.el
index 08390327414..b94817cdb02 100644
--- a/lisp/emacs-lisp/elp.el
+++ b/lisp/emacs-lisp/elp.el
@@ -258,7 +258,7 @@ FUNSYM must be a symbol of a defined function."
258 ;; the autoload here, since that could have side effects, and 258 ;; the autoload here, since that could have side effects, and
259 ;; elp-instrument-function is similar (in my mind) to defun-ish 259 ;; elp-instrument-function is similar (in my mind) to defun-ish
260 ;; type functionality (i.e. it shouldn't execute the function). 260 ;; type functionality (i.e. it shouldn't execute the function).
261 (and (eq (car-safe funguts) 'autoload) 261 (and (autoloadp funguts)
262 (error "ELP cannot profile autoloaded function: %s" funsym)) 262 (error "ELP cannot profile autoloaded function: %s" funsym))
263 ;; We cannot profile functions used internally during profiling. 263 ;; We cannot profile functions used internally during profiling.
264 (unless (elp-profilable-p funsym) 264 (unless (elp-profilable-p funsym)
diff --git a/lisp/emacs-lisp/find-func.el b/lisp/emacs-lisp/find-func.el
index d64281d0e81..e1e153d9117 100644
--- a/lisp/emacs-lisp/find-func.el
+++ b/lisp/emacs-lisp/find-func.el
@@ -347,8 +347,7 @@ in `load-path'."
347 (if aliases 347 (if aliases
348 (message "%s" aliases)) 348 (message "%s" aliases))
349 (let ((library 349 (let ((library
350 (cond ((eq (car-safe def) 'autoload) 350 (cond ((autoloadp def) (nth 1 def))
351 (nth 1 def))
352 ((subrp def) 351 ((subrp def)
353 (if lisp-only 352 (if lisp-only
354 (error "%s is a built-in function" function)) 353 (error "%s is a built-in function" function))
diff --git a/lisp/emacs-lisp/gv.el b/lisp/emacs-lisp/gv.el
index eb0e64e22b8..d1f997c99c4 100644
--- a/lisp/emacs-lisp/gv.el
+++ b/lisp/emacs-lisp/gv.el
@@ -84,14 +84,7 @@ DO must return an Elisp expression."
84 (if (symbolp place) 84 (if (symbolp place)
85 (funcall do place (lambda (v) `(setq ,place ,v))) 85 (funcall do place (lambda (v) `(setq ,place ,v)))
86 (let* ((head (car place)) 86 (let* ((head (car place))
87 (gf (get head 'gv-expander))) 87 (gf (function-get head 'gv-expander 'autoload)))
88 ;; Autoload the head, if applicable, since that might define
89 ;; `gv-expander'.
90 (when (and (null gf) (fboundp head)
91 (eq 'autoload (car-safe (symbol-function head))))
92 (with-demoted-errors
93 (load (nth 1 (symbol-function head)) 'noerror 'nomsg)
94 (setq gf (get head 'gv-expander))))
95 (if gf (apply gf do (cdr place)) 88 (if gf (apply gf do (cdr place))
96 (let ((me (macroexpand place ;FIXME: expand one step at a time! 89 (let ((me (macroexpand place ;FIXME: expand one step at a time!
97 ;; (append macroexpand-all-environment 90 ;; (append macroexpand-all-environment
diff --git a/lisp/emacs-lisp/lisp-mode.el b/lisp/emacs-lisp/lisp-mode.el
index 350b0bd949d..e29407f5a8b 100644
--- a/lisp/emacs-lisp/lisp-mode.el
+++ b/lisp/emacs-lisp/lisp-mode.el
@@ -158,7 +158,8 @@ It has `lisp-mode-abbrev-table' as its parent."
158 (goto-char listbeg) 158 (goto-char listbeg)
159 (and (looking-at "([ \t\n]*\\(\\(\\sw\\|\\s_\\)+\\)") 159 (and (looking-at "([ \t\n]*\\(\\(\\sw\\|\\s_\\)+\\)")
160 (match-string 1))))) 160 (match-string 1)))))
161 (docelt (and firstsym (get (intern-soft firstsym) 161 (docelt (and firstsym
162 (function-get (intern-soft firstsym)
162 lisp-doc-string-elt-property)))) 163 lisp-doc-string-elt-property))))
163 (if (and docelt 164 (if (and docelt
164 ;; It's a string in a form that can have a docstring. 165 ;; It's a string in a form that can have a docstring.
@@ -1135,7 +1136,8 @@ Lisp function does not specify a special indentation."
1135 (let ((function (buffer-substring (point) 1136 (let ((function (buffer-substring (point)
1136 (progn (forward-sexp 1) (point)))) 1137 (progn (forward-sexp 1) (point))))
1137 method) 1138 method)
1138 (setq method (or (get (intern-soft function) 'lisp-indent-function) 1139 (setq method (or (function-get (intern-soft function)
1140 'lisp-indent-function)
1139 (get (intern-soft function) 'lisp-indent-hook))) 1141 (get (intern-soft function) 'lisp-indent-hook)))
1140 (cond ((or (eq method 'defun) 1142 (cond ((or (eq method 'defun)
1141 (and (null method) 1143 (and (null method)
diff --git a/lisp/emacs-lisp/macroexp.el b/lisp/emacs-lisp/macroexp.el
index 65a72aa5312..70eab149837 100644
--- a/lisp/emacs-lisp/macroexp.el
+++ b/lisp/emacs-lisp/macroexp.el
@@ -185,12 +185,7 @@ Assumes the caller has bound `macroexpand-all-environment'."
185 ;; Macro expand compiler macros. This cannot be delayed to 185 ;; Macro expand compiler macros. This cannot be delayed to
186 ;; byte-optimize-form because the output of the compiler-macro can 186 ;; byte-optimize-form because the output of the compiler-macro can
187 ;; use macros. 187 ;; use macros.
188 (let ((handler nil)) 188 (let ((handler (function-get func 'compiler-macro)))
189 (while (and (symbolp func)
190 (not (setq handler (get func 'compiler-macro)))
191 (fboundp func))
192 ;; Follow the sequence of aliases.
193 (setq func (symbol-function func)))
194 (if (null handler) 189 (if (null handler)
195 ;; No compiler macro. We just expand each argument (for 190 ;; No compiler macro. We just expand each argument (for
196 ;; setq/setq-default this works alright because the variable names 191 ;; setq/setq-default this works alright because the variable names
@@ -198,12 +193,9 @@ Assumes the caller has bound `macroexpand-all-environment'."
198 (macroexp--all-forms form 1) 193 (macroexp--all-forms form 1)
199 ;; If the handler is not loaded yet, try (auto)loading the 194 ;; If the handler is not loaded yet, try (auto)loading the
200 ;; function itself, which may in turn load the handler. 195 ;; function itself, which may in turn load the handler.
201 (when (and (not (functionp handler)) 196 (unless (functionp handler)
202 (fboundp func) (eq (car-safe (symbol-function func))
203 'autoload))
204 (ignore-errors 197 (ignore-errors
205 (load (nth 1 (symbol-function func)) 198 (autoload-do-load (indirect-function func) func)))
206 'noerror 'nomsg)))
207 (let ((newform (macroexp--compiler-macro handler form))) 199 (let ((newform (macroexp--compiler-macro handler form)))
208 (if (eq form newform) 200 (if (eq form newform)
209 ;; The compiler macro did not find anything to do. 201 ;; The compiler macro did not find anything to do.
diff --git a/lisp/emacs-lisp/pcase.el b/lisp/emacs-lisp/pcase.el
index 3f4ce605cb0..4aeed7e4d0e 100644
--- a/lisp/emacs-lisp/pcase.el
+++ b/lisp/emacs-lisp/pcase.el
@@ -114,7 +114,8 @@ QPatterns for vectors are not implemented yet.
114 114
115PRED can take the form 115PRED can take the form
116 FUNCTION in which case it gets called with one argument. 116 FUNCTION in which case it gets called with one argument.
117 (FUN ARG1 .. ARGN) in which case it gets called with N+1 arguments. 117 (FUN ARG1 .. ARGN) in which case it gets called with an N+1'th argument
118 which is the value being matched.
118A PRED of the form FUNCTION is equivalent to one of the form (FUNCTION). 119A PRED of the form FUNCTION is equivalent to one of the form (FUNCTION).
119PRED patterns can refer to variables bound earlier in the pattern. 120PRED patterns can refer to variables bound earlier in the pattern.
120E.g. you can match pairs where the cdr is larger than the car with a pattern 121E.g. you can match pairs where the cdr is larger than the car with a pattern
diff --git a/lisp/help-fns.el b/lisp/help-fns.el
index 2e56da0bcaa..f585bff871f 100644
--- a/lisp/help-fns.el
+++ b/lisp/help-fns.el
@@ -150,7 +150,7 @@ the same names as used in the original source code, when possible."
150 arglist))) 150 arglist)))
151 (unless (zerop rest) (push '&rest arglist) (push 'rest arglist)) 151 (unless (zerop rest) (push '&rest arglist) (push 'rest arglist))
152 (nreverse arglist)))) 152 (nreverse arglist))))
153 ((and (eq (car-safe def) 'autoload) (not (eq (nth 4 def) 'keymap))) 153 ((and (autoloadp def) (not (eq (nth 4 def) 'keymap)))
154 "[Arg list not available until function definition is loaded.]") 154 "[Arg list not available until function definition is loaded.]")
155 (t t))) 155 (t t)))
156 156
@@ -288,7 +288,7 @@ defined. If several such files exist, preference is given to a file
288found via `load-path'. The return value can also be `C-source', which 288found via `load-path'. The return value can also be `C-source', which
289means that OBJECT is a function or variable defined in C. If no 289means that OBJECT is a function or variable defined in C. If no
290suitable file is found, return nil." 290suitable file is found, return nil."
291 (let* ((autoloaded (eq (car-safe type) 'autoload)) 291 (let* ((autoloaded (autoloadp type))
292 (file-name (or (and autoloaded (nth 1 type)) 292 (file-name (or (and autoloaded (nth 1 type))
293 (symbol-file 293 (symbol-file
294 object (if (memq type (list 'defvar 'defface)) 294 object (if (memq type (list 'defvar 'defface))
@@ -468,7 +468,7 @@ FILE is the file where FUNCTION was probably defined."
468 (concat beg "Lisp macro")) 468 (concat beg "Lisp macro"))
469 ((eq (car-safe def) 'closure) 469 ((eq (car-safe def) 'closure)
470 (concat beg "Lisp closure")) 470 (concat beg "Lisp closure"))
471 ((eq (car-safe def) 'autoload) 471 ((autoloadp def)
472 (format "%s autoloaded %s" 472 (format "%s autoloaded %s"
473 (if (commandp def) "an interactive" "an") 473 (if (commandp def) "an interactive" "an")
474 (if (eq (nth 4 def) 'keymap) "keymap" 474 (if (eq (nth 4 def) 'keymap) "keymap"
@@ -563,7 +563,7 @@ FILE is the file where FUNCTION was probably defined."
563 ;; If the function is autoloaded, and its docstring has 563 ;; If the function is autoloaded, and its docstring has
564 ;; key substitution constructs, load the library. 564 ;; key substitution constructs, load the library.
565 (doc (progn 565 (doc (progn
566 (and (eq (car-safe real-def) 'autoload) 566 (and (autoloadp real-def)
567 help-enable-auto-load 567 help-enable-auto-load
568 (string-match "\\([^\\]=\\|[^=]\\|\\`\\)\\\\[[{<]" 568 (string-match "\\([^\\]=\\|[^=]\\|\\`\\)\\\\[[{<]"
569 doc-raw) 569 doc-raw)
diff --git a/lisp/speedbar.el b/lisp/speedbar.el
index d8c8c4a56be..16993ce1891 100644
--- a/lisp/speedbar.el
+++ b/lisp/speedbar.el
@@ -1864,9 +1864,7 @@ of the special mode functions."
1864 ;; If it is autoloaded, we need to load it now so that 1864 ;; If it is autoloaded, we need to load it now so that
1865 ;; we have access to the variable -speedbar-menu-items. 1865 ;; we have access to the variable -speedbar-menu-items.
1866 ;; Is this XEmacs safe? 1866 ;; Is this XEmacs safe?
1867 (let ((sf (symbol-function v))) 1867 (autoload-do-load (symbol-function v) v)
1868 (if (and (listp sf) (eq (car sf) 'autoload))
1869 (load-library (car (cdr sf)))))
1870 (setq speedbar-special-mode-expansion-list (list v)) 1868 (setq speedbar-special-mode-expansion-list (list v))
1871 (setq v (intern-soft (concat ms "-speedbar-key-map"))) 1869 (setq v (intern-soft (concat ms "-speedbar-key-map")))
1872 (if (not v) 1870 (if (not v)
diff --git a/lisp/subr.el b/lisp/subr.el
index 882ad3cd23d..76fec5dd5ac 100644
--- a/lisp/subr.el
+++ b/lisp/subr.el
@@ -1691,6 +1691,23 @@ If TOGGLE has a `:menu-tag', that is used for the menu item's label."
1691 1691
1692;;; Load history 1692;;; Load history
1693 1693
1694(defsubst autoloadp (object)
1695 "Non-nil if OBJECT is an autoload."
1696 (eq 'autoload (car-safe object)))
1697
1698;; (defun autoload-type (object)
1699;; "Returns the type of OBJECT or `function' or `command' if the type is nil.
1700;; OBJECT should be an autoload object."
1701;; (when (autoloadp object)
1702;; (let ((type (nth 3 object)))
1703;; (cond ((null type) (if (nth 2 object) 'command 'function))
1704;; ((eq 'keymap t) 'macro)
1705;; (type)))))
1706
1707;; (defalias 'autoload-file #'cadr
1708;; "Return the name of the file from which AUTOLOAD will be loaded.
1709;; \n\(fn AUTOLOAD)")
1710
1694(defun symbol-file (symbol &optional type) 1711(defun symbol-file (symbol &optional type)
1695 "Return the name of the file that defined SYMBOL. 1712 "Return the name of the file that defined SYMBOL.
1696The value is normally an absolute file name. It can also be nil, 1713The value is normally an absolute file name. It can also be nil,
@@ -1703,7 +1720,7 @@ TYPE is `defun', `defvar', or `defface', that specifies function
1703definition, variable definition, or face definition only." 1720definition, variable definition, or face definition only."
1704 (if (and (or (null type) (eq type 'defun)) 1721 (if (and (or (null type) (eq type 'defun))
1705 (symbolp symbol) (fboundp symbol) 1722 (symbolp symbol) (fboundp symbol)
1706 (eq 'autoload (car-safe (symbol-function symbol)))) 1723 (autoloadp (symbol-function symbol)))
1707 (nth 1 (symbol-function symbol)) 1724 (nth 1 (symbol-function symbol))
1708 (let ((files load-history) 1725 (let ((files load-history)
1709 file) 1726 file)
@@ -2752,6 +2769,20 @@ computing the hash. If BINARY is non-nil, return a string in binary
2752form." 2769form."
2753 (secure-hash 'sha1 object start end binary)) 2770 (secure-hash 'sha1 object start end binary))
2754 2771
2772(defun function-get (f prop &optional autoload)
2773 "Return the value of property PROP of function F.
2774If AUTOLOAD is non-nil and F is an autoloaded macro, try to autoload
2775the macro in the hope that it will set PROP."
2776 (let ((val nil))
2777 (while (and (symbolp f)
2778 (null (setq val (get f prop)))
2779 (fboundp f))
2780 (let ((fundef (symbol-function f)))
2781 (if (and autoload (autoloadp fundef)
2782 (not (equal fundef (autoload-do-load fundef f 'macro))))
2783 nil ;Re-try `get' on the same `f'.
2784 (setq f fundef))))
2785 val))
2755 2786
2756;;;; Support for yanking and text properties. 2787;;;; Support for yanking and text properties.
2757 2788
diff --git a/src/ChangeLog b/src/ChangeLog
index 88c90dd84d8..eb74f458942 100644
--- a/src/ChangeLog
+++ b/src/ChangeLog
@@ -1,3 +1,8 @@
12012-07-26 Stefan Monnier <monnier@iro.umontreal.ca>
2
3 * eval.c (Fautoload_do_load): Rename from do_autoload, export to Lisp,
4 add argument, tune behavior, and adjust all callers.
5
12012-07-25 Paul Eggert <eggert@cs.ucla.edu> 62012-07-25 Paul Eggert <eggert@cs.ucla.edu>
2 7
3 Use typedef for EMACS_INT, EMACS_UINT. 8 Use typedef for EMACS_INT, EMACS_UINT.
diff --git a/src/data.c b/src/data.c
index 110e8ae41ab..b23bcbe15b3 100644
--- a/src/data.c
+++ b/src/data.c
@@ -761,7 +761,7 @@ Value, if non-nil, is a list \(interactive SPEC). */)
761 { 761 {
762 struct gcpro gcpro1; 762 struct gcpro gcpro1;
763 GCPRO1 (cmd); 763 GCPRO1 (cmd);
764 do_autoload (fun, cmd); 764 Fautoload_do_load (fun, cmd, Qnil);
765 UNGCPRO; 765 UNGCPRO;
766 return Finteractive_form (cmd); 766 return Finteractive_form (cmd);
767 } 767 }
@@ -2059,7 +2059,7 @@ function chain of symbols. */)
2059 return Qnil; 2059 return Qnil;
2060} 2060}
2061 2061
2062/* Extract and set vector and string elements */ 2062/* Extract and set vector and string elements. */
2063 2063
2064DEFUN ("aref", Faref, Saref, 2, 2, 0, 2064DEFUN ("aref", Faref, Saref, 2, 2, 0,
2065 doc: /* Return the element of ARRAY at index IDX. 2065 doc: /* Return the element of ARRAY at index IDX.
diff --git a/src/eval.c b/src/eval.c
index a0143c372de..a0a05ebf0dc 100644
--- a/src/eval.c
+++ b/src/eval.c
@@ -988,26 +988,14 @@ definitions to shadow the loaded ones for use in file byte-compilation. */)
988 { 988 {
989 /* SYM is not mentioned in ENVIRONMENT. 989 /* SYM is not mentioned in ENVIRONMENT.
990 Look at its function definition. */ 990 Look at its function definition. */
991 struct gcpro gcpro1;
992 GCPRO1 (form);
993 def = Fautoload_do_load (def, sym, Qmacro);
994 UNGCPRO;
991 if (EQ (def, Qunbound) || !CONSP (def)) 995 if (EQ (def, Qunbound) || !CONSP (def))
992 /* Not defined or definition not suitable. */ 996 /* Not defined or definition not suitable. */
993 break; 997 break;
994 if (EQ (XCAR (def), Qautoload)) 998 if (!EQ (XCAR (def), Qmacro))
995 {
996 /* Autoloading function: will it be a macro when loaded? */
997 tem = Fnth (make_number (4), def);
998 if (EQ (tem, Qt) || EQ (tem, Qmacro))
999 /* Yes, load it and try again. */
1000 {
1001 struct gcpro gcpro1;
1002 GCPRO1 (form);
1003 do_autoload (def, sym);
1004 UNGCPRO;
1005 continue;
1006 }
1007 else
1008 break;
1009 }
1010 else if (!EQ (XCAR (def), Qmacro))
1011 break; 999 break;
1012 else expander = XCDR (def); 1000 else expander = XCDR (def);
1013 } 1001 }
@@ -1952,22 +1940,35 @@ un_autoload (Lisp_Object oldqueue)
1952 FUNNAME is the symbol which is the function's name. 1940 FUNNAME is the symbol which is the function's name.
1953 FUNDEF is the autoload definition (a list). */ 1941 FUNDEF is the autoload definition (a list). */
1954 1942
1955void 1943DEFUN ("autoload-do-load", Fautoload_do_load, Sautoload_do_load, 1, 3, 0,
1956do_autoload (Lisp_Object fundef, Lisp_Object funname) 1944 doc: /* Load FUNDEF which should be an autoload.
1945If non-nil, FUNNAME should be the symbol whose function value is FUNDEF,
1946in which case the function returns the new autoloaded function value.
1947If equal to `macro', MACRO-ONLY specifies that FUNDEF should only be loaded if
1948it is defines a macro. */)
1949 (Lisp_Object fundef, Lisp_Object funname, Lisp_Object macro_only)
1957{ 1950{
1958 ptrdiff_t count = SPECPDL_INDEX (); 1951 ptrdiff_t count = SPECPDL_INDEX ();
1959 Lisp_Object fun;
1960 struct gcpro gcpro1, gcpro2, gcpro3; 1952 struct gcpro gcpro1, gcpro2, gcpro3;
1961 1953
1954 if (!CONSP (fundef) || !EQ (Qautoload, XCAR (fundef)))
1955 return fundef;
1956
1957 if (EQ (macro_only, Qmacro))
1958 {
1959 Lisp_Object kind = Fnth (make_number (4), fundef);
1960 if (! (EQ (kind, Qt) || EQ (kind, Qmacro)))
1961 return fundef;
1962 }
1963
1962 /* This is to make sure that loadup.el gives a clear picture 1964 /* This is to make sure that loadup.el gives a clear picture
1963 of what files are preloaded and when. */ 1965 of what files are preloaded and when. */
1964 if (! NILP (Vpurify_flag)) 1966 if (! NILP (Vpurify_flag))
1965 error ("Attempt to autoload %s while preparing to dump", 1967 error ("Attempt to autoload %s while preparing to dump",
1966 SDATA (SYMBOL_NAME (funname))); 1968 SDATA (SYMBOL_NAME (funname)));
1967 1969
1968 fun = funname;
1969 CHECK_SYMBOL (funname); 1970 CHECK_SYMBOL (funname);
1970 GCPRO3 (fun, funname, fundef); 1971 GCPRO3 (funname, fundef, macro_only);
1971 1972
1972 /* Preserve the match data. */ 1973 /* Preserve the match data. */
1973 record_unwind_save_match_data (); 1974 record_unwind_save_match_data ();
@@ -1982,18 +1983,28 @@ do_autoload (Lisp_Object fundef, Lisp_Object funname)
1982 The value saved here is to be restored into Vautoload_queue. */ 1983 The value saved here is to be restored into Vautoload_queue. */
1983 record_unwind_protect (un_autoload, Vautoload_queue); 1984 record_unwind_protect (un_autoload, Vautoload_queue);
1984 Vautoload_queue = Qt; 1985 Vautoload_queue = Qt;
1985 Fload (Fcar (Fcdr (fundef)), Qnil, Qt, Qnil, Qt); 1986 /* If `macro_only', assume this autoload to be a "best-effort",
1987 so don't signal an error if autoloading fails. */
1988 Fload (Fcar (Fcdr (fundef)), macro_only, Qt, Qnil, Qt);
1986 1989
1987 /* Once loading finishes, don't undo it. */ 1990 /* Once loading finishes, don't undo it. */
1988 Vautoload_queue = Qt; 1991 Vautoload_queue = Qt;
1989 unbind_to (count, Qnil); 1992 unbind_to (count, Qnil);
1990 1993
1991 fun = Findirect_function (fun, Qnil);
1992
1993 if (!NILP (Fequal (fun, fundef)))
1994 error ("Autoloading failed to define function %s",
1995 SDATA (SYMBOL_NAME (funname)));
1996 UNGCPRO; 1994 UNGCPRO;
1995
1996 if (NILP (funname))
1997 return Qnil;
1998 else
1999 {
2000 Lisp_Object fun = Findirect_function (funname, Qnil);
2001
2002 if (!NILP (Fequal (fun, fundef)))
2003 error ("Autoloading failed to define function %s",
2004 SDATA (SYMBOL_NAME (funname)));
2005 else
2006 return fun;
2007 }
1997} 2008}
1998 2009
1999 2010
@@ -2200,7 +2211,7 @@ eval_sub (Lisp_Object form)
2200 xsignal1 (Qinvalid_function, original_fun); 2211 xsignal1 (Qinvalid_function, original_fun);
2201 if (EQ (funcar, Qautoload)) 2212 if (EQ (funcar, Qautoload))
2202 { 2213 {
2203 do_autoload (fun, original_fun); 2214 Fautoload_do_load (fun, original_fun, Qnil);
2204 goto retry; 2215 goto retry;
2205 } 2216 }
2206 if (EQ (funcar, Qmacro)) 2217 if (EQ (funcar, Qmacro))
@@ -2729,7 +2740,6 @@ usage: (funcall FUNCTION &rest ARGUMENTS) */)
2729 ptrdiff_t i; 2740 ptrdiff_t i;
2730 2741
2731 QUIT; 2742 QUIT;
2732 maybe_gc ();
2733 2743
2734 if (++lisp_eval_depth > max_lisp_eval_depth) 2744 if (++lisp_eval_depth > max_lisp_eval_depth)
2735 { 2745 {
@@ -2742,10 +2752,13 @@ usage: (funcall FUNCTION &rest ARGUMENTS) */)
2742 backtrace.next = backtrace_list; 2752 backtrace.next = backtrace_list;
2743 backtrace_list = &backtrace; 2753 backtrace_list = &backtrace;
2744 backtrace.function = &args[0]; 2754 backtrace.function = &args[0];
2745 backtrace.args = &args[1]; 2755 backtrace.args = &args[1]; /* This also GCPROs them. */
2746 backtrace.nargs = nargs - 1; 2756 backtrace.nargs = nargs - 1;
2747 backtrace.debug_on_exit = 0; 2757 backtrace.debug_on_exit = 0;
2748 2758
2759 /* Call GC after setting up the backtrace, so the latter GCPROs the args. */
2760 maybe_gc ();
2761
2749 if (debug_on_next_call) 2762 if (debug_on_next_call)
2750 do_debug_on_call (Qlambda); 2763 do_debug_on_call (Qlambda);
2751 2764
@@ -2857,7 +2870,7 @@ usage: (funcall FUNCTION &rest ARGUMENTS) */)
2857 val = funcall_lambda (fun, numargs, args + 1); 2870 val = funcall_lambda (fun, numargs, args + 1);
2858 else if (EQ (funcar, Qautoload)) 2871 else if (EQ (funcar, Qautoload))
2859 { 2872 {
2860 do_autoload (fun, original_fun); 2873 Fautoload_do_load (fun, original_fun, Qnil);
2861 CHECK_CONS_LIST (); 2874 CHECK_CONS_LIST ();
2862 goto retry; 2875 goto retry;
2863 } 2876 }
@@ -3582,6 +3595,7 @@ alist of active lexical bindings. */);
3582 defsubr (&Scalled_interactively_p); 3595 defsubr (&Scalled_interactively_p);
3583 defsubr (&Scommandp); 3596 defsubr (&Scommandp);
3584 defsubr (&Sautoload); 3597 defsubr (&Sautoload);
3598 defsubr (&Sautoload_do_load);
3585 defsubr (&Seval); 3599 defsubr (&Seval);
3586 defsubr (&Sapply); 3600 defsubr (&Sapply);
3587 defsubr (&Sfuncall); 3601 defsubr (&Sfuncall);
diff --git a/src/keyboard.c b/src/keyboard.c
index 0c03a2143d8..1f6c47eaf79 100644
--- a/src/keyboard.c
+++ b/src/keyboard.c
@@ -8827,18 +8827,12 @@ access_keymap_keyremap (Lisp_Object map, Lisp_Object key, Lisp_Object prompt,
8827 8827
8828 next = access_keymap (map, key, 1, 0, 1); 8828 next = access_keymap (map, key, 1, 0, 1);
8829 8829
8830 /* Handle symbol with autoload definition. */
8831 if (SYMBOLP (next) && !NILP (Ffboundp (next))
8832 && CONSP (XSYMBOL (next)->function)
8833 && EQ (XCAR (XSYMBOL (next)->function), Qautoload))
8834 do_autoload (XSYMBOL (next)->function, next);
8835
8836 /* Handle a symbol whose function definition is a keymap 8830 /* Handle a symbol whose function definition is a keymap
8837 or an array. */ 8831 or an array. */
8838 if (SYMBOLP (next) && !NILP (Ffboundp (next)) 8832 if (SYMBOLP (next) && !NILP (Ffboundp (next))
8839 && (ARRAYP (XSYMBOL (next)->function) 8833 && (ARRAYP (XSYMBOL (next)->function)
8840 || KEYMAPP (XSYMBOL (next)->function))) 8834 || KEYMAPP (XSYMBOL (next)->function)))
8841 next = XSYMBOL (next)->function; 8835 next = Fautoload_do_load (XSYMBOL (next)->function, next, Qnil);
8842 8836
8843 /* If the keymap gives a function, not an 8837 /* If the keymap gives a function, not an
8844 array, then call the function with one arg and use 8838 array, then call the function with one arg and use
@@ -10282,7 +10276,7 @@ a special event, so ignore the prefix argument and don't clear it. */)
10282 struct gcpro gcpro1, gcpro2; 10276 struct gcpro gcpro1, gcpro2;
10283 10277
10284 GCPRO2 (cmd, prefixarg); 10278 GCPRO2 (cmd, prefixarg);
10285 do_autoload (final, cmd); 10279 Fautoload_do_load (final, cmd, Qnil);
10286 UNGCPRO; 10280 UNGCPRO;
10287 } 10281 }
10288 else 10282 else
diff --git a/src/keymap.c b/src/keymap.c
index 510c5ea7f3e..feaf0cfd961 100644
--- a/src/keymap.c
+++ b/src/keymap.c
@@ -225,7 +225,7 @@ when reading a key-sequence to be looked-up in this keymap. */)
225 Fdefine_key should cause keymaps to be autoloaded. 225 Fdefine_key should cause keymaps to be autoloaded.
226 226
227 This function can GC when AUTOLOAD is non-zero, because it calls 227 This function can GC when AUTOLOAD is non-zero, because it calls
228 do_autoload which can GC. */ 228 Fautoload_do_load which can GC. */
229 229
230Lisp_Object 230Lisp_Object
231get_keymap (Lisp_Object object, int error_if_not_keymap, int autoload) 231get_keymap (Lisp_Object object, int error_if_not_keymap, int autoload)
@@ -259,7 +259,7 @@ get_keymap (Lisp_Object object, int error_if_not_keymap, int autoload)
259 struct gcpro gcpro1, gcpro2; 259 struct gcpro gcpro1, gcpro2;
260 260
261 GCPRO2 (tem, object); 261 GCPRO2 (tem, object);
262 do_autoload (tem, object); 262 Fautoload_do_load (tem, object, Qnil);
263 UNGCPRO; 263 UNGCPRO;
264 264
265 goto autoload_retry; 265 goto autoload_retry;
diff --git a/src/lisp.h b/src/lisp.h
index e4eb8ce5084..d9305555778 100644
--- a/src/lisp.h
+++ b/src/lisp.h
@@ -2822,7 +2822,6 @@ extern Lisp_Object unbind_to (ptrdiff_t, Lisp_Object);
2822extern _Noreturn void error (const char *, ...) ATTRIBUTE_FORMAT_PRINTF (1, 2); 2822extern _Noreturn void error (const char *, ...) ATTRIBUTE_FORMAT_PRINTF (1, 2);
2823extern _Noreturn void verror (const char *, va_list) 2823extern _Noreturn void verror (const char *, va_list)
2824 ATTRIBUTE_FORMAT_PRINTF (1, 0); 2824 ATTRIBUTE_FORMAT_PRINTF (1, 0);
2825extern void do_autoload (Lisp_Object, Lisp_Object);
2826extern Lisp_Object un_autoload (Lisp_Object); 2825extern Lisp_Object un_autoload (Lisp_Object);
2827extern void init_eval_once (void); 2826extern void init_eval_once (void);
2828extern Lisp_Object safe_call (ptrdiff_t, Lisp_Object *); 2827extern Lisp_Object safe_call (ptrdiff_t, Lisp_Object *);
@@ -2834,7 +2833,7 @@ extern void mark_backtrace (void);
2834#endif 2833#endif
2835extern void syms_of_eval (void); 2834extern void syms_of_eval (void);
2836 2835
2837/* Defined in editfns.c */ 2836/* Defined in editfns.c. */
2838extern Lisp_Object Qfield; 2837extern Lisp_Object Qfield;
2839extern void insert1 (Lisp_Object); 2838extern void insert1 (Lisp_Object);
2840extern Lisp_Object format2 (const char *, Lisp_Object, Lisp_Object); 2839extern Lisp_Object format2 (const char *, Lisp_Object, Lisp_Object);
@@ -2851,7 +2850,7 @@ const char *get_system_name (void);
2851extern void syms_of_editfns (void); 2850extern void syms_of_editfns (void);
2852extern void set_time_zone_rule (const char *); 2851extern void set_time_zone_rule (const char *);
2853 2852
2854/* Defined in buffer.c */ 2853/* Defined in buffer.c. */
2855extern int mouse_face_overlay_overlaps (Lisp_Object); 2854extern int mouse_face_overlay_overlaps (Lisp_Object);
2856extern _Noreturn void nsberror (Lisp_Object); 2855extern _Noreturn void nsberror (Lisp_Object);
2857extern void adjust_overlays_for_insert (ptrdiff_t, ptrdiff_t); 2856extern void adjust_overlays_for_insert (ptrdiff_t, ptrdiff_t);
@@ -2870,7 +2869,7 @@ extern void init_buffer (void);
2870extern void syms_of_buffer (void); 2869extern void syms_of_buffer (void);
2871extern void keys_of_buffer (void); 2870extern void keys_of_buffer (void);
2872 2871
2873/* Defined in marker.c */ 2872/* Defined in marker.c. */
2874 2873
2875extern ptrdiff_t marker_position (Lisp_Object); 2874extern ptrdiff_t marker_position (Lisp_Object);
2876extern ptrdiff_t marker_byte_position (Lisp_Object); 2875extern ptrdiff_t marker_byte_position (Lisp_Object);