Greylisting je zajímavá metoda filtrování spamu. Je založena na tom, že spamovací automaty nemají ve většině případů plně implementované veškeré RFC. Jak to funguje a jak jej implementovat do Qmailu? | Greylisting is an interesting method to fight against spam. It’s based on the fact most spam is not sent out by fully compliant MTA’s. How it works and how this can be implemented into Qmail? |
Určitě znáte metodu whitelistů a blacklistů. Kdo/co je na whitelistu – tak projde filtry vždycky, kdo je na blacklistu – neprojde nikdy. Greylist funguje na úrovni SMTP spojení a říká neznámým serverům “teď od tebe nemohu přijmout poštu, zkus to za chvíli”. Správně implementované poštovní servery (sendmail, qmail, postfix, atd.) zařadí poštu do fronty a zkusí to znovu za nějakou dobu. Spammeři se většinou nikdy nevrátí a už to nezkusí, protože nemají tak chytré nástroje na spamování. Většinou spamují napadené počítače, které se bezhlavě připojují na servery a rozesílají spamy. A kdyby přeci jen spammer přšel znovu, získali jsme nějaký čas, během kterého se již ip adresa útočníka může dostat na blacklist rbl filtrů. Více se o metodě můžete dozvědět na www.greylisting.org.Při implementaci greylistingu pro Qmail jsem vycházel z doporučení identifikovat příchozí poštu podle trojice indentifikátorů. A to je adresa odesílatele, adresa příjemce a IP adresa příchozího serveru. Pokud se tato trojice objeví při SMTP spojení poprvé, odmítneme spojení z dočasných důvodů (kód 421). Správně fungující server se vrátí za několik minut a zkusí to znovu. V tu dobu už odesílatele známe a pošta je přijata. Společně s RBL filtrem (sbl-xbl.spamhaus.org) se jedná o velmi účinnou obranu. Takto vypadají statistiky za několik málo dní na jednom z administrovaných poštovních serverů: Odmítnuté spojení na základě RBL: 6712 Mnoho implementací využívá databázi (ať už MySQL nebo PostgreSQL) pro evidenci pokusů o doručení, což se mi zdálo jako kanon na vrabce, proto jsem použil obyčejné soubory pro uchování těchto informací. Celý program je napsán v perlu (rychlost je pro operaci se soubory více než dostačující) a je volán ze smtp daemonu (qmail-smtpd), ktrerý se na základě návratového kódu rozhoduje, zda zprávu přijme nebo ne. Celý vtip je v tom, že vytváříme prázdné soubory. Všechny informace jsou uloženy buď v názvu (trojice indentifikátorů) a v čase vytvoření a změny souboru (ctime a mtime). Ze všeho nejdříve tedy musíme patchnout qmail-smtpd. Použil jsem metodu Guenthera Maira (který pro greylisting použil PostgreSQL a C): | You surely know the method of whitelists and blackists. Who/what is on a whitelist will pass a filter without any restriction. Who is on blacklist will never pass. Greylist method works on SMTP layer during server communication. It says to unknown servers “I’m unable to receive a message, try again later”. Correctly implemented MTA’s (sendmail, qmail, postfix, etc) spool this message for later delivering. Spammers ussualy never return because their mail agents are too stupid to do so. Usually, they are spamming from compromited computers using very small scripts which are connecting SMTP servers like headless chicken. Yes, some spammers have more intelligent MTA, but they are able to be identified by other antispam tools during the time when waiting for 2nd attempt. You can find more info about greylisting method on www.greylisting.org.I have used a recommendation to identify all incoming mails on unique triplet for identifying a mail during my Qmail greylisting implementation. This unique triplet consists of the envelope sender address, the envelope recipient and the IP address of incoming server. If this triplet occurs for the first time, we will temporary reject the e-mail (reply code 421). All correctly working MTA’s will return in several minutes and will try again. In this time, we already know the triplet and the mail is accepted. Together with RBL filtering (sbl-xbl.spamhaus.org) it is a very effective solution. Here are some statistic data during last several days from one of Qmail servers: RBL denied connections: 6712 Many greylist implementations use a database (MySQL or PostgreSQL) for storing the data, but it looks as an overhead for me. Therefore I used simple files for storing all those info. The script is written in perl (the performance is fast enough for the file processing) and it is called within the smtp daemon (qmail-smtpd). It will decide if the mail is accepted or not on a return code of the called script. The point is that we will create empty files, all the info is stored in the names of files (unique triplet) and in the creation and modification time (ctime and mtime). The very first step is to patch the qmail-smtpd.c. I have used the Guenther Mair idea (he used PostgreSQL and C for greylisting): |
+#define GREYLIST_STATFILE “/var/qmail/control/greylist”+void die() { _exit(111); } + int safewrite(fd,buf,len) int fd; char *buf; int len; { int r; @@ -49,6 +55,8 @@ void die_ipme() { out(“421 unable to figure out my IP addresses (#4.3.0)rn”); flush(); _exit(1); } void straynewline() { out(“451 See http://pobox.com/~djb/docs/smtplf.html.rn”); flush(); _exit(1); } +void err_tempfail() { out(“421 temporary envelope failure (#4.3.0)rn”); } +int envelope_scanner() | |
Greylisting (volani sciptu bin/greylist) aktivujeme vytvorenim (prazdneho) souboru /var/qmail/control/greylist. Vlastní perlovský program má v sobě ještě proceduru pro čištění adresáře pro kontrolní soubory. Tento adresář (/var/spool/greylist) musí existovat a uživatel, pod kterým běží qmail-smtpd (qmail, vpopmail), do něj musí mít právo zapisovat. V programu je také implementován zakladní whitelist a blacklist na IP adresy. | Greylisting (calling the script bin/greylist from smtp daemon) is activated by touching file /var/qmail/control/greylist. The perl script itself has a procedure for cleaning up the directory where the control files are stored. This directory (/var/spool/greylist) has to exist and the user the qmail-smtpd is running under has to have permission to write there. There is also a simple blacklist and whitelist implemented there. |
# constantsour $LOGING = 2; # loging level: 0:nothing, 1:basic, 2:verbose, 3:debug our $GREYDIR = “/var/spool/greylist”; our $CLEAN = $GREYDIR .”/clean”; our @WHITELIST = (“127.0.0.1″,”88.10.175.111”); our @BLACKLIST = (“62.18.116.86”); # mail info # time related variables # exit codes ####################################### # add a local address into the @WHITELIST # and index lists # functions sub debug { sub touch { sub _exit { sub cleanup { } # first, do a clean up debug(1,”Checking $m_from -> $m_to ($m_ip)”); # isn’t it blacklisted? # isn’t it whitelisted? # compose a file name my $filename = “$GREYDIR/grey:$m_to:$m_from:$m_ip”; if (-f $filename) { # non-patient sender: }else{
| |
Komentáře vítány | Comments are welcome |