Writing an HTTP Server in C

ยท

3 min read

One project I've really been keen to work on for a year or so now has been an HTTP server.

I'm not exactly sure why this interested me, but it might have something to do with my facination for critical infrastructure. Http servers like Apache and NGINX are critical backbones of the web as we know it, and having a general understanding of how they work seemed cool to me. Along with this, when I first had the idea suggested to me on a podcast I was listening to, it seemed like such an unreachable goal.

In my previous semester at university I took a Systems Programming course where we learned C, and the basics of interacting with the Linux kernel, which included basic socket programming with TCP sockets. With this knowledge, I felt armed and ready to finally build an HTTP server.

Getting started

I honestly didn't feel ready to jump directly into the project. Firstly, I didn't have an amazing understanding of the backbones of this project, mainly TCP and HTTP. I picked up this book, and worked through the first few exercises. These were a super small program that lists your machines outward facing IP addresses, a simple TCP server that will capitalize a string sent to it, and a TCP Client.

These were fun little programs to write and taught me a lot of fun C tricks, and how TCP works.

Writing the server

After prepping all the knowledge, this wasn't actually too hard. I wasn't aiming to build a competitor to Apache or anything, so this only handles simple GET requests, and returns 200, 400, 404, or 500 responses. (I also added 418, but that was just for fun ๐Ÿ˜Š)

One issue I saw from the start was preventing a directory traversal exploit. Because the parser is simple, and will go to whatever directory supplied, a malicious actor could add ".." to the path, which will go up a directory, and traverse to directories which they should not have access to, and potentially see things they shouldn't. the way I prevented this (Although liktely not bulletproof) was to check for ".." at the front of the string, and return a 400 response.

My least favourite thing about writing in C is dealing with strings. Whenever I work with strings in PHP or Python, I feel so darn spoiled. When I work with C, I feel like jumping off a cliff. luckily, building the 200 response was only slightly annoying in this respect. There is always going to be at least one segmentation fault.

Closing

Overall this was a fun project and I learned a lot. This was a bucket list item for me so I'm happy to finish it up!

ย