PF Hairpinning with pf

I've spent hours searching the web and read all the FreeBSD forum posts with "hairpinning" referenced. Even asked chatGPT for a how-to (none of the extensive suggestions worked). In most of the FreeBSD forum posts referenced going back for many years, SirDice has made comments about pf hairpinning, such as this one, "Connecting from the inside to the outside addresses is simply not going to work without some hairpin NAT trickery."

I'm seeking a description of that trickery. A how-to that works.

What I've tried: From the openbsd "PF - Traffic Redirection (Port Forwarding)", specifically:
Code:
pass in on $int_if proto tcp from $int_net to egress port 80 rdr-to $server
pass out on $int_if proto tcp to $server port 80 received-on $int_if nat-to $int_if
Since that isn't in FreeBSD pf-speak, I asked chatGPT to convert it and got these:
Code:
  rdr on $int_if proto tcp from $int_net to any port 80 -> $server
  pass in on $int_if proto tcp from $int_net to $server port 80

and

  nat on $int_if from $int_net to $server port 80 -> ($int_if)
  pass out on $int_if proto tcp from $int_net to $server port 80
They didn't work for me. Anyone have some freeBSD hairpinning pf rules that do?
 
What is your goal? Port forwarding your server that resides in a private network, to the public network?

If so, here is a good documentation on NAT for port forwarding
I've always found this article quite helpful. I've used it to run a web server in a jail, using PF to NAT traffic in and out of the jail without problems. It's much like mumu's description with the addition of using PF to NAT.

The author suggests ezjail, but I've always done it by just making a jail as per the handbook's instructions and going from there. It's just cloning an interface, putting the ip in /etc/jail.conf, and setting up pf.

I have a private network 192.168.2.0/24 for my Jails. My pf rule for NAT:

Code:
nat pass on alc0 inet from 192.168.2.0/24 to any -> 192.168.1.2
rdr pass on alc0 inet proto tcp from any to 192.168.1.2 port = 8000 -> 192.168.2.2

That being said, any incoming traffic hitting 192.168.1.2 (my FreeBSD server) at port 8000 will be redirected into my Jail at 192.168.2.2. Any outgoing traffic from 192.168.2.2 will be NATed to public.
 
The ultimate goal is to have inbound/outbound access to the net/rustdesk-server that I'm running in a jail. Presently, all rustdesk clients on the LAN can talk to all other rustdesk clients on the LAN. Same is true for rustdesk clients on the internet talking with other rustdesk clients on the internet.

But I can't get a rustdesk client on the LAN to talk with a rustdesk client on the internet or vice-versa. From my reading, it is the NAT router (FreeBSD) that is blocking that and a hairpin NAT is the solution I seek. In effect, I think having a hairpin NAT working would put both the now-separate LAN and internet sides of the rustdesk-server on the same side of the firewall.

You provided a link I hadn't seen before. I'll try that setup tomorrow.

Thank you.
 
Back
Top