-1

The following are my ip6tables rules:

# ip6tables -t nat -L -v
Chain PREROUTING (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination         
    0     0 DNAT       all      eth0   any     anywhere             2001:470:4a71:f170::/64  to:fdde:ad00:beef:0:91f5:6dd4:e66f:cf5b

Chain INPUT (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination         

Chain OUTPUT (policy ACCEPT 19 packets, 1936 bytes)
 pkts bytes target     prot opt in     out     source               destination         

Chain POSTROUTING (policy ACCEPT 19 packets, 1936 bytes)
 pkts bytes target     prot opt in     out     source               destination         
    0     0 MASQUERADE  all      any    eth0    fdde:ad00:beef::/64  anywhere            
    0     0 MASQUERADE  udp      any    eth0    fd11:22::/64         anywhere            
    0     0 MASQUERADE  tcp      any    eth0    fd11:22::/64         anywhere 

I'm seeing packets leave through eth0 using tshark. Here is one representative packet (received on interface wpan0):

221 480.196225356 fd11:22::703c:ef83:a03d:7e1b ? 2600:1f1c:c93:da00:76c2:1dbd:72c2:d063 TCP 94 [TCP Retransmission] 49998 ? 50000 [SYN] Seq=0 Win=9 Len=0 MSS=474 WS=1 SACK_PERM=1 TSval=2889901 TSecr=0

I want these packets to go through the MASQUERADE filter, so their source addresses are rewritten to be the host's IPv6 address on the ethernet (eth0). However, this is not happening, even though I would expect the packets to match the ip6tables rules. In fact, the packet is not even matching any of the MASQUERADE rules (witnessed by the pkts counter). I'm not sure how to debug this --- does anyone know why these packets are not being masqueraded?

Things I've tried:

  1. Delete all conntrack entries: conntrack -f ipv6 -D
  2. Restart the machine.

Thanks for your help!

Edit:

Here is some more useful output:

# ip6tables-save -c
# Generated by ip6tables-save v1.6.0 on Sun Sep  2 11:44:06 2018
*filter
:INPUT ACCEPT [1812:134308]
:FORWARD ACCEPT [22:1760]
:OUTPUT ACCEPT [1782:210084]
COMMIT
# Completed on Sun Sep  2 11:44:06 2018
# Generated by ip6tables-save v1.6.0 on Sun Sep  2 11:44:06 2018
*nat
:PREROUTING ACCEPT [1:137]
:INPUT ACCEPT [1:137]
:OUTPUT ACCEPT [41:5757]
:POSTROUTING ACCEPT [41:5757]
[0:0] -A PREROUTING -d 2001:470:4a71:f170::/64 -i eth0 -j DNAT --to-destination fdde:ad00:beef:0:91f5:6dd4:e66f:cf5b
[0:0] -A POSTROUTING -s fdde:ad00:beef::/64 -o eth0 -j MASQUERADE
[0:0] -A POSTROUTING -s fd11:22::/64 -o eth0 -p udp -j MASQUERADE
[0:0] -A POSTROUTING -s fd11:22::/64 -o eth0 -p tcp -j MASQUERADE
COMMIT
# Completed on Sun Sep  2 11:44:06 2018

# ip -6 link
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP mode DEFAULT group default qlen 1000
    link/ether b8:27:eb:96:eb:75 brd ff:ff:ff:ff:ff:ff
3: wlan0: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state DOWN mode DEFAULT group default qlen 1000
    link/ether b8:27:eb:c3:be:20 brd ff:ff:ff:ff:ff:ff
4: tap0: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state DOWN mode DEFAULT group default qlen 1000
    link/ether 06:8a:53:01:68:f2 brd ff:ff:ff:ff:ff:ff
5: wpan0: <POINTOPOINT,MULTICAST,NOARP,UP,LOWER_UP> mtu 1280 qdisc pfifo_fast state UNKNOWN mode DEFAULT group default qlen 500
    link/none

# ip -6 -brief address
lo               UNKNOWN        ::1/128 
eth0             UP             2001:470:4a71:f000::11/64 fe80::ba27:ebff:fe96:eb75/64 
wpan0            UNKNOWN        fdde:ad00:beef:0:cc1e:c6e2:8252:e44b/64 fd11:22::1c4d:925:de45:9d30/64 fe80::1c4d:925:de45:9d30/64 fe80::2ccb:f19:edce:c49e/64

# ip -6 route
2001:470:4a71:f000::/64 dev eth0  proto kernel  metric 256  pref medium
fd11:22::/64 dev wpan0  proto kernel  metric 256  pref medium
fdde:ad00:beef::/64 dev wpan0  proto kernel  metric 256  pref medium
fe80::/64 dev eth0  proto kernel  metric 256  pref medium
fe80::/64 dev wpan0  proto kernel  metric 256  pref medium
default via 2001:470:4a71:f000::1 dev eth0  metric 1024  pref medium
Sam Kumar
  • 111
  • 4
  • can you rewrite or add the rules with the output of `ip6tables-save -c` ? and you should add informations on interface and route informations for both the router and the system behind: `ip -brief link; ip -6 -brief address; ip -6 route` (remove `-brief` if it's not working). The system behind must have this router/nat as gateway for everything to work as intended – A.B Sep 02 '18 at 10:15
  • Thanks for your comment. I've updated the question with the output you asked for. – Sam Kumar Sep 02 '18 at 11:49
  • Why are you assigning ULA addresses to devices that need globally routable addresses? You have a routed /48, why aren't you assigning addresses from that instead? – kasperd Sep 02 '18 at 12:07
  • 1
    This is not how you do IPv6. You _route_ your /48 from Hurricane Electric. You DO NOT NAT. – Michael Hampton Sep 02 '18 at 13:42

2 Answers2

1

Turns out this is because the TCP checksum was incorrect (host's TCP stack had a bug). Apparently tshark doesn't show this by default, but it was causing ip6tables to not masquerade the source address.

Thanks to everyone for trying to help. Regarding kasperd's suggestion, it turns out that a similar solution works in my setting (I have a /60, not a /48) so I will try to move away from ip6tables.

Edit: I have the setup working without a NAT now. Thanks for suggesting this.

Sam Kumar
  • 111
  • 4
  • One of the great benefits of IPv6 is that you have plenty of addresses, and you do not need to use a kludge, like NAT. You can get all the global addresses you need, and restore the IP end-to-end paradigm. – Ron Maupin Sep 02 '18 at 20:48
  • Even a /60 is 16 subnets, more than enough for most homes and many small businesses. There is still absolutely no need for you to NAT. It will just make your life miserable, both now and later. Set it up properly the first time. – Michael Hampton Sep 02 '18 at 20:59
-1

OK, I had the same problem. The solution turned out to be simple, just run: "ip6tables -A FORWARD -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT"

The problem is, ip6tables code does not load conntrack module by default, so statefull rules transparently fail to work.

And for the "IPv6 doesn't need NAT!" brigade - sometimes you DO need it, for example if you want to run Docker containers on AWS. It doesn't support DHCP PD so you're stuck with NAT.

Cyberax
  • 249
  • 1
  • 5