mirror of
git://git.sv.gnu.org/emacs.git
synced 2025-12-17 03:10:58 -08:00
* net/tramp.el (top): Move loading of tramp-util.el and
tramp-vc.el to tramp-compat.el. (tramp-make-tramp-temp-file): Complete rewrite. Create remote temporary file if possible, in order to avoid a security hole. (tramp-do-copy-or-rename-file-out-of-band) (tramp-maybe-open-connection): Call `tramp-make-tramp-temp-file' with DONT-CREATE, because the connection is not setup yet. (tramp-handle-process-file): Rewrite temporary file handling. (tramp-completion-mode): New defvar. (tramp-completion-mode-p): Use it. * net/tramp-compat.el (top): Load tramp-util.el and tramp-vc.el. * net/tramp-fish.el (tramp-fish-handle-process-file): Rewrite temporary file handling.
This commit is contained in:
parent
ea3fc256d4
commit
a6e9632782
4 changed files with 129 additions and 74 deletions
|
|
@ -1,3 +1,21 @@
|
||||||
|
2007-10-06 Michael Albinus <michael.albinus@gmx.de>
|
||||||
|
|
||||||
|
* net/tramp.el (top): Move loading of tramp-util.el and
|
||||||
|
tramp-vc.el to tramp-compat.el.
|
||||||
|
(tramp-make-tramp-temp-file): Complete rewrite. Create remote
|
||||||
|
temporary file if possible, in order to avoid a security hole.
|
||||||
|
(tramp-do-copy-or-rename-file-out-of-band)
|
||||||
|
(tramp-maybe-open-connection): Call `tramp-make-tramp-temp-file'
|
||||||
|
with DONT-CREATE, because the connection is not setup yet.
|
||||||
|
(tramp-handle-process-file): Rewrite temporary file handling.
|
||||||
|
(tramp-completion-mode): New defvar.
|
||||||
|
(tramp-completion-mode-p): Use it.
|
||||||
|
|
||||||
|
* net/tramp-compat.el (top): Load tramp-util.el and tramp-vc.el.
|
||||||
|
|
||||||
|
* net/tramp-fish.el (tramp-fish-handle-process-file): Rewrite
|
||||||
|
temporary file handling.
|
||||||
|
|
||||||
2007-10-06 Eric S. Raymond <esr@snark.thyrsus.com>
|
2007-10-06 Eric S. Raymond <esr@snark.thyrsus.com>
|
||||||
|
|
||||||
* vc.el: workfile version -> focus version change. Port various
|
* vc.el: workfile version -> focus version change. Port various
|
||||||
|
|
|
||||||
|
|
@ -40,6 +40,32 @@
|
||||||
(require 'timer-funcs)
|
(require 'timer-funcs)
|
||||||
(require 'timer))
|
(require 'timer))
|
||||||
|
|
||||||
|
;; tramp-util offers integration into other (X)Emacs packages like
|
||||||
|
;; compile.el, gud.el etc. Not necessary in Emacs 23.
|
||||||
|
(eval-after-load "tramp"
|
||||||
|
;; We check whether `start-file-process' is an alias.
|
||||||
|
'(when (or (not (fboundp 'start-file-process))
|
||||||
|
(symbolp (symbol-function 'start-file-process)))
|
||||||
|
(require 'tramp-util)
|
||||||
|
(add-hook 'tramp-unload-hook
|
||||||
|
'(lambda ()
|
||||||
|
(when (featurep 'tramp-util)
|
||||||
|
(unload-feature 'tramp-util 'force))))))
|
||||||
|
|
||||||
|
;; Make sure that we get integration with the VC package. When it
|
||||||
|
;; is loaded, we need to pull in the integration module. Not
|
||||||
|
;; necessary in Emacs 23.
|
||||||
|
(eval-after-load "vc"
|
||||||
|
(eval-after-load "tramp"
|
||||||
|
;; We check whether `start-file-process' is an alias.
|
||||||
|
'(when (or (not (fboundp 'start-file-process))
|
||||||
|
(symbolp (symbol-function 'start-file-process)))
|
||||||
|
(require 'tramp-vc)
|
||||||
|
(add-hook 'tramp-unload-hook
|
||||||
|
'(lambda ()
|
||||||
|
(when (featurep 'tramp-vc)
|
||||||
|
(unload-feature 'tramp-vc 'force)))))))
|
||||||
|
|
||||||
;; Avoid byte-compiler warnings if the byte-compiler supports this.
|
;; Avoid byte-compiler warnings if the byte-compiler supports this.
|
||||||
;; Currently, XEmacs supports this.
|
;; Currently, XEmacs supports this.
|
||||||
(when (featurep 'xemacs)
|
(when (featurep 'xemacs)
|
||||||
|
|
|
||||||
|
|
@ -734,8 +734,8 @@ target of the symlink differ."
|
||||||
(error "Implementation does not handle immediate return"))
|
(error "Implementation does not handle immediate return"))
|
||||||
|
|
||||||
(with-parsed-tramp-file-name default-directory nil
|
(with-parsed-tramp-file-name default-directory nil
|
||||||
(let ((temp-name-prefix (tramp-make-tramp-temp-file v))
|
(let (command input tmpinput output tmpoutput stderr tmpstderr
|
||||||
command input output stderr outbuf tmpfile ret)
|
outbuf tmpfile ret)
|
||||||
;; Compute command.
|
;; Compute command.
|
||||||
(setq command (mapconcat 'tramp-shell-quote-argument
|
(setq command (mapconcat 'tramp-shell-quote-argument
|
||||||
(cons program args) " "))
|
(cons program args) " "))
|
||||||
|
|
@ -747,15 +747,14 @@ target of the symlink differ."
|
||||||
;; INFILE is on the same remote host.
|
;; INFILE is on the same remote host.
|
||||||
(setq input (with-parsed-tramp-file-name infile nil localname))
|
(setq input (with-parsed-tramp-file-name infile nil localname))
|
||||||
;; INFILE must be copied to remote host.
|
;; INFILE must be copied to remote host.
|
||||||
(setq input (concat temp-name-prefix ".in"))
|
(setq input (tramp-make-tramp-temp-file v)
|
||||||
(copy-file
|
tmpinput (tramp-make-tramp-file-name method user host input))
|
||||||
infile
|
(copy-file infile tmpinput t)))
|
||||||
(tramp-make-tramp-file-name method user host input)
|
|
||||||
t)))
|
|
||||||
(when input (setq command (format "%s <%s" command input)))
|
(when input (setq command (format "%s <%s" command input)))
|
||||||
|
|
||||||
;; Determine output.
|
;; Determine output.
|
||||||
(setq output (concat temp-name-prefix ".out"))
|
(setq output (tramp-make-tramp-temp-file v)
|
||||||
|
tmpoutput (tramp-make-tramp-file-name method user host output))
|
||||||
(cond
|
(cond
|
||||||
;; Just a buffer
|
;; Just a buffer
|
||||||
((bufferp destination)
|
((bufferp destination)
|
||||||
|
|
@ -781,7 +780,9 @@ target of the symlink differ."
|
||||||
(cadr destination) nil localname))
|
(cadr destination) nil localname))
|
||||||
;; stderr must be copied to remote host. The temporary
|
;; stderr must be copied to remote host. The temporary
|
||||||
;; file must be deleted after execution.
|
;; file must be deleted after execution.
|
||||||
(setq stderr (concat temp-name-prefix ".err"))))
|
(setq stderr (tramp-make-tramp-temp-file v)
|
||||||
|
tmpstderr (tramp-make-tramp-file-name
|
||||||
|
method user host stderr))))
|
||||||
;; stderr to be discarded
|
;; stderr to be discarded
|
||||||
((null (cadr destination))
|
((null (cadr destination))
|
||||||
(setq stderr "/dev/null"))))
|
(setq stderr "/dev/null"))))
|
||||||
|
|
@ -790,9 +791,6 @@ target of the symlink differ."
|
||||||
(setq outbuf (current-buffer))))
|
(setq outbuf (current-buffer))))
|
||||||
(when stderr (setq command (format "%s 2>%s" command stderr)))
|
(when stderr (setq command (format "%s 2>%s" command stderr)))
|
||||||
|
|
||||||
;; If we have a temporary file, it must be removed after operation.
|
|
||||||
(when (and input (string-match temp-name-prefix input))
|
|
||||||
(setq command (format "%s; rm %s" command input)))
|
|
||||||
;; Goto working directory.
|
;; Goto working directory.
|
||||||
(unless
|
(unless
|
||||||
(tramp-fish-send-command-and-check
|
(tramp-fish-send-command-and-check
|
||||||
|
|
@ -821,16 +819,15 @@ target of the symlink differ."
|
||||||
;; We should show the output anyway.
|
;; We should show the output anyway.
|
||||||
(when outbuf
|
(when outbuf
|
||||||
(with-current-buffer outbuf (insert-file-contents tmpfile))
|
(with-current-buffer outbuf (insert-file-contents tmpfile))
|
||||||
(when display (display-buffer outbuf)))
|
(when display (display-buffer outbuf))))
|
||||||
;; Remove output file.
|
|
||||||
(delete-file (tramp-make-tramp-file-name method user host output)))
|
|
||||||
;; When the user did interrupt, we should do it also.
|
;; When the user did interrupt, we should do it also.
|
||||||
(error (setq ret 1)))
|
(error (setq ret 1)))
|
||||||
(unless ret
|
|
||||||
;; Provide error file.
|
;; Provide error file.
|
||||||
(when (and stderr (string-match temp-name-prefix stderr))
|
(when tmpstderr (rename-file tmpstderr (cadr destination) t))
|
||||||
(rename-file (tramp-make-tramp-file-name method user host stderr)
|
;; Cleanup.
|
||||||
(cadr destination) t)))
|
(when tmpinput (delete-file tmpinput))
|
||||||
|
(when tmpoutput (delete-file tmpoutput))
|
||||||
;; Return exit status.
|
;; Return exit status.
|
||||||
ret)))
|
ret)))
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -149,16 +149,7 @@
|
||||||
(add-hook 'tramp-unload-hook
|
(add-hook 'tramp-unload-hook
|
||||||
'(lambda ()
|
'(lambda ()
|
||||||
(when (featurep 'tramp-gw)
|
(when (featurep 'tramp-gw)
|
||||||
(unload-feature 'tramp-gw 'force)))))
|
(unload-feature 'tramp-gw 'force)))))))
|
||||||
|
|
||||||
;; tramp-util offers integration into other (X)Emacs packages like
|
|
||||||
;; compile.el, gud.el etc. Not necessary in Emacs 23.
|
|
||||||
(unless (functionp 'start-file-process)
|
|
||||||
(require 'tramp-util)
|
|
||||||
(add-hook 'tramp-unload-hook
|
|
||||||
'(lambda ()
|
|
||||||
(when (featurep 'tramp-util)
|
|
||||||
(unload-feature 'tramp-util 'force)))))))
|
|
||||||
|
|
||||||
;;; User Customizable Internal Variables:
|
;;; User Customizable Internal Variables:
|
||||||
|
|
||||||
|
|
@ -1974,13 +1965,42 @@ The intent is to protect against `obsolete variable' warnings."
|
||||||
(put 'tramp-let-maybe 'lisp-indent-function 2)
|
(put 'tramp-let-maybe 'lisp-indent-function 2)
|
||||||
(put 'tramp-let-maybe 'edebug-form-spec t)
|
(put 'tramp-let-maybe 'edebug-form-spec t)
|
||||||
|
|
||||||
(defsubst tramp-make-tramp-temp-file (vec)
|
(defsubst tramp-make-tramp-temp-file (vec &optional dont-create)
|
||||||
(format
|
"Create a temporary file on the remote host identified by VEC.
|
||||||
"/tmp/%s%s"
|
Return the local name of the temporary file.
|
||||||
tramp-temp-name-prefix
|
If DONT-CREATE is non-nil, just the file name is returned without
|
||||||
(if (get-buffer-process (tramp-get-connection-buffer vec))
|
creation of the temporary file. This is not the preferred way to run,
|
||||||
(process-id (get-buffer-process (tramp-get-connection-buffer vec)))
|
but it is necessary during connection setup, because we cannot create
|
||||||
(emacs-pid))))
|
a remote file at this time. This parameter shall NOT be set to
|
||||||
|
non-nil else."
|
||||||
|
(if dont-create
|
||||||
|
;; It sounds a little bit stupid to create a LOCAL file name.
|
||||||
|
;; But we intend to use the remote directory "/tmp", and we have
|
||||||
|
;; no chance to check whether a temporary file exists already
|
||||||
|
;; remotely, because we have no working connection yet.
|
||||||
|
(make-temp-name (expand-file-name tramp-temp-name-prefix "/tmp"))
|
||||||
|
|
||||||
|
(let ((prefix
|
||||||
|
(tramp-make-tramp-file-name
|
||||||
|
(tramp-file-name-method vec)
|
||||||
|
(tramp-file-name-user vec)
|
||||||
|
(tramp-file-name-host vec)
|
||||||
|
(expand-file-name tramp-temp-name-prefix "/tmp")))
|
||||||
|
result)
|
||||||
|
(while (not result)
|
||||||
|
;; `make-temp-file' would be the first choice for
|
||||||
|
;; implementation. But it calls `write-region' internally,
|
||||||
|
;; which also needs a temporary file - we would end in an
|
||||||
|
;; infinite loop.
|
||||||
|
(setq result (make-temp-name prefix))
|
||||||
|
(if (file-exists-p result)
|
||||||
|
(setq result nil)
|
||||||
|
;; This creates the file by side effect.
|
||||||
|
(set-file-times result)
|
||||||
|
(set-file-modes result (tramp-octal-to-decimal "0700"))))
|
||||||
|
|
||||||
|
;; Return the local part.
|
||||||
|
(with-parsed-tramp-file-name result nil localname))))
|
||||||
|
|
||||||
|
|
||||||
;;; Config Manipulation Functions:
|
;;; Config Manipulation Functions:
|
||||||
|
|
@ -3188,7 +3208,7 @@ be a local filename. The method used must be an out-of-band method."
|
||||||
|
|
||||||
;; Compose copy command.
|
;; Compose copy command.
|
||||||
(setq spec `((?h . ,host) (?u . ,user) (?p . ,port)
|
(setq spec `((?h . ,host) (?u . ,user) (?p . ,port)
|
||||||
(?t . ,(tramp-make-tramp-temp-file v))
|
(?t . ,(tramp-make-tramp-temp-file v 'dont-create))
|
||||||
(?k . ,(if keep-date " " "")))
|
(?k . ,(if keep-date " " "")))
|
||||||
copy-program (tramp-get-method-parameter
|
copy-program (tramp-get-method-parameter
|
||||||
method 'tramp-copy-program)
|
method 'tramp-copy-program)
|
||||||
|
|
@ -3639,8 +3659,7 @@ beginning of local filename are not substituted."
|
||||||
(error "Implementation does not handle immediate return"))
|
(error "Implementation does not handle immediate return"))
|
||||||
|
|
||||||
(with-parsed-tramp-file-name default-directory nil
|
(with-parsed-tramp-file-name default-directory nil
|
||||||
(let ((temp-name-prefix (tramp-make-tramp-temp-file v))
|
(let (command input tmpinput stderr tmpstderr outbuf ret)
|
||||||
command input stderr outbuf ret)
|
|
||||||
;; Compute command.
|
;; Compute command.
|
||||||
(setq command (mapconcat 'tramp-shell-quote-argument
|
(setq command (mapconcat 'tramp-shell-quote-argument
|
||||||
(cons program args) " "))
|
(cons program args) " "))
|
||||||
|
|
@ -3652,11 +3671,9 @@ beginning of local filename are not substituted."
|
||||||
;; INFILE is on the same remote host.
|
;; INFILE is on the same remote host.
|
||||||
(setq input (with-parsed-tramp-file-name infile nil localname))
|
(setq input (with-parsed-tramp-file-name infile nil localname))
|
||||||
;; INFILE must be copied to remote host.
|
;; INFILE must be copied to remote host.
|
||||||
(setq input (concat temp-name-prefix ".in"))
|
(setq input (tramp-make-tramp-temp-file v)
|
||||||
(copy-file
|
tmpinput (tramp-make-tramp-file-name method user host input))
|
||||||
infile
|
(copy-file infile tmpinput t)))
|
||||||
(tramp-make-tramp-file-name method user host input)
|
|
||||||
t)))
|
|
||||||
(when input (setq command (format "%s <%s" command input)))
|
(when input (setq command (format "%s <%s" command input)))
|
||||||
|
|
||||||
;; Determine output.
|
;; Determine output.
|
||||||
|
|
@ -3685,7 +3702,9 @@ beginning of local filename are not substituted."
|
||||||
(cadr destination) nil localname))
|
(cadr destination) nil localname))
|
||||||
;; stderr must be copied to remote host. The temporary
|
;; stderr must be copied to remote host. The temporary
|
||||||
;; file must be deleted after execution.
|
;; file must be deleted after execution.
|
||||||
(setq stderr (concat temp-name-prefix ".err"))))
|
(setq stderr (tramp-make-tramp-temp-file v)
|
||||||
|
tmpstderr (tramp-make-tramp-file-name
|
||||||
|
method user host stderr))))
|
||||||
;; stderr to be discarded
|
;; stderr to be discarded
|
||||||
((null (cadr destination))
|
((null (cadr destination))
|
||||||
(setq stderr "/dev/null"))))
|
(setq stderr "/dev/null"))))
|
||||||
|
|
@ -3694,9 +3713,6 @@ beginning of local filename are not substituted."
|
||||||
(setq outbuf (current-buffer))))
|
(setq outbuf (current-buffer))))
|
||||||
(when stderr (setq command (format "%s 2>%s" command stderr)))
|
(when stderr (setq command (format "%s 2>%s" command stderr)))
|
||||||
|
|
||||||
;; If we have a temporary file, it must be removed after operation.
|
|
||||||
(when (and input (string-match temp-name-prefix input))
|
|
||||||
(setq command (format "%s; rm %s" command input)))
|
|
||||||
;; Goto working directory.
|
;; Goto working directory.
|
||||||
(tramp-send-command
|
(tramp-send-command
|
||||||
v (format "cd %s" (tramp-shell-quote-argument localname)))
|
v (format "cd %s" (tramp-shell-quote-argument localname)))
|
||||||
|
|
@ -3716,13 +3732,13 @@ beginning of local filename are not substituted."
|
||||||
(error
|
(error
|
||||||
(kill-buffer (tramp-get-connection-buffer v))
|
(kill-buffer (tramp-get-connection-buffer v))
|
||||||
(setq ret 1)))
|
(setq ret 1)))
|
||||||
(unless ret
|
|
||||||
;; Check return code.
|
;; Check return code.
|
||||||
(setq ret (tramp-send-command-and-check v nil))
|
(unless ret (setq ret (tramp-send-command-and-check v nil)))
|
||||||
;; Provide error file.
|
;; Provide error file.
|
||||||
(when (and stderr (string-match temp-name-prefix stderr))
|
(when tmpstderr (rename-file tmpstderr (cadr destination) t))
|
||||||
(rename-file (tramp-make-tramp-file-name method user host stderr)
|
;; Cleanup.
|
||||||
(cadr destination) t)))
|
(when tmpinput (delete-file tmpinput))
|
||||||
;; Return exit status.
|
;; Return exit status.
|
||||||
ret)))
|
ret)))
|
||||||
|
|
||||||
|
|
@ -4555,7 +4571,15 @@ Falls back to normal file name handler if no tramp file name handler exists."
|
||||||
(add-hook 'tramp-unload-hook
|
(add-hook 'tramp-unload-hook
|
||||||
'(lambda () (ad-unadvise 'PC-expand-many-files)))))
|
'(lambda () (ad-unadvise 'PC-expand-many-files)))))
|
||||||
|
|
||||||
;;; File name handler functions for completion mode
|
;;; File name handler functions for completion mode.
|
||||||
|
|
||||||
|
(defvar tramp-completion-mode nil
|
||||||
|
"If non-nil, external packages signal that they are in file name completion.
|
||||||
|
|
||||||
|
This is necessary, because Tramp uses a heuristic depending on last
|
||||||
|
input event. This fails when external packages use other characters
|
||||||
|
but <TAB>, <SPACE> or ?\\? for file name completion. This variable
|
||||||
|
should never be set globally, the intention is to let-bind it.")
|
||||||
|
|
||||||
;; Necessary because `tramp-file-name-regexp-unified' and
|
;; Necessary because `tramp-file-name-regexp-unified' and
|
||||||
;; `tramp-completion-file-name-regexp-unified' aren't different. If
|
;; `tramp-completion-file-name-regexp-unified' aren't different. If
|
||||||
|
|
@ -4571,23 +4595,25 @@ Falls back to normal file name handler if no tramp file name handler exists."
|
||||||
(defun tramp-completion-mode-p ()
|
(defun tramp-completion-mode-p ()
|
||||||
"Checks whether method / user name / host name completion is active."
|
"Checks whether method / user name / host name completion is active."
|
||||||
(or
|
(or
|
||||||
;; Emacs
|
;; Signal from outside.
|
||||||
|
tramp-completion-mode
|
||||||
|
;; Emacs.
|
||||||
(equal last-input-event 'tab)
|
(equal last-input-event 'tab)
|
||||||
(and (natnump last-input-event)
|
(and (natnump last-input-event)
|
||||||
(or
|
(or
|
||||||
;; ?\t has event-modifier 'control
|
;; ?\t has event-modifier 'control.
|
||||||
(char-equal last-input-event ?\t)
|
(char-equal last-input-event ?\t)
|
||||||
(and (not (event-modifiers last-input-event))
|
(and (not (event-modifiers last-input-event))
|
||||||
(or (char-equal last-input-event ?\?)
|
(or (char-equal last-input-event ?\?)
|
||||||
(char-equal last-input-event ?\ )))))
|
(char-equal last-input-event ?\ )))))
|
||||||
;; XEmacs
|
;; XEmacs.
|
||||||
(and (featurep 'xemacs)
|
(and (featurep 'xemacs)
|
||||||
;; `last-input-event' might be nil.
|
;; `last-input-event' might be nil.
|
||||||
(not (null last-input-event))
|
(not (null last-input-event))
|
||||||
;; `last-input-event' may have no character approximation.
|
;; `last-input-event' may have no character approximation.
|
||||||
(funcall (symbol-function 'event-to-character) last-input-event)
|
(funcall (symbol-function 'event-to-character) last-input-event)
|
||||||
(or
|
(or
|
||||||
;; ?\t has event-modifier 'control
|
;; ?\t has event-modifier 'control.
|
||||||
(char-equal
|
(char-equal
|
||||||
(funcall (symbol-function 'event-to-character)
|
(funcall (symbol-function 'event-to-character)
|
||||||
last-input-event) ?\t)
|
last-input-event) ?\t)
|
||||||
|
|
@ -6151,7 +6177,7 @@ connection if a previous connection has died for some reason."
|
||||||
l-user (or l-user "")
|
l-user (or l-user "")
|
||||||
l-port (or l-port "")
|
l-port (or l-port "")
|
||||||
spec `((?h . ,l-host) (?u . ,l-user) (?p . ,l-port)
|
spec `((?h . ,l-host) (?u . ,l-user) (?p . ,l-port)
|
||||||
(?t . ,(tramp-make-tramp-temp-file vec)))
|
(?t . ,(tramp-make-tramp-temp-file vec 'dont-create)))
|
||||||
command
|
command
|
||||||
(concat
|
(concat
|
||||||
command " "
|
command " "
|
||||||
|
|
@ -7468,18 +7494,6 @@ please ensure that the buffers are attached to your email.\n\n")
|
||||||
|
|
||||||
(provide 'tramp)
|
(provide 'tramp)
|
||||||
|
|
||||||
;; Make sure that we get integration with the VC package.
|
|
||||||
;; When it is loaded, we need to pull in the integration module.
|
|
||||||
;; This must come after (provide 'tramp) because tramp-vc.el
|
|
||||||
;; requires tramp. Not necessary in Emacs 23.
|
|
||||||
(eval-after-load "vc"
|
|
||||||
'(unless (functionp 'start-file-process)
|
|
||||||
(require 'tramp-vc)
|
|
||||||
(add-hook 'tramp-unload-hook
|
|
||||||
'(lambda ()
|
|
||||||
(when (featurep 'tramp-vc)
|
|
||||||
(unload-feature 'tramp-vc 'force))))))
|
|
||||||
|
|
||||||
;;; TODO:
|
;;; TODO:
|
||||||
|
|
||||||
;; * Allow putting passwords in the filename.
|
;; * Allow putting passwords in the filename.
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue