Механика DDoS
           Крижановский Александр
              ak@natsys-lab.com




10/23/12
«Механика»
●   Чем в среднем отличается DdoS от flash crowd (не исчерпывающее
    описание и без специальных случаев)
●   Процессы, происходящие с HTTP-акселератором под DdoS
●   Как не надо и как лучше отражать HTTP DDoS
●   Пример — Nginx, но говорим «в целом»
Нормальный HTTP трафик
●   Запросы достаточно большие за счет Cookie и URL (~1KB, часто
    больше)
●   Ответ — Web-страница (десятки килобайт), считанная из файла
●   Сотни или тысячи Keep-Alive соединений (к одному HTTP-
    акселератору), каждое из которых генерирует умеренное число
    запросов
HTTP DDoS трафик
●   Запросы часто сильно меньше (десятки или сотни байт)
●   Ответов сервера сильно меньше, чем получаемых запросов
●   Десятки или сотни тысяч соединений
    ●   много запросов в каждом соединении
    ●   или постоянная переустановка соединений с каждого хоста
Nginx, netstat, grep, fail2ban и др.
●   Посмотреть netstat'ом соединения и добавить правила в Iptables
●   Погрепать access.log и/или error.log и добавить правила в ipset
●   Fail2ban
●   Лимитирование на сервере (limit zone для Nginx)
●   Iptables connlimit и hashlimit


=> HTTP-акселератор + Firewall


Чтение логов – не самая быстрая операция, особенно в условиях
высокой нагрузки
Обработка лимита (Nginx)
epoll_wait(12, {{EPOLLIN, ....}}, 512, 500) = 1
recvfrom(3, "GET / HTTP/1.1rnHost: ....", 1024, 0, NULL, NULL) = 327
// parse HTTP
write(11, “...limiting requests, excess...", 176) = 176
writev(3, [{"HTTP/1.1 503 Service Temporarily Una....", 200}], 1) = 200
sendfile(3, 7, [0], 383)          = 383
recvfrom(3, 0xa1bac0, 1024, 0, 0, 0) = -1 EAGAIN
epoll_wait(12, {{EPOLLIN, ....}}, 512, 500) = 1
recvfrom(3, "", 1024, 0, NULL, NULL) = 0
close(3)                          = 0
Горячая точка (Nginx, без логов)
samples   %         image name           symbol name
496099     1.5719   nginx                ngx_vslprintf
325148     1.0303   nginx                ngx_http_parse_header_line
219699     0.6961   vmlinux              cfq_set_request
202023     0.6401   libc-2.12.so         memcpy
183268     0.5807   libpthread-2.12.so   recv
162710     0.5156   nginx                ngx_linux_sendfile_chain
157504     0.4990   nginx                ngx_http_limit_req_handler
Nginx и DDoS
●   Логировать запросы от ботов дорого
●   Парсить логи тоже дорого
●   Вместо логирования лимитов – простой модуль, добавляющий
    правило в netfilter
Обработка пакетов
●   Параллельность: MSI-X, irq round-
    robin
●   RPS (Receive Packet Steering)
    позволяет «разбрасывать» пакеты
    по softirq на разных ядрах если
    MSI-X недостаточно (или железо
    вообще не может параллелить
    прерывания)
●   RFS (Receive Flow Steering)
    позволяет отправлять пакеты на
    CPU прикладного процесса
●   Улучшают параллельность, но
    ухудшают кэширование
User space vs Kernel
●   Более 15 context switch
●   Kernel/userspace копирования запросов и ответов
●   Zero-copy network IO (splice(2)) не работает в общем случае на чтение
    из сокета
●   Проблема с очередями сокетов все равно остается (парсить HTTP
    нужно синхронно в skb)
Kernel HTTP-акселераторы
●   Первая половина 2000x: TUX (Linux), OpenKETA (FreeBSD), khttpd
    (Linux) и комерческие прокеты


=> Основное узкое место, которое может решить kernel-based HTTP-
сервер – копирование на отправке файла – решается в user space
через sendfile().
L7 DDoS-mitigation HTTP-акселератор:
               специальный случай
●   Нужно минимизировать накладные расходы на обработку запросов от
    ботов
●   Более тесная интеграция с Netfilter
●   Возможность держать до 1 млн. Cоединений:
    ●   Обработка TCP in-order данных сразу, не откладывая в очередь
        (лучше cache hit, меньше расход памяти)
    ●   Per-connection и per-host resource management/QoS
    ●   Желательно блокировать не по IP, а содержимому HTTP запроса
Спасибо!



ak@natsys-lab.com

Механика DDoS (Александр Крижановский)

  • 1.
    Механика DDoS Крижановский Александр ak@natsys-lab.com 10/23/12
  • 2.
    «Механика» ● Чем в среднем отличается DdoS от flash crowd (не исчерпывающее описание и без специальных случаев) ● Процессы, происходящие с HTTP-акселератором под DdoS ● Как не надо и как лучше отражать HTTP DDoS ● Пример — Nginx, но говорим «в целом»
  • 3.
    Нормальный HTTP трафик ● Запросы достаточно большие за счет Cookie и URL (~1KB, часто больше) ● Ответ — Web-страница (десятки килобайт), считанная из файла ● Сотни или тысячи Keep-Alive соединений (к одному HTTP- акселератору), каждое из которых генерирует умеренное число запросов
  • 4.
    HTTP DDoS трафик ● Запросы часто сильно меньше (десятки или сотни байт) ● Ответов сервера сильно меньше, чем получаемых запросов ● Десятки или сотни тысяч соединений ● много запросов в каждом соединении ● или постоянная переустановка соединений с каждого хоста
  • 5.
    Nginx, netstat, grep,fail2ban и др. ● Посмотреть netstat'ом соединения и добавить правила в Iptables ● Погрепать access.log и/или error.log и добавить правила в ipset ● Fail2ban ● Лимитирование на сервере (limit zone для Nginx) ● Iptables connlimit и hashlimit => HTTP-акселератор + Firewall Чтение логов – не самая быстрая операция, особенно в условиях высокой нагрузки
  • 6.
    Обработка лимита (Nginx) epoll_wait(12,{{EPOLLIN, ....}}, 512, 500) = 1 recvfrom(3, "GET / HTTP/1.1rnHost: ....", 1024, 0, NULL, NULL) = 327 // parse HTTP write(11, “...limiting requests, excess...", 176) = 176 writev(3, [{"HTTP/1.1 503 Service Temporarily Una....", 200}], 1) = 200 sendfile(3, 7, [0], 383) = 383 recvfrom(3, 0xa1bac0, 1024, 0, 0, 0) = -1 EAGAIN epoll_wait(12, {{EPOLLIN, ....}}, 512, 500) = 1 recvfrom(3, "", 1024, 0, NULL, NULL) = 0 close(3) = 0
  • 7.
    Горячая точка (Nginx,без логов) samples % image name symbol name 496099 1.5719 nginx ngx_vslprintf 325148 1.0303 nginx ngx_http_parse_header_line 219699 0.6961 vmlinux cfq_set_request 202023 0.6401 libc-2.12.so memcpy 183268 0.5807 libpthread-2.12.so recv 162710 0.5156 nginx ngx_linux_sendfile_chain 157504 0.4990 nginx ngx_http_limit_req_handler
  • 8.
    Nginx и DDoS ● Логировать запросы от ботов дорого ● Парсить логи тоже дорого ● Вместо логирования лимитов – простой модуль, добавляющий правило в netfilter
  • 9.
    Обработка пакетов ● Параллельность: MSI-X, irq round- robin ● RPS (Receive Packet Steering) позволяет «разбрасывать» пакеты по softirq на разных ядрах если MSI-X недостаточно (или железо вообще не может параллелить прерывания) ● RFS (Receive Flow Steering) позволяет отправлять пакеты на CPU прикладного процесса ● Улучшают параллельность, но ухудшают кэширование
  • 10.
    User space vsKernel ● Более 15 context switch ● Kernel/userspace копирования запросов и ответов ● Zero-copy network IO (splice(2)) не работает в общем случае на чтение из сокета ● Проблема с очередями сокетов все равно остается (парсить HTTP нужно синхронно в skb)
  • 11.
    Kernel HTTP-акселераторы ● Первая половина 2000x: TUX (Linux), OpenKETA (FreeBSD), khttpd (Linux) и комерческие прокеты => Основное узкое место, которое может решить kernel-based HTTP- сервер – копирование на отправке файла – решается в user space через sendfile().
  • 12.
    L7 DDoS-mitigation HTTP-акселератор: специальный случай ● Нужно минимизировать накладные расходы на обработку запросов от ботов ● Более тесная интеграция с Netfilter ● Возможность держать до 1 млн. Cоединений: ● Обработка TCP in-order данных сразу, не откладывая в очередь (лучше cache hit, меньше расход памяти) ● Per-connection и per-host resource management/QoS ● Желательно блокировать не по IP, а содержимому HTTP запроса
  • 13.