tags:

views:

1130

answers:

1

I'm trying to play around with netcat to learn more about how HTTP works. I'd like to script some of it in bash or Perl, but I've hit upon a stumbling block early on in my testing.

If I run netcat straight from the prompt and type in a HEAD request, it works and I receive the headers for the web server I'm probing.

This works:

    [romandas@localhost ~]$ nc 10.1.1.2 80
    HEAD / HTTP/1.0

    HTTP/1.1 200 OK
    MIME-Version: 1.0
    Server: Edited out
    Content-length: 0
    Cache-Control: public
    Expires: Sat, 01 Jan 2050 18:00:00 GMT

    [romandas@localhost ~]$
But when I put the same information into a text file and feed it to netcat through a pipe or via redirection, in preparation for scripting, it doesn't return the headers. The text file consists of the HEAD request and two newlines:
HEAD / HTTP/1.0

Also sending the same information via echo or printf doesn't work.

$ printf "HEAD / HTTP/1.0\r\n"; |nc -n 10.1.1.2 80
$ /bin/echo -ne 'HEAD / HTTP/1.0\n\n' |nc 10.1.1.2 80

Any ideas what I'm doing wrong? Not sure if it's a bash problem, an echo problem, or a netcat problem.

I checked the traffic via Wireshark, and the successful request (manually typed) sends the trailing newline in a second packet, whereas the echo, printf, and text file methods keep the newline in the same packet, but I'm not sure what causes this behavior.

+3  A: 

You need two lots of "\r\n", and also to tell netcat to wait for a response. printf "HEAD / HTTP/1.0\r\n\r\n" |nc -n -i 1 10.1.1.2 80 or similar should work.

moonshadow
This doesn't work for me. I copied your line directly, but the connection still terminates before transmitting the header.
romandas
Then the problem is at your server end. printf "HEAD / HTTP/1.0\r\n\r\n" | nc www.toothycat.net 80 works here.
moonshadow
The server isn't terminating the request; it's initiated by the client. Wireshark shows my client sending a FIN packet right after the HEAD request packet, then the server ACKs and terminates gracefully. Not sure what causes the difference. What version of netcat are you using?
romandas
1.10-33Oh, try adding a -q 10 to make netcat wait for a response after it gets the EOF on STDIN.
moonshadow
Ah, that did it. I'm using GNU netcat (v1.84), so the option is -i 1 (to wait between successive lines of input). That caused the second newline to be sent later, and produced the desired HEAD response. Edit that into your answer, and I'll go ahead and accept it. :) Thanks!
romandas
Heh - glad to be of use :)
moonshadow
FYI, just the two newlines matter \n\n works (for me) just as well as \r\n\r\n.
romandas
The RFC requires CRLF pairs; best to be safe if you can.
moonshadow