Monday, April 27, 2009

Open Source Application Layer Firewall part 2

Continuing my discussion on setting up an open-source application-layer firewall. In the last post we talked about the need for such a device and kind of layed the groundwork for what was going to come. In this post I'm going to talk about setting up our vulnerable application that requires protecting.

The first thing I set up was my back-end server. This is the machine that I am trying to protect. I didn't need to do anything fancy with this machine, so I just slapped a default installation of OpenBSD on a virtual machine. The virtual machine has one virtual NIC on it, and that was initially set up with a live IP address so that I could download the sets from the Internet. Once the installation was complete, I rebooted and changed the ip address to something static. Here is how that is done.
1. Edit hostname.em0. On OpenBSD, the interfaces are not named eth0, eth1, etc. Instead the name comes from the manufacturer or the NIC. You can run ifconfig to see which interface has an ip address. In my case, that interface is em0, so that cards configuration is in hostname.em0. The file was set up to allow DHCP, but I don't want that. So I'll set it up with a static ip address on a private network.
#vi /etc/hostname.em0
inet 192.168.1.10 255.255.255.0
I also need to set a default gateway which is in the file /etc/mygate
#vi /etc/mygate
192.168.1.1
Now I shut down the virtual machine and changed the virtual NIC to use a host-only network. When I booted up, I no longer had access to the Internet from this machine. Next up, we need to create an SSL certificate to be used when making https connections to this machine.
openssl genrsa -out /etc/ssl/private/192.168.1.10.key 1024
openssl req -new -key /etc/ssl/private/192.168.1.10.key /
-out /etc/ssl/private/192.168.1.10.csr
openssl x509 -req -days 365 -in /etc/ssl/private/192.168.1.10.csr /
-signkey /etc/ssl/private/192.168.1.10.key /
-out /etc/ssl/192.168.1.10.crt


We need to make a quick change to the configuration file too. The file /var/www/conf/httpd.conf instructs httpd to look for certificates at /etc/ssl/server.crt. Let's change line 1041 of the default httpd.conf file to point to the correct file name: /etc/ssl/192.168.1.10.crt. You will also have to make a similar change to line 1046. Now we can fire up our http server and test it out. This is really easy to do since we're using the httpd server that comes with OpenBSD. You just have to type httpd. I'm going to use the -DSSL option so that it will fire up with SSL support using the keys we just made.
httpd -DSSL

We can use lynx to test it. Type in lynx http://localhost and you should see a text version of the default Apache startup page. Press Q to quit and type lynx https://localhost to see if you've got working SSL. You should ignore the ssl warning because we're using a self-signed certificate. Note that you wont be able to pull anything up on a browser from another machine because we haven't opened up the http/https ports in pf. If lynx indicates that the https server is working right, then we can make it start up by default whenever we fire up this machine.
#vi /etc/rc.conf
# Find the httpd_flags line and change it to this:
httpd_flags="DSSL"
That is all the configuration that we need to do right now to test this thing out. However, if you're feeling a little saucy like I was, we can whip up a quick and simple php application so that we can test out the features of mod_security down the road a bit. Here is how I did that. I added another virtual NIC and configured it for dhcp so that I could get to the Internet.

Install php from packages and update httpd.conf to support php
# export PKG_PATH=ftp://ftp.openbsd.org/pub/OpenBSD/4.4/packages/i386/
# pkg_info -Q php more (look for one called php5-core-something)
# pkg_add php5-core-5.2.6
Edit the configuration file /var/www/conf/httpd.conf. Find the line that reads AddType application/x-httpd-php and change it to read: AddType application/x-httpd-php .php .php4 .php3 .htm .html

Now I edited the file /var/www/htdocs/index.html and added this to the file after the BODY tag.
<?php
$Fname = $_POST["Fname"];
$Lname = $_POST["Lname"];
$Ccard = $_POST["Ccard"];
echo "Hello, ".$Fname." ".$Lname;
echo "<br />";
echo "Credit card: ".$Ccard;
?>

<form method="post" action="<?php echo $PHP_SELF; ?>">
First Name<input type="text" size="12" maxlength="12" name="Fname"><br />
Last Name<input type="text" size="12" maxlength="36" name="Lname"><br />
Credit Card<input type="text" size="12" maxlength="36" name="Ccard"><br />
<input type="submit" value="submit" name="submit"><br /></form><br />
Now I have a basic and very insecure web application that runs on my web server. This is what we will use for testing out our Application Layer Firewall. Once we have everything set up, we should be able to establish an SSL connection to this server that is proxied through our firewall. Our firewall should also be able to make sure that we don't enter improper text into our form. I will now remove the virtual NIC that connects this to the Internet so that there is no access to this server except through our firewall.

No comments: