-;;; esh-util.el --- general utilities
+;;; esh-util.el --- general utilities -*- lexical-binding:t -*-
-;; Copyright (C) 1999-2011 Free Software Foundation, Inc.
+;; Copyright (C) 1999-2013 Free Software Foundation, Inc.
;; Author: John Wiegley <johnw@gnu.org>
;;; Code:
+(eval-when-compile (require 'cl-lib))
+
(defgroup eshell-util nil
"This is general utility code, meant for use by Eshell itself."
:tag "General utilities"
Numeric form is tested using the regular expression
`eshell-number-regexp'.
-NOTE: If you find that numeric conversions are intefering with the
+NOTE: If you find that numeric conversions are interfering with the
specification of filenames (for example, in calling `find-file', or
some other Lisp function that deals with files, not numbers), add the
-following in your .emacs file:
+following in your init file:
(put 'find-file 'eshell-no-numeric-conversions t)
(defmacro eshell-condition-case (tag form &rest handlers)
"If `eshell-handle-errors' is non-nil, this is `condition-case'.
Otherwise, evaluates FORM with no error handling."
+ (declare (indent 2))
(if eshell-handle-errors
`(condition-case ,tag
,form
,@handlers)
form))
-(put 'eshell-condition-case 'lisp-indent-function 2)
-
(defun eshell-find-delimiter
(open close &optional bound reverse-p backslash-p)
"From point, find the CLOSE delimiter corresponding to OPEN.
"Content of $PATH.
It might be different from \(getenv \"PATH\"\), when
`default-directory' points to a remote host.")
+(make-variable-buffer-local 'eshell-path-env)
(defun eshell-parse-colon-path (path-env)
"Split string with `parse-colon-path'.
text))
(defmacro eshell-for (for-var for-list &rest forms)
- "Iterate through a list"
+ "Iterate through a list."
+ (declare (obsolete dolist "24.1"))
+ (declare (indent 2))
`(let ((list-iter ,for-list))
(while list-iter
(let ((,for-var (car list-iter)))
,@forms)
(setq list-iter (cdr list-iter)))))
-(put 'eshell-for 'lisp-indent-function 2)
-
-(make-obsolete 'eshell-for 'dolist "24.1")
-
(defun eshell-flatten-list (args)
"Flatten any lists within ARGS, so that there are no sublists."
(let ((new-list (list t)))
(insert-file-contents eshell-hosts-file)
(goto-char (point-min))
(while (re-search-forward
- "^\\(\\S-+\\)\\s-+\\(\\S-+\\)\\(\\s-*\\(\\S-+\\)\\)?" nil t)
+ "^\\([^#[:space:]]+\\)\\s-+\\(\\S-+\\)\\(\\s-*\\(\\S-+\\)\\)?" nil t)
(if (match-string 1)
- (add-to-list 'hosts (match-string 1)))
+ (cl-pushnew (match-string 1) hosts :test #'equal))
(if (match-string 2)
- (add-to-list 'hosts (match-string 2)))
+ (cl-pushnew (match-string 2) hosts :test #'equal))
(if (match-string 4)
- (add-to-list 'hosts (match-string 4)))))
- (sort hosts 'string-lessp)))
+ (cl-pushnew (match-string 4) hosts :test #'equal))))
+ (sort hosts #'string-lessp)))
(defun eshell-read-hosts (file result-var timestamp-var)
"Read the contents of /etc/passwd for user names."
(substring string 0 sublen)
string)))
+(defvar ange-cache)
+
(and (featurep 'xemacs)
(not (fboundp 'directory-files-and-attributes))
(defun directory-files-and-attributes (directory &optional full match nosort id-format)
(cons file (eshell-file-attributes (expand-file-name file directory)))))
(directory-files directory full match nosort)))))
-(defvar ange-cache)
-
(defun eshell-directory-files-and-attributes (dir &optional full match nosort id-format)
"Make sure to use the handler for `directory-file-and-attributes'."
(let* ((dir (expand-file-name dir)))
(autoload 'parse-time-string "parse-time"))
(eval-when-compile
- (require 'ange-ftp nil t)
- (require 'tramp nil t))
+ (require 'ange-ftp nil t)) ; ange-ftp-parse-filename
+
+(defvar tramp-file-name-structure)
+(declare-function ange-ftp-ls "ange-ftp"
+ (file lsargs parse &optional no-error wildcard))
+(declare-function ange-ftp-file-modtime "ange-ftp" (file))
(defun eshell-parse-ange-ls (dir)
+ (require 'ange-ftp)
+ (require 'tramp)
(let ((ange-ftp-name-format
(list (nth 0 tramp-file-name-structure)
(nth 3 tramp-file-name-structure)