ONLamp.com
oreilly.comSafari Books Online.Conferences.

advertisement


Secure Your Wireless with IPsec
Pages: 1, 2

Racoon Likes to Keep Secrets

Instead of manually changing the shared secrets in your /etc/ipsec.conf file, you can keep one shared secret and use the IKE protocol to negotiate a key. Racoon speaks IKE (ISAKMP/Oakley), which is a key management protocol.

I installed Racoon from the ports tree. Here are the configuration files from both my laptop and the gateway. The only difference between the two files is that I instruct the gateway to listen on only one address (it has two NICs). Here is the diff, if you are interested:

--- racoon.conf.laptop        Wed Sep 15 19:26:03 2004
+++ racoon.conf.gateway Wed Sep 15 19:31:46 2004
@@ -33,6 +33,8 @@
        #isakmp 202.249.11.124 [500];
        #admin [7002];          # administrative's port by kmpstat.
        #strict_address;        # required all addresses must be bound.
+
+       isakmp 10.0.0.1;
 }
 
 # Specification of default various timer.

The configuration file tells Racoon the main things it needs to know. One of the items is the preshared key file. Look for this directive:

# search this file for pre_shared_key with various ID key.
path pre_shared_key "/usr/local/etc/racoon/psk.txt" ;

From man racoon.conf:

Pre-shared key File
  Pre-shared key file defines a pair of the identifier and the shared
  secret key which are used at Pre-shared key authentication method in
  phase 1.  The pair in each lines are separated by some number of blanks
  and/or tab characters like hosts(5).  Key can be included any blanks
  because all of the words after 2nd column are interpreted as a secret
  key.  Lines start with #' are ignored.  Keys which start with ' are
  hexa-decimal strings.  Note that the file must be owned by the user ID
  running racoon(8) (usually the privileged user), and must not be accessi-
  ble by others.

Here is the /usr/local/etc/racoon/psk.txt file on my laptop:

10.0.0.1 MySecretValue

Here is the file from the wireless gateway:

10.0.0.10 MySecretValue

With these values, Racoon on my laptop knows that when it talks to 10.0.0.1 (the gateway) it should use the shared key MySecretValue. Similarly, the Racoon running on the gateway knows to use the same shared key when speaking to 10.0.0.10 (my laptop).

To start Racoon, issue this command:

/usr/local/etc/rc.d/racoon.sh start

If you're running a recent version of FreeBSD (for example, 4.10-RELEASE), add this entry in /etc/rc.conf:

racoon_enable="YES"

Ensure that Racoon is running on both the laptop and the gateway. Then remove the SAD entries from both machines, and Racoon should negotiate a new set of keys.

# setkey -c
flush;
^D

If that doesn't work, try running Racoon in the foreground (after first stopping the one running in the background):

/usr/local/sbin/racoon -F

It should just work.

Fun with Keys: Understanding What Happens

I thought it might be interesting to clear out the SAD entries and see what happens when it comes time to negotiate new keys. I started a ping running and ran tcpdump while I issued this command:

# setkey -F

As you can see, the ping missed a few steps. That is understandable.

[dan@laptop:~] $ ping -A 192.168.0.18
PING xeon.unixathome.org (192.168.0.18): 56 data bytes
64 bytes from 192.168.0.18: icmp_seq=0 ttl=63 time=4.880 ms
64 bytes from 192.168.0.18: icmp_seq=1 ttl=63 time=4.847 ms
64 bytes from 192.168.0.18: icmp_seq=2 ttl=63 time=5.126 ms
64 bytes from 192.168.0.18: icmp_seq=3 ttl=63 time=5.209 ms
64 bytes from 192.168.0.18: icmp_seq=6 ttl=63 time=5.468 ms
64 bytes from 192.168.0.18: icmp_seq=7 ttl=63 time=4.838 ms
64 bytes from 192.168.0.18: icmp_seq=8 ttl=63 time=5.270 ms
^C
--- xeon.unixathome.org ping statistics ---
9 packets transmitted, 7 packets received, 22% packet loss
round-trip min/avg/max/stddev = 4.838/5.091/5.468/0.226 ms
[dan@laptop:~] $

Two pings went missing and never reached the machine on the other side of the gateway. Here is some of the tcpdump traffic:

16:36:34.517794 10.0.0.10 > 10.0.0.1: ESP(spi=0x02dc8063,seq=0x1d)
16:36:34.867830 10.0.0.10 > 10.0.0.1: ESP(spi=0x02dc8063,seq=0x1e)
16:36:34.873592 10.0.0.1 > 10.0.0.10: ESP(spi=0x0751ce23,seq=0x1d)
16:36:35.737921 10.0.0.10.500 > 10.0.0.1.500: isakmp: phase 2/others 
     ? inf[E]: [encrypted hash]
16:36:35.904270 10.0.0.10.500 > 10.0.0.1.500: isakmp: phase 2/others 
     ? oakley-quick[E]: [encrypted hash]
16:36:36.604941 10.0.0.1.500 > 10.0.0.10.500: isakmp: phase 2/others 
     ? oakley-quick[E]: [encrypted hash]
16:36:36.605565 10.0.0.10.500 > 10.0.0.1.500: isakmp: phase 2/others 
     ? oakley-quick[E]: [encrypted hash]
16:36:36.887859 10.0.0.10 > 10.0.0.1: ESP(spi=0x01f4fcea,seq=0x1)
16:36:37.897889 10.0.0.10 > 10.0.0.1: ESP(spi=0x01f4fcea,seq=0x2)

The lines that contain isakmp represent the two Racoon daemons negotiating a new key.

As an experiment, I turned off IPsec on my laptop by commenting out the ipsec_enable line in /etc/rc.conf. Then I rebooted. Interestingly, I still received an IP address from my DHCP server on the other side of the wireless gateway. However, I could not get through the gateway. Even simple pings to the gateway went unanswered. At this time, the firewall on the wireless gateway allowed all traffic to pass. Therefore, the gateway rejected the traffic because it did not use IPsec.

To make IPsec work again, I did this while the ping was still running:

[root@laptop:/home/dan] # setkey -f /etc/ipsec.conf
[root@laptop:/home/dan] # tcpdump -ni wi0 tcpdump: listening on wi0
17:21:20.168434 10.0.0.10.500 > 10.0.0.1.500: isakmp: phase 2/others 
     ? oakley-quick[E]: [encrypted hash]
17:21:46.426485 10.0.0.10.500 > 10.0.0.1.500: isakmp: phase 2/others 
     ? oakley-quick[E]: [encrypted hash]
17:21:47.112010 10.0.0.1.500 > 10.0.0.10.500: isakmp: phase 2/others 
     ? oakley-quick[E]: [encrypted hash]
17:21:47.113115 10.0.0.10.500 > 10.0.0.1.500: isakmp: phase 2/others 
     ? oakley-quick[E]: [encrypted hash]
17:21:47.375549 10.0.0.10 > 10.0.0.1: ESP(spi=0x02c19c7a,seq=0x1)
17:21:48.385549 10.0.0.10 > 10.0.0.1: ESP(spi=0x02c19c7a,seq=0x2)
17:21:48.390088 10.0.0.1 > 10.0.0.10: ESP(spi=0x041e48fb,seq=0x1)
17:21:49.395564 10.0.0.10 > 10.0.0.1: ESP(spi=0x02c19c7a,seq=0x3)
17:21:49.399754 10.0.0.1 > 10.0.0.10: ESP(spi=0x041e48fb,seq=0x2)

The first line populates the SPD1 database, based upon the data within the file /etc/ipsec.conf. From there, Racoon must negotiate a new key. It took some time (about 26 seconds), but Racoon eventually succeeded. Immediately thereafter, the pings resumed.

1Actually, the command populates only the SAD because the file in question contains only add commands. I commented out the spdadd commands.

DHCP Server

I mentioned above that I could still receive an IP address from my DHCP server that was running on my gateway. I had not previously mentioned it, but I think it might be useful to you. Here are the basics; the rest you should be able to piece together yourself.

Installing dhcpd

To install the dhcp server, I did this:

# cd /usr/ports/net/isc-dhcp3-server
# make install clean

Starting at boot time

This will install /usr/local/etc/rc.d/isc-dhcpd.sh. Remember to add dhcpd_enable="YES" to /etc/rc.conf, or the script will not start the server. I also added dhcpd_ifaces="dc0" so that dhcpd would listen only on the one NIC--the one attached to the same hub as the WAP.

The configuration file

The port installs /usr/local/etc/dhcpd.conf. It is full of examples, but here is what I'm using, slightly altered to protect the obvious:

default-lease-time 600;
max-lease-time 7200;

authoritative;
ddns-update-style none;

option domain-name "example.org";

#
# this points to my local DNS server on the other
# side of the wireless gateway
#
option domain-name-servers 192.168.0.101;

default-lease-time 86400;
max-lease-time 86400;


# This is a very basic subnet declaration.

subnet 10.0.0.0 netmask 255.255.255.0 {
        option routers 10.0.0.1;
        range 10.0.0.192 10.0.0.207; # this is 10.0.0.200/27 => (28)

        host laptop.example.org {
                option dhcp-client-identifier "laptop.example.org";
                fixed-address laptop.example.org;
        }
}

That fixed-address relates to the following entry in /etc/dhclient.conf:

send dhcp-client-identifier "laptop.example.org";

This allows the laptop to tell the DHCP server who it is, which I use to assign a specific IP address. Note: this method is convenient, but it is not necessarily secure. If you're like me, sometimes using wireless with your laptop and sometimes connecting via wire, then you might want to give it a different IP address depending on where it is. I do that by having two DHCP servers. I'm sure someone will suggest another method.

Is That Enough?

Now you have your wireless laptop connected to your LAN, with encrypted and secured traffic. Nobody else can use your gateway unless they guess the secret key. That's not easy. The key will change from time to time, so even if someone guesses a key, there's a new one coming along soon. The only thing you have to secure is the preshared secret. Don't use what I've supplied. Come up with something odd, even some random values. Pick some text from IRC. That should work.

Are you being paranoid enough? I think for one of my next tasks I will look for any unusual traffic coming on the gateway, from any IP other than my laptop. There are whole books written on intrusion detection, and that topic is well beyond what I can cover here.

Enjoy.

Dan Langille runs a consulting group in Ottawa, Canada, and lives in a house ruled by felines.


Return to the BSD DevCenter.



Sponsored by: