Hatalı satır numarasını göster


15

Diyelim ki emacs benim anlamadığım bir hata veriyor. Ya da belki hata "Değişken olarak sembolün değeri geçersiz: modları" diyor, ancak modesbenim kod sembolün birçok kez var , bu yüzden bazı bağlam gerekir. Emacs, hangi kodun hataya neden olduğunu bilmem için lisp kodunun satır numarasını belirtecek şekilde yapılandırılabilir mi?

Yapmayı denedim (setq stack-trace-on-error '(buffer-read-only))ve kalıcı kodu bir yığın izleme almak için bir çaba koştu. Yığın izi de yok.

Ben de edebug-defunbenim işlev çağrı ve üzerinden adım atmayı denedim . Fonksiyonun dışına çıkana kadar hata atılamaz.

(Elisp için genel hata ayıklama becerilerini geliştirirken şu anda karşılaştığım hatanın nedeniyle gerçekten ilgilenmiyorum. Lütfen bir satır numarasını, bir sexp'yi veya hata.)


Zaten olmayanı denedin nil debug-on-errormi? Bu yardımcı olmuyor mu?
Drew

Hayır! Hiçbir şey yapmıyor gibi görünüyor. (Bunu ayarladıktan tve sonra hata atma fonksiyonunu değerlendirmeye devam ettikten sonra )
Jackson

Muhtemelen, başka bir kodun hatayı yakalaması ve sadece hata mesajını yazdırmasıdır. Ayrıca debug-ignored-errorsherhangi bir hata listelemediğini kontrol edin . debug-on-signalNon- olarak ayarlarsanız nilve diğer kod hatayı işlediyse, diğer kod yapılmadan önce hatayı alabilirsiniz.
wvxvw

Şu anda benzer bir durumdayım ve bu soruyu okuyordum. Hata-yığın-izleme hatası merak ediyorum. Bu değişken Emacs 25.1'de belgelenmemiştir.
Matthias

Yanıtlar:


15

Emacs tesisler dahil ayıklama iyi bir miktar sağlar M-x toggle-debug-on-error, M-x toggle-debug-on-quit(göndererek kullanılabilir sinyali hata ayıklama USR2dışarıdan Emacs), debug-on-entry(a fonksiyonun) debug-on-message, (bir mesajın belirli bir regexp maçı görünce) ve son olarak debugalternatif olarak kendisini ile bir fonksiyonun gösterilmesi C-u C-M-x.

Hem debugve edebugtespit etmek lazım işlevsellik sunan devlet sen ilgilenen yılında, isabet o kodu değerlendirirken Emacs ebir ifade girerek.

Bununla birlikte, edebugenstrümanlı fonksiyondaki yere atlar ve bu nedenle size nereye bakmanız gerektiğine dair bir ipucu verirken (tam olarak neyi enstrüman kullandığınızı zaten bildiğinizden bu kadar saçmadır), debugbunu hiç yapmaz. debugBir arabellek değerlendirdiğinde, hata ile ilişkili nokta değerini yayar keşfettikten sonra küçük bir kesmek çıkardı ; başka bir deyişle, bu bilgiyi arabellekte kullanmak geri izlemede bir satır numarası verebilir!

(with-eval-after-load 'debug
  (defun debugger-setup-buffer (debugger-args)
    "Initialize the `*Backtrace*' buffer for entry to the debugger.
That buffer should be current already."
    (setq buffer-read-only nil)
    (erase-buffer)
    (set-buffer-multibyte t)        ;Why was it nil ?  -stef
    (setq buffer-undo-list t)
    (let ((standard-output (current-buffer))
          (print-escape-newlines t)
          (print-level 8)
          (print-length 50))
      (backtrace))
    (goto-char (point-min))
    (delete-region (point)
                   (progn
                     (search-forward "\n  debug(")
                     (forward-line (if (eq (car debugger-args) 'debug)
                                       2    ; Remove implement-debug-on-entry frame.
                                     1))
                     (point)))
    (insert "Debugger entered")
    ;; lambda is for debug-on-call when a function call is next.
    ;; debug is for debug-on-entry function called.
    (pcase (car debugger-args)
      ((or `lambda `debug)
       (insert "--entering a function:\n"))
      ;; Exiting a function.
      (`exit
       (insert "--returning value: ")
       (setq debugger-value (nth 1 debugger-args))
       (prin1 debugger-value (current-buffer))
       (insert ?\n)
       (delete-char 1)
       (insert ? )
       (beginning-of-line))
      ;; Debugger entered for an error.
      (`error
       (insert "--Lisp error: ")
       (prin1 (nth 1 debugger-args) (current-buffer))
       (insert ?\n))
      ;; debug-on-call, when the next thing is an eval.
      (`t
       (insert "--beginning evaluation of function call form:\n"))
      ;; User calls debug directly.
      (_
       (insert ": ")
       (prin1 (if (eq (car debugger-args) 'nil)
                  (cdr debugger-args) debugger-args)
              (current-buffer))
       (insert ?\n)))
    ;; After any frame that uses eval-buffer,
    ;; insert a line that states the buffer position it's reading at.
    (save-excursion
      (let ((tem eval-buffer-list))
        (while (and tem
                    (re-search-forward "^  eval-\\(buffer\\|region\\)(" nil t))
          (beginning-of-line)
          (insert (format "Error at line %d in %s: "
                          (with-current-buffer (car tem)
                            (line-number-at-pos (point)))
                          (with-current-buffer (car tem)
                            (buffer-name))))
          (pop tem))))
    (debugger-make-xrefs)))

Bununla başlıktaki orijinal soru cevaplanmalıdır. İlk etapta geri çekilme sorununa gelince, yararlı fikirlerim kalmadı.


Yardımınız için teşekkürler, ancak hat numarasını nasıl alacağımı hala anlamıyorum. M-x debug...? O zaman ne basıyorum?
Jackson

Bu kodla, tarafından yapılan geri izlemelerde bir satır numarası göreceksiniz debug, hatalı bir elisp dosyasını ziyaret ederek kontrol ederek kontrol edebilirsiniz M-x toggle-debug-on-errorve M-x eval-bufferardından sorunlu konumda bir satır numarası olan bir geri izleme açılır.
wasamasa

Kullanmazsanız bu işe yarar mı eval-buffer? Örneğin, hata ayıklayıcıda başarısız olan ve *Backtrace*arabelleğe açılan özel bir komutu çalıştıran bir klavye kısayoluna basarsanız ..
Håkon Hægland

Hayır, olmayacak. Sembolün işlev değerini alırsınız (ya bir liste ya da bayt-derlenmiş bir şey olabilir) ve hemen hemen bu.
wasamasa

4

Belki şimdi 2018 olduğu için, ancak benim durumumda, sadece wasamasa'nın önerdiği gibi hata ayıklamayı açmak zorunda kaldım: Mx hataya geçiş yapma

Bundan sonra, benim hatalı Elisp dosyamdaki Mx eval-buffer hatanın konumunu sağlayarak bağlam verdi, şöyle: Debugger entered--Lisp error: (invalid-read-syntax ")") eval-buffer() ; Reading at buffer position 523 [....]

Mx goto-char hata konumuna atlar: M-x goto-char 523


Güzel bulmak! Bu, 2017'de, geri izleme öğelerinin bir listesinde çalışmak için bu işlevi yeniden çalıştıklarında eklenmiş gibi görünüyor.
wasamasa

1

Wasamasa'nın cevabını ek bilgiler içerecek şekilde genişlettim:

(save-excursion
  (let ((tem eval-buffer-list))
    (while (and tem
                (re-search-forward "^  eval-\\(buffer\\|region\\)(" nil t))
      (beginning-of-line)
      (insert (apply 'format "Error at line %d, column %d (point %d) in %s\n"
                     (with-current-buffer (car tem)
                       (list (line-number-at-pos (point))
                             (current-column)
                             (point)
                             (buffer-name)))))
      (pop tem))))
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.