> From: "Andrey V. Malyshev"

> пароль утащен вирусом/трояном

Именно.

Еще боты проверяют на дефолтные и самые часто используемые пароли,
причем эти проверки идут не только через SMTP, но и через POP3.
В качестве сервера POP3 я использую программу popa3d, вызываемую из inetd,
в inetd.conf лимит 5 соединений в минуту с одного IP-адреса:

pop3 stream tcp nowait/0/5 root /usr/local/libexec/popa3d popa3d

В логе видно, что лимит срабатывает часто.

> не пропустил ли я какой-нибудь
> уязвимости в аутентификаторах exim'а?

Если пользователи в sql, то в конфиге нужно грамотно написать,
чтобы не сделать уязвимость (пропускающую несуществующего пользователя
с пустым паролем).

> есть ли какие-то 
> принципиальные идеи по борьбе с таким

Посмотрите, пожалуйста, в логах, много ли было ответов MX получателей спама
5xx User unknown и других 5xx с тем же смыслом?

Идея основана на том, что спамеры рассылают по громадным спискам
email адресов, в которых полно более не существующих email адресов
и никогда не существовавших: Message-IDы; куски содержимого RAM и дисков,
принятые ботами за email адреса, а на самом деле представляющие собой
случайно склеившиеся куски email адресов и других текстовых строк.
Поэтому я лимитирую не количество писем в единицу времени,
а количество несуществующих адресов получателей в единицу времени.
При превышении лимита пользователь автоматически блокируется,
админ получает уведомление, и все письма от этого пользователя
замораживаются в очереди. Админ с помощью команды exipick смотрит содержимое
нескольких замороженных писем. Если это не спам (весьма маловероятно),
то достаточно удалить строку с идентификатором пользователя из файла
текстовым редактором (если в файле одна строка, а так обычно и будет,
то можно просто удалить файл) и разморозить письма с помощью команды
exipick. Если это спам, то нужно поменять пароль пользователя,
в соответствии с заранее предусмотренным пунктом договора
взыскать с пользователя штраф, используя заморорженный спам как
доказательство, затем удалить спам опять же используя exipick
и тоже удалить строку или файл.
Нижеприведенные фрагменты конфига Exim реализуют автоматические
блокирование и уведомление.

> и не пропустил ли я какой-нибудь 
> уязвимости в аутентификаторах exim'а?

Уязвимости в винде. Бесконечные. Антивирусы помогают, но далеко не 100%,
т.к. даже хорошие антивирусы начинают распознавать malware с задержкой.
Сохраненные пользователями пароли будут украдены, вопрос только времени.
Это касается всех админов Exim: у всех есть пользователи с виндой.

> как можно вставить задержку (delay) 
> после неудачной попытки аутентификации?

Я делаю не только задержку, но еще и автоматический отлов подбора паролей.
Далее реализация этого, а также вышеупомянутое.

LIM = 100
PERIOD = 1h
WARNTO = [email protected]
EXIMBINARY = /usr/local/sbin/exim -f root
SHELL = /bin/sh
...
begin acl
acl_check_rcpt:
...
  accept authenticated = *
        set acl_m_user = $authenticated_id
# in case of mailboxes in /var/mail: ${sg{$authenticated_id}{\N\W.*$\N}{}}
        condition = ${if exists{$spool_directory/blocked_authenticated_users}}
        condition = ${lookup{$acl_m_user}lsearch\
                    {$spool_directory/blocked_authenticated_users}{1}{0}}
        control = freeze/no_tell
        control = submission/domain=
        add_header = X-Authenticated-As: $acl_m_user

  accept authenticated = *
        !verify = recipient/defer_ok/callout=10s,defer_ok,use_sender
        ratelimit = LIM / PERIOD / per_rcpt / user-$acl_m_user
        continue = ${run{SHELL -c "echo $acl_m_user \
           >>$spool_directory/blocked_authenticated_users; \
           \N{\N echo Subject: user $acl_m_user blocked; echo; echo because \
           has sent mail to LIM invalid recipients during PERIOD.; \
           \N}\N | EXIMBINARY WARNTO"}}
        control = freeze/no_tell
        control = submission/domain=
        add_header = X-Authenticated-As: $acl_m_user

  accept authenticated = *
        condition = ${if !={$received_port}{25}}
        control = submission/domain=

  accept hosts = !@[] : +relay_from_hosts
        set acl_m_user = $sender_host_address
                         # or an userid from RADIUS
        condition = ${if exists{$spool_directory/blocked_relay_users}}
        condition = ${lookup{$acl_m_user}lsearch\
                    {$spool_directory/blocked_relay_users}{1}{0}}
        control = freeze/no_tell
        control = submission/domain=
        add_header = X-Relayed-From: $acl_m_user

  accept hosts = !@[] : +relay_from_hosts
        !verify = recipient/defer_ok/callout=10s,defer_ok,use_sender
        ratelimit = LIM / PERIOD / per_rcpt / relayuser-$acl_m_user
        continue = ${run{SHELL -c "echo $acl_m_user \
           >>$spool_directory/blocked_relay_users; \
           \N{\N echo Subject: relay user $acl_m_user blocked; echo; echo \
           because has sent mail to LIM invalid recipients during PERIOD.; \
           \N}\N | EXIMBINARY WARNTO"}}
        control = freeze/no_tell
        control = submission/domain=
        add_header = X-Relayed-From: $acl_m_user

  accept  hosts         = +relay_from_hosts
          control       = submission/domain=
...
acl_check_auth:
  drop  message = authentication is allowed only once per message in order \
                  to slow down bruteforce cracking
        set acl_m_auth = ${eval10:0$acl_m_auth+1}
        condition = ${if >{$acl_m_auth}{2}}
        delay = 22s

  drop  message = blacklisted for bruteforce cracking attempt
        set acl_c_authnomail = ${eval10:0$acl_c_authnomail+1}
        condition = ${if >{$acl_c_authnomail}{4}}
        continue = ${run{SHELL -c "echo $sender_host_address \
           >>$spool_directory/blocked_IPs; \
           \N{\N echo Subject: $sender_host_address blocked; echo; echo \
           for bruteforce auth cracking attempt.; \
           \N}\N | EXIMBINARY WARNTO"}}

  accept

acl_check_quit:
  warn  condition = ${if def:authentication_failed}
        condition = $authentication_failed
        logwrite = :reject: quit after authentication failed: \
                            ${sg{$sender_rcvhost}{\N[\n\t]+\N}{\040}}
        ratelimit = 7 / 5m / strict / per_conn
        continue = ${run{SHELL -c "echo $sender_host_address \
           >>$spool_directory/blocked_IPs; \
           \N{\N echo Subject: $sender_host_address blocked; echo; echo \
           for bruteforce auth cracking attempt.; \
           \N}\N | EXIMBINARY WARNTO"}}

acl_check_notquit:
  warn  condition = ${if def:authentication_failed}
        condition = $authentication_failed
        logwrite = :reject: $smtp_notquit_reason after authentication failed: \
                            ${sg{$sender_rcvhost}{\N[\n\t]+\N}{\040}}
        condition = ${if eq{$smtp_notquit_reason}{connection-lost}}
        ratelimit = 7 / 5m / strict / per_conn
        continue = ${run{SHELL -c "echo $sender_host_address \
           >>$spool_directory/blocked_IPs; \
           \N{\N echo Subject: $sender_host_address blocked; echo; echo \
           for bruteforce auth cracking attempt.; \
           \N}\N | EXIMBINARY WARNTO"}}

acl_check_mail:
  accept set acl_c_authnomail = 0

acl_check_connect:
  drop  message = $sender_host_address locally blacklisted for a bruteforce \
                  auth (login+password) cracking attempt
        condition = ${if exists{$spool_directory/blocked_IPs}}
        condition = ${lookup{$sender_host_address}lsearch\
                    {$spool_directory/blocked_IPs}{1}{0}}

  accept


_______________________________________________
Exim-users mailing list
[email protected]
http://mailground.net/mailman/listinfo/exim-users

Ответить