26.07.2018 Views

hacking-the-art-of-exploitation

You also want an ePaper? Increase the reach of your titles

YUMPU automatically turns print PDFs into web optimized ePapers that Google loves.

This reveals that <strong>the</strong> webserver is Apache version 2.0.52 and even that<br />

<strong>the</strong> host runs CentOS. This can be useful for pr<strong>of</strong>iling, so let’s write a program<br />

that automates this manual process.<br />

The next few programs will be sending and receiving a lot <strong>of</strong> data. Since<br />

<strong>the</strong> standard socket functions aren’t very friendly, let’s write some functions<br />

to send and receive data. These functions, called send_string() and recv_line(),<br />

will be added to a new include file called <strong>hacking</strong>-network.h.<br />

The normal send() function returns <strong>the</strong> number <strong>of</strong> bytes written, which<br />

isn’t always equal to <strong>the</strong> number <strong>of</strong> bytes you tried to send. The send_string()<br />

function accepts a socket and a string pointer as arguments and makes sure<br />

<strong>the</strong> entire string is sent out over <strong>the</strong> socket. It uses strlen() to figure out <strong>the</strong><br />

total length <strong>of</strong> <strong>the</strong> string passed to it.<br />

You may have noticed that every packet <strong>the</strong> simple server received ended<br />

with <strong>the</strong> bytes 0x0D and 0x0A. This is how telnet terminates <strong>the</strong> lines—it sends<br />

a carriage return and a newline character. The HTTP protocol also expects<br />

lines to be terminated with <strong>the</strong>se two bytes. A quick look at an ASCII table<br />

shows that 0x0D is a carriage return ('\r') and 0x0A is <strong>the</strong> newline character<br />

('\n').<br />

reader@<strong>hacking</strong>:~/booksrc $ man ascii | egrep "Hex|0A|0D"<br />

Reformatting ascii(7), please wait...<br />

Oct Dec Hex Char Oct Dec Hex Char<br />

012 10 0A LF '\n' (new line) 112 74 4A J<br />

015 13 0D CR '\r' (carriage ret) 115 77 4D M<br />

reader@<strong>hacking</strong>:~/booksrc $<br />

The recv_line() function reads entire lines <strong>of</strong> data. It reads from <strong>the</strong> socket<br />

passed as <strong>the</strong> first argument into <strong>the</strong> a buffer that <strong>the</strong> second argument points<br />

to. It continues receiving from <strong>the</strong> socket until it encounters <strong>the</strong> last two linetermination<br />

bytes in sequence. Then it terminates <strong>the</strong> string and exits <strong>the</strong><br />

function. These new functions ensure that all bytes are sent and receive data<br />

as lines terminated by '\r\n'. They are listed below in a new include file called<br />

<strong>hacking</strong>-network.h.<br />

<strong>hacking</strong>-network.h<br />

/* This function accepts a socket FD and a ptr to <strong>the</strong> null terminated<br />

* string to send. The function will make sure all <strong>the</strong> bytes <strong>of</strong> <strong>the</strong><br />

* string are sent. Returns 1 on success and 0 on failure.<br />

*/<br />

int send_string(int sockfd, unsigned char *buffer) {<br />

int sent_bytes, bytes_to_send;<br />

bytes_to_send = strlen(buffer);<br />

while(bytes_to_send > 0) {<br />

sent_bytes = send(sockfd, buffer, bytes_to_send, 0);<br />

if(sent_bytes == -1)<br />

return 0; // Return 0 on send error.<br />

Networking 209

Hooray! Your file is uploaded and ready to be published.

Saved successfully!

Ooh no, something went wrong!