Networking in C · intermediate · ~15 min
Walk through an HTTP request line and extract the method, path, and version into a struct.
Read the three tokens, copy them into a struct with bounded copies, and reject the input on overflow or a bad terminator.
The request line is where every HTTP attack starts. A bounded, allow-list parser stops the easy attacks at the door.
Every web proxy, every WAF (web application firewall), and every reverse-proxy access log begins the same way. They read the first line of an HTTP request and pull out three tokens:
GET)/index.html)HTTP/1.1)This first line is plain ASCII text and ends in \r\n (a carriage return followed by a newline). Because the whole protocol is text-driven, a C parser for it is small and worth reading closely.
This is the parser side of tools like Burp, mitmproxy, and nginx's access log. Here, we just write it ourselves.
A raw request arrives like this:
GET /index.html HTTP/1.1\r\n
Host: example.com\r\n
\r\n
The request line is the first line: three space-separated tokens, followed by \r\n.
Implement this function:
int parse_request_line(const char *buf, http_req_t *out);
The http_req_t struct holds three fixed-size (bounded) char arrays:
method[8]path[256]version[16]Return 0 on success, or -1 on any malformed input.
strcpy without a bounds check.\r\n./, alphanumerics, ?, &, =, ., -, and _. Reject any other character for this exercise.sscanf("%s %s %s", ...) without length specifiers. That is an uncontrolled write into memory.\r\n terminator.parse-http-smuggling-defence.\r\n terminator.