Связка PF + Blocklistd для SSH
Если ваш сервер смотрит в мир с открытым 22-м портом, вы знаете: боты начинают атаку через секунды после аптайма. Традиционный fail2ban на Python — это классика, но во FreeBSD есть более элегантное, нативное и «легкое» решение: blocklistd.
В этой статье мы настроим «двухслойную броню»: PF будет отсекать сетевой флуд, а blocklistd — наказывать за неверные пароли.
Зачем нам два слоя?
- Слой PF (Защита от флуда): Мгновенно блокирует IP, который пытается открыть слишком много соединений в секунду. Это защищает сам сервис
sshdот перегрузки. - Слой Blocklistd (Защита от перебора): Блокирует тех, кто заходит медленно и аккуратно, но постоянно вводит неправильный пароль.
1. Настройка PF (Packet Filter)
Отредактируйте /etc/pf.conf. Мы добавим таблицу для «скорострелов» и якорь для умной блокировки.
PF
# Глобальные опции
set skip on lo0
set block-policy drop
# 1. Таблица для ручной блокировки и защиты от флуда
table <bruteforce> persist
# 2. Якорь для blocklistd
anchor "blocklistd/*" in quick
# ==========================================
# ПРАВИЛА ФИЛЬТРАЦИИ
# ==========================================
# Блокируем всё по дефолту
block in all
# Мгновенный бан из таблицы
block in quick from <bruteforce>
pass out all keep state
# Разрешаем SSH с лимитом на соединения (5 коннектов за 3 сек)
pass in proto tcp from any to any port 22 flags S/SA keep state \
(max-src-conn 15, max-src-conn-rate 5/3, \
overload <bruteforce> flush global)
# Разрешаем Веб и ICMP
pass in proto tcp from any to any port { 80, 443 }
pass in inet proto icmp all icmp-type echoreq
Примените конфиг:
Bash
pfctl -nf /etc/pf.conf && pfctl -f /etc/pf.conf
2. Настройка blocklistd
Создайте или отредактируйте /etc/blocklistd.conf:
Plaintext
# [адрес:порт] [тип] [протокол] [владелец] [название_якоря] [nfail] [время_бана]
[local]
ssh stream tcp * * 3 24h
ftp stream tcp * * 3 24h
* * * * * 3 60
Здесь 3 — количество провалов авторизации до бана на 24h.
3. Настройка SSHD
Во FreeBSD 15 поддержка blocklistd встроена в базовый sshd. Просто включите её в /etc/ssh/sshd_config:
Plaintext
UseBlocklist yes
4. Запуск системы
Добавим сервисы в автозагрузку и запустим их:
Bash
sysrc pf_enable="YES"
sysrc blocklistd_enable="YES"
sysrc sshd_enable="YES"
service pf restart
service blocklistd start
service sshd restart
5. Мониторинг: Кто в бане?
Теперь у вас есть две точки контроля.
Проверка "умных" банов (за пароли):
Bash
blocklistctl dump
Если в колонке id стоит OK, значит IP заблокирован. Вы можете увидеть это правило в PF:
Bash
pfctl -a "blocklistd/22" -sr
Проверка "глупых" банов (за флуд):
Посмотреть список IP, которые пытались открыть слишком много соединений:
Bash
pfctl -t bruteforce -T show
Итог
Такая конфигурация делает ваш сервер максимально неудобной целью. PF берет на себя черную работу по фильтрации сетевого шума, а blocklistd точечно выбивает тех, кто пытается подобрать ключи к вашей системе.
Member discussion