#! /bin/sh /usr/share/dpatch/dpatch-run ## 10_spamass-milter-cvs-2006-06-17-rejecttext-and-internal-network2.dpatch by Herbert Straub ## ## All lines beginning with `## DP:' are a description of the patch. ## DP: Customizeable reject text, internal networks and customizeable reject ## DP: text and score @DPATCH@ --- spamass-milt/spamass-milter.cpp.ORIG 2006-06-17 11:06:30.000000000 +0200 +++ spamass-milt/spamass-milter.cpp 2006-06-18 14:04:06.000000000 +0200 @@ -154,14 +154,21 @@ int flag_debug = (1<= nn with an SMTP error.\n" " use -1 to reject any messages tagged by SA." << endl; + cout << " -R RejectText: using this Reject Text." << endl; + cout << " -s nn: reject messages from the internal network\n" + " with a score >= nn with an SMTP error.\n" + " use -1 to reject any messages tagged by SA.\n" + " This require the specification of the internal network\n" + " with the -I option." << endl; + cout << " -S RejectText: specifiy a alternate reject text for rejects\n" + " coming from the internal network" << endl; cout << " -u defaultuser: pass the recipient's username to spamc.\n" " Uses 'defaultuser' if there are multiple recipients." << endl; cout << " -x: pass email address through alias and virtusertable expansion." << endl; @@ -307,6 +351,14 @@ exit(EX_USAGE); } + /* Set standard reject text */ + if (rejecttext == NULL) { + rejecttext = strdup ("Blocked by SpamAssassin"); + } + if (rejecttext_intern == NULL) { + rejecttext_intern = strdup ("Blocked by Spamassassin"); + } + if (pidfilename) { unlink(pidfilename); @@ -377,8 +429,20 @@ debug(D_UORI, "u_or_i: newstring: <%s>", newstring.c_str()); oldsize = callsetter(*assassin,setter)(newstring); - - if (!dontmodify) + + struct context *sctx = (struct context*)smfi_getpriv(ctx); + bool internal_network=false; + if (ip_in_networklist(sctx->connect_ip, &internalnets)) { + internal_network=true; + debug(D_NET, "%s is in our internal list(update_or_insert)", + inet_ntoa(sctx->connect_ip)); + } + + /* + * if -M then dontmodify headers + * if -O and -n, then dont modify headers (mail from internal network) + */ + if (!(dontmodify || (dontmodify_intern && internal_network))) { if (newstring != oldstring) { @@ -422,14 +486,26 @@ update_or_insert(assassin, ctx, assassin->spam_flag(), &SpamAssassin::set_spam_flag, "X-Spam-Flag"); update_or_insert(assassin, ctx, assassin->spam_status(), &SpamAssassin::set_spam_status, "X-Spam-Status"); + bool internal_network = false; + struct context *sctx = (struct context*)smfi_getpriv(ctx); + + if (ip_in_networklist(sctx->connect_ip, &internalnets)) + { + internal_network = true; + debug(D_NET, "%s is in our internal list - accepting message", + inet_ntoa(sctx->connect_ip)); + } + /* Summarily reject the message if SA tagged it, or if we have a minimum score, reject if it exceeds that score. */ - if (flag_reject) + if (flag_reject || flag_reject_intern) { bool do_reject = false; - if (reject_score == -1 && !assassin->spam_flag().empty()) + + if ((flag_reject && reject_score == -1 && !assassin->spam_flag().empty()) || + (flag_reject_intern && reject_score_intern == -1 && !assassin->spam_flag().empty())) do_reject = true; - if (reject_score != -1) + if (reject_score != -1 || reject_score_intern != -1) { int score, rv; const char *spam_status = assassin->spam_status().c_str(); @@ -445,14 +521,15 @@ else { debug(D_MISC, "SA score: %d", score); - if (score >= reject_score) + if ((flag_reject && score >= reject_score) || + (flag_reject_intern && score >= reject_score_intern)) do_reject = true; } } if (do_reject) { debug(D_MISC, "Rejecting"); - smfi_setreply(ctx, "550", "5.7.1", "Blocked by SpamAssassin"); + smfi_setreply(ctx, "550", "5.7.1", (internal_network) ?(rejecttext_intern) : (rejecttext)); if (flag_bucket) @@ -560,7 +637,9 @@ // However, only issue the header replacement calls if the content has // actually changed. If SA didn't change subject or content-type, don't // replace here unnecessarily. - if (!dontmodifyspam && assassin->spam_flag().size()>0) + // + // if -O and -n, then don't modiy Mail (mail from internal network) + if (!(dontmodifyspam || (dontmodifyspam_intern && internal_network)) && assassin->spam_flag().size()>0) { update_or_insert(assassin, ctx, assassin->subject(), &SpamAssassin::set_subject, "Subject"); update_or_insert(assassin, ctx, assassin->content_type(), &SpamAssassin::set_content_type, "Content-Type");