WPA2-Enterprise on your home network


Off and on for the last few years I have been wanting to document the process for rolling your own WPA2-Enterprise (802.1x) secured network for home and small businesses using various free and open source tools. Time delays, various platform excentricities and general distraction kept me from completing this. Tim Lisko at PrivacyWonk.net on the other hand wrote up a great guide to rolling your own setup that pretty much encompasses everything I wanted in my efforts. As well, in all honesty, he did a better job than I think I ever could.

After chatting with Tim, I have recieved permission to copy his guide below in an effort to ensure it's continued existance but also to get it to a wider audience. Once again, I want to stress, this is not an original RenderLab creation, it was originally posted HERE at PrivacyWonk.net and is replicated with permission. All copyrights and other such stuff belong to Tim.


Security How-To: WPA2-Enterprise on your home network

The following post is very technical and a departure from most of the conversation here at PrivacyWonk; however, good security and privacy go hand-in-hand.  If you want to protect your home network and ensure the privacy of your communications over a wireless network, this post is for you.  If you're a small business owner who has to comply with Health Insurance Portability Accountability Act (HIPAA), Health Information for Economic and Clinical Health (HITECH) requirements, the newly passed Massachusetts data breach law, or other legislation this post is for you. 

The article will walk you through how to deploy WPA2-Enterprise certificate based, 802.1x, wireless authentication for your home/small business network, specifically using Extensible Authentication Protocol-Transport Layer Security (EAP-TLS).  This is a ridiculous level of security for your home WiFi but it will help thwart a would-be attacker by making the time-investment to crack your network greater than their mortal lifetime.  You should all know by now: WEP protection is a joke; it can be cracked in 60 seconds. WPA Pre-Shared Keys (PSK) are breakable by brute force and depend largely on the strength of the key. Brute forcing keys has been becoming increasingly easier for those with access to Rainbow tables or Rainbow table services, reducing the work factor significantly.

This article provides a step-by-step guide on how to configure, install, and deploy this insane level of security within your home/small business.

Please leave questions, comments, or concerns in the comments section or drop me an e-mail.  Enjoy.


Required software/hardware:

  • FreeBSD 8.1 -- My favorite unix operating system and the OS used in the following post.
  • FreeRADIUS -- Available through the FreeBSD ports tree at: /usr/ports/net/freeradius2/
  • OpenSSL -- Available standard through the FreeBSD installation; however, ensure you are working with the most up-to-date release as OpenSSL tends to have some security issues.
  • A router and/or access point that supports RADIUS servers and WPA2-Enterprise. DD-WRT is an excellent third-party firmware and will be used during this example.


The 12 step tutorial below represents all you need to get an operational instance of a WPA2-Enterprise protected network in your home or small business. The tutorial will walk you through certificate creation, deployment, configuration of FreeRADIUS, your Access Point/Router and your clients. I highly encourage you to read through the documentation provided by both OpenSSL and FreeRADIUS, especially around configuration files. The documentation will provide you greater insight into the software packages and is a life saver when you are trouble shooting. Always RTFM. Lastly, I would encourage you to read up on Public Key Infrastructure and digital certificates to ensure you understand exactly what is being done correctly here and the short cuts that have been taken.will walk you through certificate creation, deployment, configuration of FreeRADIUS, your Access Point/Router and your clients. I highly encourage you to read through the documentation provided by both OpenSSL and FreeRADIUS, especially around configuration files. The documentation will provide you greater insight into the software packages and is a life saver when you are trouble shooting. Always RTFM. Lastly, I would encourage you to read up on Public Key Infrastructure and digital certificates to ensure you understand exactly what is being done correctly here and the short cuts that have been taken.

Please use the index below to quickly jump around the document if you are looking for details on a specific step:

Step 1: Creating your Certificate Authority
Step 2: Generate new Certificate Authority Certificate
Step 3: Generate RADIUS Server certificate
Step 4: Generate Client Certificates
Step 5: Sign all Client Certificates
Step 6: Export Certificates for Windows & Mac
Step 7: Set up and Configure FreeRADIUS
Step 8: Test your Server Configuration
Step 9: Configure Wireless AP
Step 10: Deploying Certificates to Client Devices
Step 11: Setup Client Wireless (detailed directions for Windows XP SP3 Below)
Step 12: Configure FreeRADIUS to Start on Boot
Terminology
Summation



Step 1: Creating your Certificate Authority



1.1 Create the directories needed by OpenSSL and FreeRADIUS:

/bin/mkdir /etc/certstore
/bin/mkdir /etc/certstore/CA
/bin/mkdir /etc/certstore/CA/private
/bin/mkdir /etc/certstore/certs
/bin/mkdir /etc/certstore/crl
/bin/mkdir /etc/certstore/private
/bin/mkdir /etc/certstore/newcerts
/bin/mkdir /etc/certstore/export
/bin/mkdir /etc/wireless
/bin/mkdir /etc/wireless/certs
/bin/mkdir /etc/wireless/certs/clients
/bin/mkdir /etc/wireless/certs/server



  • certstore/CA is our Certificate Authority's directory.
  • certstore/CA/private is for our CA's private key
  • certstore/certs directory is where our server certificates will be placed.
  • certstore/newcerts directory is where OpenSSL puts the created certificates in PEM (unencrypted) format and in the form cert_serial_number.pem (e.g. 100001.pem). OpenSSL needs this directory, so we create it.
  • certstore/crl is where our certificate revocation list is placed.
  • certstore/private is the directory where our private keys are placed.
  • certstore/newcerts is the directory where we will place newly created certs and requests
  • certstore/newcerts is the directory where we will place exported PCKS#12 formatted keys
  • wireless/certs is our FreeRADIUS Certificate Store (keeping CA functionality and Server functionality separate)
  • wireless/certs/clients is where we will keep our client certificates.
  • wireless/certs/server is where server credentials will be kept.

Be sure that you set restrictive permissions to all your private keys so that they can be read only by root, or the user with whose privileges a server runs. If anyone steals your private keys, then things get really bad.

1.2 Ensure directory is protected to root only access:

/bin/chmod -R 0700 /etc/certstore


Permissions Explanation: 0700 = Read, write, execute owner (root) only


1.3 Create a database to keep track of each signed cert. The "serial" file keeps track of signed certificates.

/bin/echo '100001' >/etc/certstore/serial
/usr/bin/touch /etc/certstore/certindex.txt

1.4 Edit openssl.cnf to customize to your needs


#############################################
# OpenSSL Configuration File
# Version 1.0
# privacywonk@privacywonk.net
# 23 October 2010
#############################################

# Establish working directory.

dir =/etc/certstore

[ ca ]
default_ca = CA_default

[ CA_default ]
serial = $dir/serial
database = $dir/certindex.txt
new_certs_dir = $dir/certs
certificate = $dir/CA/cacert.pem
private_key = $dir/CA/private/cakey.pem
default_days = 365 #2 years = 730, 3 years = 1095 4yrs = 1460 5yrs = 1825
default_md = sha1
preserve = no
email_in_dn = no
nameopt = default_ca
certopt = default_ca
policy = policy_match

[ policy_match ]
countryName = match
stateOrProvinceName = match
organizationName = match
organizationalUnitName = optional
commonName = supplied
emailAddress = optional

[ req ]
default_bits = 1024 # Size of keys
default_keyfile = key.pem # name of generated keys
default_md = sha1 # message digest algorithm 23 October 2010 changed to SHA1
string_mask = nombstr # permitted characters
distinguished_name = req_distinguished_name
req_extensions = v3_req

[ req_distinguished_name ]
# Variable name Prompt string
#------------------------- ----------------------------------
0.organizationName = Organization Name (company)
organizationalUnitName = Organizational Unit Name (department, division)
emailAddress = Email Address
emailAddress_max = 40
localityName = Locality Name (city, district)
stateOrProvinceName = State or Province Name (full name)
countryName = Country Name (2 letter code)
countryName_min = 2
countryName_max = 2
commonName = Common Name (hostname, IP, or your name)
commonName_max = 64

# Default values for the above, for consistency and less typing.
# Variable name Value
#------------------------ ------------------------------
0.organizationName_default = Awesome Wifi
organizationalUnitName_default = Security
localityName_default = <<Your City>>
stateOrProvinceName_default = <<Your State>>
countryName_default = US
commonName_default = 10.0.1.75 #IP Address or name of your RADIUS Server

[ v3_ca ]
basicConstraints = CA:TRUE
subjectKeyIdentifier = hash
authorityKeyIdentifier = keyid:always,issuer:always

[ v3_req ]
basicConstraints = CA:FALSE
subjectKeyIdentifier = hash
################################################################################

1.5 Create xpextensions file
The xpextensions file holds Extended Key Usage object identifier codes (OID) that are required to have OpenSSL generated certificates work with Microsoft products. Create the file and add the following content:


[ xpclient_ext ]
extendedKeyUsage = 1.3.6.1.5.5.7.3.2

[ xpserver_ext ]
extendedKeyUsage = 1.3.6.1.5.5.7.3.1


1.6: Ensure restrictive permissions of your config file:

/bin/chmod 0600 /etc/certstore/openssl.cnf


Permissions Explanation: 0600 = read/write owner (root) only



Step 2: Generate new Certificate Authority Certificate


Generating your own Certificate Authority key pair will allow you to create and sign your own server and client certificates. As this is an internal network, we do not need to concern ourselves with having a certificate on a published trusted root authority list. Later in the deployment, we will use our own generated certificates and add them to a Trusted Root Authority certificate store for Windows clients.


Make sure these commands are executed in the /etc/certstore directory.

2.1 Generate the CA Certificate and Key pair

openssl req -new -x509 -extensions v3_ca -keyout CA/private/cakey.pem -out CA/cacert.pem -days 3650 -config ./openssl.cnf


Note: The "-days" option is set to 3650, this means the CA cert will last for 10 years. This is because I am lazy and accept the security risk it introduces.

IMPORTANT: This where you must start keeping track of passwords for each of these files. I suggest creating a file on removable media. However, understand this introduces a security risk. I would also suggest using a random password generator that includes lower case, upper case, special characters, and numbers. Again, this is for your home network so you do not need 128-character passwords but they sure won't hurt. However, every time you need to sign a new certificate you will need this password.

2.2. Protect your newly created private key:

/bin/chmod 0400 /etc/certstore/CA/private/cakey.pem


Permissions Explanation: 0400 = Read only by owner

2.3 Export your CA Key for deployment
These keys will be used for your client computers, they will need to have access to the CA key as they would a trusted CA like VeriSign, etc.

openssl x509 -in CA/private/cacert.pem -outform DER -out export/AwesomeCA.der



Step 3: Generate RADIUS Server certificate


3.1 Server signing request:

openssl req -new -nodes -keyout newcerts/radius_key.pem -out newcerts/radius_req.pem -days 1825 -config openssl.cnf


3.2 Sign Radius Server Certificate

openssl ca -config ./openssl.cnf -out newcerts/radius_cert.pem -extensions xpserver_ext -extfile ./xpextensions -infiles newcerts/radius_req.pem


Enter password. Confirm signing action.


3.3 Copy server key pair and CA key to /etc/wireless/certs/server

cp /etc/certstore/newcerts/radius_cert.pem /etc/wireless/certs/server
cp /etc/certstore/newcerts/radius_key.pem /etc/wireless/certs/server
cp /etc/certstore/CA/cacert.pem /etc/wireless/certs/server



Step 4: Generate Client Certificates

This is an important step. Take an inventory of the devices that will be connecting through your wireless network. Ensure each device under your control has a unique certificate. I also make utility certificates for future use and a few guest certificates. For example:
  • XPLaptop1
  • XPLaptop2
  • XPLaptop3
  • XPLaptop4
  • XPLaptop5
  • Android1
  • Android2
  • AppleIOS1
  • AppleIOS2
  • GuestKey1
  • GuestKey2
  • GuestKeyOSX1

I invest the time to make these keys upfront and store them on a USB drive (kingston datatraveler, iron key, or some other encrypted USB drive) or CD-R for future use. It's easier to dig up the removable media than to remember exactly how to make the key if this isn't something you do regularly. Note: Ensure the Common Name field is changed from the default. Common Names should be unique to the specific key, i.e. XPLaptop1. Keep track of the common names used.

You will need to create a PEM password for each of these, choose something strong. Keep this PEM password on file as well.


openssl req -new -keyout newcerts/XPLaptop1_key.pem -out newcerts/XPLaptop1_req.pem -days 1825 -config ./openssl.cnf



Step 5: Sign all client certificates


For each certificate generated you must sign it with the CA key.

5.1 For windows certificates use the following command:

openssl ca -config ./openssl.cnf -out newcerts/XPLaptop1_cert.pem -extensions xpclient_ext -extfile ./xpextensions -infiles newcerts/XPLaptop1_req.pem


5.2 For MAC OSX clients use the following command:

openssl ca -config ./openssl.cnf -out newcerts/GuestOSX1_cert.pem -infiles newcerts/GuestOSX1_req.pem


5.3 Copy client certificates (public key) to FreeRADIUS CertStore: /etc/wireless/certs/clients

cp /etc/certstore/newcerts/*_cert.pem /etc/wireless/certs/clients



Step 6: Export Certificates for Windows & Mac


It is recommended to use Public-Key Cryptography Standards (PKCS) 12 to export certificates for Microsoft compatibility. PKCS#12 defines a file format commonly used to store X.509 private keys with accompanying public key certificates, protected with a password-based symmetric key. When you are ready to move these files to movable media, simply download the entire contents of /etc/certstore/export.


openssl pkcs12 -export -in newcerts/XPLaptop_cert.pem -inkey newcerts/XPLaptop_key.pem -out export/XPLaptop_cert.p12 -clcerts

A note on export passwords. Ideally, you should allow each user to choose their password. However, that will generally allow individuals to choose horribly weak passwords, thus compromising the certificate and making it susceptible to brute force attacks. X.509 certificates combine public and private key pairs into one binary file, the export password will control the access to the private key area. Choose something random and strong, just as you did for the PEM password.


Step 7: Set up and Configure FreeRADIUS


7.1 -- Setup Diffie-Hellman parameters and random file


cd /etc/wireless/
openssl dhparam -check -text -5 1024 -out dh


Command Output:
Generating DH parameters, 1024 bit long safe prime, generator 5
This is going to take a long time
.............+.......+.....................+.......................................................................
......................................+.............+...............+..+..+.+............+..............+.....
.................................+......+.................+....................................+.......+.........
+.......++*++*++*++*++*++* (and screen fulls more of this)
DH parameters appear to be ok.


dd if=/dev/urandom of=random count=2


Command Output:
2+0 records in
2+0 records out
1024 bytes transferred in 0.000078 secs (13134457 bytes/sec)


/usr/sbin/chown freeradius:freeradius /etc/wireless/dh
/usr/sbin/chown freeradius:freeradius /etc/wireless/random

/bin/chmod 0600 /etc/wireless/dh
/bin/chmod 0600 /etc/wireless/random


Permissions Explanation: We chown the dh file to ensure freeradius can access it for use in DH exchanges. We then chmod it so that write permissions are removed from any other users. o = others "-w" = remove write permissions.

The "dh" file created by openssl is a Diffie-Hellman parameters file. It is used by FreeRADIUS for negotiating TLS session keys. The Random file created by the "dd" program is used for random data in TLS operations.


7.2 Configure eap.conf

#################################################################
# eap.conf -- Configuration for WiFi EAP-TLS (and other types)
# Version 1.0
# 23 October 2010
# privacywonk@privacywonk.net
#################################################################

eap {
default_eap_type = tls
timer_expire = 60
ignore_unknown_eap_types = no
cisco_accounting_username_bug = no
max_sessions = 4096

## EAP-TLS
tls {
certdir = /etc/wireless/certs/clients #client cert directory

#private_key_password = #Challenge password for private keys (if set)
private_key_file = /etc/wireless/certs/server/radius_key.pem
certificate_file = /etc/wireless/certs/server/radius_cert.pem

# Trusted Root CA file
CA_file = /etc/wireless/certs/server/cacert.pem

# Diffie-Hellman parameters file; used by freeradius for negotiating TLS session keys
dh_file = /etc/wireless/dh

# Random bitstream file that also is used in TLS operations:
random_file = /etc/wireless/random


fragment_size = 1024

#cipher_list = "DEFAULT" #man 1 ciphers, weak sauce
cipher_list = "HIGH" #force high...may still be weak sauce for windows (3DES).

} #close TLS config
##################################################
#
# !!!!! WARNINGS for Windows compatibility !!!!!
#
##################################################
#
# If you see the server send an Access-Challenge,
# and the client never sends another Access-Request,
# then
#
# STOP!
#
# The server certificate has to have special OID's
# in it, or else the Microsoft clients will silently
# fail. See the "scripts/xpextensions" file for
# details, and the following page:
#
# http://support.microsoft.com/kb/814394/en-us
#
# For additional Windows XP SP2 issues, see:
#
# http://support.microsoft.com/kb/885453/en-us
#
#
# If is still doesn't work, and you're using Samba,
# you may be encountering a Samba bug. See:
#
# https://bugzilla.samba.org/show_bug.cgi?id=6563
#
# Note that we do not necessarily agree with their
# explanation... but the fix does appear to work.
#
##################################################
} #close eap configuration


7.3 Configure Clients.conf

#################################################################
# clients.conf -- client configuration directives
# Version 1.0
# 23 October 2010
# privacywonk@privacywonk.net
#################################################################

client localhost {
ipaddr = 127.0.0.1
secret = testing123
require_message_authenticator = no
nastype = other # localhost isn't usually a NAS...
} #close localhost

client 10.0.1.1 { #This should be the IP address or host name of your AP/Router
secret = <<Your Secret Password Shared Between AP and RADIUS. Beware special characters>>
shortname = <<Your SSID Network Name>>
nastype = other #appropriate NAS type for a wireless AP
} #close WiFi


7.4 Configure radius.conf

#################################################################
# clients.conf -- FreeRADIUS server configuration file.
# Version 1.0
# 23 October 2010
# privacywonk@privacywonk.net
#################################################################
#
# Read "man radiusd" before editing this file. See the section
# titled DEBUGGING. It outlines a method where you can quickly
# obtain the configuration you want, without running into
# trouble.
#
# Run the server in debugging mode, and READ the output.
#
# $ radiusd -X
#
#################################################################


prefix = /usr/local
exec_prefix = ${prefix}
sysconfdir = ${prefix}/etc
localstatedir = /var
sbindir = ${exec_prefix}/sbin
logdir = /var/log
raddbdir = ${sysconfdir}/raddb
radacctdir = ${logdir}/radacct

# name of the running server. See also the "-n" command-line option.
name = radiusd

# Location of config and logfiles.
confdir = ${raddbdir}
run_dir = ${localstatedir}/run/${name}

# Should likely be ${localstatedir}/lib/radiusd
db_dir = ${raddbdir}

#
# libdir: Where to find the rlm_* modules.
libdir = /usr/local/lib/freeradius-2.1.9

# pidfile: Where to place the PID of the RADIUS server.
pidfile = ${run_dir}/${name}.pid


# user/group: The name (or #number) of the user/group to run radiusd as.
#
user = freeradius
group = freeradius

# max_request_time: The maximum time (in seconds) to handle a request.
max_request_time = 10

# cleanup_delay: The time to wait (in seconds) before cleaning up a reply which was sent to the NAS.
cleanup_delay = 5

# max_requests: The maximum number of requests which the server keeps
# track of. This should be 256 multiplied by the number of clients.
# e.g. With 20 clients, this number should be 5120.
max_requests = 5120

# listen: Make the server listen on a particular IP address, and send
# replies out from that address. This directive is most useful for
# hosts with multiple IP addresses on one interface.

listen {
type = auth
ipaddr = 10.0.1.75
# 0 means "use /etc/services for the proper port"
port = 0
}

# This second "listen" section is for listening on the accounting
# port, too.
#
listen {
type = acct
ipaddr = 10.0.1.75
port = 0
}

hostname_lookups = no
allow_core_dumps = no #only turn on for debugging
regular_expressions = yes
extended_expressions = yes


################# LOGGING ####################################
#
# Logging section. The various "log_*" configuration items
# will eventually be moved here.
#
log {
destination = files
file = ${logdir}/radius.log
syslog_facility = daemon
# for initial debugging purposes everything below is set to yes. This will provide verbose log files to ensure smooth operations. Once that is established, these can all be changed to no.
stripped_names = yes
auth = yes
auth_badpass = yes
auth_goodpass = yes

}

# The program to execute to do concurrency checks.
checkrad = ${sbindir}/checkrad

################# SECURITY CONFIGURATION ####################################
# There may be multiple methods of attacking on the server. This
# section holds the configuration items which minimize the impact
# of those attacks
#
security {
max_attributes = 200 #default value
reject_delay = 1
status_server = yes
}

################# PROXY CONFIGURATION ####################################
# proxy_requests: Turns proxying of RADIUS requests on or off.
proxy_requests = no
#$INCLUDE proxy.conf

################# CLIENTS CONFIGURATION ####################################
# Client configuration is defined in "clients.conf".

$INCLUDE clients.conf

################# THREAD POOL CONFIGURATION ####################################
# The thread pool is a long-lived group of threads which
# take turns (round-robin) handling any incoming requests.
thread pool {
start_servers = 5
max_servers = 32
min_spare_servers = 3
max_spare_servers = 10
max_requests_per_server = 0
}

# MODULE CONFIGURATION
#
# The names and configuration of each module is located in this section.
#
# After the modules are defined here, they may be referred to by name,
# in other sections of this configuration file.
#
modules {
# $INCLUDE ${confdir}/modules/
$INCLUDE ${confdir}/modules/exec
$INCLUDE ${confdir}/modules/expr
$INCLUDE ${confdir}/modules/expiration
$INCLUDE ${confdir}/modules/logintime
$INCLUDE ${confdir}/modules/preprocess
$INCLUDE ${confdir}/modules/acct_unique
$INCLUDE ${confdir}/modules/realm
$INCLUDE ${confdir}/modules/detail
$INCLUDE ${confdir}/modules/attr_filter
$INCLUDE ${confdir}/modules/radutmp

# Extensible Authentication Protocol
$INCLUDE eap.conf
}

# Instantiation
#
instantiate {
#
# Allows the execution of external scripts.
# The entire command line (and output) must fit into 253 bytes.
#
# e.g. Framed-Pool = `%{exec:/bin/echo foo}`
exec

#
# The expression module doesn't do authorization,
# authentication, or accounting. It only does dynamic
# translation, of the form:
#
# Session-Timeout = `%{expr:2 + 3}`
#
# So the module needs to be instantiated, but CANNOT be
# listed in any other section. See 'doc/rlm_expr' for
# more information.
#
expr
# daily #default...
expiration
logintime
}

######################################################################
#
# Policies that can be applied in multiple places are listed
# globally.
$INCLUDE policy.conf

######################################################################
#
# Load virtual servers.
$INCLUDE sites-enabled/
######################################################################


Note: The directives for logging stripped names, good and bad passwords will produce verbose log files. These are useful for debugging purposes; however, the logs can give away critical information. Below is an example of a log file produced when all of these directives are turned on:


Tue Oct 26 21:53:47 2010 : Auth: Login OK: [YourCertsCommonName1/] (from client YourAP/Router port 60 cli 0088dbc207e6)
Wed Oct 27 05:09:30 2010 : Auth: Login OK: [YourCertsCommonName2/] (from client Your/Router port 42 cli 00516f9b3176)
Mon Oct 25 02:13:06 2010 : Auth: Login incorrect: [InvalidKeyCommonName/] (from client boomsquad port 46 cli f09defea03fa4)
Mon Oct 25 02:14:15 2010 : Error: TLS Alert read:fatal:unknown CA
Mon Oct 25 02:14:15 2010 : Error: TLS_accept:failed in SSLv3 read client certificate A
Mon Oct 25 02:14:15 2010 : Error: rlm_eap: SSL error error:14094418:SSL routines:SSL3_READ_BYTES:tlsv1 alert unknown ca
Mon Oct 25 02:14:15 2010 : Error: SSL: SSL_read failed inside of TLS (-1), TLS session fails.


7.5 Update /usr/local/etc/raddb/sites-available/default
This file controls the authentication, authorization, and accounting modules available to FreeRADIUS. We want to lock this down to EAP only.


#################################################################
# sites-available/default -- FreeRADIUS default sites/authentication files.
# Version 1.0
# 23 October 2010
# privacywonk@privacywonk.net
#################################################################

# Authorization. First preprocess (hints and huntgroups files),
# then realms, and finally look in the "users" file.
#
# The order of the realm modules will determine the order that
# we try to find a matching realm.
#
# Make *sure* that 'preprocess' comes before any realm if you
# need to setup hints for the remote radius server
authorize {
#
# The preprocess module takes care of sanitizing some bizarre
# attributes in the request, and turning them into attributes
# which are more standard.
#
# It takes care of processing the 'raddb/hints' and the
# 'raddb/huntgroups' files.
preprocess
#
# This module takes care of EAP-MD5, EAP-TLS, and EAP-LEAP
# authentication.
#
# It also sets the EAP-Type attribute in the request
# attribute list to the EAP type from the packet.
#
# As of 2.0, the EAP module returns "ok" in the authorize stage
# for TTLS and PEAP. In 1.x, it never returned "ok" here, so
# this change is compatible with older configurations.
#
# The example below uses module failover to avoid querying all
# of the following modules if the EAP module returns "ok".
# Therefore, your LDAP and/or SQL servers will not be queried
# for the many packets that go back and forth to set up TTLS
# or PEAP. The load on those servers will therefore be reduced.
#
eap {
ok = return
}


#
} #end authorize

# Authentication.
#
#
# This section lists which modules are available for authentication.
authenticate {
eap
} #end authenticate

# Pre-accounting. Decide which accounting type to use.
#
preacct {
preprocess
acct_unique
suffix
} #close preacct

# Accounting. Log the accounting data.
#
accounting {
detail

# Filter attributes from the accounting response.
attr_filter.accounting_response
} #close accounting

# Session database, used for checking Simultaneous-Use. Either the radutmp
# or rlm_sql module can handle this.
# The rlm_sql module is *much* faster
session {
radutmp
} #close session

# Post-Authentication
# Once we KNOW that the user has been authenticated, there are
# additional steps we can take.
post-auth {
exec
Post-Auth-Type REJECT {
attr_filter.access_reject
} #close reject
} #close post auth



7.6 Secure FreeRADIUS Configuration files and Certificates
We need to protect our configuration files and certstore from prying eyes...


chown -R freeradius:freeradius /usr/local/etc/raddb/
chmod -R 0700 /usr/local/etc/raddb/
chmod 0400 /usr/local/etc/raddb/*.conf

chown -R freeradius:freeradius /etc/wireless
chmod -R 0700 /etc/wireless/certs
chmod 0400 /etc/wireless/certs/server/*.pem
chmod 0400 /etc/wireless/certs/clients/*.pem


Permissions Explanation: Directories must be 0700 (Read, write, execute owner only) to allow for execution by the FreeRADIUS server; however, as the configuration files and certificates are not changed by the server they can be locked down to 0400 (read only).



Step 8: Test your Server Configuration


8.1 Test your config files

/usr/local/sbin/radiusd -X -f


This will spit out a huge amount of debug text. You should not see any Warning or Error statements at all. Ideally, it will end with something along the lines of:


Listening on authentication address 10.0.1.75 port 1812
Listening on accounting address 10.0.1.75 port 1813
Listening on command file /var/run/radiusd/radiusd.sock
Ready to process requests.


Click here to see the full debug output of a successful startup.

If you see any errors, review your configuration files, RTFM, hit google, or leave me a comment and I will try to diagnose.

Once you have a successful startup and have figured out any potential configuration issues kill any running servers (Ctrl-C) and restart like so:

/usr/local/sbin/radiusd -X -f > ~root/radius.debug.log.txt


Move to a new terminal window run the following command:

/usr/bin/tail -f ~root/radius.debug.log.txt


This will allow you to watch the log in real time and also preserve a copy for later review. As we move toward setting up our access points and clients (supplicants) we can monitor if the AP is correctly passing traffic to the FreeRADIUS server, if the client (supplicant) is using the proper certificate, etc.

8.2 Testing FreeRADIUS
If you want to take the time to conduct a proper test, I would suggest the very detailed EAP-TLS testing methodology presented in the Free Software Magazine: HOWTO: Incremental Setup of FreeRADIUS Server for EAP Authentications. Specifically, "Step 4. Full swing with EAP-TLS, EAP-TTLS and PEAP".

It will will be very apparent if the configuration presented in this tutorial is working or not. However, good testing is always encouraged!



Step 9: Configure Wireless AP

Hopefully we have not wasted a lot of time only to find out your router does not support WPA2-Enterprise authentication. My Cisco/Linksys home router did not support it out of the box but DD-WRT, a third-party firmware, does.

Here is a screenshot. Setup is very simple:




Step 10: Deploying Certificates to Client Devices

Download the exported certificates to a USB drive or burn to a CD-R. If you have elected to setup random password in place of user supplied passwords, make sure you have a list you can copy and paste from while installing. This isn't great security but it makes deployment easier. Again, this is your home network not a classified network.

10.1 Install the Certificate Authority Certificate

Double click on the .DER file we made earlier (AwesomeCA.der). The following screen will show up:



Click the "Install" Button.

This will take you to a screen that prompts for selection of a Certificate Store.

Select the second radio button "Place all certificates in the following store" and click "Browse."

Select the "Trusted Root Certification Authorities" store from the list. Click OK.



Click "Next"

You will be prompted with a security warning. Click here for a screen shot (too big to display on webpage). Click Yes.

10.2 Install the Client Certificates

Double click on the .p12 file we made earlier.



Click Next.

A screen will verify the location of the key you want to import.



Click Next.

Enter the export password for the certificate. This will allow windows to successfully import the cert.



Click Next. Windows will inform you the certificate was successfully imported.

Step 11: Setup Client Wireless (detailed directions for Windows XP SP3 only below)

Setup a new Wireless network. Select WPA2 with AES Encryption



Click the Authentication Tab. Make sure to select "Smart Card or other Certificate." Click Properties.



Scroll to find and select the name of your Cert Authority in the list. Click OK.



iPhone Instructions
MAC OSX Instructions


Step 12: Configure FreeRADIUS to Start on Boot


If your clients have successfully connected, kill whatever radius instances you may be running through the command line (for example, debugging server mention in step 8).

12.1 Add Radius to rc.conf to ensure FreeRADIUS starts on boot.

/bin/echo radiusd_enable="YES" >> /etc/rc.conf


12.2 Start the server through the rc.d script.

/usr/local/etc/rc.d/radiusd start

Terminology
Authentication, Authorization, and Accounting (AAA) Protocol:

Authentication - Authentication refers to the process where an entity's identity is authenticated, typically by providing evidence that it holds a specific digital identity such as an identifier and the corresponding credentials. The digital certificates generated in this tutorial are a type of credential.

Authorization - Determines whether a particular entity is authorized to perform a given activity, typically logging on to an application or service

Accounting - tracking of the consumption of network resources by users.

Supplicant -- an entity at one end of a point-to-point LAN segment that seeks to be authenticated by an authenticator attached to the other end of that link. In practice, a supplicant is a software application installed on an
end-user's computer. The user invokes the supplicant and submits
credentials to connect the computer to a secure network. If the
authentication is successful, the authenticator typically allows the
computer to connect to the network

Authenticator -- an entity at one end of a point-to-point LAN segment that facilitates authentication of the entity attached to the other end of that link. In practice, the authenticator is usually a network switch or wireless access point/router that serves as the point of connection for computers joining the network.

Authentication Server -- servers that provide authentication services to users or other systems via networking. Remotely placed users and other servers authenticate to such a server, and receive cryptographic tickets. These tickets are then exchanged with one another to verify identity. In practice, and applicable to use in this post, FreeRADIUS.

Remote Authentication Dial In User Service (RADIUS) -- a networking protocol that provides centralized Authentication, Authorization, and Accounting (AAA) management for computers to connect and use a network service.


Summation


While the content of this post will help you deploy some kick ass wireless security it is not a complete security solution. In fact, as I noted in the post, my way of handling keys and associated pass phrases introduces security risks. Protecting and managing your keys is critical to ensure the network remains secure.

Make sure you have locked down the FreeBSD computer that hosts the Certificate Authority and FreeRADIUS server.

If you have frequent guests using your network, I would suggest creating a segregated Virtual Wireless LAN for them to use instead giving them certificate-based access.

A note about maintaining a Certificate Authority. It's annoying. If you expect any a level of fluidity in your user base, employees leaving, frequent guests, etc. I would highly suggest investing the time into automating the certificate generation process. There are many tools out there that can assist in this. For example, TinyCA.

Lastly, I hope the post was useful and that you were able to successfully replicate a deployment of WPA2. I know there were a few unexplained areas in the post, if you have any questions please reach out.

Return to Main