User Tools

Site Tools


Sidebar


Tags Cloud
ddos_ipset

This is an old revision of the document!


Борьба с DDOS посредством использования утилиты ipset на выделенных серверах с Debian

  • Тянем последний patch-o-matic-ng в /usr/src, распаковываем, заходим в директорию и стартуем ./runme set.
    При этом подразумевается что исходники текущего ядра находятся в /usr/src/linux, а iptables - в /usr/src/iptables.
    После заходим в /usr/src/linux и делаем make oldconfig, где указываем поддержку фич ipset модулями.

Собираем и устанавливаем ядро:

# make-kpkg --bzImage kernel_image
# dpkg -i /usr/src/linux-image-x.x.x-blablabla.deb
  • Устанавливаем ipset из репозитория:
# apt-get install ipset
  • Добавляем загрузку модуля ipset в /etc/modules и либо загружаем модуль modprobe ipset, либо перезагружаемся в новое ядро.
  • Создаем хеш ip-адресов для использования в правилах iptables. Стоит учесть, что максимальное количество ip в списке - 65536 штук:
# ipset -N blacklist iphash
  • Создаем перловый скрипт /root/antiddos/num-filter.pl для отбора ip-адресов, с которых идет большое количество одинаковых запросов:
#!/usr/bin/perl
while ($line = <STDIN>) {
  if ($line =~ /^\s+(\d+) (\d+)\.(\d+)\.(\d+)\.(\d+)/) {
    print $2, ".", $3, ".", $4, ".", $5, "\n" if ($1 > $ARGV[0]);
  }
}
  • Создаем скрипт /root/antiddos/blacklist.sh для cron:
#!/bin/bash
# variables, change them to get script work
BADREQUEST="GET / HTTP/1.1";
LOGPATH="/home/clients/login_ftp0/domains/domain.com/logs/access_log";
MINREQUESTS="50";
SCRIPTHOME="/root/antiddos";
# don't change anything bellow
grep "${BADREQUEST}" $LOGPATH | awk -F ' ' '{ print $ 1 }' | sort | uniq -c | ${SCRIPTHOME}/num-filter.pl $MINREQUESTS >> ${SCRIPTHOME}/in_blacklist.add.pre
sort -u < ${SCRIPTHOME}/in_blacklist.add.pre > ${SCRIPTHOME}/in_blacklist.add
cat ${SCRIPTHOME}/in_blacklist.add > ${SCRIPTHOME}/in_blacklist
for i in `cat ${SCRIPTHOME}/in_blacklist`;
do
  /usr/sbin/ipset -q -A blacklist $i;
done
  • Добавляем правила для iptables:
  /sbin/iptables -F
  /sbin/iptables -X DDOS_HTTP_FILTER
  /sbin/iptables -N DDOS_HTTP_FILTER
  /sbin/iptables -A DDOS_HTTP_FILTER -d $IP -p tcp --syn --dport 80 -m set --set blacklist src -j DROP
  /sbin/iptables -A DDOS_HTTP_FILTER -d $IP -p tcp --syn --dport 80 -m hashlimit --hashlimit 10/min --hashlimit-burst 30 --hashlimit-mode srcip --hashlimit-name DDOS --hashlimit-htable-size 32768 --hashlimit-htable-max 32768 --hashlimit-htable-gcinterval 1000 --hashlimit-htable-expire 100000 -j ACCEPT
  /sbin/iptables -A DDOS_HTTP_FILTER -d $IP -p tcp --dport 80 --syn -j DROP
  /sbin/iptables -A DDOS_HTTP_FILTER -d $IP -p tcp --syn --dport 80 -m connlimit --connlimit-above 10 -j DROP
  /sbin/iptables -A DDOS_HTTP_FILTER -j ACCEPT
  /sbin/iptables -A INPUT -p tcp --dport http -j DDOS_HTTP_FILTER
  • Добавляем запуск скрипта /root/antiddos/blacklist.sh в крон с интервалом в 10 минут.
ПРИМЕР ФАЕРВОЛА С ИСПОЛЬЗОВАНИЕМ GEOIP
#!/bin/bash

iptables=/usr/local/sbin/iptables
ipset=/usr/sbin/ipset
WHITE="195.88.52.82/32"

ddos_enable() {
    # whitelist
    $iptables -N WHITELIST
    for i in $WHITE;
    do
        $iptables -A WHITELIST -s $i -j ACCEPT;
    done
    $iptables -A WHITELIST -j DROP

    $iptables -N DDOS_HTTP_FILTER
    $iptables -A DDOS_HTTP_FILTER -m hashlimit --hashlimit 15/min --hashlimit-burst 30 --hashlimit-mode srcip --hashlimit-name HTTPDDOS --hashlimit-htable-size 32768 --hashlimit-htable-max 32768 --hashlimit-htable-gcinterval 1000 --hashlimit-htable-expire 100000 -j ACCEPT
    $iptables -A DDOS_HTTP_FILTER -m connlimit --connlimit-above 15 -j DROP
    $iptables -A DDOS_HTTP_FILTER -j ACCEPT

    $iptables -N SORT_FILTER
    $iptables -A SORT_FILTER -p tcp --dport 80 --syn -j DDOS_HTTP_FILTER
    $iptables -A SORT_FILTER -p tcp -m multiport --dports 25,53 -j ACCEPT
    $iptables -A SORT_FILTER -p udp --dport 53 -j ACCEPT
    $iptables -A SORT_FILTER -j WHITELIST

    $iptables -N GEOIP_FILTER
    $iptables -A GEOIP_FILTER -m geoip --src-cc AM,AZ,BY -j SORT_FILTER
    $iptables -A GEOIP_FILTER -m geoip --src-cc EE,GE,KZ -j SORT_FILTER
    $iptables -A GEOIP_FILTER -m geoip --src-cc LV,MD,NL,RU -j SORT_FILTER
    $iptables -A GEOIP_FILTER -m geoip --src-cc UA,UZ,US -j SORT_FILTER
    $iptables -A GEOIP_FILTER -j DROP

    $iptables -I INPUT 1 -i lo -j ACCEPT
    $iptables -I INPUT 2 -m set --set blacklist src -j DROP
    $iptables -I INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT

    $iptables -A INPUT -j GEOIP_FILTER
}

start_iptables() {
    # whitelist
    $iptables -N WHITELIST
    for i in $WHITE;
    do
        $iptables -A WHITELIST -s $i -j ACCEPT;
    done
    $iptables -A WHITELIST -j DROP

    # default rules
    $iptables -I INPUT 1 -i lo -j ACCEPT
    $iptables -I INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
    $iptables -A INPUT -p tcp -m multiport --dports 25,53,80 -j ACCEPT
    $iptables -A INPUT -p udp --dport 53 -j ACCEPT
    $iptables -A INPUT -j WHITELIST
}

clear_iptables() {
    $iptables -F
    $iptables -X
}

start_ipset() {
    $ipset -q -N blacklist iphash
}

clear_ipset() {
    $ipset -q -F blacklist
    $ipset -q -X blacklist
}

case "$1" in
    normal)
        clear_iptables
        start_iptables
        echo "normal mode activated"
    ;;

    stop)
        clear_iptables
        clear_ipset
        echo "iptabes cleared"
    ;;

    hard)
        clear_iptables
        start_ipset
        ddos_enable
        echo "hard mode activated"

    ;;
    *)
        echo "Usage $0 {normal|hard|stop}"
        exit 1
    ;;
esac
ddos_ipset.1251355714.txt.gz · Last modified: 2009/08/27 06:48 by kyxap