#include "policyd.h"
/*
*
*
* Policy Daemon
*
* policy daemon is used in conjuction with postfix to combat spam.
*
* Copyright (C) 2004 Cami Sardinha (cami@mweb.co.za)
*
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
* Free Software Foundation; either version 2 of the License, or (at your
* option) any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation Inc.,
* 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
*
*
*/
/*
* function: throttle_sasl
* purpose: throttle users based on SASL info
* return: 0 for new record, 1 for update
*/
int
throttle_sasl (unsigned int fd)
{
if(DEBUG > 0)
logmessage("DEBUG: fd: %d checking throttle-sasl\n", fd);
/* user is not in the database */
if(strlen(mysqlchar_array[fd][0]) < 2)
{
if(atol(triplet_array[fd][3]) >= atol(mysqlchar_array[fd][7]))
goto abuse;
logmessage("rcpt=%lu, throttle=new(a), host=%s, from=%s, to=%s, size=%d/%d, "
"quota=%d/%d, count=1/%d(1), rcpt=1/%d(1), threshold=0%|0%|0%, sasl_username=%s\n",
rcpt_count, /* recipient count */
host_array[fd][2], /* host */
triplet_array[fd][1], /* from */
triplet_array[fd][2], /* to */
atol(triplet_array[fd][3]), /* size_cur */
atol(mysqlchar_array[fd][7]), /* size_max */
atol(triplet_array[fd][3]), /* quota_cur */
atol(mysqlchar_array[fd][5]), /* quota_max */
atol(mysqlchar_array[fd][1]), /* count_max */
atol(mysqlchar_array[fd][9]), /* rcpt_max */
triplet_array[fd][4] /* sasl_username */
);
/* build up & execute query */
snprintf(mysqlquery_array[fd], 512,
"INSERT DELAYED INTO throttle "
"(_date,_from,_quota_cur,_quota_max,_rcpt_max,_mail_size,_count_max, _time_limit)"
" VALUES (%d, '%s', %d, %ld, %ld, %ld, %ld, %ld)",
timenow,
triplet_array[fd][4],
atoi(triplet_array[fd][3]),
atol(mysqlchar_array[fd][5]),
atol(mysqlchar_array[fd][9]),
atol(mysqlchar_array[fd][7]),
atol(mysqlchar_array[fd][1]),
atol(mysqlchar_array[fd][6]));
if(db_doquery(fd) == -1) return(db_failure(fd, "throttle"));
/* sender does not exist in the database, insert and allow */
return (0);
}
/* if sender is sending a message bigger than allowed, reject */
if(atol(triplet_array[fd][3]) >= atol(mysqlchar_array[fd][7]))
{
abuse:
logmessage("rcpt=%lu, throttle=abuse(f), host=%s, from=%s, to=%s, size=%d/%d, "
"quota=%d/%d, count=%d/%d(%d), rcpt=%d/%d(%d), threshold=%d%|%d%|%d%, sasl_username=%s\n",
rcpt_count, /* recipient count */
host_array[fd][2], /* host */
triplet_array[fd][1], /* from */
triplet_array[fd][2], /* to */
atol(triplet_array[fd][3]), /* size_cur */
atol(mysqlchar_array[fd][7]), /* size_max */
atol(mysqlchar_array[fd][4]), /* quota_cur */
atol(mysqlchar_array[fd][5]), /* quota_max */
atol(mysqlchar_array[fd][2]), /* count_cur */
atol(mysqlchar_array[fd][1]), /* count_max */
atol(mysqlchar_array[fd][8]), /* count_tot */
atol(mysqlchar_array[fd][10]), /* rcpt_cur */
atol(mysqlchar_array[fd][9]), /* rcpt_max */
atol(mysqlchar_array[fd][11]), /* rcpt_tot */
tquota[fd], /* quota percentage */
tcount[fd], /* count percentage */
trcpt[fd], /* rcpt percentage */
triplet_array[fd][4] /* sasl_username */
);
return (-3);
}
/* if time has expired, clear quota for size+message count */
if(timenow > (unsigned int)(atol(mysqlchar_array[fd][6])+atol(mysqlchar_array[fd][3])))
{
logmessage("rcpt=%lu, throttle=clear(a), host=%s, from=%s, to=%s, size=%d/%d, "
"quota=%d/%d, count=1/%d(%d), rcpt=1/%d(%d), threshold=0%|0%|0%, sasl_username=%s\n",
rcpt_count, /* recipient count */
host_array[fd][2], /* host */
triplet_array[fd][1], /* from */
triplet_array[fd][2], /* to */
atol(triplet_array[fd][3]), /* size_cur */
atol(mysqlchar_array[fd][7]), /* size_max */
atoi(triplet_array[fd][3]), /* quota_cur */
atol(mysqlchar_array[fd][5]), /* quota_max */
atol(mysqlchar_array[fd][1]), /* count_max */
atol(mysqlchar_array[fd][8]), /* count_tot */
atol(mysqlchar_array[fd][9]), /* rcpt_max */
atol(mysqlchar_array[fd][11])+1, /* rcpt_tot */
triplet_array[fd][4] /* sasl_username */
);
/* build up & execute query */
snprintf(mysqlquery_array[fd], 512,
"UPDATE throttle SET"
" _rcpt_cur=1,"
" _rcpt_tot=_rcpt_tot+1,"
" _date=%d,"
" _quota_cur=%d,"
" _count_cur=1,"
" _count_tot=_count_tot+%d,"
" _abuse_tot=_abuse_tot+_abuse_cur,"
" _abuse_cur=0"
" WHERE _from='%s'",
timenow,
atoi(triplet_array[fd][3]),
instance_inc[fd],
triplet_array[fd][4]);
if(db_doquery(fd) == -1) return(db_failure(fd, "throttle"));
/* counter reset because of expiry, allow mail */
return (0);
}
/* if the sender is past his quota and the timeout has not expired */
/* then reject the message */
if(atol(mysqlchar_array[fd][2]) >= atol(mysqlchar_array[fd][1]) || /* count */
atol(mysqlchar_array[fd][4]) >= atol(mysqlchar_array[fd][5]) || /* quota */
atol(mysqlchar_array[fd][10]) >= atol(mysqlchar_array[fd][9])) /* rcpt max */
{
if((instance_inc[fd] == 0) && (atol(mysqlchar_array[fd][10]) < atol(mysqlchar_array[fd][9])))
goto update;
logmessage("rcpt=%lu, throttle=abuse(f), host=%s, from=%s, to=%s, size=%d/%d, "
"quota=%d/%d, count=%d/%d(%d), rcpt=%d/%d(%d), threshold=%d%|%d%|%d%, sasl_username=%s\n",
rcpt_count, /* recipient count */
host_array[fd][2], /* host */
triplet_array[fd][1], /* from */
triplet_array[fd][2], /* to */
atol(triplet_array[fd][3]), /* size_cur */
atol(mysqlchar_array[fd][7]), /* size_max */
atol(mysqlchar_array[fd][4]), /* quota_cur */
atol(mysqlchar_array[fd][5]), /* quota_max */
atol(mysqlchar_array[fd][2]), /* count_cur */
atol(mysqlchar_array[fd][1]), /* count_max */
atol(mysqlchar_array[fd][8]), /* count_tot */
atol(mysqlchar_array[fd][10]), /* rcpt_cur */
atol(mysqlchar_array[fd][9]), /* rcpt_max */
atol(mysqlchar_array[fd][11]), /* rcpt_tot */
tquota[fd], /* quota percentage */
tcount[fd], /* count percentage */
trcpt[fd], /* rcpt percentage */
triplet_array[fd][4] /* sasl_username */
);
/* build up & execute query */
snprintf(mysqlquery_array[fd], 512,
"UPDATE throttle SET"
" _abuse_cur=1"
" WHERE _from='%s'",
triplet_array[fd][1]);
if(db_doquery(fd) == -1) return(db_failure(fd, "throttle"));
return (-5);
}
update:
/* if the sender has not reached his quota, increase count */
logmessage("rcpt=%lu, throttle=update(%c), host=%s, from=%s, to=%s, size=%d/%d, "
"quota=%d/%d, count=%d/%d(%d), rcpt=%d/%d(%d), threshold=%d%|%d%|%d%, sasl_username=%s\n",
rcpt_count, /* recipient count */
tattrib_array[fd][0], /* attribute state */
host_array[fd][2], /* host */
triplet_array[fd][1], /* from */
triplet_array[fd][2], /* to */
atol(triplet_array[fd][3]), /* size_cur */
atol(mysqlchar_array[fd][7]), /* size_max */
atol(mysqlchar_array[fd][4])+atol(triplet_array[fd][3]), /* quota_cur */
atol(mysqlchar_array[fd][5]), /* quota_max */
atol(mysqlchar_array[fd][2])+instance_inc[fd], /* count_cur */
atol(mysqlchar_array[fd][1]), /* count_max */
atol(mysqlchar_array[fd][8])+instance_inc[fd], /* count_tot */
atol(mysqlchar_array[fd][10])+1, /* rcpt_cur */
atol(mysqlchar_array[fd][9]), /* rcpt_max */
atol(mysqlchar_array[fd][11])+1, /* rcpt_tot */
tquota[fd], /* quota percentage */
tcount[fd], /* count percentage */
trcpt[fd], /* rcpt percentage */
triplet_array[fd][4] /* sasl_username */
);
/* build up & execute query */
snprintf(mysqlquery_array[fd], 512,
"UPDATE throttle SET"
" _rcpt_cur=_rcpt_cur+1,"
" _rcpt_tot=_rcpt_tot+1,"
" _quota_cur=_quota_cur+%ld,"
" _count_cur=_count_cur+%d,"
" _count_tot=_count_tot+%d,"
" _abuse_cur=0"
" WHERE _from='%s'",
atol(triplet_array[fd][3]),
instance_inc[fd],
instance_inc[fd],
triplet_array[fd][4]);
if(db_doquery(fd) == -1) return(db_failure(fd, "throttle"));
return (0); /* never reached */
}
/* EOF */
syntax highlighted by Code2HTML, v. 0.9.1