Current-Users archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Re: IPFilter issue in -current



On Jan 6, 2013, at 5:32 AM, Darren Reed <darrenr%netbsd.org@localhost> wrote:

> My thoughts are that the patch should be somewhat different and rather than 
> add
> more code that does the hash swapping, just perform that check once when 
> nat_hv[0]
> and nat_hv[1] are assigned. This then means that ipf_nat_delete() and other
> functions do not need to know about that complexity. Additionally, the NAT 
> code
> for IPv6 also needs to be fixed in this area.

That sounds like a really good idea. It will also fix the same problem in 
ipf_nat_tabmove, which I've since discovered needs it.

> If you can, please try out the attached patch.

I'll try this out in a couple hours.

In the meantime, I think I understand why I see so many ipf_nat_newrdr 
failures. I'm not sure if it's an algorithmic problem, or if I just need to 
write better rules.

The NAT router lives at (numbers made up, but consistent) 7.8.9.10, and there 
is a host at 192.168.10.11 that makes outbound connections from source port 
56789, and also accepts inbound connections on the same port. So, I have (among 
others) these rules in my ipnat.conf file:

map wm0 192.168.10.0/24 -> 0/32

rdr wm0 7.8.9.10/32 port 56789 -> 192.168.10.11 port 56789 tcp/udp

(Perhaps that rdr rule could be written "rdr wm0 0/32 port 49162 -> 
192.168.10.11 port 56789 tcp/udp"; I haven't tried.)

If the internal host 192.168.10.11 makes an outbound connection to some outside 
host 1.2.3.4 on port 12345, then this MAP entry will be created:

MAP 192.168.10.11   56789 <- -> 7.8.9.10     43210 [1.2.3.4 12345]

Notice that the NAT rules as written have chosen a new, random port for the 
local side of the connection. As far as the remote host is concerned, it has a 
connection from 7.8.9.10:43210. Then, that same remote host tries to connect 
back to the internal host, using 7.8.9.10:56789, and normally, ipnat would 
create an RDR entry like this:

RDR 192.168.10.11   56789 <- -> 7.8.9.10     56789 [1.2.3.4 12345]

But instead, it finds that the MAP entry above matches, and aborts creating the 
RDR entry. (It does this because duplicate entries would presumably cause 
failures of both connections.) I don't think the new connection can succeed, 
then, since the MAP entry won't actually match for inbound packets.

This seems like a failure in the matching logic in ipf_nat_newrdr around the 
call to ipf_nat_outlookup. Should this really be treated as a match?

I suspect I can work around the whole problem by adding a special-case map rule 
(before the map rule above) that makes sure that outbound connections from that 
particular port number never have their source ports rewritten. But it seems 
like that shouldn't be necessary. On the other hand, without it, what will the 
internal host do with two connections to the remote host, both at the same 
address and port on both sides? That seems like a basic socket error. To the 
remote host, though, it'd be fine, since it sees different remote (our local) 
ports. So maybe a special-case rule is unavoidable to prevent this situation in 
the first place.

Thanks,
- Geoff



Home | Main Index | Thread Index | Old Index