]> code.delx.au - gnu-emacs/blobdiff - lisp/emacs-lisp/check-declare.el
Use 'grep-find-program' in check-declare.el
[gnu-emacs] / lisp / emacs-lisp / check-declare.el
index 3135b9b582737f91e89e0c38c1f24f533bf5e56c..b8a00b3fb4e3ac92b5cfc166932dcee53acd43e7 100644 (file)
@@ -1,6 +1,6 @@
 ;;; check-declare.el --- Check declare-function statements
 
-;; Copyright (C) 2007-201 Free Software Foundation, Inc.
+;; Copyright (C) 2007-2016 Free Software Foundation, Inc.
 
 ;; Author: Glenn Morris <rgm@gnu.org>
 ;; Keywords: lisp, tools, maint
@@ -28,7 +28,7 @@
 ;; checks that all such statements in a file or directory are accurate.
 ;; The entry points are `check-declare-file' and `check-declare-directory'.
 
-;; For more information, see Info node `elisp(Declaring Functions)'.
+;; For more information, see Info node `(elisp)Declaring Functions'.
 
 ;;; TODO:
 
@@ -98,7 +98,7 @@ don't know how to recognize (e.g. some macros)."
                  (stringp (setq fnfile (nth 2 form)))
                  (setq fnfile (check-declare-locate fnfile
                                                     (expand-file-name file)))
-                 ;; Use `t' to distinguish unspecified arglist from empty one.
+                 ;; Use t to distinguish unspecified arglist from empty one.
                  (or (eq t (setq arglist (if (> len 3)
                                              (nth 3 form)
                                            t)))
@@ -125,6 +125,15 @@ With optional argument FULL, sums the number of elements in each element."
 
 (autoload 'byte-compile-arglist-signature "bytecomp")
 
+(defgroup check-declare nil
+  "Check declare-function statements."
+  :group 'tools)
+
+(defcustom check-declare-ext-errors nil
+  "When non-nil, warn about functions not found in :ext."
+  :version "25.1"
+  :type 'boolean)
+
 (defun check-declare-verify (fnfile fnlist)
   "Check that FNFILE contains function definitions matching FNLIST.
 Each element of FNLIST has the form (FILE FN ARGLIST FILEONLY), where
@@ -149,11 +158,12 @@ is a string giving details of the error."
           (setq re (format (if cflag
                                "^[ \t]*\\(DEFUN\\)[ \t]*([ \t]*\"%s\""
                              "^[ \t]*(\\(fset[ \t]+'\\|\
+cl-def\\(?:generic\\|method\\)\\|\
 def\\(?:un\\|subst\\|foo\\|method\\|class\\|\
 ine-\\(?:derived\\|generic\\|\\(?:global\\(?:ized\\)?-\\)?minor\\)-mode\\|\
 \\(?:ine-obsolete-function-\\)?alias[ \t]+'\\|\
 ine-overloadable-function\\)\\)\
-\[ \t]*%s\\([ \t;]+\\|$\\)")
+[ \t]*%s\\([ \t;]+\\|$\\)")
                            (regexp-opt (mapcar 'cadr fnlist) t)))
           (while (re-search-forward re nil t)
             (skip-chars-forward " \t\n")
@@ -192,8 +202,8 @@ ine-overloadable-function\\)\\)\
                               type)
                              'obsolete)
                             ;; Can't easily check arguments in these cases.
-                            ((string-match "\\`\\(def\\(alias\\|\
-method\\|class\\)\\|fset\\)\\>" type)
+                            ((string-match "\\`\\(def\\(alias\\|class\\)\\|\
+fset\\|\\(?:cl-\\)?defmethod\\)\\>" type)
                              t)
                             ((looking-at "\\((\\|nil\\)")
                              (byte-compile-arglist-signature
@@ -226,7 +236,8 @@ method\\|class\\)\\|fset\\)\\>" type)
       (when type
         (setq errlist (cons (list (car e) (cadr e) type) errlist))))
     (message "%s%s" m
-             (if (or re (not ext))
+             (if (or re (or check-declare-ext-errors
+                            (not ext)))
                  (check-declare-errmsg errlist)
                (progn
                  (setq errlist nil)
@@ -251,12 +262,29 @@ Returned list has elements FNFILE (FILE ...)."
   "Warn that FILE made a false claim about FN in FNFILE.
 TYPE is a string giving the nature of the error.  Warning is displayed in
 `check-declare-warning-buffer'."
-  (display-warning 'check-declare
-                   (format "%s said `%s' was defined in %s: %s"
-                           (file-name-nondirectory file) fn
-                           (file-name-nondirectory fnfile)
-                           type)
-                   nil check-declare-warning-buffer))
+  (let ((warning-prefix-function
+         (lambda (level entry)
+           (let ((line 0)
+                 (col 0))
+             (insert
+              (with-current-buffer (find-file-noselect file)
+                (goto-char (point-min))
+                (when (re-search-forward
+                       (format "(declare-function[ \t\n]+%s" fn) nil t)
+                  (goto-char (match-beginning 0))
+                  (setq line (line-number-at-pos))
+                  (setq col (1+ (current-column))))
+                (format "%s:%d:%d:"
+                        (file-name-nondirectory file)
+                        line col))))
+           entry))
+        (warning-fill-prefix "    "))
+    (display-warning 'check-declare
+                     (format-message "said `%s' was defined in %s: %s"
+                                     fn (file-name-nondirectory fnfile) type)
+                     nil check-declare-warning-buffer)))
+
+(declare-function compilation-forget-errors "compile" ())
 
 (defun check-declare-files (&rest files)
   "Check veracity of all `declare-function' statements in FILES.
@@ -269,13 +297,20 @@ Return a list of any errors found."
     (dolist (e (check-declare-sort alist))
       (if (setq err (check-declare-verify (car e) (cdr e)))
           (setq errlist (cons (cons (car e) err) errlist))))
+    (setq errlist (nreverse errlist))
     (if (get-buffer check-declare-warning-buffer)
         (kill-buffer check-declare-warning-buffer))
+    (with-current-buffer (get-buffer-create check-declare-warning-buffer)
+      (unless (derived-mode-p 'compilation-mode)
+        (compilation-mode))
+      (let ((inhibit-read-only t))
+        (insert "\f\n"))
+      (compilation-forget-errors))
     ;; Sort back again so that errors are ordered by the files
     ;; containing the declare-function statements.
     (dolist (e (check-declare-sort errlist))
-        (dolist (f (cdr e))
-          (check-declare-warn (car e) (cadr f) (car f) (nth 2 f))))
+      (dolist (f (cdr e))
+        (check-declare-warn (car e) (cadr f) (car f) (nth 2 f))))
     errlist))
 
 ;;;###autoload
@@ -304,7 +339,7 @@ Returns non-nil if any false statements are found."
         errlist files)
     (message "%s" m)
     (message "%s" m2)
-    (setq files (process-lines find-program root
+    (setq files (process-lines grep-find-program root
                               "-name" "*.el"
                               "-exec" grep-program
                               "-l" "^[ \t]*(declare-function" "{}" ";"))