Subject: bug#33458: 27.0.50; dired loses position when reverted from outside place

From: [email-masked]
Date: Thu, 13 Dec 2018 10:39:14 +0300

Playing with patched dired.el I can see error message in some cases
while buffer creating, deleting and selecting:

"wrong-type-argument stringp nil"

Quickfix:

--- /usr/share/emacs/27.0.50/lisp/dired.el      2018-12-12 10:46:49.000000000 +0300
+++ /tmp/dired.el       2018-12-13 09:52:24.102587567 +0300
@@ -1531,7 +1531,8 @@
               (when (and (markerp point)
                          (eq (marker-buffer point) buffer))
                 (unless (and (nth 1 prev)
-                             (dired-goto-file (nth 1 prev)))
+                             (ignore-errors
+                               (dired-goto-file (nth 1 prev))))
                   (goto-char (point-min))
                  (forward-line (1- (nth 2 prev))))
                (dired-move-to-filename)

May be we need same treatment for other `dired-goto-file' lines or make
more general check for `prev's structure?

On Tue, Dec 04 2018, martin rudalics wrote:

> diff --git a/lisp/dired.el b/lisp/dired.el
> index cbd85fe..e5dc862 100644
> --- a/lisp/dired.el
> +++ b/lisp/dired.el
> @@ -1478,12 +1478,36 @@ dired-save-positions
>                 (list w
>  		     (dired-get-filename nil t)
>                       (line-number-at-pos (window-point w)))))
> -	   (get-buffer-window-list nil 0 t))))
> +	   (get-buffer-window-list nil 0 t))
> +   ;; For each window that showed the current buffer before, scan its
> +   ;; list of previous buffers.  For each association thus found save
> +   ;; a triple <point, name, line> where 'point' is that window's
> +   ;; window-point marker stored in the window's list of previous
> +   ;; buffers, 'name' is the filename at the position of 'point' and
> +   ;; 'line' is the line number at the position of 'point'.
> +   (let ((buffer (current-buffer))
> +         prevs)
> +     (walk-windows
> +      (lambda (window)
> +        (let ((prev (assq buffer (window-prev-buffers window))))
> +          (when prev
> +            (with-current-buffer buffer
> +              (save-excursion
> +                (goto-char (nth 2 prev))
> +                (setq prevs
> +                      (cons
> +                       (list (nth 2 prev)
> +                             (dired-get-filename nil t)
> +                             (line-number-at-pos (point)))
> +                       prevs)))))))
> +      'nomini t)
> +     prevs)))
>  
>  (defun dired-restore-positions (positions)
>    "Restore POSITIONS saved with `dired-save-positions'."
>    (let* ((buf-file-pos (nth 0 positions))
> -	 (buffer (nth 0 buf-file-pos)))
> +	 (buffer (nth 0 buf-file-pos))
> +         (prevs (nth 2 positions)))
>      (unless (and (nth 1 buf-file-pos)
>  		 (dired-goto-file (nth 1 buf-file-pos)))
>        (goto-char (point-min))
> @@ -1497,7 +1521,21 @@ dired-restore-positions
>  		       (dired-goto-file (nth 1 win-file-pos)))
>              (goto-char (point-min))
>  	    (forward-line (1- (nth 2 win-file-pos)))
> -	    (dired-move-to-filename)))))))
> +	    (dired-move-to-filename)))))
> +    (when prevs
> +      (with-current-buffer buffer
> +        (save-excursion
> +          (dolist (prev prevs)
> +            (let ((point (nth 0 prev)))
> +              ;; Sanity check of the point marker.
> +              (when (and (markerp point)
> +                         (eq (marker-buffer point) buffer))
> +                (unless (and (nth 0 prev)
> +                             (dired-goto-file (nth 1 prev)))
> +                  (goto-char (point-min))
> +	          (forward-line (1- (nth 2 prev))))
> +	        (dired-move-to-filename)
> +                (move-marker point (point) buffer)))))))))
>  
>  (defun dired-remember-marks (beg end)
>    "Return alist of files and their marks, from BEG to END."

-- 
WBR, Yuri