31 January 2011

Static Routes in FreeBSD

A friend of mine recently told me that while he appreciated the detail
and content of my writings, a good deal of the subject matter was a
little beyond him.  In support of the fresh-faced sysadmins and those
that might be new to FreeBSD (we were all there once), this write up is
how to add static routes to a FreeBSD host.  Our details for this are:
        HOST:           beastie
        PROMPT:         beastie [0]
        OS:             FreeBSD 8.1
While the examples are performed on FreeBSD 8.1, they should equally
apply at least back to FreeBSD 4.8.

In the following example, a route is added for a management network with
a destination of 10.11.18.0/24.  This network encompasses all addresses
starting from 10.11.18.0 and ending 10.11.18.255:
        beastie [0] /sbin/route add -net 10.11.18.0/24 -iface em0
        add net 10.11.18.0: gateway em0
The route is added with a gateway of one of our network interfaces
(-iface em0), meaning the network is directly reachable through this
interface.  In the next example, we add a route for a monitoring network.
The destination is 10.17.4.35, using 10.0.22.44 as the gateway and
255.255.255.224 as the netmask (addresses 10.17.4.32 - 10.17.4.63 (CIDR:
10.17.4.32/27)):
        beastie [0] /sbin/route add -net 10.17.4.35 10.0.22.44 255.255.255.224
        add net 10.17.4.35: gateway 10.0.22.44
The above 'route' commands illustrate two different ways 'route' allows
for specifying a netmask for the network in question.  The first uses
CIDR notation (/24) immediately following the destination.  In the second
example, the netmask is specified following the gateway.  Either way is
perfectly acceptable.  In the next command, a host route for an operations
server is added for host 192.168.34.43, with 192.168.56.88 as the gateway:
        beastie [0] /sbin/route add -host 192.168.34.43 192.168.56.88
        add host 192.168.34.43: gateway 192.168.56.88
A check of our routing table shows the newly added routes (I've identified
them with "<====" at the end of the lines):
        beastie [0] /usr/bin/netstat -f inet -nr
        Routing tables
        
        Internet:
        Destination        Gateway            Flags    Refs      Use  Netif Expire
        default            127.0.0.1          US          0        0    lo0
        10.0.22.0/23       link#1             U           0        0    em0
        10.0.23.181        link#1             UHS         0        0    lo0
        10.0.23.182        link#1             UHS         0        0    lo0
        10.11.18.0/24      08:00:27:ce:11:c0  US          0        0    em0  <====
        10.17.4.32/27      10.0.22.44         UGS         0        0    em0  <====
        127.0.0.1          link#3             UH          0       82    lo0
        192.168.34.43      192.168.56.88      UGHS        0        0    em1  <====
        192.168.56.0/24    link#2             U           1     1287    em1
        192.168.56.35      link#2             UHS         0        0    lo0
In order to retain the above routes through a reboot, we need to update
'/etc/rc.conf'.  To specify static routes, we add "static_routes" and
supply a double quoted, space delimited string as its value:
        static_routes="monitoring management ops_server"
Each element of the string gets a separate subsequent entry of
"route_ELEMENT" whose value is passed off to 'route add' during system
bootup:
        route_monitoring="-net 10.11.18.0/24 -iface em0"
        route_management="-net 10.17.4.35 10.0.22.44 255.255.255.224"
        route_ops_server="-host 192.168.34.43 192.168.56.88"
Of note, static routes need to be added after their dependent interfaces
are brought online.  Also, while underscores (_) are accepted as part of
the element, hyphens (-) are not.  Below are the contents of our updated
'/etc/rc.conf' accounting for our new static routes after our interfaces:
        beastie [0] /usr/bin/grep -v ^# /etc/rc.conf
        defaultrouter="127.0.0.1"
        hostname="beastie"
        ifconfig_em0="inet 10.0.23.181 netmask 255.255.254.0"
        ipv4_addrs_em0="10.0.23.182/23"
        ifconfig_em1="inet 192.168.56.35  netmask 255.255.255.0"
        static_routes="monitoring management ops_server"
        route_monitoring="-net 10.11.18.0/24 -iface em0"
        route_management="-net 10.17.4.35 10.0.22.44 255.255.255.224"
        route_ops_server="-host 192.168.34.43 192.168.56.88"
        inetd_enable="YES"
        sshd_enable="YES"
        sendmail_enable="NO"
        sendmail_submit_enable="NO"

see also:
    Static Routes in Solaris
    Static Routes in Linux