Function: ange-ftp-ls

ange-ftp-ls is a byte-compiled function defined in ange-ftp.el.gz.

Signature

(ange-ftp-ls FILE LSARGS PARSE &optional NO-ERROR WILDCARD)

Documentation

Return the output of a DIR or ls command done over FTP.

FILE is the full name of the remote file, LSARGS is any args to pass to the ls command, and PARSE specifies that the output should be parsed and stored away in the internal cache.

Source Code

;; Defined in /usr/src/emacs/lisp/net/ange-ftp.el.gz
(defun ange-ftp-ls (file lsargs parse &optional no-error wildcard)
  "Return the output of a `DIR' or `ls' command done over FTP.
FILE is the full name of the remote file, LSARGS is any args to pass to the
`ls' command, and PARSE specifies that the output should be parsed and stored
away in the internal cache."
  (while (string-match "^--dired\\s-+" lsargs)
    (setq lsargs (replace-match "" nil t lsargs)))
  ;; If parse is t, we assume that file is a directory. i.e. we only parse
  ;; full directory listings.
  (let* ((ange-ftp-this-file (ange-ftp-expand-file-name file))
	 (parsed (ange-ftp-ftp-name ange-ftp-this-file)))
    (if parsed
	(let* ((host (nth 0 parsed))
	       (user (nth 1 parsed))
	       (name (ange-ftp-quote-string (nth 2 parsed)))
	       (key (directory-file-name ange-ftp-this-file))
	       (host-type (ange-ftp-host-type host user))
	       (dumb (memq host-type ange-ftp-dumb-host-types))
	       result
	       temp
	       lscmd parse-func)
	  (if (string-equal name "")
	      (setq name
		    (ange-ftp-real-file-name-as-directory
		     (ange-ftp-expand-dir host user "~"))))
	  (if (and ange-ftp-ls-cache-file
		   (string-equal key ange-ftp-ls-cache-file)
		   ;; Don't care about lsargs for dumb hosts.
		   (or dumb (string-equal lsargs ange-ftp-ls-cache-lsargs)))
	      ange-ftp-ls-cache-res
	    (setq temp (ange-ftp-make-tmp-name host))
	    (if wildcard
		(progn
		  (ange-ftp-cd host user (file-name-directory name))
		  (setq lscmd (list 'ls file temp lsargs)))
	      (setq lscmd (list 'dir name temp lsargs)))
	    (unwind-protect
		(if (car (setq result (ange-ftp-send-cmd
				       host
				       user
				       lscmd
				       (format "Listing %s"
					       (ange-ftp-abbreviate-filename
						ange-ftp-this-file)))))
		    (with-current-buffer (get-buffer-create
                                          ange-ftp-data-buffer-name)
		      (erase-buffer)
		      (if (ange-ftp-real-file-readable-p temp)
			  (ange-ftp-real-insert-file-contents temp)
			(sleep-for ange-ftp-retry-time)
					;wait for file to possibly appear
			(if (ange-ftp-real-file-readable-p temp)
			    ;; Try again.
			    (ange-ftp-real-insert-file-contents temp)
			  (ange-ftp-error host user
					  (format
					   "list data file %s not readable"
					   temp))))
                      ;; remove ^M inserted by the w32 ftp client
                      (while (re-search-forward "\r$" nil t)
                        (replace-match ""))
                      (goto-char 1)
		      (run-hooks 'ange-ftp-before-parse-ls-hook)
		      (if parse
			  (ange-ftp-set-files
			   ange-ftp-this-file
			   (if (setq
				parse-func
				(cdr (assq host-type
					   ange-ftp-parse-list-func-alist)))
			       (funcall parse-func)
			     (ange-ftp-parse-dired-listing lsargs))))
                      ;; Place this hook here to convert the contents of the
                      ;; buffer to a ls compatible format if the host system
                      ;; that is being queried is other than Unix i.e. VMS
                      ;; returns an ls format that really sucks.
                      (run-hooks 'ange-ftp-after-parse-ls-hook)
		      (setq ange-ftp-ls-cache-file key
			    ange-ftp-ls-cache-lsargs lsargs
					; For dumb hosts-types this is
					; meaningless but harmless.
			    ange-ftp-ls-cache-res (buffer-string))
		      ;; (kill-buffer (current-buffer))
		      (if (equal ange-ftp-ls-cache-res "total 0\n")
			  ;; wu-ftpd seems to return a successful result
			  ;; with an empty file-listing when doing a
			  ;; `DIR /some/file/.' which leads ange-ftp to
			  ;; believe that /some/file is a directory ;-(
			  nil
			ange-ftp-ls-cache-res))
		  (if no-error
		      nil
		    (ange-ftp-error host user
				    (concat "DIR failed: " (cdr result)))))
	      (ange-ftp-del-tmp-name temp))))
      (error "This should never happen; please report this as a bug"))))