]> code.delx.au - gnu-emacs/blob - test/automated/elisp-mode-tests.el
Update copyright year to 2016
[gnu-emacs] / test / automated / elisp-mode-tests.el
1 ;;; elisp-mode-tests.el --- Tests for emacs-lisp-mode -*- lexical-binding: t; -*-
2
3 ;; Copyright (C) 2015-2016 Free Software Foundation, Inc.
4
5 ;; Author: Dmitry Gutov <dgutov@yandex.ru>
6 ;; Author: Stephen Leake <stephen_leake@member.fsf.org>
7
8 ;; This file is part of GNU Emacs.
9
10 ;; GNU Emacs is free software: you can redistribute it and/or modify
11 ;; it under the terms of the GNU General Public License as published by
12 ;; the Free Software Foundation, either version 3 of the License, or
13 ;; (at your option) any later version.
14
15 ;; GNU Emacs is distributed in the hope that it will be useful,
16 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
17 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 ;; GNU General Public License for more details.
19
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>.
22
23 ;;; Code:
24
25 (require 'ert)
26 (require 'xref)
27
28 ;;; Completion
29
30 (defun elisp--test-completions ()
31 (let ((data (elisp-completion-at-point)))
32 (all-completions (buffer-substring (nth 0 data) (nth 1 data))
33 (nth 2 data)
34 (plist-get (nthcdr 3 data) :predicate))))
35
36 (ert-deftest elisp-completes-functions ()
37 (with-temp-buffer
38 (emacs-lisp-mode)
39 (insert "(ba")
40 (let ((comps (elisp--test-completions)))
41 (should (member "backup-buffer" comps))
42 (should-not (member "backup-inhibited" comps)))))
43
44 (ert-deftest elisp-completes-variables ()
45 (with-temp-buffer
46 (emacs-lisp-mode)
47 (insert "(foo ba")
48 (let ((comps (elisp--test-completions)))
49 (should (member "backup-inhibited" comps))
50 (should-not (member "backup-buffer" comps)))))
51
52 (ert-deftest elisp-completes-anything-quoted ()
53 (dolist (text '("`(foo ba" "(foo 'ba"
54 "`(,foo ba" "`,(foo `ba"
55 "'(foo (ba"))
56 (with-temp-buffer
57 (emacs-lisp-mode)
58 (insert text)
59 (let ((comps (elisp--test-completions)))
60 (should (member "backup-inhibited" comps))
61 (should (member "backup-buffer" comps))
62 (should (member "backup" comps))))))
63
64 (ert-deftest elisp-completes-variables-unquoted ()
65 (dolist (text '("`(foo ,ba" "`(,(foo ba" "`(,ba"))
66 (with-temp-buffer
67 (emacs-lisp-mode)
68 (insert text)
69 (let ((comps (elisp--test-completions)))
70 (should (member "backup-inhibited" comps))
71 (should-not (member "backup-buffer" comps))))))
72
73 (ert-deftest elisp-completes-functions-in-special-macros ()
74 (dolist (text '("(declare-function ba" "(cl-callf2 ba"))
75 (with-temp-buffer
76 (emacs-lisp-mode)
77 (insert text)
78 (let ((comps (elisp--test-completions)))
79 (should (member "backup-buffer" comps))
80 (should-not (member "backup-inhibited" comps))))))
81
82 (ert-deftest elisp-completes-functions-after-hash-quote ()
83 (ert-deftest elisp-completes-functions-after-let-bindings ()
84 (with-temp-buffer
85 (emacs-lisp-mode)
86 (insert "#'ba")
87 (let ((comps (elisp--test-completions)))
88 (should (member "backup-buffer" comps))
89 (should-not (member "backup-inhibited" comps))))))
90
91 (ert-deftest elisp-completes-local-variables ()
92 (with-temp-buffer
93 (emacs-lisp-mode)
94 (insert "(let ((bar 1) baz) (foo ba")
95 (let ((comps (elisp--test-completions)))
96 (should (member "backup-inhibited" comps))
97 (should (member "bar" comps))
98 (should (member "baz" comps)))))
99
100 (ert-deftest elisp-completest-variables-in-let-bindings ()
101 (dolist (text '("(let (ba" "(let* ((ba"))
102 (with-temp-buffer
103 (emacs-lisp-mode)
104 (insert text)
105 (let ((comps (elisp--test-completions)))
106 (should (member "backup-inhibited" comps))
107 (should-not (member "backup-buffer" comps))))))
108
109 (ert-deftest elisp-completes-functions-after-let-bindings ()
110 (with-temp-buffer
111 (emacs-lisp-mode)
112 (insert "(let ((bar 1) (baz 2)) (ba")
113 (let ((comps (elisp--test-completions)))
114 (should (member "backup-buffer" comps))
115 (should-not (member "backup-inhibited" comps)))))
116
117 ;;; xref
118
119 (defun xref-elisp-test-descr-to-target (xref)
120 "Return an appropriate `looking-at' match string for XREF."
121 (let* ((loc (xref-item-location xref))
122 (type (or (xref-elisp-location-type loc)
123 'defun)))
124
125 (cl-case type
126 (defalias
127 ;; summary: "(defalias xref)"
128 ;; target : "(defalias 'xref"
129 (concat "(defalias '" (substring (xref-item-summary xref) 10 -1)))
130
131 (defun
132 (let ((summary (xref-item-summary xref))
133 (file (xref-elisp-location-file loc)))
134 (cond
135 ((string= "c" (file-name-extension file))
136 ;; summary: "(defun buffer-live-p)"
137 ;; target : "DEFUN (buffer-live-p"
138 (concat
139 (upcase (substring summary 1 6))
140 " (\""
141 (substring summary 7 -1)
142 "\""))
143
144 (t
145 (substring summary 0 -1))
146 )))
147
148 (defvar
149 (let ((summary (xref-item-summary xref))
150 (file (xref-elisp-location-file loc)))
151 (cond
152 ((string= "c" (file-name-extension file))
153 ;; summary: "(defvar system-name)"
154 ;; target : "DEFVAR_LISP ("system-name", "
155 ;; summary: "(defvar abbrev-mode)"
156 ;; target : DEFVAR_PER_BUFFER ("abbrev-mode"
157 (concat
158 (upcase (substring summary 1 7))
159 (if (bufferp (variable-binding-locus (xref-elisp-location-symbol loc)))
160 "_PER_BUFFER (\""
161 "_LISP (\"")
162 (substring summary 8 -1)
163 "\""))
164
165 (t
166 (substring summary 0 -1))
167 )))
168
169 (feature
170 ;; summary: "(feature xref)"
171 ;; target : "(provide 'xref)"
172 (concat "(provide '" (substring (xref-item-summary xref) 9 -1)))
173
174 (otherwise
175 (substring (xref-item-summary xref) 0 -1))
176 )))
177
178
179 (defun xref-elisp-test-run (xrefs expected-xrefs)
180 (should (= (length xrefs) (length expected-xrefs)))
181 (while xrefs
182 (let* ((xref (pop xrefs))
183 (expected (pop expected-xrefs))
184 (expected-xref (or (when (consp expected) (car expected)) expected))
185 (expected-source (when (consp expected) (cdr expected))))
186
187 ;; Downcase the filenames for case-insensitive file systems.
188 (setf (xref-elisp-location-file (oref xref location))
189 (downcase (xref-elisp-location-file (oref xref location))))
190
191 (setf (xref-elisp-location-file (oref expected-xref location))
192 (downcase (xref-elisp-location-file (oref expected-xref location))))
193
194 (should (equal xref expected-xref))
195
196 (xref--goto-location (xref-item-location xref))
197 (back-to-indentation)
198 (should (looking-at (or expected-source
199 (xref-elisp-test-descr-to-target expected)))))
200 ))
201
202 (defmacro xref-elisp-deftest (name computed-xrefs expected-xrefs)
203 "Define an ert test for an xref-elisp feature.
204 COMPUTED-XREFS and EXPECTED-XREFS are lists of xrefs, except if
205 an element of EXPECTED-XREFS is a cons (XREF . TARGET), TARGET is
206 matched to the found location; otherwise, match
207 to (xref-elisp-test-descr-to-target xref)."
208 (declare (indent defun)
209 (debug (symbolp "name")))
210 `(ert-deftest ,(intern (concat "xref-elisp-test-" (symbol-name name))) ()
211 (let ((find-file-suppress-same-file-warnings t))
212 (xref-elisp-test-run ,computed-xrefs ,expected-xrefs)
213 )))
214
215 ;; When tests are run from the Makefile, 'default-directory' is $HOME,
216 ;; so we must provide this dir to expand-file-name in the expected
217 ;; results. This also allows running these tests from other
218 ;; directories.
219 ;;
220 ;; We add 'downcase' here to deliberately cause a potential problem on
221 ;; case-insensitive file systems. On such systems, `load-file-name'
222 ;; may not have the same case as the real file system, since the user
223 ;; can set `load-path' to have the wrong case (on my Windows system,
224 ;; `load-path' has the correct case, so this causes the expected test
225 ;; values to have the wrong case). This is handled in
226 ;; `xref-elisp-test-run'.
227 (defconst emacs-test-dir (downcase (file-name-directory (or load-file-name (buffer-file-name)))))
228
229
230 ;; alphabetical by test name
231
232 ;; Autoloads require no special support; they are handled as functions.
233
234 ;; FIXME: defalias-defun-c cmpl-prefix-entry-head
235 ;; FIXME: defalias-defvar-el allout-mode-map
236
237 (xref-elisp-deftest find-defs-constructor
238 (elisp--xref-find-definitions 'xref-make-elisp-location)
239 ;; 'xref-make-elisp-location' is just a name for the default
240 ;; constructor created by the cl-defstruct, so the location is the
241 ;; cl-defstruct location.
242 (list
243 (cons
244 (xref-make "(cl-defstruct (xref-elisp-location (:constructor xref-make-elisp-location)))"
245 (xref-make-elisp-location
246 'xref-elisp-location 'define-type
247 (expand-file-name "../../lisp/progmodes/elisp-mode.el" emacs-test-dir)))
248 ;; It's not worth adding another special case to `xref-elisp-test-descr-to-target' for this
249 "(cl-defstruct (xref-elisp-location")
250 ))
251
252 (xref-elisp-deftest find-defs-defalias-defun-el
253 (elisp--xref-find-definitions 'Buffer-menu-sort)
254 (list
255 (xref-make "(defalias Buffer-menu-sort)"
256 (xref-make-elisp-location
257 'Buffer-menu-sort 'defalias
258 (expand-file-name "../../lisp/buff-menu.elc" emacs-test-dir)))
259 (xref-make "(defun tabulated-list-sort)"
260 (xref-make-elisp-location
261 'tabulated-list-sort nil
262 (expand-file-name "../../lisp/emacs-lisp/tabulated-list.el" emacs-test-dir)))
263 ))
264
265 ;; FIXME: defconst
266
267 ;; FIXME: eieio defclass
268
269 ;; Possible ways of defining the default method implementation for a
270 ;; generic function. We declare these here, so we know we cover all
271 ;; cases, and we don't rely on other code not changing.
272 ;;
273 ;; When the generic and default method are declared in the same place,
274 ;; elisp--xref-find-definitions only returns one.
275
276 (cl-defstruct (xref-elisp-root-type)
277 slot-1)
278
279 (cl-defgeneric xref-elisp-generic-no-methods (arg1 arg2)
280 "doc string generic no-methods"
281 ;; No default implementation, no methods, but fboundp is true for
282 ;; this symbol; it calls cl-no-applicable-method
283 )
284
285 ;; WORKAROUND: ‘this’ is unused, and the byte compiler complains, so
286 ;; it should be spelled ‘_this’. But for some unknown reason, that
287 ;; causes the batch mode test to fail; the symbol shows up as
288 ;; ‘this’. It passes in interactive tests, so I haven't been able to
289 ;; track down the problem.
290 (cl-defmethod xref-elisp-generic-no-default ((this xref-elisp-root-type) arg2)
291 "doc string generic no-default xref-elisp-root-type"
292 "non-default for no-default")
293
294 ;; defgeneric after defmethod in file to ensure the fallback search
295 ;; method of just looking for the function name will fail.
296 (cl-defgeneric xref-elisp-generic-no-default (arg1 arg2)
297 "doc string generic no-default generic"
298 ;; No default implementation; this function calls the cl-generic
299 ;; dispatching code.
300 )
301
302 (cl-defgeneric xref-elisp-generic-co-located-default (arg1 arg2)
303 "doc string generic co-located-default"
304 "co-located default")
305
306 (cl-defmethod xref-elisp-generic-co-located-default ((this xref-elisp-root-type) arg2)
307 "doc string generic co-located-default xref-elisp-root-type"
308 "non-default for co-located-default")
309
310 (cl-defgeneric xref-elisp-generic-separate-default (arg1 arg2)
311 "doc string generic separate-default"
312 ;; default implementation provided separately
313 )
314
315 (cl-defmethod xref-elisp-generic-separate-default (arg1 arg2)
316 "doc string generic separate-default default"
317 "separate default")
318
319 (cl-defmethod xref-elisp-generic-separate-default ((this xref-elisp-root-type) arg2)
320 "doc string generic separate-default xref-elisp-root-type"
321 "non-default for separate-default")
322
323 (cl-defmethod xref-elisp-generic-implicit-generic (arg1 arg2)
324 "doc string generic implicit-generic default"
325 "default for implicit generic")
326
327 (cl-defmethod xref-elisp-generic-implicit-generic ((this xref-elisp-root-type) arg2)
328 "doc string generic implicit-generic xref-elisp-root-type"
329 "non-default for implicit generic")
330
331
332 (xref-elisp-deftest find-defs-defgeneric-no-methods
333 (elisp--xref-find-definitions 'xref-elisp-generic-no-methods)
334 (list
335 (xref-make "(cl-defgeneric xref-elisp-generic-no-methods)"
336 (xref-make-elisp-location
337 'xref-elisp-generic-no-methods 'cl-defgeneric
338 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
339 ))
340
341 (xref-elisp-deftest find-defs-defgeneric-no-default
342 (elisp--xref-find-definitions 'xref-elisp-generic-no-default)
343 (list
344 (xref-make "(cl-defgeneric xref-elisp-generic-no-default)"
345 (xref-make-elisp-location
346 'xref-elisp-generic-no-default 'cl-defgeneric
347 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
348 (xref-make "(cl-defmethod xref-elisp-generic-no-default ((this xref-elisp-root-type) arg2))"
349 (xref-make-elisp-location
350 '(xref-elisp-generic-no-default xref-elisp-root-type t) 'cl-defmethod
351 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
352 ))
353
354 (xref-elisp-deftest find-defs-defgeneric-co-located-default
355 (elisp--xref-find-definitions 'xref-elisp-generic-co-located-default)
356 (list
357 (xref-make "(cl-defgeneric xref-elisp-generic-co-located-default)"
358 (xref-make-elisp-location
359 'xref-elisp-generic-co-located-default 'cl-defgeneric
360 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
361 (xref-make "(cl-defmethod xref-elisp-generic-co-located-default ((this xref-elisp-root-type) arg2))"
362 (xref-make-elisp-location
363 '(xref-elisp-generic-co-located-default xref-elisp-root-type t) 'cl-defmethod
364 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
365 ))
366
367 (xref-elisp-deftest find-defs-defgeneric-separate-default
368 (elisp--xref-find-definitions 'xref-elisp-generic-separate-default)
369 (list
370 (xref-make "(cl-defgeneric xref-elisp-generic-separate-default)"
371 (xref-make-elisp-location
372 'xref-elisp-generic-separate-default 'cl-defgeneric
373 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
374 (xref-make "(cl-defmethod xref-elisp-generic-separate-default (arg1 arg2))"
375 (xref-make-elisp-location
376 '(xref-elisp-generic-separate-default t t) 'cl-defmethod
377 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
378 (xref-make "(cl-defmethod xref-elisp-generic-separate-default ((this xref-elisp-root-type) arg2))"
379 (xref-make-elisp-location
380 '(xref-elisp-generic-separate-default xref-elisp-root-type t) 'cl-defmethod
381 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
382 ))
383
384 (xref-elisp-deftest find-defs-defgeneric-implicit-generic
385 (elisp--xref-find-definitions 'xref-elisp-generic-implicit-generic)
386 (list
387 (xref-make "(cl-defmethod xref-elisp-generic-implicit-generic (arg1 arg2))"
388 (xref-make-elisp-location
389 '(xref-elisp-generic-implicit-generic t t) 'cl-defmethod
390 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
391 (xref-make "(cl-defmethod xref-elisp-generic-implicit-generic ((this xref-elisp-root-type) arg2))"
392 (xref-make-elisp-location
393 '(xref-elisp-generic-implicit-generic xref-elisp-root-type t) 'cl-defmethod
394 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
395 ))
396
397 ;; Test that we handle more than one method
398
399 ;; When run from the Makefile, etags is not loaded at compile time,
400 ;; but it is by the time this test is run. interactively; don't fail
401 ;; for that.
402 (require 'etags)
403 (xref-elisp-deftest find-defs-defgeneric-el
404 (elisp--xref-find-definitions 'xref-location-marker)
405 (list
406 (xref-make "(cl-defgeneric xref-location-marker)"
407 (xref-make-elisp-location
408 'xref-location-marker 'cl-defgeneric
409 (expand-file-name "../../lisp/progmodes/xref.el" emacs-test-dir)))
410 (xref-make "(cl-defmethod xref-location-marker ((l xref-elisp-location)))"
411 (xref-make-elisp-location
412 '(xref-location-marker xref-elisp-location) 'cl-defmethod
413 (expand-file-name "../../lisp/progmodes/elisp-mode.el" emacs-test-dir)))
414 (xref-make "(cl-defmethod xref-location-marker ((l xref-file-location)))"
415 (xref-make-elisp-location
416 '(xref-location-marker xref-file-location) 'cl-defmethod
417 (expand-file-name "../../lisp/progmodes/xref.el" emacs-test-dir)))
418 (xref-make "(cl-defmethod xref-location-marker ((l xref-buffer-location)))"
419 (xref-make-elisp-location
420 '(xref-location-marker xref-buffer-location) 'cl-defmethod
421 (expand-file-name "../../lisp/progmodes/xref.el" emacs-test-dir)))
422 (xref-make "(cl-defmethod xref-location-marker ((l xref-bogus-location)))"
423 (xref-make-elisp-location
424 '(xref-location-marker xref-bogus-location) 'cl-defmethod
425 (expand-file-name "../../lisp/progmodes/xref.el" emacs-test-dir)))
426 (xref-make "(cl-defmethod xref-location-marker ((l xref-etags-location)))"
427 (xref-make-elisp-location
428 '(xref-location-marker xref-etags-location) 'cl-defmethod
429 (expand-file-name "../../lisp/progmodes/etags.el" emacs-test-dir)))
430 ))
431
432 (xref-elisp-deftest find-defs-defgeneric-eval
433 (elisp--xref-find-definitions (eval '(cl-defgeneric stephe-leake-cl-defgeneric ())))
434 nil)
435
436 ;; Define some mode-local overloadable/overridden functions for xref to find
437 (require 'mode-local)
438
439 (define-overloadable-function xref-elisp-overloadable-no-methods ()
440 "doc string overloadable no-methods")
441
442 (define-overloadable-function xref-elisp-overloadable-no-default ()
443 "doc string overloadable no-default")
444
445 ;; FIXME: byte compiler complains about unused lexical arguments
446 ;; generated by this macro.
447 (define-mode-local-override xref-elisp-overloadable-no-default c-mode
448 (start end &optional nonterminal depth returnonerror)
449 "doc string overloadable no-default c-mode."
450 "result overloadable no-default c-mode.")
451
452 (define-overloadable-function xref-elisp-overloadable-co-located-default ()
453 "doc string overloadable co-located-default"
454 "result overloadable co-located-default.")
455
456 (define-mode-local-override xref-elisp-overloadable-co-located-default c-mode
457 (start end &optional nonterminal depth returnonerror)
458 "doc string overloadable co-located-default c-mode."
459 "result overloadable co-located-default c-mode.")
460
461 (define-overloadable-function xref-elisp-overloadable-separate-default ()
462 "doc string overloadable separate-default.")
463
464 (defun xref-elisp-overloadable-separate-default-default ()
465 "doc string overloadable separate-default default"
466 "result overloadable separate-default.")
467
468 (define-mode-local-override xref-elisp-overloadable-separate-default c-mode
469 (start end &optional nonterminal depth returnonerror)
470 "doc string overloadable separate-default c-mode."
471 "result overloadable separate-default c-mode.")
472
473 (xref-elisp-deftest find-defs-define-overload-no-methods
474 (elisp--xref-find-definitions 'xref-elisp-overloadable-no-methods)
475 (list
476 (xref-make "(define-overloadable-function xref-elisp-overloadable-no-methods)"
477 (xref-make-elisp-location
478 'xref-elisp-overloadable-no-methods 'define-overloadable-function
479 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
480 ))
481
482 (xref-elisp-deftest find-defs-define-overload-no-default
483 (elisp--xref-find-definitions 'xref-elisp-overloadable-no-default)
484 (list
485 (xref-make "(define-overloadable-function xref-elisp-overloadable-no-default)"
486 (xref-make-elisp-location
487 'xref-elisp-overloadable-no-default 'define-overloadable-function
488 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
489 (xref-make "(define-mode-local-override xref-elisp-overloadable-no-default c-mode)"
490 (xref-make-elisp-location
491 '(xref-elisp-overloadable-no-default-c-mode . c-mode) 'define-mode-local-override
492 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
493 ))
494
495 (xref-elisp-deftest find-defs-define-overload-co-located-default
496 (elisp--xref-find-definitions 'xref-elisp-overloadable-co-located-default)
497 (list
498 (xref-make "(define-overloadable-function xref-elisp-overloadable-co-located-default)"
499 (xref-make-elisp-location
500 'xref-elisp-overloadable-co-located-default 'define-overloadable-function
501 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
502 (xref-make "(define-mode-local-override xref-elisp-overloadable-co-located-default c-mode)"
503 (xref-make-elisp-location
504 '(xref-elisp-overloadable-co-located-default-c-mode . c-mode) 'define-mode-local-override
505 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
506 ))
507
508 (xref-elisp-deftest find-defs-define-overload-separate-default
509 (elisp--xref-find-definitions 'xref-elisp-overloadable-separate-default)
510 (list
511 (xref-make "(define-overloadable-function xref-elisp-overloadable-separate-default)"
512 (xref-make-elisp-location
513 'xref-elisp-overloadable-separate-default 'define-overloadable-function
514 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
515 (xref-make "(defun xref-elisp-overloadable-separate-default-default)"
516 (xref-make-elisp-location
517 'xref-elisp-overloadable-separate-default-default nil
518 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
519 (xref-make "(define-mode-local-override xref-elisp-overloadable-separate-default c-mode)"
520 (xref-make-elisp-location
521 '(xref-elisp-overloadable-separate-default-c-mode . c-mode) 'define-mode-local-override
522 (expand-file-name "elisp-mode-tests.el" emacs-test-dir)))
523 ))
524
525 (xref-elisp-deftest find-defs-defun-el
526 (elisp--xref-find-definitions 'xref-find-definitions)
527 (list
528 (xref-make "(defun xref-find-definitions)"
529 (xref-make-elisp-location
530 'xref-find-definitions nil
531 (expand-file-name "../../lisp/progmodes/xref.el" emacs-test-dir)))))
532
533 (xref-elisp-deftest find-defs-defun-eval
534 (elisp--xref-find-definitions (eval '(defun stephe-leake-defun ())))
535 nil)
536
537 (xref-elisp-deftest find-defs-defun-c
538 (elisp--xref-find-definitions 'buffer-live-p)
539 (list
540 (xref-make "(defun buffer-live-p)"
541 (xref-make-elisp-location 'buffer-live-p nil "src/buffer.c"))))
542
543 ;; FIXME: deftype
544
545 (xref-elisp-deftest find-defs-defun-c-defvar-c
546 (xref-backend-definitions 'elisp "system-name")
547 (list
548 (xref-make "(defvar system-name)"
549 (xref-make-elisp-location 'system-name 'defvar "src/editfns.c"))
550 (xref-make "(defun system-name)"
551 (xref-make-elisp-location 'system-name nil "src/editfns.c")))
552 )
553
554 (xref-elisp-deftest find-defs-defun-el-defvar-c
555 (xref-backend-definitions 'elisp "abbrev-mode")
556 ;; It's a minor mode, but the variable is defined in buffer.c
557 (list
558 (xref-make "(defvar abbrev-mode)"
559 (xref-make-elisp-location 'abbrev-mode 'defvar "src/buffer.c"))
560 (cons
561 (xref-make "(defun abbrev-mode)"
562 (xref-make-elisp-location
563 'abbrev-mode nil
564 (expand-file-name "../../lisp/abbrev.el" emacs-test-dir)))
565 "(define-minor-mode abbrev-mode"))
566 )
567
568 ;; Source for both variable and defun is "(define-minor-mode
569 ;; compilation-minor-mode". There is no way to tell that directly from
570 ;; the symbol, but we can use (memq sym minor-mode-list) to detect
571 ;; that the symbol is a minor mode. See `elisp--xref-find-definitions'
572 ;; for more comments.
573 ;;
574 ;; IMPROVEME: return defvar instead of defun if source near starting
575 ;; point indicates the user is searching for a variable, not a
576 ;; function.
577 (require 'compile) ;; not loaded by default at test time
578 (xref-elisp-deftest find-defs-defun-defvar-el
579 (elisp--xref-find-definitions 'compilation-minor-mode)
580 (list
581 (cons
582 (xref-make "(defun compilation-minor-mode)"
583 (xref-make-elisp-location
584 'compilation-minor-mode nil
585 (expand-file-name "../../lisp/progmodes/compile.el" emacs-test-dir)))
586 "(define-minor-mode compilation-minor-mode")
587 ))
588
589 (xref-elisp-deftest find-defs-defvar-el
590 (elisp--xref-find-definitions 'xref--marker-ring)
591 (list
592 (xref-make "(defvar xref--marker-ring)"
593 (xref-make-elisp-location
594 'xref--marker-ring 'defvar
595 (expand-file-name "../../lisp/progmodes/xref.el" emacs-test-dir)))
596 ))
597
598 (xref-elisp-deftest find-defs-defvar-c
599 (elisp--xref-find-definitions 'default-directory)
600 (list
601 (cons
602 (xref-make "(defvar default-directory)"
603 (xref-make-elisp-location 'default-directory 'defvar "src/buffer.c"))
604 ;; IMPROVEME: we might be able to compute this target
605 "DEFVAR_PER_BUFFER (\"default-directory\"")))
606
607 (xref-elisp-deftest find-defs-defvar-eval
608 (elisp--xref-find-definitions (eval '(defvar stephe-leake-defvar nil)))
609 nil)
610
611 (xref-elisp-deftest find-defs-face-el
612 (elisp--xref-find-definitions 'font-lock-keyword-face)
613 ;; 'font-lock-keyword-face is both a face and a var
614 (list
615 (xref-make "(defvar font-lock-keyword-face)"
616 (xref-make-elisp-location
617 'font-lock-keyword-face 'defvar
618 (expand-file-name "../../lisp/font-lock.el" emacs-test-dir)))
619 (xref-make "(defface font-lock-keyword-face)"
620 (xref-make-elisp-location
621 'font-lock-keyword-face 'defface
622 (expand-file-name "../../lisp/font-lock.el" emacs-test-dir)))
623 ))
624
625 (xref-elisp-deftest find-defs-face-eval
626 (elisp--xref-find-definitions (eval '(defface stephe-leake-defface nil "")))
627 nil)
628
629 (xref-elisp-deftest find-defs-feature-el
630 (elisp--xref-find-definitions 'xref)
631 (list
632 (cons
633 (xref-make "(feature xref)"
634 (xref-make-elisp-location
635 'xref 'feature
636 (expand-file-name "../../lisp/progmodes/xref.el" emacs-test-dir)))
637 ";;; Code:")
638 ))
639
640 (xref-elisp-deftest find-defs-feature-eval
641 (elisp--xref-find-definitions (eval '(provide 'stephe-leake-feature)))
642 nil)
643
644 (provide 'elisp-mode-tests)
645 ;;; elisp-mode-tests.el ends here