# pf nat for vnet jail doesn't work



## nantex (Jul 1, 2021)

Howdy,

I have a vnet jail with ip 172.20.20.1/24 configured with vnet. The epair is connected to the bridge, whose ip address is pingable from inside the jail. A pf nat rule for outgoing traffic is configured but it doesn't work at all.

Network setup:


```
# bridge:
jailsw0: flags=8843<UP,BROADCAST,RUNNING,SIMPLEX,MULTICAST> metric 0 mtu 1500
        ether 02:bd:fc:61:71:01
        inet 172.20.20.1 netmask 0xffffff00 broadcast 172.20.20.255
        id 00:00:00:00:00:00 priority 32768 hellotime 2 fwddelay 15
        maxage 20 holdcnt 6 proto stp-rstp maxaddr 2000 timeout 1200
        root id 00:00:00:00:00:00 priority 32768 ifcost 0 port 0
        member: epbilla.h flags=143<LEARNING,DISCOVER,AUTOEDGE,AUTOPTP>
                ifmaxaddr 0 port 5 priority 128 path cost 2000
        groups: bridge
        nd6 options=9<PERFORMNUD,IFDISABLED>

# epair inside jail and route:
epbilla.j: flags=8843<UP,BROADCAST,RUNNING,SIMPLEX,MULTICAST> metric 0 mtu 1500
        options=8<VLAN_MTU>
        ether 02:43:a9:17:0e:0b
        inet6 fe80::43:a9ff:fe17:e0b%epbilla.j prefixlen 64 tentative scopeid 0x3
        inet 172.20.20.10 netmask 0xffffff00 broadcast 172.20.20.255
        groups: epair
        media: Ethernet 10Gbase-T (10Gbase-T <full-duplex>)
        status: active
        nd6 options=29<PERFORMNUD,IFDISABLED,AUTO_LINKLOCAL>

# routes inside jail:
(jail) root@billa:/ # netstat -rnfinet
Routing tables

Internet:
Destination        Gateway            Flags     Netif Expire
default            172.20.20.1        UGS    epbilla.
127.0.0.1          link#1             UH          lo0
172.20.20.0/24     link#3             U      epbilla.
172.20.20.10       link#3             UHS         lo0
```

The pf config for the jail (added via an anchor)

```
ext        = em0
lanip      = 172.20.20.10
extip      = 144.76.*.*

# outgoing
nat on $ext from $lanip to any -> $extip

# incoming
rdr pass on $ext proto tcp from any to $extip port 80 -> $lanip port 80

# allow incoming
pass in quick on $ext proto tcp from any to $extip port 80 keep state
```

When I login into the jail and issue a ping (or dns request or whatever), this is what I see with tcpdump on the external interface:

```
12:21:32.351341 IP 172.20.20.10 > 141.1.1.1: ICMP echo request, id 39294, seq 6, length 64
```

The nat rule didn't mach:

```
nat on em0 inet from 172.20.20.10 to any -> 144.76.*.*
  [ Evaluations: 0         Packets: 0         Bytes: 0           States: 0     ]
  [ Inserted: uid 0 pid 674 State Creations: 0     ]
```

I also tried to replace the "on em0" part of the nat rule with the bridge interface with the same result. Also this variant doesn't work:


```
nat on $ext from $lanip to any -> ($ext)
```


Any ideas?


Many thanks in advance,
Tom


----------



## nantex (Jul 1, 2021)

Ok I found a workaround:

Currently I load the pf rules for the jail with an anchor from an extra file:

```
pfctl -a /jail/billa -f /jail/etc/billa/pf.conf -v
```

I do not load anchors from the main pf.conf since jails come and go and are not static. This works very nice with pass rules but not with rdr and nat rules. Obviously I' need some way to define a rdr anchor like "rdr-anchor" does.

So when I move the nat rule to the main pf.conf, then it works as it should.


----------



## nantex (Jul 1, 2021)

So I solved it. I had the following line at the end of my main pf.conf:


```
anchor "/jail/*"
```

However, I had to add these two at the front:


```
nat-anchor "/jail/*"
rdr-anchor "/jail/*"
```

The good thing is, I can use the same file for all 3 kinds of rules.


----------

