Should I rate-limit packets with iptables?
A rate limit is not a prevention but rather an invitation to DoS - especially in the flavor presented above where packets are going to be dropped if a certain rate of unauthenticated packets without state information has been exceeded. Since everybody can forge packets (including source IP addresses) at this connection state without greater effort, a new DoS attack vector leveraging your rate limit facility will arise.
A rate limit generally will only make sense if you have
- either a predictable hard or a soft connection limit in your configuration
- set the rate limit for general traffic below this limit in order to be able to set up connections for priority or administrative traffic regardless of the load
While 1. often is hard enough to determine to even bother, 2. will obviously only work if you are able to reliably differentiate "priority or administrative" traffic from the rest upon connection setup - e.g. if it is coming through a different network interface.
In other cases, it would rather reduce your system's resiliency than add to it.
The problem with -m limit is the limitation of all TCP packets whatever the source IP addresses. So, if you have a low limitation for syn packets like
-A INPUT -p tcp --syn -m limit --limit 30/s --limit-burst 30 -j ACCEPT
-A INPUT -p tcp --syn -j DROP
only one client with the hping command line can take down your server by sending as many tcp packets with SYN flag because the limit rule will match and it will drop many packets whatever the sources IP addresses. limit does not make difference between good traffic and bad traffic. It will take the down the good incoming traffic too.
hping could be something like:
hping thetargetedhostip -p 80 -S -c 1000 -i u20000
It is better to use hashlimit to limit incoming tcp connections per IP address. The following rule will match only if 30 packets per seconds will be received reducing the number of authorized packet per IP to 15 packets per second.
-A INPUT -p tcp --syn -m hashlimit --hashlimit 15/s --hashlimit-burst 30 --hashlimit-mode srcip --hashlimit-srcmask 32 --hashlimit-name synattack -j ACCEPT
-A INPUT -p tcp --syn -j DROP
In Fact, I am CONVINCED that many servers that are taken down today aren't taken by being out of resources during an attack but because of the limit module dropping all the incoming traffic.