Monday, October 1, 2012

ASA 8.2 and Hairpin NAT

Don't ask me why people still do this, but there is occasionally the need to set up hairpin NAT on a firewall. This functionality is where a LAN user accesses another server on the LAN by its static public IP. For example, if i am 10.0.0.6 and i try to access 1.1.1.5, the firewall will turn the traffic around (and rewrite the IP) and send it down to whatever 1.1.1.5 is mapped to in the LAN. This functionality is different depending on the version of ASA software you're running, this is specifically for 8.2. This gets a little messier when you have a mixture of people with 1:1 NAT and PAT set up, but it works either way. Base config that will not work for hairpinning:
interface Vlan1
 nameif inside
 security-level 100
 ip address 10.0.0.1 255.255.255.0

interface Vlan2
 nameif outside
 security-level 0
 ip address 1.1.1.1 255.255.255.0

global (outside) 1 interface
nat (inside) 1 0.0.0.0 0.0.0.0

static (inside,outside) 1.1.1.5 10.0.0.5 netmask 255.255.255.255
static (inside,outside) 1.1.1.6 10.0.0.6 netmask 255.255.255.255
The issue with this is that if any user on the LAN tries to access 1.1.1.6, the ASA doesn't really know what to do with it, and drops it. So there are a few things that need to be fixed at this point:

Allow the ASA to turn the traffic around:

same-security-traffic permit intra-interface

Allow PAT'd users to have their IP rewritten when being hairpinned:

global (inside) 1 interface

Allow static NAT users to have their IP rewritten as well:

static (inside,inside) 1.1.1.5 10.0.0.5 netmask 255.255.255.255
static (inside,inside) 1.1.1.6 10.0.0.6 netmask 255.255.255.255


At this point it should be working normally, so here is the completed config:
interface Vlan1
 nameif inside
 security-level 100
 ip address 10.0.0.1 255.255.255.0

interface Vlan2
 nameif outside
 security-level 0
 ip address 1.1.1.1 255.255.255.0

same-security-traffic permit intra-interface
global (outside) 1 interface
global (inside) 1 interface
nat (inside) 1 0.0.0.0 0.0.0.0

static (inside,outside) 1.1.1.5 10.0.0.5 netmask 255.255.255.255
static (inside,outside) 1.1.1.6 10.0.0.6 netmask 255.255.255.255
static (inside,inside) 1.1.1.5 10.0.0.5 netmask 255.255.255.255
static (inside,inside) 1.1.1.6 10.0.0.6 netmask 255.255.255.255


Once this is done, you should be able to access the public IPs internally and get the traffic routed appropriately. If you are still having problems, i highly recommend the packet-trace command which can help you find out where the problem is occurring.