Expect: sending larger files with ftp-inband
Available news archives: comp.lang.tcl - comp.lang.python - comp.security.firewalls - sci.crypt - comp.lang.php - comp.lang.javascript
Google
 
Web news.hping.org


comp.lang.tcl archive

Expect: sending larger files with ftp-inband

From: <vdichev@gmail.com>
Date: Fri Oct 28 2005 - 09:21:04 CEST

Hi guys (and girls),

I recently discovered expect and was especially charmed by the
ftp-inband script (found in http://expect.nist.gov/example/). I work as
support and often all I have is a telnet connection to a UNIX server
(not ssh!), and I often have to transfer files. Kermit is a nice
option, but not many of the UNIX hosts I connect to have it installed
by default, and I am not allowed to install software. The beauty of
ftp-inband is that it uses the lowest-common-denominator tools-
uuencode and uudecode, cat and shell. But let me get to the point.

While I was trying to make the script a bit more robust and flexible, I
found that putting a file to the remote machine didn't work
successfully for a bit larger files (and by large I mean even a couple
of KB). At some point of time some of the output seems to be lost down
the line, so corrupted output occurs (and that's TCP we're talking
here). The piece of code which does this is as follows:

while {1} {
                if {-1 == [gets $fp buf]} break
                send_verbose "."
                send -- "$buf\r"
        }

which seems to be a standard idiom in Tcl/Expect for copying a file
line by line. So the first thing I thought is that this is some kind of
bufferring problem. I tried the send_slow option, and it did seem that
for more frequent and larger pauses, the file could be transferred
successfully, but the transfer is already quite slow and this made it
so much slower. Surprisingly, when I "slurped" the whole file by
"append"-ing to a text variable, and then "send"-ing this variable
containing the file- it worked...

Then I tried the following non-tcl/expect alternatives:

+ pasting the X selection directly into an interactive telnet session
("cat > filename", middle-click and then Ctrl+D) also worked.
+ using "tail -f session | netcat -t host 23" also worked by sending
the username, password, "cat > filename" and file itself to the
file/fifo named session, using cat and echo.
- using perl's module Net::Telnet, it didn't work unless I paused every
once in a while after sending some lines. Unlike Expect, slurping
didn't work here.

So what is the reason and what are my options? It's obviously some kind
of bufferring issue, but which buffer? Since it kinda works in
lower-level tools like netcat and pasting directly to the virtual
terminal, I thought it's probably expect's... But how do I change it?
Also: is "send"-ing done over a blocking or non-blocking channel? If
this is caused by a non-blocking channel, could this be the problem?

If anyone is interested in what I'm trying to do, I'd love to hear your
comments. I have also enhanced the ftp-inband script, so I'd be happy
to contribute my changes if anyone is interested to have these features
in it:
-checking for different compressors- bzip2, gzip and compress, in that
order; if none is found (is there ever a machine with none of these,
which can still be called UNIX?), it works without a compressor.
-checking if "stty -echo" works

Thanks in advance,
Vassil Dichev
Received on Mon Nov 21 00:36:20 2005