Защита SSH от Brute-force attack (брутфорс) на любом порту
В первой части данной инструкции (статьи) мы создали SSH-ключи для пользователя «root» (главного администратора), во второй части данной инструкции (статьи) мы создали пользователя под которым будем работать, а так же создали для этого пользователя SSH-ключи и в конце статьи закрыли возможность входа по паролю пользователя оставив вход только с помощью SSH-ключей.
Сейчас самое время перейти к защите от Brute-force attack
Brute-force (брутфорс) он же «метод Грубой силы» — это хакерская атака путем полного перебора (подбора) пароля. Вручную, естественно, этим никто заниматься не будет – создаются бот-сети (botnet), которые в автоматическом режиме, 24 часа в сутки 7 дней в неделю 365 дней в году, сканируют целые сегменты IP-адресов и при получении отклика начинают данную атаку. Перебирать, суммарно, по 5 млн. паролей в сутки для ботнета совсем не проблема.
СКОРЕЕ ВСЕГО ВАШ СЕРВЕР УЖЕ ПОД АТАКОЙ!
Вероятно возник вопрос: Зачем я то им нужен? У меня и красть там нечего, по большому счёту.
Дело в том, что красть то у нас, по большому счёту, никто ничего не собирается.
Цель атаки: Заразить (зомбировать) наш сервер/компьютер - сделать его частью ботнета, а далее уже только фантазия брутфорсера решит как этим воспользоваться. Наш сервер, будучи зомби, может брутфорсить другие сервера для расширения ботнета или, скажем, быть атакующей машиной при DDoS-атаке (кстати, услуга DDoS-атаки сайта/сервера какого-нибудь конкурента стоит очень не дешево, но эта услуга востребована).
Если Вы читали первую и вторую части данной инструкции, тогда на данном этапе у Вас уже настроено соединение по SSH-ключам и отключен вход по паролям и, в принципе, Вам уже не страшен брутфорс так как вход по паролям отключен и подбирать нечего, НО…
Атака брутфорс всё равно продолжается и создаёт некую нагрузку на ваш сервер, пусть и не большую, но создаёт и в данной части инструкции мы настроим защиту от брутфорс и сведём нагрузку к нулю, в отличие от той же защиты с помощью File2Ban, которая, так или иначе, даёт нагрузку примерно в 5%.
Ну что, давайте приступим?!
Примечание: Данная настройка оттестирована на ОС Ubuntu 20.04, на других ОС команды могут немного отличаться.
Сначала, если есть желание, можно убедиться в том, что наш сервер действительно атакуют.
Проверьте свой сервер введя одну из команд (из под пользователя «root»):
grep -a "Failed password" /var/log/auth.log
либо:
egrep -a "Failed|Failure" /var/log/auth.log
Вероятнее всего, если еще не настроен Fifewall (контроль и фильтрация проходящего сетевого трафика в соответствии с заданными правилами), мы увидим приличный список неудачных попыток входа по логину и паролю, по разным портам:
Впечатляюще, не правда ли?
Вот именно поэтому я всегда рекомендую сначала позаботиться о защите с помощью SSH-ключей, потом отключить возможность входа по паролю, потом настроить Firewall для защиты от Brute-force attack
Ну собственно, переходим к самой настройке защиты:
Первым делом я бы рекомендовал произвести обновления репозиториев и обновление системы, команды следующие:
❗️ Делать обновление или нет - это каждый решает самостоятельно.
❗️ Дальнейшие действия продолжаем делать под пользователем «root».
Обновление репозиториев - вводим команду и нажимаем «Enter»:
apt update
Ждём окончания обновления репозиториев:
Обновление системы - вводим команду и нажимаем «Enter»:
apt full-upgrade
Конфликтующие пакеты могут быть удалены, а новые, дополнительные - установлены.
Система сообщает о том, что будет установлено и что обновлено и задаст вопрос - желаем ли мы продолжить:
Для подтверждения нажимаем клавишу «y» и нажимаем «Enter»
Ожидаем и при появлении такого или подобного окна (если появится)и выбираем пункт отмеченный по умолчанию - нажимаем «Enter»:
После завершения обновлений (обновление занимает некоторое время) система будет ожидать ввода команд:
Приступим к самой настройке Firewall
Подсистема «iptables» и «netfilter» встроены в ядро, но вот набор утилит для управления всем этим не всегда поставляется вместе с системой.
Для установки утилиты в Ubuntu , нужно ввести команду и нажать «Enter»:
apt install iptables
Если попросит ввести пароль - вводим пароль текущего пользователя
В моем случае система сообщила о том, что у меня уже установлены последние обновления «iptables»:
Далее, введя эту команду, можно увидеть список всех имеющихся у нас правил с номерами (не забываем нажимать «Enter» после ввода каждой команды):
iptables -L -n --line-numbers
В моем случае система отобразила 3 раздела правил и все они пустые:
Запоминаем, визуально, какие правила у нас на текущий момент (если они есть, но на скриншоте выше список пуст).
Примечание: Вы не можете просто так отключить iptables остановив сервис обновления правил iptables через systemd или даже удалив набор утилит для настройки. Подсистема работает на уровне ядра и не зависит от того, что там у вас установлено. Поэтому если сделаете что-то не так, то нужно будет очистить правила. Для этого нужно ввести команду:
sudo iptables -F
Создаем правила (вставляем блоки целиком, по очереди):
iptables -A INPUT -p tcp -m tcp --dport 22 -m state --state NEW -m hashlimit --hashlimit 1/hour --hashlimit-burst 2 --hashlimit-mode srcip --hashlimit-name SSH --hashlimit-htable-expire 60000 -j ACCEPT
Нажимаем «Enter»
iptables -A INPUT -p tcp -m tcp --dport 22 --tcp-flags SYN,RST,ACK SYN -j DROP
Нажимаем «Enter»
iptables -A INPUT -p tcp -m state --state NEW -m tcp --dport 22 -j ACCEPT
Нажимаем «Enter»
Проверяем добавились правила или нет - вводим команду и нажимаем «Enter»:
iptables -L -n --line-numbers
Видим, что теперь добавлено 3 правила (номера пометил на скриншоте):
Все настройки «iptables», которые мы указали с помощью этих команд сохранятся только до перезагрузки. После перезагрузки сервера все изменения будут выгружены из памяти и стерты. Поэтому чтобы сохранить правила «iptables» в файле, нужно выполнить специальную команду.
❗️ ВНИМАНИЕ: На хостерах First Bite, MskHost (если выявите других хостеров - дайте знать) замечено то, что после выполнения ниже описанных действий правила не подгружаются. Для Вас решение немного другое - в принципе, должно сработает на всех хостерах, поэтому сами решайте как реализовать подгрузку правил:
Блок для хостеров у которых правила не подгружаются сервисом:
--------------------
Установить пакет сохранения:
apt install iptables-persistent
В процессе установки на оба вопроса ответить Yes.
Сохранить текущие правила:
service netfilter-persistent save
❗️ ВСЁ! При следующей загрузке сохраненные правила подгрузятся как положено.
--------------------
Конец блока
Далее информация для тех кто решил создать сервис подгружающий правила (работает не на всех хостерах, но на Hetzner, Digital Ocean работает нормально).
❗️ Оба варианта делать не нужно, если сделали один и он работает - другой делать не нужно
Вот только перед сохранением файла iptables.rules в директорию iptables - нужно создать эту директорию.
Вводим команду и нажимаем «Enter»:
mkdir /etc/iptables
Команду создания директории ввели:
Видим, что после ввода команды появилась новая строчка - ожидание следующей команды. Ошибки никакой не появилось - это значит, что команда принята и папка создана.
Сохраняем введенные правила в файл, команда:
iptables-save > /etc/iptables/iptables.rules
Примечание: в разных дистрибутивах команда отличается, данная команда для Ubuntu.
На всякий случай проверим есть ли правила в сохраненном файле (продолжаем работать под пользователем «root») - вводим команду:
cat /etc/iptables/iptables.rules
Появляется вот такое окно:
На скриншоте выше мы видим, что добавленные нами правила сохранились файле.
Путь к файлу и название самого файла, с правилами, можно указать любыми (в пределах папки «etc»), но я люблю порядок и поэтому выбрал путь и название файла именно такими: /etc/iptables/iptables.rules
Описание самих правил:
Вникать не обязательно – просто прочтите для общего понимания того, как работают правила.
Третье правило разрешает доступ к серверу по ssh.
Все самое интересное (военная тайна) кроется в первом и втором правилах:
Первое правило разрешает две попытки соединения на 22-й порт в течение часа, после чего начнёт срабатывать второе правило. Срок действия хэш-таблицы с IP-адресами – 60 секунд, после которых можно повторить попытку.
Однако при срабатывании второго правила этот счетчик будет сбрасываться при каждой последующей попытке установить соединение нашим сервером.
Если не принимать попыток соединения (входа) до истечения таймера (в данном случае это 1 минута) информация о наших попытках потухнет и можно будет снова повторить две попытки входа, но, если, не дожидаясь истечения таймера произвести попытку соединения с сервером пакет будет убит, а таймер начнет новый отсчет 60000 миллисекунд и так до бесконечности.
Таким образом, если вы «Нетерпеливый брутфорсер» и будете тупо долбить порт после блокировки, то вы с каждой попыткой будете продлевать свой бан! Иными словами: забаните себя навечно!
При действии этих правил в: /proc/net/ipt_hashlimit будет создаваться файл с именем, заданным параметром –hashlimit-name (в нашем случае это ssh ).
После второй попытки подключения туда попадает информация:
55 ХХ.ХХ.ХХ.ХХ:0->0.0.0.0:0 11533000 230400000 115000000
первое число — кол-во оставшихся секунд, можно смотреть как оно равномерно тикает
Таким образом решены две проблемы:
— если пользователь вдруг опечатался, ему не нужно долго ждать новых попыток
— брутфорсеры сами себя загоняют в «вечный» бан.
Что делать, если вы вдруг с нескольких попыток не смогли ввести пароль?
Не суетиться — подождать спокойно минуту и попробовать еще несколько раз.
Итак: правила созданы и сохранены, но вот только после перезагрузки они перестанут работать т.к. не подгружены – исправляем эту проблему:
Создаем сервис подгрузки правил Firewall (вставляем блок целиком):
cat >> /etc/systemd/system/iptables-rules-restore.service <<EOF
[Unit]
Description = Apply iptables rules
[Service]
Type=oneshot
ExecStart=/bin/sh -c 'iptables-restore < /etc/iptables/iptables.rules'
[Install]
WantedBy=network-pre.target
EOF
Нажимаем «Enter»
Видим что команда принялась - ошибок не выдало:
Даём права на исполнение файла:
chmod +x /etc/systemd/system/iptables-rules-restore.service
Нажимаем «Enter»
Подключаем сервис :
systemctl enable iptables-rules-restore.service
Нажимаем «Enter»
Обновляем конфигурацию всех служб:
systemctl daemon-reload
Нажимаем «Enter»
Запускаем сервис подгрузки правил Firewall :
systemctl start iptables-rules-restore.service
Нажимаем «Enter»
Вот, собственно, и всё!
❗️ Правила Firewall созданы и при перезагрузке сервера будут загружаться как сервис.
Давайте проверим загружаются ли правила, автоматически, при перезагрузке сервера, для этого нам поможет священный «reboot» (перезагрузка) нашего сервера.
Существует два способа перезагрузки сервера: «Через панель управления в личном кабинете на сайте хостера» и «Командой в консоли».
Сейчас мы воспользуемся командой в консоли, вводим команду:
reboot
Нажимаем «Enter»
и еще 1-2 раза «Enter»
«Перезагрузка» процесс НЕ мгновенный - ожидаем буквально несколько секунд и система запросит у нас ввод пароля от SSH-ключа.
После перезагрузки нашего сервера вводим команду (если требуется - подтверждаем паролем):
iptables -L -n --line-numbers
отображение списка всех имеющихся у нас правил с номерами
После ввода команды появится вот такое окно и если в нем присутствуют правила (изначально правил не было) значит все в порядке:
❗️ ВСЁ! При следующей загрузке сохраненные правила подгрузятся как положено.
Я полагаю, что Вам не терпится проверить то, как работает данная защита?!
Ну что же, давайте проверим.
Закрываем окно консоли и открываем снова (Вы это уже умеете):
Выставляем настройки по умолчанию (Default Settings) и вводим IP-адрес сервера.
Далее нажимаем «Соединиться»
Вводим логин - например: «root» и нажимаем «Enter»
Появляется вот такое окно с ошибкой:
Мы видим ошибку так как при настройке SSH-ключей мы отключили вход по паролям пользователей.
Закрываем окна и пробуем подключиться снова (Default Settings) - вводим логин и опять точно такая же ошибка как на скриншоте выше.
Опять закрываем и пробуем подключиться еще раз и что мы видим?
Система даже логин, у нас, не запрашивает!
Поздравляю, с этого моменты мы в БАНе - сервер перестал принимать пакеты с нашего IP-адреса и теперь мы будем долбится в закрытые двери (если бы мы были брутфорсером и пытались подобрать пароль) .
Иными словами: брутфорсер смог предпринять ДВЕ попытки подбора логина и ни одной пароля, после чего попал в БАН и все последующие его попытки будут убиты (ни один пакет сервер не примет), а таймер будет продлеваться на 60 секунд после каждой попытки (вечный бан).
Чтобы сервер начал принимать пакеты от нашего IP-адреса - нужно не пытаться с ним соединиться в течение 60 сек, если не меняли настройку «hashlimit-htable-expire 60000».
(120000 - это 2 минуты, 180000 - это 3 минуты и т.д).
Ну вот и всё, на этом инструкция по настройке защиты сервера подошла к концу и я очень надеюсь на то, что мне удалось сделать эту инструкцию доступной для понимания даже ребенку.
Если какие-то моменты были не понятны - не стесняйтесь сообщить мне об этом и я буду редактировать эту инструкцию.
А сейчас, желающие установить и настроить ноду блокчейна Idena (майнинг криптовалюты iDNA) как сервис, чтобы нода запускалась автоматически при загрузке/перезагрузке сервера - переходите по ссылке к следующей инструкции:
Установка ноды IDENA на сервер (VPS/VDS) как сервис
Пожертвования и благодарность:
Яндекс (Ю.Money): https://sobe.ru/na/nuzhdy_Andrey_N
IDNA: 0x5d69be52a201f9d0a2f3ec49060112811a63e4d1