File: efs-cms-knet.el

package info (click to toggle)
xemacs20 20.4-13
  • links: PTS
  • area: main
  • in suites: slink
  • size: 67,324 kB
  • ctags: 57,643
  • sloc: lisp: 586,197; ansic: 184,662; sh: 4,296; asm: 3,179; makefile: 2,021; perl: 1,059; csh: 96; sed: 22
file content (245 lines) | stat: -rw-r--r-- 8,632 bytes parent folder | download | duplicates (3)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
;; -*-Emacs-Lisp-*-
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;;
;; File:         efs-cms-knet.el
;; Release:      $efs release: 1.15 $
;; Version:      #Revision: 1.1 $
;; RCS:          
;; Description:  CMS support for efs using KNET/VM server
;; Authors:	 Sandy Rutherford <sandy@ibm550.sissa.it>
;;               Joerg-Martin Schwarz <schwarz@hal1.physik.uni-dortmund.de>
;; Created:      Wed Mar 23 14:39:00 1994 by schwarz on hal1 from efs-cms.el
;; Modified:     Sun Nov 27 11:45:58 1994 by sandy on gandalf
;; Language:     Emacs-Lisp
;;
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

;;; This file is part of efs. See efs.el for copyright
;;; (it's copylefted) and warrranty (there isn't one) information.

(provide 'efs-cms-knet)
(require 'efs)

(defconst efs-cms-knet-version
  (concat (substring "$efs release: 1.15 $" 14 -2)
	  "/"
	  (substring "#Revision: 1.1 $" 11 -2)))

;;;; ------------------------------------------------------------
;;;; CMS support for KNET-VM server
;;;; ------------------------------------------------------------

;;; efs has full support, including tree dired support, for hosts running
;;; CMS.  It should be able to automatically recognize any CMS machine.
;;; We would be grateful if you would report any failures to automatically
;;; recognize a CMS host as a bug.
;;; 
;;; Filename syntax:
;;;
;;; KNET/VM Support (J. M. Schwarz, Mar 12, 1994):
;;; This code has been developed and tested with 
;;; "KNET/VM FTP server Release 3.2.0" by Spartacus.
;;;
;;; This server uses not only a different listing format than the one used in
;;; efs-cms.el, but also handles minidisks differently. 
;;; The cd command for changing minidisk is not supported, 
;;; instead a full filename syntax "FILENAME.FILETYPE.FM" is used, where
;;; FM is the filemode. To access a file "PROFILE EXEC A0", efs uses a
;;; syntax "/cms-hostname:/A:/PROFILE.EXEC"   (Note the ':')
;;; 
;;; In this directory notation, "/A0:" is actually a subset of the "/A:"
;;; directory.

(efs-defun efs-send-pwd cms-knet (host user &optional xpwd)
  ;; cms-knet has no concept of current directory.
  ;; Is it safe to always assume this is the user's home?
  (cons "A" ""))

(efs-defun efs-fix-path cms-knet (path &optional reverse)
  ;; Convert PATH from UNIX-ish to CMS. If REVERSE is given, convert
  ;; from CMS to UNIX. Actually, CMS doesn't have a full pathname syntax,
  ;; so we fudge things by sending cd's.
  (if reverse
      ;; Since we only convert output from a pwd in this direction,
      ;; this should never be applied, as PWD doesn't work for this server.
      (concat "/" path "/")
    (efs-save-match-data
      (if (string-match "^/[A-Z]/\\([-A-Z0-9$_+@:]+\\.[-A-Z0-9$_+@:]+\\)$"
			path)
	  (concat
	   (substring path (match-beginning 1) (match-end 1))
	   "."
	   ;; minidisk
	   (substring path 1 2))
	(error "Invalid CMS-KNET filename")))))

(efs-defun efs-fix-dir-path cms-knet (dir-path)
  ;; Convert path from UNIX-ish to CMS-KNET ready for a DIRectory listing.
  (cond
   ((string-equal "/" dir-path)
    "*.*.*")
   ((string-match
     "^/[A-Z]/\\([-A-Z0-9$._+@:]+\\.[-A-Z0-9$._+@:]+\\)?$"
     dir-path)
    (concat 
     (if (match-beginning 1)
	 (substring dir-path (match-beginning 1) (match-end 1))
       "*")
     "."
     (substring dir-path 1 2)))
   (t (error "Invalid CMS-KNET pathname"))))

(defconst efs-cms-knet-file-name-regexp
  (concat
   "^  *\\([-A-Z0-9$_+@:]+\\) +\\([-A-Z0-9$_+@:]+\\) +"
   "\\([A-Z]\\)[0-9] +[VF] +[0-9]+ "))

(efs-defun efs-parse-listing cms-knet
  (host user dir path &optional switches)
  ;; Parse the current buffer which is assumed to be a CMS directory listing.
  ;; HOST = remote host name
  ;; USER = remote user name
  ;; DIR = directory as a full remote path
  ;; PATH = directory as a full efs-path
  (let ((tbl (efs-make-hashtable)))
    (goto-char (point-min))
    (efs-save-match-data
      (if (string-equal dir "/")
	  (let ((case-fold (memq 'cms-knet efs-case-insensitive-host-types))
		tbl-alist md md-tbl)
	    (while (re-search-forward efs-cms-knet-file-name-regexp nil t)
	      (setq md (buffer-substring (match-beginning 3) (match-end 3))
		    md-tbl (or (cdr (assoc md tbl-alist))
			       (let ((new-tbl (efs-make-hashtable)))
				 (setq tbl-alist
				       (cons (cons md new-tbl)
					     tbl-alist))
				 new-tbl)))
	      (efs-put-hash-entry md '(t) tbl)
	      (efs-put-hash-entry (concat
				   (buffer-substring (match-beginning 1)
						     (match-end 1))
				   "."
				   (buffer-substring (match-beginning 2)
						     (match-end 2)))
				  '(nil) md-tbl)
	      (forward-line 1))
	    (while tbl-alist
	      (setq md (car (car tbl-alist))
		    md-tbl (cdr (car tbl-alist)))
	      (efs-put-hash-entry "." '(t) md-tbl)
	      (efs-put-hash-entry ".." '(t) md-tbl)
	      (efs-put-hash-entry (concat path md "/") md-tbl
				  efs-files-hashtable case-fold)
	      (setq tbl-alist (cdr tbl-alist))))
	(while (re-search-forward efs-cms-knet-file-name-regexp nil t)
	  (efs-put-hash-entry
	   (concat (buffer-substring (match-beginning 1)
				     (match-end 1))
		   "."
		   (buffer-substring (match-beginning 2)
				     (match-end 2)))
	   '(nil) tbl)
	  (forward-line 1)))
      (efs-put-hash-entry "." '(t) tbl)
      (efs-put-hash-entry ".." '(t) tbl))
    tbl))

(efs-defun efs-allow-child-lookup cms-knet (host user dir file)
  ;; Returns t if FILE in directory DIR could possibly be a subdir
  ;; according to its file-name syntax, and therefore a child listing should
  ;; be attempted.
  
  ;; CMS file system is flat. Only minidisks are "subdirs".
  (string-equal "/" dir))

;;; Tree dired support:

(defconst efs-dired-cms-re-exe
  "^. +[-A-Z0-9$_+@:]+ +\\(EXEC\\|MODULE\\) "
  "Regular expression to use to search for CMS executables.")

(or (assq 'cms efs-dired-re-exe-alist)
    (setq efs-dired-re-exe-alist
	  (cons (cons 'cms-knet efs-dired-cms-re-exe)
		efs-dired-re-exe-alist)))

(efs-defun efs-dired-insert-headerline cms-knet (dir)
  ;; CMS has no total line, so we insert a blank line for
  ;; aesthetics.
  (insert "\n")
  (forward-char -1)
  (efs-real-dired-insert-headerline dir))

(efs-defun efs-dired-manual-move-to-filename cms-knet
  (&optional raise-error bol eol)
  ;; In dired, move to the first char of filename on this line.
  ;; This is the CMS version.
  (or eol (setq eol (save-excursion (skip-chars-forward "^\n\r") (point))))
  (let (case-fold-search)
    (if bol
	(goto-char bol)
      (skip-chars-backward "^\n\r")
      (setq bol (point)))
    (if (re-search-forward efs-cms-knet-file-name-regexp eol t)
	(goto-char (match-beginning 1))
      (if raise-error
	  (error "No file on this line.")
	(goto-char bol)))))

(efs-defun efs-dired-manual-move-to-end-of-filename cms-knet
  (&optional no-error bol eol)
  ;; Assumes point is at beginning of filename.
  ;; So, it should be called only after (dired-move-to-filename t).
  ;; case-fold-search must be nil, at least for VMS.
  ;; On failure, signals an error or returns nil.
  ;; This is the CMS version.
  (and selective-display
       (null no-error)
       (eq (char-after
	    (1- (or bol (save-excursion
			  (skip-chars-backward "^\r\n")
			  (point)))))
	   ?\r)
       ;; File is hidden or omitted.
       (cond
	((dired-subdir-hidden-p (dired-current-directory))
	 (error
	  (substitute-command-keys
	   "File line is hidden. Type \\[dired-hide-subdir] to unhide.")))
	((error
	  (substitute-command-keys
	   "File line is omitted. Type \\[dired-omit-toggle] to un-omit."
	   )))))
  (if (looking-at "[-A-Z0-9$_+@:]+ +[-A-Z0-9$_+@:]+ +[A-Z][0-9] ")
      (goto-char (- (match-end 0) 2)) ; return point
    (if no-error
	nil
      (error "No file on this line."))))

(efs-defun efs-dired-get-filename cms-knet
  (&optional localp no-error-if-not-filep)
  (let ((name (efs-real-dired-get-filename 'no-dir no-error-if-not-filep)))
    (and name
	 (if (string-match
	      "^\\([-A-Z0-9$_+@:]+\\) +\\([-A-Z0-9$_+@:]+\\) +\\([A-Z]\\)$"
	      name)
	     (let* ((dir (dired-current-directory))
		    (rdir (nth 2 (efs-ftp-path dir))))
	       (setq name (concat (substring name (match-beginning 1)
					     (match-end 1))
				  "."
				  (substring name (match-beginning 2)
					     (match-end 2))))
	       (if (string-equal rdir "/")
		   (setq name (concat (substring name (match-beginning 3)
						 (match-end 3)) "/" name)))
	       (if (eq localp 'no-dir)
		   name
		 (concat (if localp
			     (dired-current-directory localp)
			   dir)
			 name)))
	   (error "Strange CMS-KNET file name %s" name)))))

;;; end of efs-cms-knet.el