unofficial mirror of emacs-devel@gnu.org 
 help / color / mirror / code / Atom feed
From: Stefan Monnier <monnier@iro.umontreal.ca>
To: Klaus-Dieter Bauer <bauer.klaus.dieter@gmail.com>
Cc: Sebastian Wiesner <lunaryorn@gmail.com>, emacs-devel@gnu.org
Subject: Re: Can the byte-compiler check whether functions passed by name are defined?
Date: Wed, 07 Aug 2013 13:34:41 -0400	[thread overview]
Message-ID: <jwv61vh5rv0.fsf-monnier+emacs@gnu.org> (raw)
In-Reply-To: <jwvsiyl5xz1.fsf-monnier+emacs@gnu.org> (Stefan Monnier's message of "Wed, 07 Aug 2013 11:21:16 -0400")

>>>>> "Stefan" == Stefan Monnier <monnier@iro.umontreal.ca> writes:

>> The patch only adds a single line of code to byte-compile-normal-call
>> which calls defun byte-compile--higher-order--check-arguments.

> But there's no normal call in (if a #'foo1 #'foo2), so how can this work?


>         Stefan

I installed the patch below which checks that #'foo refers to a function
that will exist.


        Stefan


=== modified file 'lisp/ChangeLog'
--- lisp/ChangeLog	2013-08-07 16:37:04 +0000
+++ lisp/ChangeLog	2013-08-07 17:33:11 +0000
@@ -1,3 +1,11 @@
+2013-08-07  Stefan Monnier  <monnier@iro.umontreal.ca>
+
+	* emacs-lisp/bytecomp.el: Check existence of f in #'f.
+	(byte-compile-callargs-warn): Use `push'.
+	(byte-compile-arglist-warn): Ignore higher-order "calls".
+	(byte-compile-file-form-autoload): Use `pcase'.
+	(byte-compile-function-form): If quoting a symbol, check that it exists.
+
 2013-08-07  Eli Zaretskii  <eliz@gnu.org>
 
 	* progmodes/dos.el (dos-font-lock-keywords): Rename LINUX to UNIX

=== modified file 'lisp/emacs-lisp/bytecomp.el'
--- lisp/emacs-lisp/bytecomp.el	2013-06-19 07:35:00 +0000
+++ lisp/emacs-lisp/bytecomp.el	2013-08-07 17:20:38 +0000
@@ -1364,7 +1364,10 @@
       ;; This is the first definition.  See if previous calls are compatible.
       (let ((calls (assq name byte-compile-unresolved-functions))
 	    nums sig min max)
-	(when calls
+        (setq byte-compile-unresolved-functions
+              (delq calls byte-compile-unresolved-functions))
+        (setq calls (delq t calls))  ;Ignore higher-order uses of the function.
+	(when (cdr calls)
           (when (and (symbolp name)
                      (eq (function-get name 'byte-optimizer)
                          'byte-compile-inline-expand))
@@ -1382,10 +1385,7 @@
              name
              (byte-compile-arglist-signature-string sig)
              (if (equal sig '(1 . 1)) " arg" " args")
-             (byte-compile-arglist-signature-string (cons min max))))
-
-          (setq byte-compile-unresolved-functions
-                (delq calls byte-compile-unresolved-functions)))))))
+             (byte-compile-arglist-signature-string (cons min max)))))))))
 
 (defvar byte-compile-cl-functions nil
   "List of functions defined in CL.")
@@ -3574,9 +3570,31 @@
 ;; and (funcall (function foo)) will lose with autoloads.
 
 (defun byte-compile-function-form (form)
-  (byte-compile-constant (if (eq 'lambda (car-safe (nth 1 form)))
-                             (byte-compile-lambda (nth 1 form))
-                           (nth 1 form))))
+  (let ((f (nth 1 form)))
+    (when (and (symbolp f)
+               (byte-compile-warning-enabled-p 'callargs))
+      (when (get f 'byte-obsolete-info)
+        (byte-compile-warn-obsolete (car form)))
+
+      ;; Check to see if the function will be available at runtime
+      ;; and/or remember its arity if it's unknown.
+      (or (and (or (fboundp f)          ; Might be a subr or autoload.
+                   (byte-compile-fdefinition (car form) nil))
+               (not (memq f byte-compile-noruntime-functions)))
+          (eq f byte-compile-current-form) ; ## This doesn't work
+                                           ; with recursion.
+          ;; It's a currently-undefined function.
+          ;; Remember number of args in call.
+          (let ((cons (assq f byte-compile-unresolved-functions)))
+            (if cons
+                (or (memq t (cdr cons))
+                    (push t (cdr cons)))
+              (push (list f t)
+                    byte-compile-unresolved-functions)))))
+
+    (byte-compile-constant (if (eq 'lambda (car-safe f))
+                               (byte-compile-lambda f)
+                             f))))
 
 (defun byte-compile-indent-to (form)
   (let ((len (length form)))




  reply	other threads:[~2013-08-07 17:34 UTC|newest]

Thread overview: 23+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2013-07-29 10:35 Can the byte-compiler check whether functions passed by name are defined? Klaus-Dieter Bauer
2013-07-29 15:21 ` Stefan Monnier
2013-07-31 13:44   ` Klaus-Dieter Bauer
2013-07-31 17:49     ` Stefan Monnier
2013-07-31 18:01       ` Sebastian Wiesner
2013-08-01 20:31         ` Stefan Monnier
2013-08-04 18:41           ` Klaus-Dieter Bauer
2013-08-04 21:11             ` Stefan Monnier
2013-08-05  8:52               ` Klaus-Dieter Bauer
2013-08-05 14:35                 ` Stefan Monnier
2013-08-05 18:17                   ` Klaus-Dieter Bauer
2013-08-07 11:27                     ` Klaus-Dieter Bauer
2013-08-07 14:41                     ` Stefan Monnier
2013-08-07 15:11                       ` Klaus-Dieter Bauer
2013-08-07 15:21                         ` Stefan Monnier
2013-08-07 17:34                           ` Stefan Monnier [this message]
2013-08-07 21:11                             ` Glenn Morris
2013-08-07 21:59                               ` Glenn Morris
2013-08-08  1:25                                 ` Stefan Monnier
2013-08-08  8:44                                   ` Klaus-Dieter Bauer
2013-08-08 13:07                                     ` Stefan Monnier
2013-08-07 19:59                           ` Klaus-Dieter Bauer
2013-08-07 21:14                             ` Stefan Monnier

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

  List information: https://www.gnu.org/software/emacs/

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=jwv61vh5rv0.fsf-monnier+emacs@gnu.org \
    --to=monnier@iro.umontreal.ca \
    --cc=bauer.klaus.dieter@gmail.com \
    --cc=emacs-devel@gnu.org \
    --cc=lunaryorn@gmail.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).