|
|
|
---
|
|
|
|
title: Отчёт о ходе разработки f2b
|
|
|
|
tags: devel, f2b
|
|
|
|
---
|
|
|
|
|
|
|
|
Sep 9 23:06:55 f2b[10753]: jail 'asterisk': new ip found -- 89.163.146.93
|
|
|
|
Sep 9 23:09:50 f2b[10753]: jail 'asterisk': new ip match -- 89.163.146.93 (2/3)
|
|
|
|
Sep 9 23:12:43 f2b[10753]: jail 'asterisk': new ip match -- 89.163.146.93 (2/3)
|
|
|
|
Sep 9 23:15:35 f2b[10753]: jail 'asterisk': new ip match -- 89.163.146.93 (2/3)
|
|
|
|
Sep 9 23:18:40 f2b[10753]: jail 'asterisk': banned ip 89.163.146.93 for 1.0hrs
|
|
|
|
# ... попался, ублюдок!
|
|
|
|
|
|
|
|
Продолжаем неспешно пилить чудо-программу.
|
|
|
|
|
|
|
|
С момента [анонса](/articles/2016/03/17/f2b/) темпы пиления упали, т.к. сказывается "эффект УМВР",
|
|
|
|
но тем не менее сделано следующее:
|
|
|
|
|
|
|
|
---
|
|
|
|
|
|
|
|
Control socket для демона
|
|
|
|
-------------------------
|
|
|
|
|
|
|
|
Над реализацией пришлось изрядно посидеть и поэкспериментировать.
|
|
|
|
|
|
|
|
Изначально я хотел использовать ``SOCK_STREAM`` и обычный текстовый протокол.
|
|
|
|
Посидел, написал свою реализацию getline для сокета,
|
|
|
|
простенький аналог bison'а для разбора команд
|
|
|
|
и стало мне грустно от осознания объёма кода, который будет это всё обслуживать.
|
|
|
|
|
|
|
|
Плюсы:
|
|
|
|
|
|
|
|
* с этим может работать любая утилита с помощью netcat/telnet
|
|
|
|
|
|
|
|
Минусы, навскидку:
|
|
|
|
|
|
|
|
* разбор текстовых команд в виде нескольких токенов - достаточно сложное занятие.
|
|
|
|
Нужно вычленить строку (в экстремальном случае она может приходить по байту за раз),
|
|
|
|
побить её на токены, проверить синтаксис, количество аргументов.
|
|
|
|
Нужно достаточно сложное управление входным буфером:
|
|
|
|
если не распарсилось полностью - дождаться недостающего, осталось лишнее - хранить.
|
|
|
|
* перечисленное выше - работает с недоверенными данными из сети -> всё это надо выписывать с упором на безопасность.
|
|
|
|
* открывается дорога всем нашим любимым сетевым шалостям:
|
|
|
|
типа открытия 500 соединенений разом и заливки в каждое из них мегабайтной строки,
|
|
|
|
без малейших признаков "\r" или "\n" -> скажите "здравствуй" исчерпанию памяти или fd.
|
|
|
|
* ну и такой мелкий штрих: если мы хотим встроенный хелп - из-за тупости клиента,
|
|
|
|
будьте любезны тащить описание команд на серверную сторону.
|
|
|
|
|
|
|
|
...ну и не стоит забывать, что ломание кривонаписанного парсера текстового протокола - это
|
|
|
|
старая-добрая традиция, ещё начиная со времён sendmail'а и irc.
|
|
|
|
А уж как народ с самой почтой развлекается, это просто песня.
|
|
|
|
|
|
|
|
Поэтому плюнул я на это дело и взял ``SOCK_DGRAM``.
|
|
|
|
|
|
|
|
Минусы:
|
|
|
|
|
|
|
|
* нужен спецклиент
|
|
|
|
* негарантированная доставка
|
|
|
|
|
|
|
|
Но плюсов в моём случае - много:
|
|
|
|
|
|
|
|
* разом снимется проблема с разбором сообщений: readv + проверка длинны пакета.
|
|
|
|
* никаких висящих соединений: пришёл пакет - обработал, опционально ответил.
|
|
|
|
* бесплатно получаем управление несколькими инстансами в пределах локальной сети (udp+igmp)[^fn1].
|
|
|
|
* возможность использовать тот же код в качестве source/backend:
|
|
|
|
если один хост в сети засёк пидараса - делается рассылка через тот же igmp и все остальные его дружно банят
|
|
|
|
ещё до того, как он полезет сканить порты на следующий узел.
|
|
|
|
|
|
|
|
Простенький клиент
|
|
|
|
------------------
|
|
|
|
|
|
|
|
Появился в силу предыдущего пункта.
|
|
|
|
|
|
|
|
Сейчас он умеет все базовые операции: показать статистику, забанить/разбанить, перечитать конфиг, завершиться.
|
|
|
|
|
|
|
|
Есть задел и на больше - точная настройка конкретного jail'а, добавление регэкспов "на лету".
|
|
|
|
|
|
|
|
redis-backend
|
|
|
|
-------------
|
|
|
|
|
|
|
|
Написан черновик, но пока не тестировался: чтобы его использовать, нужен парный ему source,
|
|
|
|
а source у нас сейчас прибит гвоздями к файлам.
|
|
|
|
|
|
|
|
Растущее время поиска/бана для конкретного ip
|
|
|
|
---------------------------------------------
|
|
|
|
|
|
|
|
Думаю, кто пробовал настроить fail2ban видел в логах "умных" ботов,
|
|
|
|
после первого бана подстраивающих частоту запросов так, чтоб не попасть под раздачу.
|
|
|
|
|
|
|
|
Это работает, но только до той поры, пока период обнаружения фиксирован.
|
|
|
|
Если он уменьшается по мере того, как растёт число запросов - к ним приходит песец.
|
|
|
|
|
|
|
|
На примере: допустим у нас настроено ограничение 5 неправильных запросов в 5 минут.
|
|
|
|
При фиксированном времени обнаружения бот может сделать 4 запроса, и пойти покурить,
|
|
|
|
передав эстафету другому боту.
|
|
|
|
|
|
|
|
При динамическом времени обнаружения, на эти 4 запроса в первый раз боту придётся
|
|
|
|
так же подождать 5 минут, а вот в следующий раз - уже 5,5 минут, и т.д.
|
|
|
|
|
|
|
|
Вторая идея, логически продолжающая первую - увеличение времени бана при рецидивах.
|
|
|
|
Это тоже сделано, потому что важно не просто забанить бота, но и порвать ему шаблон.
|
|
|
|
|
|
|
|
Третья идея в этом плане - смотреть на "соседей" забаненного ip,
|
|
|
|
и расширять бан до подсети при необходимости. Этого у меня пока не реализовано.
|
|
|
|
|
|
|
|
CMake
|
|
|
|
-----
|
|
|
|
|
|
|
|
* добавлена поддержка GNUInstallDirs
|
|
|
|
* наведён порядок с путями конфигов, постараюсь больше не менять.
|
|
|
|
|
|
|
|
Багфиксы
|
|
|
|
--------
|
|
|
|
|
|
|
|
Без них - никуда. Исправлена пара сегфолтов в коде фильтров.
|
|
|
|
После этого были сделаны оргвыводы, и притащен strlcpy()
|
|
|
|
на замену snprintf()/strncpy() из директории уровнем выше.
|
|
|
|
|
|
|
|
Обеспечена сборка и работа под бзд. Там же был пойман забавный баг:
|
|
|
|
|
|
|
|
fgets(buf, bufsize, file->fd);
|
|
|
|
|
|
|
|
...это не работает, если у ``file->fd`` выставлен EOF, даже если файл после этого прибавил пару гигабайт.
|
|
|
|
Решение - сбрасывать руками перед каждым вызовом через clearerr().
|
|
|
|
Допускаю, что это ``implementation-defined`` поведение.
|
|
|
|
|
|
|
|
Ну и кое-что по мелочи, типа выключения буферизации у логфайла.
|
|
|
|
|
|
|
|
[^fn1]: Это планируется, пока играюсь с point-to-point через unix-сокет.
|