Search
Write a publication
Pull to refresh

Ubuntu+Postfix как антиспам шлюз для Exchange2003

Ubuntu 8.10 (Postfix) в качестве почтового шлюза для Exchange+antispam
Как все начиналось или Зе хистори оф батл! ;)
В жизни каждого системного администратора наступает такой момент, когда количество спама, переходит все мыслимые и не мыслимые пределы. Когда начальство при вашем появлении в кабинете, начинает нудить — что устало начинать свой рабочий день с разгребания спама, вместо того чтобы совершать подвиги — типа разгона облаков или мативирования подчиненных на новые трудовые свершения — на ниве капиталистического труда.)
При этом денег на покупку лицензий антиспама выделять не хочет, мотивируя это тем, что: ТЫ и так умный, вот и придумай что-нибудь, да и кризис на дворе. А лицензирование большинства современных систем фильтрации нежелательной корреспонденции, основывается на на принципе:1 почтовый ящик =1 лицензия, а если количество ящиков больше 100, а если 200 и более как у меня, то сумма получается вполне приличной.

Схема работы системы будет следующей
Канал интернета ->шлюз ubuntu->сервер win2k3(exchange 2003, AD, DNS,WINS,ISA)ну и прочие прелести от мелко-мягких.
Установку Ubuntu server 8.10 оставлю за рамками статьи
Схема работы шлюза подробнее:
1) Ubuntu принимает, входящие письма от спамеров клиентов, проверяет IP отправителя, на наличие в списках негодяев (спам листах) – если IP присутствует, соединение разрывается, если отсутствует – считаем, отправителю повезло, переходим к пункту 2
2) Поверяем как представится сервер отправитель, если в helo содержит записи типа localhost или IP адрес отправитель идет лесом, а если сервер представился правильно проводим проверку по реверс ДНС запросу – если ответ не соответствует helo при начале соединения – отправитель посылается в пешее эротическое путешествие. Вот такая вот викторина получается, ах да, совсем забыл — если во время всей этой игры в кошки-мышки сервер отправитель допустил более 1й ошибки- то что? Правильно — соединение разрывается! Но если и тут все хорошо- то отправитель признается, самым хитрым спамером и я как Якубович предлагаю сыграть со мной в супер-игру, от которой нельзя отказаться с суперпризом будет велосипед, который мы только что изобрели, т.е. к переходим пункту 3.
3) .(СУПЕР игра и супер приз велосипед!) проверяем наличие почтовых ящиков получателей в Exhange, если получатель отсутствует в списке, то отправитель уходит несолоно хлебавши, со следами пинка на пятой точке и клеймом спамера-неудачника, соединение разрывается, не доходя то закачки тела сообщения ( экономия на трафике на лицо) — если присутствует то отправитель признается абсолютным чемпионом и письмо передается на exchange, который тихо сидит backend и его не видно, снаружи.

Переходим непосредственно к первой части нашего эротического боевика.
Предполагаю что система, уже установлена и обновления поставлены, настройки сделаны.
Заходим в качестве супер-пользователя
#Sudo su
Вводим пароль администратора
Ставим postfix

apt-get install postfix

Ну и далее запускаем текстовый редактор.
Вместо «сервер конторы.ru» подставляем реальные данные ВАШЕГО домена.
Начнем:
nano /etc/postfix/main.cf

нас интересуют следующие строки
myhostname = mail.сервер конторы.ru # полное имя хоста
mydomain = сервер конторы.ru # имя домена от имени которого приходит почта

mydestination = mail. сервер конторы.ru, localhost. сервер конторы.ru,, localhost
mynetworks = 127.0.0.0/8, 192.168.200.20 [::ffff:127.0.0.0]/104 [::1]/128 # список доверенных сетей из которых разрешена неавторизированная отправка, сервер win2k3 имеет адрес 192.168.200.20( это IP не я придумал, пришел на новую работу так все уже было настроено, ну а я систему ломать не стал), этой директивой мы разрешаем отправку почты наружу через postfix только непосредственно серверу с Exchange на борту, даже клиенты локальной сети должны отправлять почту только через Exhcange.

virtual_mailbox_domains = сервер конторы.ru

transport_maps = hash:/etc/postfix/transport
virtual_transport = hash:/etc/postfix/transport
Эти пункты отвечают за то, куда будет передаваться принятая почта.

В конце конфига добавляем

bounce_queue_lifetime = 1d
maximal_queue_lifetime = 1d
minimal_backoff_time = 180s
maximal_backoff_time = 12h

strict_rfc821_envelopes = yes
disable_vrfy_command = yes
smtpd_delay_reject = yes
smtpd_helo_required = yes
anvil_rate_time_unit = 60s
smtp_always_send_ehlo = yes
smtpd_hard_error_limit = 1
smtpd_recipient_limit = 1
smtpd_sasl_security_options = noanonymous

anvil_rate_time_unit = 60s
smtpd_client_connection_count_limit = 5
smtpd_client_connection_rate_limit = 6
smtpd_client_message_rate_limit = 6
smtpd_client_recipient_rate_limit = 1

smtpd_client_restrictions =
reject_unauth_pipelining,
permit_sasl_authenticated,
permit_mynetworks,
check_helo_access regexp:/etc/postfix/helo,
reject_unknown_client_hostname,
check_client_access regexp:/etc/postfix/dul_checks,
permit

smtpd_helo_restrictions =
permit_mynetworks,
permit_sasl_authenticated,
reject_unknown_client,
# проверяем IP на присутствие в спам листах
reject_rbl_client cbl.abuseat.org,
reject_rbl_client sbl-xbl.spamhaus.org,
reject_rbl_client sbl.spamhaus.org,
reject_rbl_client dnsbl.njabl.org,
check_helo_access regexp:/etc/postfix/helo,
reject_invalid_helo_hostname,
reject_non_fqdn_helo_hostname,
reject_unknown_helo_hostname,
check_sender_access hash:/etc/postfix/access,
check_recipient_access hash:/etc/postfix/recipients,
permit

smtpd_sender_restrictions =
permit_sasl_authenticated,
permit_mynetworks,
reject_non_fqdn_sender,
reject_unknown_sender_domain,
permit

smtpd_recipient_restrictions =
reject_unauth_pipelining,
permit_mynetworks,
permit_sasl_authenticated,
reject_unauth_destination,
reject_invalid_hostname,
reject_non_fqdn_recipient,
reject_unknown_recipient_domain,
permit

сохраняем конфиг и выходим в консоль.
Подробно на всех пунктах останавливаться не буду их назначение легко найти в гугле,
Все содержимое можно просто за копипастить как есть. Остановлюсь на тех, которые нужно редактировать

Нам необходимо создать следующие файлы:
nano /etc/postfix/transport # отвечает за то, куда нужно передавать принятую почту, содержт:

серверконторы.ru smtp:[192.168.200.20]

где: smtp-серер получатель, IP в [ ] говорит о том, что не нужно проверять его ДНС зону, а передавать почту на этот адрес как есть, а там разберутся!

nano /etc/postfix/recipients
Это наш список получателей, который экспортируется из Exchange
Содержит записи вида:

user@серверконторы.ru OK

где: user-имя пользователя в AD c mailbox, серверконторы.ru-домен получателя, OK –директива, как поступить с письмом, в нашем случае – пропустить.
Сведения о получателях будут содержаться именно в этом файле, можно конечно сделать опрос exchange в реальном времени, но тут появляется ненужная нагрузка на контроллер домена, а оно вам надо?! Причем если одновременно долбиться несколько сот тыс. отправителей все эти запросы посыпятся и на AD. Это и потерянное время на ожидание ответа от винды и нагрузка на процессор уже 2х серверов. По моему глубокому мнению, проще запустить скрит через, который в заданное время, выдернет список получателей, и перебросит их в файл, как часто его запускать — решать вам, у меня он запускается 2 раза в день 12 и 15 часов — больше не требуется. А ночью, мы, слава богу, не работаем.

nano /etc/postfix/helo
содержит:
/([0-9]{1,3}(\.|-)){3}[0-9]{1,3}/i REJECT IP-able helo SPAM!
/localhost/i REJECT you are SPAM!
/ сервер конторы.ru/i REJECT you are not in my local networks-SPAM!

В этом файле используются регулярные выражения для фильтрации команды helo
Если отправитель представился IP адресом-то это нарушение и почту от него не принимают, тоже самое со вторым пунктом localhost –нормальный сервер не может представляться так, либо там админ криворукий (пускай настраивает нормально) либо на другом конце просто сильно запаршивевший компьютер, который является частью ботнета, рассылаешего спам. Ну и последнее если отправитель представляется — серверконторы.ru, ну не может на другом конце быть мой сервер — где же тогда я нахожусь, это на 100% спамер можно посылать смело. Команда REJECT указывает на то, что сделать при выполнении условий.
Да ксати после идет ответ сервера, с указанием причины отказа в принятии почты, туда можно вписать что-то обидное ;) и это сообщение увидят на том конце. Но это дело воспитания конкретного индивидуума.

nano /etc/postfix/access
содержание данного файла схоже с предыдущим, но тут уже используются явные указатели, этим файлом можно, например, блокировать отдельные ящики пользователей.
bad_user@сервер конторы.ru REJECT user is note available
сервер конторы.ru REJECT you are not in my local networks
IP вашего сервера REJECT you are not in my local networks
localhost REJECT you are SPAM!

nano /etc/postfix/dul_checks
проверка на наличии в различных сетях
содержит регулярные выражения различных сетей и как следствие признаков что это не почтовые сервера а зараженные клиентские компьютеры, а если там действительно работают нормальные сервера, то почту можно отправлять и через релей провайдера или на худой конец обратиться в тех поддержку чтобы прописали обратную DNS зону.

/([0-9]*-){3}[0-9]*(\..*){2,}/i REJECT 553 SPAM_ip-add-rr-ess_networks
/([0-9]*\.){4}(.*\.){3,}.*/i REJECT 553 SPAM_ip-add-rr-ess_networks
/.*\.broadband\.hu/i REJECT 553 SPAM_broadband-hu
/client.*\..*\..*/i REJECT 553 SPAM_CLIENT
/cable.*\..*\..*/i REJECT 553 SPAM_CABLE
/pool.*\..*\..*/i REJECT 553 SPAM_POOL
/dial.*\..*\..*/i REJECT 553 SPAM_DIAL
/ppp.*\..*\..*/i REJECT 553 SPAM_PPP
/dslam.*\..*\..*/i REJECT 553 SPAM_DSLAM
/dhcp.*\..*\..*/i REJECT 553 SPAM_DHCP
/[\.-]dsl.*\..*\..*/i REJECT 553 SPAM_DSL
/[ax]dsl.*\..*\..*/i REJECT 553 SPAM_XDSL
/.*([0-9]*\.){4}cableonline\.com\.mx/i REJECT 553 SPAM_IP-cableonline-com-mx
/.*\.([0-9]*\.){4}ip\.holtonks\.net/i REJECT 553 SPAM_ip-holtonks-net
/([0-9]*-){3}[0-9]*\.fibertel\.com\.ar/i REJECT 553 SPAM_IP-fibertel-com-ar
/.*[0-9]*-[0-9]*\.fibertel\.com\.ar/i REJECT 553 SPAM_IP-fibertel-com-ar
/[0-9]*\.user\.veloxzone\.com\.br/i REJECT 553 SPAM_user-veloxzone-com-br
/[0-9]*\.customer\.alfanett\.no/i REJECT 553 SPAM_customer-alfanett-no
/.*([0-9]*-){3}[0-9]*\.telecom\.net\.ar/i REJECT 553 SPAM_host-telecom-net-ar
/.*(-[0-9]*){2}\.telpol\.net\.pl/i REJECT 553 SPAM_host-telpol-net-pl
/(.*\.){2}maxonline\.com\.sg/i REJECT 553 SPAM_host-maxonline-com-sg
/(.*-){2}.*\.fairgamemail\.us/i REJECT 553 SPAM_host-fairgamemail-us
/[0-9]*[0-9]*-\.wispnet\.net/i REJECT 553 SPAM_host-wispnet-net
/.*-.*(\..*){2}\.ne\.jp/i REJECT 553 SPAM_host-ne-jp
/[0-9]*\..*\.ne\.jp/i REJECT 553 SPAM_h09t-ne-jp
/(.*\.){3}ad\.jp/i REJECT 553 SPAM_host-ad-jp
/(.*\.){4}revip\.asianet\.co\.th/i REJECT 553 SPAM_revip-asianet-co-th
/[0-9]*\..*\.virtua\.com\.br/i REJECT 553 SPAM_host-virtua-com-br
/([0-9]*-){3}[0-9]*\.exatt\.net/i REJECT 553 SPAM_host-exatt-net
/([0-9]*\.){4}ip\.alltel\.net/i REJECT 553 SPAM_host-ip-alltel-net
/[0-9]{6,}\.chello\.../i REJECT 553 SPAM_host-chello
/.*[0-9]*\..*\.chello\.../i REJECT 553 SPAM_host-chello-xx
/.*\..*\.t-dialin\.net/i REJECT 553 SPAM_t-dialin-net
/.*\..*\.t-ipconnect\.de/i REJECT 553 SPAM_t-ipconnect-de
/([0-9]*-){2,3}[0-9]*\..*\.cgocable\.net/i REJECT 553 SPAM_host-cgocable-net
/.*\..*\.shawcable\.net/i REJECT 553 SPAM_host-shawcable-net
/p[0-9]*\.mp[0-9]*\.aaanet\.ru/i REJECT 553 SPAM_aaa_modem_pool
/([0-9]*-){2}[0-9]*\.ip\.adsl\.hu/i REJECT 553 SPAM_ip-adsl-hu
/([0-9]{1,3}\.){2}broadband4\.iol\.cz/i REJECT 553 SPAM_broadband-iol-cz

В результате у нас должно получиться 5 файлов
Их нужно превратить в фалы базы данных принимаемые posfix,
выделяем все и копируем в консоль, если все проходит без ошибок, двигаемся дальше.

postmap /etc/postfix/transport
postmap /etc/postfix/recipients
postmap /etc/postfix/helo
postmap /etc/postfix/access
postmap /etc/postfix/dul_checks

вот пожалуй и все с ubuntu

Чась вторая: Настройка Win2k3

По моему глубокому мнению, не имеет смысла пускать сервер с передовой, в тыл нашей обороны, по этой же причине мы не будем давать лазить в системе и опрашивать ее, мы разрешим ей видеть только то, что мы сами разрешили.
Как это можно реализовать на практике?! Postfix будет видеть только тот список получателей который мы ему сами дадим -уже готовый!
В то время когда я только собирался все это безобразие настраивать-у меня был скрипт, на перле, который опрашивает AD, но с ним что-то не заладилось, во-первых там была какае-то шляпа с ключами, да и пересобирать openLDAP не очень хотелось.
Я пошел иным путем, на самом сервере win 2003 через планировщик заданий мы будем запускать скрипт который будет сбрасывать нам список пользователей в файл recipients.

Схема работы системы Win:
В AD заводится пользователь с минимальными правами, без почтового ящика, с правом доступа, лишь в одну папку. Назовем его postfix с паролем 1234567.
Через планировщик заданий создается новое задание с частотой выполнения нужной вам.
На просторах сети был найден скрипт, который не полностью соответствовал нашим задачам, я его слегка допилил и теперь он делает на 100% то что нужно.
Сам скрипт написан на VBS, назовем его mail.vbs-такого содержания:

Option Explicit

Dim StartTime,EndTime: StartTime = Now ' For seeing how long the script takes to run
Dim objShell
Dim objFSO
Const ScriptVersion = «1.01»
Set objShell = WScript.CreateObject(«WScript.Shell»)
Set objFSO = CreateObject(«Scripting.FileSystemObject»)
Wscript.Echo «StartTime = » & StartTime
' ***************************************************************** '
Const ForReading = 1, ForWriting = 2, ForAppending = 8
Dim objRootDSE
Dim objDomain
Dim objContainer
Dim objOrganizationalUnit
Dim strOutputFileName, objOutputFileName, GarbageRC
Dim intUserObjectCountAll, intUserObjectCountSelected

strOutputFileName = «c:\путь\ к расшаренной папке\ для пользователя postfix\recipients»

Set objOutputFileName = objFSO.OpenTextFile(strOutputFileName, ForWriting, True)
intUserObjectCountAll = 0
intUserObjectCountSelected = 0

Set objRootDSE = GetObject(«LDAP://RootDSE»)
Set objDomain = GetObject(«LDAP://» & objRootDSE.Get(«DefaultNamingContext»))

Call Sub_EnumOUs(objDomain.ADsPath)

Sub Sub_EnumOUs(sADsPath)
Set objContainer = GetObject(sADsPath)
objContainer.Filter = Array(«OrganizationalUnit»)
For Each objOrganizationalUnit in objContainer
WScript.Echo «Checking OU: » & objOrganizationalUnit.ADsPath
Wscript.Echo " User Object Count: " & intUserObjectCountAll
Sub_EnumUsers(objOrganizationalUnit.ADsPath)
Sub_EnumOUs(objOrganizationalUnit.ADsPath)
Next
End Sub

Sub Sub_EnumUsers(sADsPath)
Dim objADobject
Set objContainer = GetObject(sADsPath)
objContainer.Filter = Array(«User»)
For Each objADobject in objContainer
If objADobject.Class = «user» Then
intUserObjectCountAll = intUserObjectCountAll + 1
If objADobject.Mail <> "" Then
objOutputFileName.Writeline( objADobject.Mail & " OK" ) ' *** "[TAB]OK"- разделение с помощью табуляции **** '
intUserObjectCountSelected = intUserObjectCountSelected + 1
End If
End If
Next
End Sub

objOutputFileName.Close

' ***************************************************************** '

Чтобы создать задание в планировщике, в строку инициализации нашего скрипта пишем:
c:\windows\system32\cscript.exe c:\путь к папке со скриптом\mail.vbs
ВСЕ это одной строкой!
Ну и выставляем время, когда он будет выполнятся, и как часто.
Далее создаем директорию и открываем в нее доступ по сети пользователю postfix.

Часть треться –заключительная.
Теперь задача, чтобы наш linux сервер мог увидеть содержимое папки с файлом recipirnts
Я предпочел монтировать нашаренную директорию при старте системы, по этому, запихал команду в файл монтирования /etc/rc.local.
Также необходимо создать в директории media директорию win. Почему именно win- чтобы через несколько месяцев, можно было понять, что это такое и откуда оно взялось.
Сначала ставим пакет smbfs -без него наша директория не примантируется.
Sudo apt-get install smbfs
Sudo nano /etc/rc.local
И перед строкой exit0 вписываем команду монтирования шары:
mount -t smbfs //192.168.200.20/antispam /media/win/ -o iocharset=utf8,user=postfix,pass=1234567

где: 192.168.200.20-ip сервера с exchange.
antispam-директория в которой лежит файл recipients.
/media/win/-куда должна примантироваться виндовая шара.
iocharset=utf8-кодировака, если случайно в ней появятся папки с русскими названиями то они будут читаемы, а не ???????????, да и хуже от этого не будет, в общем делаем сразу как надо и спим спокойно.
user=postfix,pass=1234567 –имя пользователя и пароль для доступа к шаре.

Перезагружаем Ubuntu лезем в /media/win/ видим ее содержимое виндовой шары- значит все отлично.

Далее создадим небольшой скрипт который будет переписывать файл recipients
В директорию /etc/postfix затем будет пере конвертировать его в базу данных postfix
И перезагружать почтовик.

#!/bin/bash
cp /media/win/recipients /etc/postfix/
postmap /etc/postfix/recipients
/etc/init.d/postfix restart

Создаем задание в CRON которое будет выполняться через 3 мин после выполнения задания на Win2k3-на всякий случай

Вот и все!

Что мы получили
Аниспам фильтр, с высокой степенью эффективности-до его установки я каждое утро разгребал по 240-260 писем сейчас наблюдаю только нужную почту.
Единственный ящик в который спам, все таки доходит, это ящик на который приходят заявки для нашей конторы, но их число не превышает 3-4.
Безопасность — в случае компрометации сервера Linux шлюз легко восстанавливается,
Да и злоумышленник не получит доступа к корреспонденции, т.к ее на нем просто нет, она сразу передается Exchange-если проходит все проверки.
Кросс платформенность-нет смысла собирать модули с поддержкой всяких экзотических функций.

Время на развертывание-1 час с условием что Интернет шустрый, да и если все копипастить как есть — система протестирована в течении 3х мес. -работает без сбоев.
А теперь, как говорят в Одессе -Подабьем бабки…
Стоимость шлюза 14000руб. –можно и дешевле.
Стоимость антиспама от “Кашпировского” по минимуму 34500, по хорошему 76000-это так, на вскидку.
Вычитаем затраты на железо = сальдо в нашу пользу! Можно у руководства просить премию…
А что еще можно прикрутить к нему- решать вам.

Да немного аналитики-за время использования данной схемы читал логи, так вот-в первые 2 недели работы, очень много писем отбрасывалось по IP заблокированных спам-листами.
Теперь в основном по helo -т.е используются в основном IP не попавшие в спам-листы, очень удивило что на той стороне силы, все анализируется и проверяется… Много думал!
Кстати нужно будет протестировать на Win2k8 и Exchange2k7 по всем вариантам должно пахать нормально.
Tags:
Hubs:
You can’t comment this publication because its author is not yet a full member of the community. You will be able to contact the author only after he or she has been invited by someone in the community. Until then, author’s username will be hidden by an alias.