comparison lisp/emacs-lisp/edebug.el @ 51321:e005bbe7be9e

(edebug-window-list): Use push. (edebug-macrop): Use functionp. (edebug-functionp): Remove. (edebug-get-displayed-buffer-points): Use push. (edebug-set-buffer-points): Use save-current-buffer and buffer-live-p. (edebug-list-form): Remove dead code. (backquote-form): Correctly handle `(a . ,b). (edebug-mode-map, global-edebug-map): Move init to inside the defvar.
author Stefan Monnier <monnier@iro.umontreal.ca>
date Thu, 29 May 2003 22:09:24 +0000
parents c785a7ac61c7
children 8933bf0b436a
comparison
equal deleted inserted replaced
51320:418f1ce2a14e 51321:e005bbe7be9e
1 ;;; edebug.el --- a source-level debugger for Emacs Lisp 1 ;;; edebug.el --- a source-level debugger for Emacs Lisp
2 2
3 ;; Copyright (C) 1988, 89, 90, 91, 92, 93, 94, 95, 97, 1999, 2000, 2001 3 ;; Copyright (C) 1988, 89, 90, 91, 92, 93, 94, 95, 97, 1999, 2000, 01, 2003
4 ;; Free Software Foundation, Inc. 4 ;; Free Software Foundation, Inc.
5 5
6 ;; Author: Daniel LaLiberte <liberte@holonexus.org> 6 ;; Author: Daniel LaLiberte <liberte@holonexus.org>
7 ;; Maintainer: FSF 7 ;; Maintainer: FSF
8 ;; Keywords: lisp, tools, maint 8 ;; Keywords: lisp, tools, maint
300 300
301 (defun edebug-window-list () 301 (defun edebug-window-list ()
302 "Return a list of windows, in order of `next-window'." 302 "Return a list of windows, in order of `next-window'."
303 ;; This doesn't work for epoch. 303 ;; This doesn't work for epoch.
304 (let (window-list) 304 (let (window-list)
305 (walk-windows (lambda (w) (setq window-list (cons w window-list)))) 305 (walk-windows (lambda (w) (push w window-list)))
306 (nreverse window-list))) 306 (nreverse window-list)))
307 307
308 ;; Not used. 308 ;; Not used.
309 '(defun edebug-two-window-p () 309 '(defun edebug-two-window-p ()
310 "Return t if there are two windows." 310 "Return t if there are two windows."
320 (defun edebug-macrop (object) 320 (defun edebug-macrop (object)
321 "Return the macro named by OBJECT, or nil if it is not a macro." 321 "Return the macro named by OBJECT, or nil if it is not a macro."
322 (setq object (edebug-lookup-function object)) 322 (setq object (edebug-lookup-function object))
323 (if (and (listp object) 323 (if (and (listp object)
324 (eq 'macro (car object)) 324 (eq 'macro (car object))
325 (edebug-functionp (cdr object))) 325 (functionp (cdr object)))
326 object))
327
328 (defun edebug-functionp (object)
329 "Returns the function named by OBJECT, or nil if it is not a function."
330 (setq object (edebug-lookup-function object))
331 (if (or (subrp object)
332 (byte-code-function-p object)
333 (and (listp object)
334 (eq (car object) 'lambda)
335 (listp (car (cdr object)))))
336 object)) 326 object))
337 327
338 (defun edebug-sort-alist (alist function) 328 (defun edebug-sort-alist (alist function)
339 ;; Return the ALIST sorted with comparison function FUNCTION. 329 ;; Return the ALIST sorted with comparison function FUNCTION.
340 ;; This uses 'sort so the sorting is destructive. 330 ;; This uses 'sort so the sorting is destructive.
395 (defun edebug-get-displayed-buffer-points () 385 (defun edebug-get-displayed-buffer-points ()
396 ;; Return a list of buffer point pairs, for all displayed buffers. 386 ;; Return a list of buffer point pairs, for all displayed buffers.
397 (let (list) 387 (let (list)
398 (walk-windows (lambda (w) 388 (walk-windows (lambda (w)
399 (unless (eq w (selected-window)) 389 (unless (eq w (selected-window))
400 (setq list (cons (cons (window-buffer w) 390 (push (cons (window-buffer w)
401 (window-point w)) 391 (window-point w))
402 list))))) 392 list))))
403 list)) 393 list))
404 394
405 395
406 (defun edebug-set-buffer-points (buffer-points) 396 (defun edebug-set-buffer-points (buffer-points)
407 ;; Restore the buffer-points created by edebug-get-displayed-buffer-points. 397 ;; Restore the buffer-points created by edebug-get-displayed-buffer-points.
408 (let ((current-buffer (current-buffer))) 398 (save-current-buffer
409 (mapcar (function (lambda (buf-point) 399 (mapcar (lambda (buf-point)
410 (if (buffer-name (car buf-point)) ; still exists 400 (when (buffer-live-p (car buf-point))
411 (progn 401 (set-buffer (car buf-point))
412 (set-buffer (car buf-point)) 402 (goto-char (cdr buf-point))))
413 (goto-char (cdr buf-point)))))) 403 buffer-points)))
414 buffer-points)
415 (set-buffer current-buffer)))
416 404
417 (defun edebug-current-windows (which-windows) 405 (defun edebug-current-windows (which-windows)
418 ;; Get either a full window configuration or some window information. 406 ;; Get either a full window configuration or some window information.
419 (if (listp which-windows) 407 (if (listp which-windows)
420 (mapcar (function (lambda (window) 408 (mapcar (function (lambda (window)
1482 (edebug-&rest nil)) 1470 (edebug-&rest nil))
1483 ;; Skip the first offset. 1471 ;; Skip the first offset.
1484 (edebug-set-cursor cursor (edebug-cursor-expressions cursor) 1472 (edebug-set-cursor cursor (edebug-cursor-expressions cursor)
1485 (cdr (edebug-cursor-offsets cursor))) 1473 (cdr (edebug-cursor-offsets cursor)))
1486 (cond 1474 (cond
1487 ((null head) nil) ; () is legal.
1488
1489 ((symbolp head) 1475 ((symbolp head)
1490 (cond 1476 (cond
1491 ((null head) 1477 ((null head) nil) ; () is legal.
1492 (edebug-syntax-error "nil head"))
1493 ((eq head 'interactive-p) 1478 ((eq head 'interactive-p)
1494 ;; Special case: replace (interactive-p) with variable 1479 ;; Special case: replace (interactive-p) with variable
1495 (setq edebug-def-interactive 'check-it) 1480 (setq edebug-def-interactive 'check-it)
1496 (edebug-move-cursor cursor) 1481 (edebug-move-cursor cursor)
1497 (edebug-interactive-p-name)) 1482 (edebug-interactive-p-name))
1498 (t 1483 (t
1499 (cons head (edebug-list-form-args 1484 (cons head (edebug-list-form-args
1500 head (edebug-move-cursor cursor)))))) 1485 head (edebug-move-cursor cursor))))))
1501 1486
1502 ((consp head) 1487 ((consp head)
1503 (if (and (listp head) (eq (car head) ',)) 1488 (if (eq (car head) ',)
1489 ;; The head of a form should normally be a symbol or a lambda
1490 ;; expression but it can also be an unquote form to be filled
1491 ;; before evaluation. We evaluate the arguments anyway, on the
1492 ;; assumption that the unquote form will place a proper function
1493 ;; name (rather than a macro name).
1504 (edebug-match cursor '(("," def-form) body)) 1494 (edebug-match cursor '(("," def-form) body))
1505 ;; Process anonymous function and args. 1495 ;; Process anonymous function and args.
1506 ;; This assumes no anonymous macros. 1496 ;; This assumes no anonymous macros.
1507 (edebug-match-specs cursor '(lambda-expr body) 'edebug-match-specs))) 1497 (edebug-match-specs cursor '(lambda-expr body) 'edebug-match-specs)))
1508 1498
1509 (t (edebug-syntax-error 1499 (t (edebug-syntax-error
1510 "Head of list form must be a symbol or lambda expression."))) 1500 "Head of list form must be a symbol or lambda expression")))
1511 )) 1501 ))
1512 1502
1513 ;;; Matching of specs. 1503 ;;; Matching of specs.
1514 1504
1515 (defvar edebug-after-dotted-spec nil) 1505 (defvar edebug-after-dotted-spec nil)
2067 ;; Supports quotes inside backquotes, 2057 ;; Supports quotes inside backquotes,
2068 ;; but only at the top level inside unquotes. 2058 ;; but only at the top level inside unquotes.
2069 (def-edebug-spec backquote-form 2059 (def-edebug-spec backquote-form
2070 (&or 2060 (&or
2071 ([&or "," ",@"] &or ("quote" backquote-form) form) 2061 ([&or "," ",@"] &or ("quote" backquote-form) form)
2072 (backquote-form &rest backquote-form) 2062 ;; The simple version:
2063 ;; (backquote-form &rest backquote-form)
2064 ;; doesn't handle (a . ,b). The straightforward fix:
2065 ;; (backquote-form . [&or nil backquote-form])
2066 ;; uses up too much stack space.
2067 ;; Note that `(foo . ,@bar) is not legal, so we don't need to handle it.
2068 (backquote-form [&rest [&not ","] backquote-form]
2069 . [&or nil backquote-form])
2073 ;; If you use dotted forms in backquotes, replace the previous line 2070 ;; If you use dotted forms in backquotes, replace the previous line
2074 ;; with the following. This takes quite a bit more stack space, however. 2071 ;; with the following. This takes quite a bit more stack space, however.
2075 ;; (backquote-form . [&or nil backquote-form]) 2072 ;; (backquote-form . [&or nil backquote-form])
2076 (vector &rest backquote-form) 2073 (vector &rest backquote-form)
2077 sexp)) 2074 sexp))
3734 (define-key emacs-lisp-mode-map "\C-x\C-a\C-n" 'edebug-next-mode) 3731 (define-key emacs-lisp-mode-map "\C-x\C-a\C-n" 'edebug-next-mode)
3735 (define-key emacs-lisp-mode-map "\C-x\C-a\C-c" 'edebug-go-mode) 3732 (define-key emacs-lisp-mode-map "\C-x\C-a\C-c" 'edebug-go-mode)
3736 (define-key emacs-lisp-mode-map "\C-x\C-a\C-l" 'edebug-where) 3733 (define-key emacs-lisp-mode-map "\C-x\C-a\C-l" 'edebug-where)
3737 3734
3738 3735
3739 (defvar edebug-mode-map nil) 3736 (defvar edebug-mode-map
3740 (if edebug-mode-map 3737 (let ((map (copy-keymap emacs-lisp-mode-map)))
3741 nil
3742 (progn
3743 (setq edebug-mode-map (copy-keymap emacs-lisp-mode-map))
3744 ;; control 3738 ;; control
3745 (define-key edebug-mode-map " " 'edebug-step-mode) 3739 (define-key map " " 'edebug-step-mode)
3746 (define-key edebug-mode-map "n" 'edebug-next-mode) 3740 (define-key map "n" 'edebug-next-mode)
3747 (define-key edebug-mode-map "g" 'edebug-go-mode) 3741 (define-key map "g" 'edebug-go-mode)
3748 (define-key edebug-mode-map "G" 'edebug-Go-nonstop-mode) 3742 (define-key map "G" 'edebug-Go-nonstop-mode)
3749 (define-key edebug-mode-map "t" 'edebug-trace-mode) 3743 (define-key map "t" 'edebug-trace-mode)
3750 (define-key edebug-mode-map "T" 'edebug-Trace-fast-mode) 3744 (define-key map "T" 'edebug-Trace-fast-mode)
3751 (define-key edebug-mode-map "c" 'edebug-continue-mode) 3745 (define-key map "c" 'edebug-continue-mode)
3752 (define-key edebug-mode-map "C" 'edebug-Continue-fast-mode) 3746 (define-key map "C" 'edebug-Continue-fast-mode)
3753 3747
3754 ;;(define-key edebug-mode-map "f" 'edebug-forward) not implemented 3748 ;;(define-key map "f" 'edebug-forward) not implemented
3755 (define-key edebug-mode-map "f" 'edebug-forward-sexp) 3749 (define-key map "f" 'edebug-forward-sexp)
3756 (define-key edebug-mode-map "h" 'edebug-goto-here) 3750 (define-key map "h" 'edebug-goto-here)
3757 3751
3758 (define-key edebug-mode-map "I" 'edebug-instrument-callee) 3752 (define-key map "I" 'edebug-instrument-callee)
3759 (define-key edebug-mode-map "i" 'edebug-step-in) 3753 (define-key map "i" 'edebug-step-in)
3760 (define-key edebug-mode-map "o" 'edebug-step-out) 3754 (define-key map "o" 'edebug-step-out)
3761 3755
3762 ;; quitting and stopping 3756 ;; quitting and stopping
3763 (define-key edebug-mode-map "q" 'top-level) 3757 (define-key map "q" 'top-level)
3764 (define-key edebug-mode-map "Q" 'edebug-top-level-nonstop) 3758 (define-key map "Q" 'edebug-top-level-nonstop)
3765 (define-key edebug-mode-map "a" 'abort-recursive-edit) 3759 (define-key map "a" 'abort-recursive-edit)
3766 (define-key edebug-mode-map "S" 'edebug-stop) 3760 (define-key map "S" 'edebug-stop)
3767 3761
3768 ;; breakpoints 3762 ;; breakpoints
3769 (define-key edebug-mode-map "b" 'edebug-set-breakpoint) 3763 (define-key map "b" 'edebug-set-breakpoint)
3770 (define-key edebug-mode-map "u" 'edebug-unset-breakpoint) 3764 (define-key map "u" 'edebug-unset-breakpoint)
3771 (define-key edebug-mode-map "B" 'edebug-next-breakpoint) 3765 (define-key map "B" 'edebug-next-breakpoint)
3772 (define-key edebug-mode-map "x" 'edebug-set-conditional-breakpoint) 3766 (define-key map "x" 'edebug-set-conditional-breakpoint)
3773 (define-key edebug-mode-map "X" 'edebug-set-global-break-condition) 3767 (define-key map "X" 'edebug-set-global-break-condition)
3774 3768
3775 ;; evaluation 3769 ;; evaluation
3776 (define-key edebug-mode-map "r" 'edebug-previous-result) 3770 (define-key map "r" 'edebug-previous-result)
3777 (define-key edebug-mode-map "e" 'edebug-eval-expression) 3771 (define-key map "e" 'edebug-eval-expression)
3778 (define-key edebug-mode-map "\C-x\C-e" 'edebug-eval-last-sexp) 3772 (define-key map "\C-x\C-e" 'edebug-eval-last-sexp)
3779 (define-key edebug-mode-map "E" 'edebug-visit-eval-list) 3773 (define-key map "E" 'edebug-visit-eval-list)
3780 3774
3781 ;; views 3775 ;; views
3782 (define-key edebug-mode-map "w" 'edebug-where) 3776 (define-key map "w" 'edebug-where)
3783 (define-key edebug-mode-map "v" 'edebug-view-outside) ;; maybe obsolete?? 3777 (define-key map "v" 'edebug-view-outside) ;; maybe obsolete??
3784 (define-key edebug-mode-map "p" 'edebug-bounce-point) 3778 (define-key map "p" 'edebug-bounce-point)
3785 (define-key edebug-mode-map "P" 'edebug-view-outside) ;; same as v 3779 (define-key map "P" 'edebug-view-outside) ;; same as v
3786 (define-key edebug-mode-map "W" 'edebug-toggle-save-windows) 3780 (define-key map "W" 'edebug-toggle-save-windows)
3787 3781
3788 ;; misc 3782 ;; misc
3789 (define-key edebug-mode-map "?" 'edebug-help) 3783 (define-key map "?" 'edebug-help)
3790 (define-key edebug-mode-map "d" 'edebug-backtrace) 3784 (define-key map "d" 'edebug-backtrace)
3791 3785
3792 (define-key edebug-mode-map "-" 'negative-argument) 3786 (define-key map "-" 'negative-argument)
3793 3787
3794 ;; statistics 3788 ;; statistics
3795 (define-key edebug-mode-map "=" 'edebug-temp-display-freq-count) 3789 (define-key map "=" 'edebug-temp-display-freq-count)
3796 3790
3797 ;; GUD bindings 3791 ;; GUD bindings
3798 (define-key edebug-mode-map "\C-c\C-s" 'edebug-step-mode) 3792 (define-key map "\C-c\C-s" 'edebug-step-mode)
3799 (define-key edebug-mode-map "\C-c\C-n" 'edebug-next-mode) 3793 (define-key map "\C-c\C-n" 'edebug-next-mode)
3800 (define-key edebug-mode-map "\C-c\C-c" 'edebug-go-mode) 3794 (define-key map "\C-c\C-c" 'edebug-go-mode)
3801 3795
3802 (define-key edebug-mode-map "\C-x " 'edebug-set-breakpoint) 3796 (define-key map "\C-x " 'edebug-set-breakpoint)
3803 (define-key edebug-mode-map "\C-c\C-d" 'edebug-unset-breakpoint) 3797 (define-key map "\C-c\C-d" 'edebug-unset-breakpoint)
3804 (define-key edebug-mode-map "\C-c\C-t" 3798 (define-key map "\C-c\C-t"
3805 (function (lambda () (edebug-set-breakpoint t)))) 3799 (lambda () (interactive) (edebug-set-breakpoint t)))
3806 (define-key edebug-mode-map "\C-c\C-l" 'edebug-where) 3800 (define-key map "\C-c\C-l" 'edebug-where)
3807 )) 3801 map))
3808 3802
3809 ;; Autoloading these global bindings doesn't make sense because 3803 ;; Autoloading these global bindings doesn't make sense because
3810 ;; they cannot be used anyway unless Edebug is already loaded and active. 3804 ;; they cannot be used anyway unless Edebug is already loaded and active.
3811 3805
3812 (defvar global-edebug-prefix "\^XX" 3806 (defvar global-edebug-prefix "\^XX"
3813 "Prefix key for global edebug commands, available from any buffer.") 3807 "Prefix key for global edebug commands, available from any buffer.")
3814 3808
3815 (defvar global-edebug-map nil 3809 (defvar global-edebug-map
3810 (let ((map (make-sparse-keymap)))
3811
3812 (define-key map " " 'edebug-step-mode)
3813 (define-key map "g" 'edebug-go-mode)
3814 (define-key map "G" 'edebug-Go-nonstop-mode)
3815 (define-key map "t" 'edebug-trace-mode)
3816 (define-key map "T" 'edebug-Trace-fast-mode)
3817 (define-key map "c" 'edebug-continue-mode)
3818 (define-key map "C" 'edebug-Continue-fast-mode)
3819
3820 ;; breakpoints
3821 (define-key map "b" 'edebug-set-breakpoint)
3822 (define-key map "u" 'edebug-unset-breakpoint)
3823 (define-key map "x" 'edebug-set-conditional-breakpoint)
3824 (define-key map "X" 'edebug-set-global-break-condition)
3825
3826 ;; views
3827 (define-key map "w" 'edebug-where)
3828 (define-key map "W" 'edebug-toggle-save-windows)
3829
3830 ;; quitting
3831 (define-key map "q" 'top-level)
3832 (define-key map "Q" 'edebug-top-level-nonstop)
3833 (define-key map "a" 'abort-recursive-edit)
3834
3835 ;; statistics
3836 (define-key map "=" 'edebug-display-freq-count)
3837 map)
3816 "Global map of edebug commands, available from any buffer.") 3838 "Global map of edebug commands, available from any buffer.")
3817 3839
3818 (if global-edebug-map 3840 (global-unset-key global-edebug-prefix)
3819 nil 3841 (global-set-key global-edebug-prefix global-edebug-map)
3820 (setq global-edebug-map (make-sparse-keymap)) 3842
3821
3822 (global-unset-key global-edebug-prefix)
3823 (global-set-key global-edebug-prefix global-edebug-map)
3824
3825 (define-key global-edebug-map " " 'edebug-step-mode)
3826 (define-key global-edebug-map "g" 'edebug-go-mode)
3827 (define-key global-edebug-map "G" 'edebug-Go-nonstop-mode)
3828 (define-key global-edebug-map "t" 'edebug-trace-mode)
3829 (define-key global-edebug-map "T" 'edebug-Trace-fast-mode)
3830 (define-key global-edebug-map "c" 'edebug-continue-mode)
3831 (define-key global-edebug-map "C" 'edebug-Continue-fast-mode)
3832
3833 ;; breakpoints
3834 (define-key global-edebug-map "b" 'edebug-set-breakpoint)
3835 (define-key global-edebug-map "u" 'edebug-unset-breakpoint)
3836 (define-key global-edebug-map "x" 'edebug-set-conditional-breakpoint)
3837 (define-key global-edebug-map "X" 'edebug-set-global-break-condition)
3838
3839 ;; views
3840 (define-key global-edebug-map "w" 'edebug-where)
3841 (define-key global-edebug-map "W" 'edebug-toggle-save-windows)
3842
3843 ;; quitting
3844 (define-key global-edebug-map "q" 'top-level)
3845 (define-key global-edebug-map "Q" 'edebug-top-level-nonstop)
3846 (define-key global-edebug-map "a" 'abort-recursive-edit)
3847
3848 ;; statistics
3849 (define-key global-edebug-map "=" 'edebug-display-freq-count)
3850 )
3851 3843
3852 (defun edebug-help () 3844 (defun edebug-help ()
3853 (interactive) 3845 (interactive)
3854 (describe-function 'edebug-mode)) 3846 (describe-function 'edebug-mode))
3855 3847