Hi,
I have what I consider a bug with pf and I feel like I just hit a wall preventing me from going further.
The server is running FreeBSD 8.2-RELEASE and connected to another FreeBSD host with a gif tunnel (the other host is not really important here except for the fact both are connected so I will not speak much about it), I have most of the things I want working with the configuration files below.
My problem is with port forwarding, I want any connection on the external interface on a specific address/port (10.11.12.212 and 80 here) to be forwarded to another host behind the gif tunnel (192.168.0.23), the rules below almost work but it fails, here is what happens:
- the packet enters via the external interface (em0) with destination 10.11.12.212 on port 80
- the rdr rule translates the packet with destination 192.168.0.23 and port 80
- the pass rule with route-to routes the packet to the gif1001 interface
- the rule "pass out log on $env1c1_tunnel tagged e1c1" allows the packet to exit via gif1001
In a wonderful world that is what would happen, but with my current configuration here's what tcpdump catches exiting via em0 (I added line breaks to keep things readable):
In this packet the source address for the ipip header is wrong but I don't see anything wrong in my rules, it may be a simple mistake and I sure hope it is but it really looks like a bug somewhere.
Here is the relevant part of my rc.conf file:
And here is my pf.conf:
The only real resource I found on the internet about this would be a bug report on NetBSD: http://mail-index.netbsd.org/netbsd-bugs/2006/09/06/0000.html
I hope someone can help me on that :\
I have what I consider a bug with pf and I feel like I just hit a wall preventing me from going further.
The server is running FreeBSD 8.2-RELEASE and connected to another FreeBSD host with a gif tunnel (the other host is not really important here except for the fact both are connected so I will not speak much about it), I have most of the things I want working with the configuration files below.
My problem is with port forwarding, I want any connection on the external interface on a specific address/port (10.11.12.212 and 80 here) to be forwarded to another host behind the gif tunnel (192.168.0.23), the rules below almost work but it fails, here is what happens:
- the packet enters via the external interface (em0) with destination 10.11.12.212 on port 80
- the rdr rule translates the packet with destination 192.168.0.23 and port 80
- the pass rule with route-to routes the packet to the gif1001 interface
- the rule "pass out log on $env1c1_tunnel tagged e1c1" allows the packet to exit via gif1001
In a wonderful world that is what would happen, but with my current configuration here's what tcpdump catches exiting via em0 (I added line breaks to keep things readable):
Code:
IP 10.11.12.212 > 10.11.20.1:
IP 10.11.12.5.57151 > 192.168.0.23.80:
Flags [S], seq 1515274791, win 65535, options [mss 1460,nop,wscale 3,nop,nop,TS val 721395077 ecr 0,sackOK,[|tcp]> (ipip-proto-4)
In this packet the source address for the ipip header is wrong but I don't see anything wrong in my rules, it may be a simple mistake and I sure hope it is but it really looks like a bug somewhere.
Here is the relevant part of my rc.conf file:
Code:
# Router
ifconfig_em0="inet 10.11.12.212/24"
defaultrouter="10.11.12.253"
gateway_enable="YES"
static_routes="gif_endpoint"
route_visp="10.11.20.1/32 10.11.12.213"
pf_enable="YES"
pf_rules="/etc/pf.conf"
pflog_enable="YES"
# IPIP tunnels
gif_interfaces="gif1001"
ifconfig_em0_alias0="inet 10.11.20.2/32"
ifconfig_em0_alias1="inet 192.168.254.1/32"
gifconfig_gif1001="10.11.20.2 10.11.20.1"
ifconfig_gif1001="inet 1.2.3.1 1.2.3.2 netmask 255.255.255.252"
And here is my pf.conf:
Code:
phys_if = "em0"
env1c1_tunnel = "gif1001"
env1c1_tunnel_dst = "10.11.20.1"
env1c1_tunnel_src = "10.11.20.2"
env1c1_escape = "10.11.12.212"
set skip on lo0
set block-policy drop
scrub in on $phys_if
####
## NAT / RDR
####
nat on $phys_if tagged e1c1 -> $env1c1_escape
nat on $phys_if tagged e1c2 -> $env1c2_escape
# forwarded port (http)
rdr on $phys_if proto tcp from any to $env1c1_escape port 80 tag e1c1 -> 192.168.0.23 port 80
####
## FILTERS
####
# block any packet with no match
block log all
# allow our own services to work
pass in on $phys_if proto tcp from any to $phys_if port ssh synproxy state
pass in on $phys_if proto icmp from any to $phys_if
pass out on $phys_if proto udp from any to any port { ntp, domain }
# allow ipip traffic (tunnels)
pass in on $phys_if from $env1c1_tunnel_dst to $env1c1_tunnel_src
pass out on $phys_if from $env1c1_tunnel_src to $env1c1_tunnel_dst
pass in on $phys_if from $env1c2_tunnel_dst to $env1c2_tunnel_src
pass out on $phys_if from $env1c2_tunnel_src to $env1c2_tunnel_dst
# Port forwarding
pass in log on $phys_if route-to ( $env1c1_tunnel 1.2.3.2 ) proto tcp from any to 192.168.0.23 port 80 tagged e1c1
pass out log on $env1c1_tunnel tagged e1c1
# NAT (the server's gateway will be used, traffic is returned to the tunnel)
pass in log on $env1c1_tunnel tag e1c1
pass out log on $phys_if reply-to $env1c1_tunnel tagged e1c1
pass in log on $env1c2_tunnel tag e1c2
pass out log on $phys_if reply-to $env1c2_tunnel tagged e1c2
# sites => sites
pass in on $env1c1_tunnel route-to $env1c1_tunnel to $env1c1_sites tag e1c1
pass in on $env1c2_tunnel route-to $env1c2_tunnel to $env1c2_sites tag e1c2
The only real resource I found on the internet about this would be a bug report on NetBSD: http://mail-index.netbsd.org/netbsd-bugs/2006/09/06/0000.html
I hope someone can help me on that :\