FreeBSD: Setup IP and Port Redirection using NAT

Yesterday, our development team has deliver the new website in new server. This website is replacing our old website and really need to point to the new server immediately. Since my boss do not want to afford any data inconsistency cause by DNS propagation, I need to use this method to redirect all connections  to port 80 for old server to port 80 at new server. Once redirected, only then I will need to change the DNS records to the new server. This will result zero DNS propagation time.

I will use the most simple way to achieve this objective by using IPFirewall as firewall and natd as address/port redirector. Both package should have come by default in FreeBSD.

Variables I used is:

OS: FreeBSD 8.0 64bit
Old server main IP: 202.188.90.11
Old web server IP: 202.188.90.12
New web server IP: 202.188.100.77
Domain: mywebsite.net

1. Since we want to make this FreeBSD server as router, we need to make sure it has 2 interface setup. One is for us to connect via public network and another one is for IP redirection. Make sure you have following IP setup in /etc/rc.conf:

ifconfig_em0="inet 202.188.90.11 netmask 255.255.255.0"
ifconfig_em1="inet 202.188.90.12 netmask 255.255.255.0"

2. Restart the network interface and check whether the IP is embedded into the interface or not:

$ /etc/rc.d/netif restart
$ ifconfig | grep inet
        inet 202.188.90.11 netmask 0xffffff00 broadcast 202.188.90.255
        inet 202.188.90.12 netmask 0xffffff00 broadcast 202.188.90.255

3. In this case I am going to use em1 as the interface to receive connection for web server (since the domain is pointed to this IP/interface). Add following line to /etc/rc.conf using text editor:

gateway_enable="YES"
firewall_enable="YES"
firewall_type="OPEN"
natd_enable="YES"
natd_interface="em1"
natd_flags="-f /etc/natd.conf"

4. If you see the configuration above, we specify natd_flags to read configuration from /etc/natd.conf. So we need to create this file and put some rules into it using text editor:

port 8668
interface em1
redirect_port tcp 202.188.100.77:80 202.188.90.12:80

5. Sadly, we need to reboot the server to make this new route works. Reboot as follow:

$ init 6

6.  Lets check whether all the required application is running:

$ ps aux | grep natd
root    858  0.0  0.2 14256  1628  ??  Ss   11:37AM   0:00.01 /sbin/natd -f /etc/natd.conf -n em1
$ ipfw list
00050 divert 8668 ip4 from any to any via em1
00100 allow ip from any to any via lo0
00200 deny ip from any to 127.0.0.0/8
00300 deny ip from 127.0.0.0/8 to any
00400 deny ip from any to ::1
00500 deny ip from ::1 to any
00600 allow ipv6-icmp from :: to ff02::/16
00700 allow ipv6-icmp from fe80::/10 to fe80::/10
00800 allow ipv6-icmp from fe80::/10 to ff02::/16
00900 allow ipv6-icmp from any to any ip6 icmp6types 1
01000 allow ipv6-icmp from any to any ip6 icmp6types 2,135,136
65000 allow ip from any to any
65535 deny ip from any to any

7. Now, lets browse the website, http://mywebsite.net and see where it goes. It should load the website in new server, 202.188.100.77. We just redirect the website to the new server without any worries on DNS propagation!