[Mimedefang] filter_before

Jonas Eckerman jonas_lists at frukt.org
Thu Oct 23 06:05:35 EDT 2008


Jonas Eckerman wrote:
> I think I'll put in a check for $TerminateAndDiscard as well (so that we 
> can restream before parsing as well), and then I'll start using it here 
> (should be within the next couple of days).

Been running with filter_before here for a couple of days now. It 
now checks $TerminateAndDiscard so that restreaming can be done 
before parsing the mail as well.

It seems to work. Patches attached. I hope the man page patch 
isn't too bad (it was done quickly).

Regards
/Jonas

-- 
Jonas Eckerman, FSDB & Fruktträdet
http://whatever.frukt.org/
http://www.fsdb.org/
http://www.frukt.org/
-------------- next part --------------
--- mimedefang.pl	Fri Aug 15 20:03:41 2008
+++ mimedefang.pl.data	Mon Oct 20 17:41:08 2008
@@ -5517,10 +5517,32 @@
     if (!open(RESULTS, ">RESULTS")) {
 	fatal("$MsgID: Could not open RESULTS file: $!");
 	return -1;
     }
 
+    # Call pre-pre-scan filter if defined
+    if (defined(&filter_before)) {
+	push_status_tag("In filter_before");
+	filter_before();
+	pop_status_tag();
+	# Have we allreeady decided to reject or discard?
+	if (message_rejected()) {
+	    md_syslog('debug', "$MsgID: filter_before rejected or discarded.");
+	    signal_unchanged();
+    	    signal_complete();
+    	    return 0;
+    	}
+	# If stream_by_domain tells us to discard, do so...
+	if ($TerminateAndDiscard) {
+	    write_result_line("D", "");
+	    signal_unchanged();
+	    md_syslog('debug', "$MsgID: filter_before set TerminateAndDiscard flag.");
+	    signal_complete();
+	    return 0;
+	}
+    }
+
     my $entity;
     my $parser;
     if (defined(&filter_create_parser)) {
 	$parser = filter_create_parser();
 	if (!defined($parser) ||
-------------- next part --------------
--- mimedefang-filter.5.in	Fri Aug 15 20:03:41 2008
+++ mimedefang-filter.5.in.data	Tue Oct 21 13:20:44 2008
@@ -19,16 +19,21 @@
 directory and the e-mail message is split into parts in this directory.
 Each part is represented internally as an instance of MIME::Entity.
 
 .PP
 2) If the file \fB at CONFDIR_EVAL@/mimedefang-filter.pl\fR defines a
+Perl function called \fBfilter_before\fR, it is called before an
+e-mail is parsed.  Any return value is ignored.
+
+.PP
+3) If the file \fB at CONFDIR_EVAL@/mimedefang-filter.pl\fR defines a
 Perl function called \fBfilter_begin\fR, it is called with a single
 argument consisting of a MIME::Entity representing the parsed e-mail
 message.  Any return value is ignored.
 
 .PP
-3) For each \fIleaf\fR part of the mail message, \fBfilter\fR is
+4) For each \fIleaf\fR part of the mail message, \fBfilter\fR is
 called with four arguments: \fBentity\fR, a MIME::Entity object;
 \fBfname\fR, the suggested filename taken from the MIME
 Content-Disposition header; \fBext\fR, the file extension, and
 \fBtype\fR, the MIME Content-Type value.  For each \fInon-leaf\fR
 part of the mail message, \fBfilter_multipart\fR is called with the
@@ -44,11 +49,11 @@
 Note that both \fBfilter\fR and \fBfilter_multipart\fR are optional.
 If you do not define them, a default function that simply accepts each
 part is used.
 
 .PP
-4) After all parts have been processed, the function \fBfilter_end\fR
+5) After all parts have been processed, the function \fBfilter_end\fR
 is called if it has been defined.  It is passed a single argument consisting
 of the (possibly modified) MIME::Entity object representing the message
 about to be delivered.
 
 .SH DISPOSITION
@@ -694,12 +699,12 @@
 
 .SH GLOBAL VARIABLES SET BY MIMEDEFANG.PL
 
 The following global variables are set by \fBmimedefang.pl\fR and are
 available for use in your filter.  All of these variables are always
-available to filter_begin, filter, filter_multipart and filter_end.
-In addition, some of them are available in \fBfilter_relay\fR,
+available to filter_before, filter_begin, filter, filter_multipart and
+filter_end.  In addition, some of them are available in \fBfilter_relay\fR,
 \fBfilter_sender\fR or \fBfilter_recipient\fR.  If this is the case,
 it will be noted below.
 
 .TP
 .B %Features
@@ -1327,11 +1332,11 @@
 directory is created and its pathname returned.
 
 .TP
 .B change_sender($sender)
 This function changes the envelope sender to $sender.  It can only
-be called from \fBfilter_begin\fR or any later function.  Please note
+be called from \fBfilter_before\fR or any later function.  Please note
 that this function is \fIonly\fR supported with Sendmail/Milter 8.14.0
 or newer.  It has \fIno effect\fR if you're running older versions.
 
 .TP
 .B add_recipient($recip)
@@ -1405,11 +1410,11 @@
 .B stream_by_domain()
 \fIDo not use this function unless you have Sendmail 8.12 and locally-
 submitted e-mail is submitted using SMTP.\fR
 
 This function should \fIonly\fR be called at the very beginning of
-filter_begin(), like this:
+filter_before() or filter_begin(), like this:
 
 .nf
 	sub filter_begin {
 		if (stream_by_domain()) {
 			return;
@@ -1462,11 +1467,11 @@
 .B stream_by_recipient()
 \fIDo not use this function unless you have Sendmail 8.12 and locally-
 submitted e-mail is submitted using SMTP.\fR
 
 This function should \fIonly\fR be called at the very beginning of
-filter_begin(), like this:
+filter_before() or filter_begin(), like this:
 
 .nf
 	sub filter_begin {
 		if (stream_by_recipient()) {
 			return;
@@ -1993,12 +1998,12 @@
 If you invoked \fBmimedefang\fR with the \fB\-t\fR option and have
 defined a filter_recipient routine, it is called.
 
 .TP
 .B 5. END OF SMTP DATA
-filter_begin is called.  For each MIME part, filter is called.  Then
-filter_end is called.
+filter_before is called. filter_begin is called.  For each MIME part,
+filter is called.  Then filter_end is called.
 
 .SH PRESERVING RELAY INFORMATION
 
 .PP
 Most organizations have more than one machine handling internet
@@ -2043,11 +2048,11 @@
 When the secondary MX hosts relay to the primary MX host, $RelayAddr
 and $RelayHostname will be set based on the IP validation header.  If
 MIMEDefang notices this header, it sets the global variable $WasResent
 to 1.  Since you don't want to trust the header unless it was set by
 one of your secondary MX hosts, you should put this code in
-filter_begin:
+filter_before:
 
 .nf
 	if ($WasResent) {
 		if ($RealRelayAddr ne "ip.of.secondary.mx" and
 		    $RealRelayAddr ne "ip.of.tertiary.mx") {
@@ -2094,10 +2099,14 @@
 Not guaranteed to be available to any other function, not even
 from one filter_recipient call to the next, when receiving a
 multi-recipient email message.
 
 .TP
+.B In filter_before
+Available to filter_before, filter_begin, filter and filter_end
+
+.TP
 .B In filter_begin
 Available to filter_begin, filter and filter_end
 
 .TP
 .B In filter
@@ -2107,13 +2116,13 @@
 .B In filter_end
 Available within filter_end
 
 .PP
 The "built-in" globals like $Subject, $Sender, etc. are always available
-to filter_begin, filter and filter_end. Some are available to filter_relay,
-filter_sender or filter_recipient, but you should check the documentation
-of the variable above for details.
+to filter_before, filter_begin, filter and filter_end. Some are available to
+filter_relay, filter_sender or filter_recipient, but you should check the
+documentation of the variable above for details.
 
 .SH MAINTAINING STATE
 
 .PP
 There are four basic groups of filtering functions:
@@ -2130,11 +2139,11 @@
 .B 3
 filter_recipient
 
 .TP
 .B 4
-filter_begin, filter, filter_multipart, filter_end
+filter_before, filter_begin, filter, filter_multipart, filter_end
 
 .PP
 In general, for a given mail message, these groups of functions may
 be called in completely different Perl processes.  Thus, there is
 \fIno way\fR to maintain state inside Perl between groups of functions.


More information about the MIMEDefang mailing list