The OpenNET Project / Index page

[ новости /+++ | форум | wiki | теги | ]

форумы  помощь  поиск  регистрация  майллист  ВХОД  слежка  RSS
"Exim & greylist"
Вариант для распечатки Архивированная нить - только для чтения! 
Пред. тема | След. тема 
Форумы OpenNET: Виртуальная конференция (Public)
Изначальное сообщение [Проследить за развитием треда]

"Exim & greylist"
Сообщение от Alexander root Искать по авторуВ закладки on 11-Фев-05, 11:35  (MSK)
Добрый день!
Сделал небольшую реализацию greylist в Exim'е. Данные хранятся в MySQL.

Таблица в базе mail:
====================
CREATE TABLE Greylist (
   id bigint(20) NOT NULL auto_increment,
   relay_ip int unsigned NOT NULL,
   sender char(32) default NULL,
   recipient char(32) default NULL,
   block_expires int NOT NULL,
   record_expires int NOT NULL,
   create_time int UNSIGNED NOT NULL,
   pass_count int UNSIGNED NOT NULL default '0',
   block_count int UNSIGNED NOT NULL default '0',
   PRIMARY KEY (id),
   UNIQUE KEY (relay_ip,sender,recipient)
);

greylist.pl - скрипт вызываемый exim'ом
=======================================
#!/usr/bin/perl

# 30 минут блокировка для новой записи.
$block_expires=60*30;

# Время жизни неподтвержденной записи 24 часа.
$record_expires_init=60*60*24;

# Время жизни подтвержденной записи 60 дней с последнего письма.
$record_expires_incl=60*60*24*60;

$relay_ip=$ARGV[0];
$sender=$ARGV[1];
$recipient=$ARGV[2];

# В качестве ключа я использовал тройку:
# (inet_ntoa(relay_ip),md5('sender'),md5('recipient') = 68 байт.
# Использовал md5 по соображению безопасности и ограничении длины
# на ключ. А совпадение 64 байт для разных пар адресов - чрезвычайно  
# ничтожно.

@p=split(/\t/,`/usr/local/bin/mysql -s mail -e \"select id,(unix_timestamp()-block_expires) from Greylist where relay_ip=inet_aton('$relay_ip') and sender=md5('$sender') and recipient=md5('$recipient') limit 1\"`);

if ($p[0] > 0) {
    if ($p[1] > 0) {

        system("/usr/local/bin/mysql mail -e \"update Greylist set pass_count=pass_count+1,record_expires=unix_timestamp()+$record_expires_incl where id='$p[0]';\"");

        exit 1;
    }
    else {

        system("/usr/local/bin/mysql mail -e \"update Greylist set block_count=block_count+1 where id='$p[0]';\"");

    }
}

else {

    system("/usr/local/bin/mysql mail -e \"insert into Greylist (relay_ip,sender,recipient,block_expires,record_expires,create_time,block_count) values (inet_aton('$relay_ip'),md5('$sender'),md5('$recipient'),unix_timestamp()+$block_expires,unix_timestamp()+$record_expires_init,unix_timestamp(),1);\"");

}
exit 0;

для чистки старых записей по крону раз в N минут запускаем:
===========================================================
/usr/local/bin/mysql mail -e "delete from Greylist where unix_timestamp()>record_expires and pass_count=0;"

exim.conf
=========
acl_check_rcpt:
...skipped...

defer   domains       = +local_domains
         message       = Currently can not deliver mail. Try again later.
         condition     = ${run{/usr/local/exim/bin/greylist.pl     $sender_host_address $sender_address $local_part@$domain}{yes}{no}}

...skipped...

При правильно написанных acl exim'а, greylist работает только на почту входящую из вне.

Есть одно НО: письмо, в котором указаны несколько адресатов моего домена, попадет каждому из них, как минимут, только через $block_expires*(кол-во адресатов). Здесь по обстоятельствам, если последнее не устраивает, то можно убрать из базы и скриптов адрес получателя.

Приму конструктивную критику :-)

  Рекомендовать в FAQ | Cообщить модератору | Наверх

 Оглавление

Индекс форумов | Темы | Пред. тема | След. тема
Сообщения по теме

1. "Exim & greylist"
Сообщение от sashas emailИскать по авторуВ закладки(ok) on 11-Фев-05, 13:57  (MSK)
Пока что из критических замечаний только одно: зачем это? :) :)
  Рекомендовать в FAQ | Cообщить модератору | Наверх

2. "Exim & greylist"
Сообщение от Alexander root Искать по авторуВ закладки on 11-Фев-05, 14:37  (MSK)
>Пока что из критических замечаний только одно: зачем это? :) :)

Greylist - метод борьбы со спамом. При первом обращении неизвестного сервера, его письмо отвергается с кодом нефатальной ошибки 4xx, если отправитель нормальный MTA, то по RFC он должен повторят попытки отправки письма в течении некоторого времени. После заданного времени мой почтовик разрешает данную комбинацию IP_адрес_сервера_отправителя:Емайл_оправителя:Емайл_получателя и письма ходят без задержек.
Если же отправитель является программа рассылки спама, то врядли будет попытка повтора, тем более, что база у спамеров как правило на десятки тысяч разных адресов.

В комбинации с SpamAssassin'ом и белыми и черными списками можно добиться неплохих результатов в борьбе со спамом.

  Рекомендовать в FAQ | Cообщить модератору | Наверх

3. "Exim & greylist"
Сообщение от Alexander root Искать по авторуВ закладки on 12-Фев-05, 12:14  (MSK)
Вот еще переписал скрипт на Си, теперь будет быстрее работать...

greylist.c
================================================

#include <stdio.h>
#include "mysql.h"

/* Greylist parametrs */
#define BLOCK_EXPIRES 60*60*1
#define RECORD_EXPIRES_INITIALY 60*60*24
#define RECORD_EXPIRES_ELECTED 60*60*24*60

/* MySQL parameters */
#define MYSQL_HOST NULL
#define MYSQL_DATABASE "mail"
#define MYSQL_USER "exim"
#define MYSQL_PASSWORD "passwd"
#define MYSQL_PORT 3306
#define MYSQL_UNIXSOCKET "/tmp/mysql.sock"
#define MYSQL_CLIENTFLAG 0

void usage() {
    printf ("Usage: greylist [relay_ip] [sender] [recipient]\n");
    exit (0);
}

int main(int argc, char ** argv) {
    MYSQL mysql;
    MYSQL_ROW row;
    MYSQL_RES * result;

    unsigned long long id;
    signed int delta_time;
    char query[1024];
    
    if (argc!=4) usage();

    mysql_init(&mysql);

    if (!mysql_real_connect(&mysql,MYSQL_HOST,MYSQL_USER,MYSQL_PASSWORD,MYSQL_DATABASE,MYSQL_PORT,MYSQL_UNIXSOCKET,MYSQL_CLIENTFLAG)) {
fprintf(stderr, "Connection to MySQL failed: %s\n", mysql_error(&mysql));
exit(1);
    }

    sprintf (query,"select id,unix_timestamp()-block_expires from Greylist where relay_ip=inet_aton('%s') and sender=md5('%s') and recipient=md5('%s') limit 1",argv[1],argv[2],argv[3]);
    if (mysql_query(&mysql,query)) {
        fprintf(stderr, "SQL: \"%s\" failed: %s\n",query, mysql_error(&mysql));
        exit (1);
    }

    result = mysql_store_result(&mysql);

    if (mysql_num_rows(result)) {
        row = mysql_fetch_row(result);
        mysql_free_result(result);

id=strtoull(row[0],0,10);
        delta_time=strtol(row[1],0,10);

if (delta_time>0) {
    sprintf (query,"update Greylist set pass_count=pass_count+1,record_expires=unix_timestamp()+%lu where id='%llu'",RECORD_EXPIRES_ELECTED,id);
    if (mysql_query (&mysql,query)) fprintf(stderr, "SQL: \"%s\" failed: %s\n",query, mysql_error(&mysql));
            mysql_close(&mysql);
    exit (1);
}
else {
    sprintf (query,"update Greylist set block_count=block_count+1 where id='%llu'",id);
    if (mysql_query (&mysql,query)) {
     fprintf(stderr, "SQL: \"%s\" failed: %s\n",query, mysql_error(&mysql));
     exit (1);
    }
}    
    }
    else {
        sprintf (query,"insert into Greylist (relay_ip,sender,recipient,block_expires,record_expires,create_time,block_count) values (inet_aton('%s'),md5('%s'),md5('%s'),unix_timestamp()+%lu,unix_timestamp()+%lu,unix_timestamp(),1)",argv[1],argv[2],argv[3],BLOCK_EXPIRES,RECORD_EXPIRES_INITIALY);
if (mysql_query(&mysql,query)) {
         fprintf(stderr, "SQL: \"%s\" failed: %s\n",query, mysql_error(&mysql));
         exit (1);
}
    }
    mysql_close(&mysql);
    exit(0);
}

  Рекомендовать в FAQ | Cообщить модератору | Наверх

5. "Exim & greylist"
Сообщение от Yura Svetlanov Искать по авторуВ закладки on 14-Фев-05, 14:19  (MSK)
>Если же отправитель является программа рассылки спама, то врядли будет попытка повтора,
>тем более, что база у спамеров как правило на десятки тысяч
>разных адресов.

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

  93 [211.43.219.88]
  85 [209.124.86.69]
  64 [12.223.230.255]
  55 [64.168.26.236]
  53 [68.234.144.70]
  52 [66.189.37.38]
  50 [69.165.39.222]
  49 [24.90.189.218]
  48 [68.250.71.189]
  46 [200.214.177.160]
  45 [81.86.92.204]
  44 [68.200.80.26]

  Рекомендовать в FAQ | Cообщить модератору | Наверх

6. "Exim & greylist"
Сообщение от Alexander root Искать по авторуВ закладки on 14-Фев-05, 15:02  (MSK)
>Спамеры наоборот более настойчивы, чем легальные почтовики.

Это скорее открытые релеи, а с ними rbl хорошо справляется. Рассылки,  которые идут с временных адресов прекрасно блокируются.

  Рекомендовать в FAQ | Cообщить модератору | Наверх

8. "Exim & greylist"
Сообщение от sashas emailИскать по авторуВ закладки(ok) on 14-Фев-05, 15:07  (MSK)
>>Пока что из критических замечаний только одно: зачем это? :) :)
>
>Greylist - метод борьбы со спамом. При первом обращении неизвестного сервера, его
>письмо отвергается с кодом нефатальной ошибки 4xx, если отправитель нормальный MTA,
>то по RFC он должен повторят попытки отправки письма в течении
>некоторого времени. После заданного времени мой почтовик разрешает данную комбинацию IP_адрес_сервера_отправителя:Емайл_оправителя:Емайл_получателя
>и письма ходят без задержек.
>Если же отправитель является программа рассылки спама, то врядли будет попытка повтора,
>тем более, что база у спамеров как правило на десятки тысяч
>разных адресов.
>
>В комбинации с SpamAssassin'ом и белыми и черными списками можно добиться неплохих
>результатов в борьбе со спамом.
Что помешает спамером добавить повторное обращение к серверу? На поток такую защиту не поставить, а для себя ничего так. Удачное решение.
  Рекомендовать в FAQ | Cообщить модератору | Наверх

4. "Exim & greylist"
Сообщение от Cheeto_McMourrell Искать по авторуВ закладки(??) on 14-Фев-05, 14:11  (MSK)
>Приму конструктивную критику :-)
Ради чего делать внешний скрипт, когда запросы к БД и всю логику работы можно реализовать средствами самого exim?
  Рекомендовать в FAQ | Cообщить модератору | Наверх

7. "Exim & greylist"
Сообщение от Alexander root Искать по авторуВ закладки on 14-Фев-05, 15:06  (MSK)
>>Приму конструктивную критику :-)
>Ради чего делать внешний скрипт, когда запросы к БД и всю логику
>работы можно реализовать средствами самого exim?

Ваша правда :-).

  Рекомендовать в FAQ | Cообщить модератору | Наверх

9. "Exim & greylist"
Сообщение от cruel Искать по авторуВ закладки on 15-Фев-05, 14:20  (MSK)
wheel reinventing. look for GREYLISTING in
http://www.openbsd.org/cgi-bin/man.cgi?query=spamd

  Рекомендовать в FAQ | Cообщить модератору | Наверх


Удалить

Индекс форумов | Темы | Пред. тема | След. тема
Пожалуйста, прежде чем написать сообщение, ознакомьтесь с данными рекомендациями.




Партнёры:
PostgresPro
Inferno Solutions
Hosting by Hoster.ru
Хостинг:

Закладки на сайте
Проследить за страницей
Created 1996-2024 by Maxim Chirkov
Добавить, Поддержать, Вебмастеру