In addition to securing the wireless connection itself, it is important to lock down the rest of the services running on the computer. Unneeded services should be disabled, and a firewall should be established to protect the host. It is also worthwhile to set up a static ARP address for the gateway to protect against man-in-the-middle attacks and automate the monitoring of logs.
The System Preferences section titled Sharing controls what services will be run on the system. The Services tab, shown in Figure 7-4, controls what file-sharing services will be started on the system. Uncheck any of these you do not need to use. Remote Login is one service you might want to use; it provides a SSH login server to allow remote shell access.
The Firewall tab of the Sharing configuration allows groups of ports to be filtered. Disable access to all services, unless you need to allow access. In the example shown in Figure 7-5, the firewall is off.
You can enable the limited firewalling configuration provided in this GUI setup program by pressing the Start button. If you want to use a more complicated set of filtering rules, it requires creating a script to run at system startup.
If you don’t use the GUI
firewall configuration, you need to enable the automatic running of a
script as a startup item by the SystemStarter
program. First, create the directory
/System/Library/StartupItems/Firewall
. In this
directory, place the file
/System/Library/StartupItems/Firewall/StartupParameters.plist
.
This file describes the services provided by the startup item, and
should contain the following:
{ Description = "Firewall"; Provides = ("Firewall"); Requires = ("Network"); OrderPreference = "Late"; Messages = { start = "Starting firewall"; stop = "Stopping firewall"; }; }
The main script that starts the firewall should have the same name as
the directory it lives in. This file will be called
/System/Library/StartupItems/Firewall/Firewall
.
It writes a log message and then starts a monitoring script. The
Firewall script is:
#!/bin/sh ## # Firewall ## . /etc/rc.common ConsoleMessage "Starting Firewall" /usr/local/sbin/fwmon & echo $! > /var/run/fwmon.pid
The monitoring script called by Firewall is
/usr/local/sbin/fwmon
. This script will listen
for events signaling a change in IP addresses or the restart of
network adapters. When one of those events is received, it will call
/usr/local/sbin/firewall.sh
to reload the
ruleset. Create this file with the following contents:
#!/bin/sh SystemLog( ) { local Message="$*" logger -it fwmon "${Message}" } UpdateFirewall( ) { /usr/local/sbin/firewall.sh > /dev/null for iface in `ifconfig -lu`; do case "${iface}" in ppp*) ifconfig ${iface} mtu 1448 ;; esac done } SystemLog "Firewall monitoring started" UpdateFirewall while true do /usr/sbin/scutil -p <<-SC_SCRIPT > /dev/null open n.add State:/Network/Global/IPv4 n.wait close SC_SCRIPT sleep 3 SystemLog "IP Address added, removed or changed. Reconfiguring firewall." UpdateFirewall done exit 0
The final script is /usr/local/sbin/firewall.sh
itself. This file contains the rules that will be assigned to each
interface in the machine. It should contain:
#!/bin/sh
ipfw=ipfw
AddRule( )
{
local rule="$*"
${ipfw} add ${rule} via ${iface} > /dev/null
}
LoopbackFirewall( )
{
AddRule allow all from any to any
}
DefaultFirewall( )
{
# Prevent spoofing of the loopback network
AddRule deny log all from any to 127.0.0.0/8
# Allow DHCP traffic
AddRule allow udp from any 67 to any 67
AddRule allow udp from any 67 to any 68
AddRule allow udp from any 68 to any 67
AddRule allow udp from any 68 to any 68
# Prevent bogus addresses
AddRule deny log all from 0.0.0.0/8 to any in
AddRule deny log all from 169.254.0.0/16 to any in
AddRule deny log all from 192.0.2.0/24 to any in
AddRule deny log all from 224.0.0.0/4 to any in
AddRule deny log all from 240.0.0.0/4 to any in
AddRule deny log all from any to 0.0.0.0/8 in
AddRule deny log all from any to 169.254.0.0/16 in
AddRule deny log all from any to 192.0.2.0/24 in
AddRule deny log all from any to 224.0.0.0/4 in
AddRule deny log all from any to 240.0.0.0/4 in
# Allow established connections to persist - DANGEROUS, but unavoidable
# since ipfw sadly does not keep state as of OS X 10.1.
AddRule allow tcp from any to any established
# Allow certain ICMP traffic (ping and required stuff)
AddRule allow icmp from any to any icmptypes 0,3,4,8,11,12
# Allow DNS traffic in both directions
AddRule allow udp from any 53 to ${ipaddr} in
AddRule allow udp from ${ipaddr} to any 53 out
# Refuse AUTH requests. Reject the connection rather than deny it so
# that we don't have to wait for timeouts, etc.
AddRule reject tcp from any to any 113
# Allow traffic outgoing from this machine
AddRule allow tcp from ${ipaddr} to any out
AddRule allow udp from ${ipaddr} to any out
# If we're on our home network, allow SMB traffic
if [ "${domain}" == "yourhomedomainhere.com
" ]; then
AddRule allow tcp from ${ipaddr}:${netmask} 137-139 to any in
AddRule allow udp from ${ipaddr}:${netmask} 137-139 to any in
AddRule allow tcp from ${ipaddr} to ${ipaddr}:${netmask} 137-139 out
AddRule allow udp from ${ipaddr} to ${ipaddr}:${netmask} 137-139 out
fi
# Finally, a default rule to deny
AddRule deny log ip from any to any
}
# Ensure logging is enabled in the kernel
if [ `/usr/sbin/sysctl -n net.inet.ip.fw.verbose` == 0 ]; then
/usr/sbin/sysctl -w net.inet.ip.fw.verbose=1 > /dev/null
fi
# Cleanup any mess that may have been left behind from previous invocations
# or manual use of the firewalling interface.
${ipfw} -f flush > /dev/null
# Check the nameserver configuration to find out what our domain is
read junk domain < /etc/resolv.conf
for iface in `ifconfig -lu`; do
# Get the ip address assigned to the interface. If there is none, then
# the interface isn't truly active and we skip it.
line=`ifconfig ${iface} | grep -E '^[[:space:]]+inet[[:space:]]+.*$'`
if [ -z "${line}" ]; then
continue
fi
echo "${line}" | read junk ipaddr junk netmask junk
case "${iface}" in
lo*)
LoopbackFirewall
;;
*)
DefaultFirewall
;;
esac
done
exit 0
After creating the scripts, use the following commands to ensure that
the files are owned by the proper user and that the three script
files are set executable with chmod
:
# chown root:admin /Library/StartupItems/StaticArp/* # chown root:admin /usr/local/sbin/firewall.sh # chown root:admin /usr/local/sbin/fwmon # chmod 755 /Library/StartupItems/StaticArp/StaticArp # chmod 755 /usr/local/sbin/firewall.sh # chmod 755 /usr/local/sbin/fwmon
The firewall will start upon the next reboot, or it can be started immediately with:
# SystemStarter start Firewall
To protect against ARP man-in-the-middle attacks, which are described in Chapter 2, set static ARP entries using a startup item script similar to the one described for the firewall.
Create the directory
/System/Library/StartupItems/StaticARP
, and
place the file
/System/Library/StartupItems/StaticARP/StartupParameters.plist
in there with the following contents:
{ Description = "Static ARP"; Provides = ("StaticARP"); Requires = ("Network"); OrderPreference = "Late"; Messages = { start = "Starting Static ARP"; stop = "Stopping Static ARP"; }; }
The script
/System/Library/StartupItems/StaticARP/StaticARP
will add the ARP entry for the gateway when it is started and remove
it when stopped. Insert the correct gateway IP and MAC address into
the listing below, and place in the file:
#!/bin/sh ## # StaticArp ## . /etc/rc.common case "$1" in start) ConsoleMessage "Adding static ARP entry for gateway" /usr/sbin/arp -s;; stop) ConsoleMessage "Deleting static ARP entry for gateway" /usr/sbin/arp -d
<gatewayIP> <gatewayMAC>
;; esac
<gatewayIP>
Set the ownership of these two files, and make the script executable using these commands:
# chown root:admin /Library/StartupItems/StaticARP/* # chmod 755 /Library/StartupItems/StaticARP/StaticARP
The static ARP entries will be set upon the next reboot, or they can be set immediately with:
# SystemStarter start StaticARP
To clear the static ARP entries, use the following command:
# SystemStarter stop StaticARP
18.222.67.251