iptables vs. ip6tables

Greetings, all. I am in the process of migrating one of my servers from one VPS service to Linode and I'm pretty happy with how things are going so far… with one exception. I have a rather short but effective set of iptables rules that worked well on my previous IPv4-only host and which seem to be working well for my IPv4 traffic here. However, now that I have an IPv6 address (Finally!), I want to make sure that interface is protected too. Unfortunately, my attempts to apply the same rules to ip6tables doesn't seem to work; as soon as I apply the same rule set, the IPv6 interface ceases to respond to any inbound or outbound request. Turning off ip6tables allows traffic to flow normally.

So I officially appeal to those far more knowledgeable than I. Below is the configuration I'm trying to use for ip6tables. The OS is Fedora 15, although I doubt that's significant (the rules should be the same regardless). The rules are saved in /etc/sysconfig/ip6tables so they'll be reloaded. I've already converted the ICMP line for known IPv6 syntax differences.

Can anybody see what I'm doing wrong?

# By default drop all incoming and forwarded traffic
# Allow all outgoing traffic
*filter
:INPUT DROP [0:0]
:FORWARD DROP [0:0]
:OUTPUT ACCEPT [0:0]

# Allow returning packets
-A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT

# Next is a set of specific DROP statements to block all incoming
# traffic from know hacker IPs. Since there are no IPv6 addresses
# in this block list so far, there are no rules currently in the file.
# The IPv4 rules look something like this, however:
# -A INPUT -s 109.169.216.56 -j DROP

# Allow incoming traffic on ports 80 and 443 for web server
-A INPUT -p tcp --dport 80 -j ACCEPT
-A INPUT -p tcp --dport 443 -j ACCEPT

# Allow local traffic
-A INPUT -i lo -j ACCEPT

# Allow ping
-A INPUT -p icmpv6 --icmpv6-type echo-request -j ACCEPT

# Accept incoming SSH on an alternate port (redacted for security):
-A INPUT -p tcp --dport ##### -j ACCEPT

7 Replies

One thing to realize with IPv6 is that you're going to need to open up a much larger series of ICMP types just for routing and address auto-configuration to work. In some cases, if your filters configure too quickly in the boot cycle, you won't even get your IPv6 address assignment. In other cases, I think the default routing may not work.

Not sure that's your exact issue here, but what happens if you change your rule to just be icmpv6 in general without the type restriction?

I don't have an external reference handy, but for what it's worth, here's a copy of the chain Shorewall installed on one of my systems for it:

Chain AllowICMPs (2 references)
target     prot opt source               destination
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp destination-unreachable
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp packet-too-big
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp time-exceeded
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp parameter-problem
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp router-solicitation
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp router-advertisement
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp neighbour-solicitation
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp neighbour-advertisement
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp redirect
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp type 141
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp type 142
ACCEPT     ipv6-icmp    fe80::/10            anywhere           ipv6-icmp type 130
ACCEPT     ipv6-icmp    fe80::/10            anywhere           ipv6-icmp type 131
ACCEPT     ipv6-icmp    fe80::/10            anywhere           ipv6-icmp type 132
ACCEPT     ipv6-icmp    fe80::/10            anywhere           ipv6-icmp type 143
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp type 148
ACCEPT     ipv6-icmp    anywhere             anywhere           ipv6-icmp type 149
ACCEPT     ipv6-icmp    fe80::/10            anywhere           ipv6-icmp type 151
ACCEPT     ipv6-icmp    fe80::/10            anywhere           ipv6-icmp type 152
ACCEPT     ipv6-icmp    fe80::/10            anywhere           ipv6-icmp type 153

Looks like my ip6tables doesn't have the most recent types, so see http://www.iana.org/assignments/icmpv6-parameters for decoding those. Looks like link-local fe80::/10 rules are for local multicast announcements for example.

I think the most critical for basic functioning are the router and neighbor announcements. A different system configured with a different tool only includes the ones that were decoded above.

When I was doing some manual testing I just left icmpv6 in general open in the ip6tables, but if you use a tool to manage the firewall configurations it'll typically have much of this built-in.

– David

@jtdarlington:

Can anybody see what I'm doing wrong?

# Allow returning packets
-A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT


I believe you need a kernel version 2.6.20 or higher in order to support IPv6 stateless filter rules.

What does uname -a show? Then change your kernel as needed under your Linode Configuration Profile and reboot.

Travis

@db3l:

Not sure that's your exact issue here, but what happens if you change your rule to just be icmpv6 in general without the type restriction?
Actually, that seemed to hit the spot. Thanks, David. When I removed the "–icmpv6-type" from the ICMPv6 rule, everything seems to work. Looks like I'm OK in that regard now.

@otherbbs:

I believe you need a kernel version 2.6.20 or higher in order to support IPv6 stateless filter rules. What does uname -a show?
No problem there. I'm definitely running higher than that:

Linux [hostname] 2.6.39-linode33 #3 SMP Wed May 25 18:58:07 UTC 2011 i686 i686 i386 GNU/Linux

Since I'm here and I've bent a few ears, let me see if anyone can answer one final question. As stated above, I use some DROP statements to block all incoming packets from known IPs that have attacked my servers in the past. The IPv4 rule I use is something akin to:

-A INPUT -s 109.169.216.56 -j DROP

This should work for IPv6 addresses too, correct? I can just replace the IPv4 address above with an IPv6 one? I know some services (Apache for sure) require IPv6 addresses to be placed in square brackets ("[2600:3c03::f03c:91ff:fe93:9c48]"), but that's so they won't confuse a port specification with the address ("*:80"). This shouldn't be a problem for ip6tables, right? My DROP rules are mostly automated, so I want to make sure I get that right before I accidentally blow my IPv6 firewall apart. :D

@jtdarlington:

Since I'm here and I've bent a few ears, let me see if anyone can answer one final question. As stated above, I use some DROP statements to block all incoming packets from known IPs that have attacked my servers in the past. The IPv4 rule I use is something akin to:

-A INPUT -s 109.169.216.56 -j DROP

This should work for IPv6 addresses too, correct? (…)
Yes. And no special quoting or brackets needed for the address.

– David

Thanks for the information, guys. That solved all my problems. My server seems to be up and running without a hitch. Now I can start working on moving my flagship site (the one in my sig line) to Linode! MUHAHAHAHA!!! :twisted:

Oops, sorry… didn't mean for that maniacal laughter to ship out there. :oops:

@jtdarlington:

Since I'm here and I've bent a few ears, let me see if anyone can answer one final question. As stated above, I use some DROP statements to block all incoming packets from known IPs that have attacked my servers in the past. The IPv4 rule I use is something akin to:

-A INPUT -s 109.169.216.56 -j DROP

This should work for IPv6 addresses too, correct?
You might want to rethink the concept, though. Everyone and their dog has a /64; an attacker can easily attack from 2^64 different addresses and simply DoS your auto-firewall script (iptables are linear tests; 10,000 entries take a while to process; 100,000 rules can slow down all traffic).

However you don't want to simply block the whole /64 because anyone using a HE tunnel or a native linode address (or a Panix address) or similar as their primary outgoing address then you could end up blocking a massive number of innocents.

Many of the protections that were viable with IPv4 need to be rethought with a move to IPv6 :-(

Here are those rules in a format for use with ip6tables-apply (of course don't forget to add your own rules to it before application and save a backup copy of your ip6tables with "ip6tables-save > FILENAME"):

:ICMPv6 - [0:0]
# Approve certain ICMPv6 types and all outgoing ICMPv6
# http://forum.linode.com/viewtopic.php?p=39840#39840
-A INPUT -p icmpv6 -j ICMPv6
-A ICMPv6 -p icmpv6 --icmpv6-type echo-request -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type destination-unreachable -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type packet-too-big -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type time-exceeded -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type parameter-problem -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type router-solicitation -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type router-advertisement -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type neighbour-solicitation -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type neighbour-advertisement -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type redirect -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type 141 -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type 142 -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type 148 -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type 149 -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type 130 -s fe80::/10 -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type 131 -s fe80::/10 -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type 132 -s fe80::/10 -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type 143 -s fe80::/10 -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type 151 -s fe80::/10 -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type 152 -s fe80::/10 -j ACCEPT
-A ICMPv6 -p icmpv6 --icmpv6-type 153 -s fe80::/10 -j ACCEPT
-A ICMPv6 -j RETURN
-A OUTPUT -p icmpv6 -j ACCEPT

Reply

Please enter an answer
Tips:

You can mention users to notify them: @username

You can use Markdown to format your question. For more examples see the Markdown Cheatsheet.

> I’m a blockquote.

I’m a blockquote.

[I'm a link] (https://www.google.com)

I'm a link

**I am bold** I am bold

*I am italicized* I am italicized

Community Code of Conduct