69 |
|
|
70 |
;;; Code: |
;;; Code: |
71 |
|
|
72 |
(defconst tramp-version "2.0.5" |
;; In the Tramp CVS repository, the version numer is auto-frobbed from |
73 |
|
;; the Makefile, so you should edit the top-level Makefile to change |
74 |
|
;; the version number. |
75 |
|
(defconst tramp-version "2.0.6" |
76 |
"This version of tramp.") |
"This version of tramp.") |
77 |
|
|
78 |
(defconst tramp-bug-report-address "tramp-devel@mail.freesoftware.fsf.org" |
(defconst tramp-bug-report-address "tramp-devel@mail.freesoftware.fsf.org" |
635 |
:group 'tramp |
:group 'tramp |
636 |
:type '(repeat (list string function string))) |
:type '(repeat (list string function string))) |
637 |
|
|
638 |
(defcustom tramp-default-method "sm" |
(defcustom tramp-default-method "ssh" |
|
;;(if (featurep 'xemacs) "sm" "ftp") |
|
639 |
"*Default method to use for transferring files. |
"*Default method to use for transferring files. |
640 |
See `tramp-methods' for possibilities. |
See `tramp-methods' for possibilities. |
641 |
Also see `tramp-default-method-alist'. |
Also see `tramp-default-method-alist'. |
709 |
:type 'regexp) |
:type 'regexp) |
710 |
|
|
711 |
(defcustom tramp-wrong-passwd-regexp |
(defcustom tramp-wrong-passwd-regexp |
712 |
(concat "^.*\\(Permission denied.\\|Login [Ii]ncorrect\\|" |
(concat "^.*" |
713 |
"Received signal [0-9]+\\|Connection \\(refused\\|closed\\)\\|" |
;; These strings should be on the last line |
714 |
"Sorry, try again.\\|Name or service not known\\).*") |
(regexp-opt '("Permission denied." |
715 |
|
"Login incorrect" |
716 |
|
"Login Incorrect" |
717 |
|
"Connection refused" |
718 |
|
"Connection closed" |
719 |
|
"Sorry, try again." |
720 |
|
"Name or service not known" |
721 |
|
"Host key verification failed.") t) |
722 |
|
".*" |
723 |
|
"\\|" |
724 |
|
"^.*\\(" |
725 |
|
;; Here comes a list of regexes, separated by \\| |
726 |
|
"Received signal [0-9]+" |
727 |
|
"\\).*") |
728 |
"*Regexp matching a `login failed' message. |
"*Regexp matching a `login failed' message. |
729 |
The regexp should match at end of buffer." |
The regexp should match at end of buffer." |
730 |
:group 'tramp |
:group 'tramp |
1160 |
In the connection buffer, this variable has the value of the like-named |
In the connection buffer, this variable has the value of the like-named |
1161 |
method parameter, as specified in `tramp-methods' (which see).") |
method parameter, as specified in `tramp-methods' (which see).") |
1162 |
|
|
1163 |
|
(defvar tramp-su-program nil |
1164 |
|
"This internal variable holds a parameter for `tramp-methods'. |
1165 |
|
In the connection buffer, this variable has the value of the like-named |
1166 |
|
method parameter, as specified in `tramp-methods' (which see).") |
1167 |
|
|
1168 |
;; CCC `local in each buffer'? |
;; CCC `local in each buffer'? |
1169 |
(defvar tramp-ls-command nil |
(defvar tramp-ls-command nil |
1170 |
"This command is used to get a long listing with numeric user and group ids. |
"This command is used to get a long listing with numeric user and group ids. |
1240 |
;; Escape sequence %s is replaced with name of Perl binary.") |
;; Escape sequence %s is replaced with name of Perl binary.") |
1241 |
|
|
1242 |
;; These two use base64 encoding. |
;; These two use base64 encoding. |
1243 |
(defvar tramp-perl-encode |
(defvar tramp-perl-encode-with-module |
1244 |
"perl -MMIME::Base64 -0777 -ne 'print encode_base64($_)'" |
"perl -MMIME::Base64 -0777 -ne 'print encode_base64($_)'" |
1245 |
"Perl program to use for encoding a file. |
"Perl program to use for encoding a file. |
1246 |
|
Escape sequence %s is replaced with name of Perl binary. |
1247 |
|
This implementation requires the MIME::Base64 Perl module to be installed |
1248 |
|
on the remote host.") |
1249 |
|
|
1250 |
|
(defvar tramp-perl-decode-with-module |
1251 |
|
"perl -MMIME::Base64 -0777 -ne 'print decode_base64($_)'" |
1252 |
|
"Perl program to use for decoding a file. |
1253 |
|
Escape sequence %s is replaced with name of Perl binary. |
1254 |
|
This implementation requires the MIME::Base64 Perl module to be installed |
1255 |
|
on the remote host.") |
1256 |
|
|
1257 |
|
(defvar tramp-perl-encode |
1258 |
|
"%s -e ' |
1259 |
|
# This script contributed by Juanma Barranquero <lektu@terra.es>. |
1260 |
|
# Copyright (C) 2002 Free Software Foundation, Inc. |
1261 |
|
use strict; |
1262 |
|
|
1263 |
|
my %trans = do { |
1264 |
|
my $i = 0; |
1265 |
|
map {(substr(unpack(q(B8), chr $i++), 2, 6), $_)} |
1266 |
|
split //, q(ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/); |
1267 |
|
}; |
1268 |
|
|
1269 |
|
binmode(\*STDIN); |
1270 |
|
|
1271 |
|
# We read in chunks of 54 bytes, to generate output lines |
1272 |
|
# of 72 chars (plus end of line) |
1273 |
|
$/ = \54; |
1274 |
|
|
1275 |
|
while (my $data = <STDIN>) { |
1276 |
|
my $pad = q(); |
1277 |
|
|
1278 |
|
# Only for the last chunk, and only if did not fill the last three-byte packet |
1279 |
|
if (eof) { |
1280 |
|
my $mod = length($data) % 3; |
1281 |
|
$pad = q(=) x (3 - $mod) if $mod; |
1282 |
|
} |
1283 |
|
|
1284 |
|
# Not the fastest method, but it is simple: unpack to binary string, split |
1285 |
|
# by groups of 6 bits and convert back from binary to byte; then map into |
1286 |
|
# the translation table |
1287 |
|
print |
1288 |
|
join q(), |
1289 |
|
map($trans{$_}, |
1290 |
|
(substr(unpack(q(B*), $data) . q(00000), 0, 432) =~ /....../g)), |
1291 |
|
$pad, |
1292 |
|
qq(\n); |
1293 |
|
} |
1294 |
|
'" |
1295 |
|
"Perl program to use for encoding a file. |
1296 |
Escape sequence %s is replaced with name of Perl binary.") |
Escape sequence %s is replaced with name of Perl binary.") |
1297 |
|
|
1298 |
(defvar tramp-perl-decode |
(defvar tramp-perl-decode |
1299 |
"perl -MMIME::Base64 -0777 -ne 'print decode_base64($_)'" |
"%s -e ' |
1300 |
|
# This script contributed by Juanma Barranquero <lektu@terra.es>. |
1301 |
|
# Copyright (C) 2002 Free Software Foundation, Inc. |
1302 |
|
use strict; |
1303 |
|
|
1304 |
|
my %trans = do { |
1305 |
|
my $i = 0; |
1306 |
|
map {($_, sprintf(q(%06b), $i++))} |
1307 |
|
split //, q(ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/) |
1308 |
|
}; |
1309 |
|
|
1310 |
|
my %bytes = map {(unpack(q(B8), chr $_), chr $_)} 0 .. 255; |
1311 |
|
|
1312 |
|
binmode(\*STDOUT); |
1313 |
|
|
1314 |
|
# We are going to accumulate into $pending to accept any line length |
1315 |
|
# (we do not check they are <= 76 chars as the RFC says) |
1316 |
|
my $pending = q(); |
1317 |
|
|
1318 |
|
while (my $data = <STDIN>) { |
1319 |
|
chomp $data; |
1320 |
|
|
1321 |
|
# If we find one or two =, we have reached the end and |
1322 |
|
# any following data is to be discarded |
1323 |
|
my $finished = $data =~ s/(==?).*/$1/; |
1324 |
|
$pending .= $data; |
1325 |
|
|
1326 |
|
my $len = length($pending); |
1327 |
|
my $chunk = substr($pending, 0, $len & ~3, q()); |
1328 |
|
|
1329 |
|
# Easy method: translate from chars to (pregenerated) six-bit packets, join, |
1330 |
|
# split in 8-bit chunks and convert back to char. |
1331 |
|
print join q(), |
1332 |
|
map $bytes{$_}, |
1333 |
|
((join q(), map {$trans{$_} || q()} split //, $chunk) =~ /......../g); |
1334 |
|
|
1335 |
|
last if $finished; |
1336 |
|
} |
1337 |
|
'" |
1338 |
"Perl program to use for decoding a file. |
"Perl program to use for decoding a file. |
1339 |
Escape sequence %s is replaced with name of Perl binary.") |
Escape sequence %s is replaced with name of Perl binary.") |
1340 |
|
|
1620 |
(defun tramp-handle-file-truename (filename &optional counter prev-dirs) |
(defun tramp-handle-file-truename (filename &optional counter prev-dirs) |
1621 |
"Like `file-truename' for tramp files." |
"Like `file-truename' for tramp files." |
1622 |
(with-parsed-tramp-file-name filename nil |
(with-parsed-tramp-file-name filename nil |
1623 |
;; Ange-FTP does not support truename processing. It returns the |
;; Ange-FTP does not support truename processing, but for |
1624 |
;; file name as-is. So that's what we do, too. |
;; convenience we pretend it did and forward the call to Ange-FTP |
1625 |
|
;; anyway. Ange-FTP then just invokes `identity'. |
1626 |
(when (tramp-ange-ftp-file-name-p multi-method method) |
(when (tramp-ange-ftp-file-name-p multi-method method) |
1627 |
filename) |
(tramp-invoke-ange-ftp 'file-truename filename)) |
1628 |
(let* ((steps (tramp-split-string path "/")) |
(let* ((steps (tramp-split-string path "/")) |
1629 |
(pathdir (let ((directory-sep-char ?/)) |
(pathdir (let ((directory-sep-char ?/)) |
1630 |
(file-name-as-directory path))) |
(file-name-as-directory path))) |
1655 |
(tramp-make-tramp-file-name |
(tramp-make-tramp-file-name |
1656 |
multi-method method user host |
multi-method method user host |
1657 |
(mapconcat 'identity |
(mapconcat 'identity |
1658 |
(append '("") (reverse result) (list thisstep)) |
(append '("") |
1659 |
|
(reverse result) |
1660 |
|
(list thisstep)) |
1661 |
"/"))))) |
"/"))))) |
1662 |
(cond ((string= "." thisstep) |
(cond ((string= "." thisstep) |
1663 |
(tramp-message-for-buffer multi-method method user host |
(tramp-message-for-buffer multi-method method user host |
1844 |
(let ((f (buffer-file-name)) |
(let ((f (buffer-file-name)) |
1845 |
(coding-system-used nil)) |
(coding-system-used nil)) |
1846 |
(with-parsed-tramp-file-name f nil |
(with-parsed-tramp-file-name f nil |
1847 |
;; This operation is not handled by Ange-FTP! |
;; This operation is not handled by Ange-FTP! Compare this |
1848 |
|
;; behavior with `file-truename' which Ange-FTP does not really |
1849 |
|
;; handle, either, but at least it pretends to. I wonder if |
1850 |
|
;; Ange-FTP should also pretend to grok |
1851 |
|
;; `set-visited-file-modtime', for consistency? |
1852 |
(when (tramp-ange-ftp-file-name-p multi-method method) |
(when (tramp-ange-ftp-file-name-p multi-method method) |
1853 |
(throw 'tramp-forward-to-ange-ftp |
(throw 'tramp-forward-to-ange-ftp |
1854 |
(tramp-run-real-handler 'set-visited-file-modtime |
(tramp-run-real-handler 'set-visited-file-modtime |
2412 |
(with-parsed-tramp-file-name dir nil |
(with-parsed-tramp-file-name dir nil |
2413 |
(when (tramp-ange-ftp-file-name-p multi-method method) |
(when (tramp-ange-ftp-file-name-p multi-method method) |
2414 |
(tramp-invoke-ange-ftp 'make-directory dir parents)) |
(tramp-invoke-ange-ftp 'make-directory dir parents)) |
2415 |
(tramp-barf-unless-okay |
(save-excursion |
2416 |
multi-method method user host |
(tramp-barf-unless-okay |
2417 |
(format " %s %s" |
multi-method method user host |
2418 |
(if parents "mkdir -p" "mkdir") |
(format " %s %s" |
2419 |
(tramp-shell-quote-argument path)) |
(if parents "mkdir -p" "mkdir") |
2420 |
nil 'file-error |
(tramp-shell-quote-argument path)) |
2421 |
"Couldn't make directory %s" dir))) |
nil 'file-error |
2422 |
|
"Couldn't make directory %s" dir)))) |
2423 |
|
|
2424 |
;; CCC error checking? |
;; CCC error checking? |
2425 |
(defun tramp-handle-delete-directory (directory) |
(defun tramp-handle-delete-directory (directory) |
3203 |
(string-match "\\?" name) |
(string-match "\\?" name) |
3204 |
(string-match "\\[.*\\]" name)) |
(string-match "\\[.*\\]" name)) |
3205 |
(save-excursion |
(save-excursion |
|
;; Dissect NAME. |
|
3206 |
(let (bufstr) |
(let (bufstr) |
|
;; Perhaps invoke Ange-FTP. |
|
|
(when (string= method tramp-ftp-method) |
|
|
(signal 'tramp-run-ange-ftp (list 0))) |
|
3207 |
;; CCC: To do it right, we should quote certain characters |
;; CCC: To do it right, we should quote certain characters |
3208 |
;; in the file name, but since the echo command is going to |
;; in the file name, but since the echo command is going to |
3209 |
;; break anyway when there are spaces in the file names, we |
;; break anyway when there are spaces in the file names, we |
3597 |
|
|
3598 |
(defun tramp-action-permission-denied (p multi-method method user host) |
(defun tramp-action-permission-denied (p multi-method method user host) |
3599 |
"Signal permission denied." |
"Signal permission denied." |
3600 |
|
(pop-to-buffer (tramp-get-buffer multi-method method user host)) |
3601 |
(tramp-message 9 "Permission denied by remote host.") |
(tramp-message 9 "Permission denied by remote host.") |
3602 |
(kill-process p) |
(kill-process p) |
|
(erase-buffer) |
|
3603 |
(throw 'tramp-action 'permission-denied)) |
(throw 'tramp-action 'permission-denied)) |
3604 |
|
|
3605 |
(defun tramp-action-yesno (p multi-method method user host) |
(defun tramp-action-yesno (p multi-method method user host) |
4511 |
" -e '" tramp-perl-file-attributes "' $1 2>/dev/null\n" |
" -e '" tramp-perl-file-attributes "' $1 2>/dev/null\n" |
4512 |
"}")) |
"}")) |
4513 |
(tramp-wait-for-output) |
(tramp-wait-for-output) |
4514 |
(tramp-message 5 "Sending the Perl `mime-encode' implementation.") |
(tramp-message 5 "Sending the Perl `mime-encode' implementations.") |
4515 |
(tramp-send-linewise |
(tramp-send-linewise |
4516 |
multi-method method user host |
multi-method method user host |
4517 |
(concat "tramp_encode () {\n" |
(concat "tramp_encode () {\n" |
4519 |
" 2>/dev/null" |
" 2>/dev/null" |
4520 |
"\n}")) |
"\n}")) |
4521 |
(tramp-wait-for-output) |
(tramp-wait-for-output) |
4522 |
(tramp-message 5 "Sending the Perl `mime-decode' implementation.") |
(tramp-send-linewise |
4523 |
|
multi-method method user host |
4524 |
|
(concat "tramp_encode_with_module () {\n" |
4525 |
|
(format tramp-perl-encode-with-module tramp-remote-perl) |
4526 |
|
" 2>/dev/null" |
4527 |
|
"\n}")) |
4528 |
|
(tramp-wait-for-output) |
4529 |
|
(tramp-message 5 "Sending the Perl `mime-decode' implementations.") |
4530 |
(tramp-send-linewise |
(tramp-send-linewise |
4531 |
multi-method method user host |
multi-method method user host |
4532 |
(concat "tramp_decode () {\n" |
(concat "tramp_decode () {\n" |
4533 |
(format tramp-perl-decode tramp-remote-perl) |
(format tramp-perl-decode tramp-remote-perl) |
4534 |
" 2>/dev/null" |
" 2>/dev/null" |
4535 |
"\n}")) |
"\n}")) |
4536 |
|
(tramp-wait-for-output) |
4537 |
|
(tramp-send-linewise |
4538 |
|
multi-method method user host |
4539 |
|
(concat "tramp_decode_with_module () {\n" |
4540 |
|
(format tramp-perl-decode-with-module tramp-remote-perl) |
4541 |
|
" 2>/dev/null" |
4542 |
|
"\n}")) |
4543 |
(tramp-wait-for-output)))) |
(tramp-wait-for-output)))) |
4544 |
;; Find ln(1) |
;; Find ln(1) |
4545 |
(erase-buffer) |
(erase-buffer) |
4593 |
nil uudecode-decode-region) |
nil uudecode-decode-region) |
4594 |
("uuencode xxx" "uudecode -p" |
("uuencode xxx" "uudecode -p" |
4595 |
nil uudecode-decode-region) |
nil uudecode-decode-region) |
4596 |
|
("tramp_encode_with_module" "tramp_decode_with_module" |
4597 |
|
base64-encode-region base64-decode-region) |
4598 |
("tramp_encode" "tramp_decode" |
("tramp_encode" "tramp_decode" |
4599 |
base64-encode-region base64-decode-region)) |
base64-encode-region base64-decode-region)) |
4600 |
"List of coding commands for inline transfer. |
"List of coding commands for inline transfer. |
5665 |
|
|
5666 |
;;; TODO: |
;;; TODO: |
5667 |
|
|
5668 |
;; * Revise the comments near the beginning of the file. |
;; * Add fallback for inline encodings. This should be used |
5669 |
|
;; if the remote end doesn't support mimencode or a similar program. |
5670 |
|
;; For reading files from the remote host, we can just parse the output |
5671 |
|
;; of `od -b'. For writing files to the remote host, we construct |
5672 |
|
;; a shell program which contains only "safe" ascii characters |
5673 |
|
;; and which writes the right bytes to the file. We can use printf(1) |
5674 |
|
;; or "echo -e" or the printf function in awk and use octal escapes |
5675 |
|
;; for the "dangerous" characters. The null byte might be a problem. |
5676 |
|
;; On some systems, the octal escape doesn't work. So we try the following |
5677 |
|
;; two commands to write a null byte: |
5678 |
|
;; dd if=/dev/zero bs=1 count=1 |
5679 |
|
;; echo | tr '\n' '\000' |
5680 |
;; * Cooperate with PCL-CVS. It uses start-process, which doesn't |
;; * Cooperate with PCL-CVS. It uses start-process, which doesn't |
5681 |
;; work for remote files. |
;; work for remote files. |
5682 |
;; * Rewrite `tramp-shell-quote-argument' to abstain from using |
;; * Rewrite `tramp-shell-quote-argument' to abstain from using |
5683 |
;; `shell-quote-argument'. |
;; `shell-quote-argument'. |
5684 |
;; * Completion gets confused when you leave out the method name. |
;; * Completion gets confused when you leave out the method name. |
5685 |
;; * Support `dired-compress-file' filename handler. |
;; * Support `dired-compress-file' filename handler. |
5686 |
;; * In Emacs 21, `insert-directory' shows total number of bytes used |
;; * In Emacs 21, `insert-directory' shows total number of bytes used |