procmail
[Top] [All Lists]

Re: notifications

2001-12-02 10:05:50
At 08:43 2001-12-02 -0500, rdicaire(_at_)ardynet(_dot_)com did say:

  GOTCHA=`formail -xTo:`

Bzzt. List messages, Bcc's, CC's, even multiple To:'s will result in a failure here.

      :0 fhwc

'f' and 'c' are rather exclusive in nature (not that this won't do something - it's just unlikely to produce the desired effect) - usually you either copy, or you filter the current copy. In your case, you want to eliminate 'f', because THIS recipe is _delivering_ to sendmail, not filtering a message to be handed to the next rule.

Since you're not _really_ using the rule as a filter AND because you're using copy (i.e. failure here doesn't mean you don't still have the message), w is also unnecessary.

     | (formail -r -I"Precedence: virus alert" ; \

That's not a commonly-accepted precedence. While RFC 822 and 1327, etc don't specify Precedence: as a header, if you run sendmail, you can see what it normally recognizes as precendence:

$ grep ^P /etc/mail/sendmail.cf
        Pfirst-class=0
        Pspecial-delivery=100
        Plist=-30
        Pbulk=-60
        Pjunk=-100

The ancient RFC806 specifies some other textual values which are (or were) used by US Military, but the above should be concidered the standard list to expect. As such, "special-delivery" would seem most appropriate to an "alert" message, if you REALLY need to set a Precedence. If you MUST use a nonstandard string, "alert" seems like a better alternative, although, as the above should demonstrate, it will be meaningless to the MTA. Most email clients hide this header from view, so it isn't as if the recipient is going to see it to know what it is.

          echo " On behalf of ${GOTCHA} This mail server does accept
mail with virus vulnerable at
tachments - Mail rejected.") | $SENDMAIL -t

Bzzt. sendmail -t will scan the message headers for recipients and mail this to them. There's a high probability you'll piss off a lot of people when you send your notification To: a mailing list, and Cc: who knows how many unfortunate recipients of that mailing list message. It is unlikely you will manage to send this message to the person who sent the virus.

In the case of mailing lists, you cannot rely on the envelope sender for the same reason - that'll point to the mailing list address because that's who sent you the message.


If you have two separate sets of conditions which result in the same action, you should consider simply having them set variables:

:0
* conditions
{
        $VIRUS=$MATCH, or some static text, as appropriate
}

# Subsequent to the FIRST contion, all the "else" conditions use the E flag:

:0E
* conditions
{
        $VIRUS=whatever

        # perhaps _this_ virus condition is known to be the type where the
        # from address happens to be valid, and the message would have come
        # from the infected user.  If so, we set a variable to contain the
        # address that we'll be sending the reply to.  Don't do this
        # willy-nilly for all viruses - many forge the from.
        :0
        * From:[        ]*\/[^  ].*
        {
                $VREPLY=$MATCH
        }
}

# On your common action - note no condition necessary here, though you
# _could_ check for a non-empty $VIRUS by using the following condition:
# * ! VIRUS ?? ^^^^

:0A
{
        # first, deal with looped messages - if we entered this rule and
        # our loop header is found, some idiot sent us our own post, or an
        # autoreply to it.  Don't even bother.  Note that we're doing this
        # check within a block where we know we're going to generate a
        # notice and possibly bounce an alert to the sender *AND* the message
        # appears to contain a virus.
        :0
        * $ ^X-Loop: $LOOPALERT
        /dev/null

        # First, file our _original and unmodified_ copy of the message.
        # Note the LOCK flag on this - if you're delivering to a mailbox (or
        # to a program which may in turn deliver to a mailbox), you should
        # always LOCK.
        :0c:
        ${VIRUSDUMP}

        # Now, ditch the BODY (we're going to use the original headers in
        # our notices, but the body isn't going to be sent back).  You could
        # use a formail construct, but this is quicker.  I'm open to
        # alternatives.
        :0fb
        | cat /dev/null

        # Then "quote" the original headers (which should also further
        # disable them from interpretation by crappy mail clients such as
        # OutBreak).  BECAUSE WE DO THIS, the following recipes don't
        # need a 'h' flag, which you'd otherwise use, *AND* they cannot
        # actually match for message header content - we expect all matching
        # against the message has been performed by this point and we're in
        # the final stages of producing the notifications.  If you really
        # wanted to waste the extra cycles, you could do this filter within
        # the delivery of each of the notifications, preceeding the cat
        # operation.
        :0fh
        | sed -e 's/^/\> /'

        # If $VREPLY isn't blank, then we have an address we should
        # send the notification to -- otherwise, this rule won't
        # trigger, and we shouldn't email a notification.
        :0c
        * ! VREPLY ?? ^^^^
        | ( cat $AUTOREPLY/virusbounce.msg - | \
formail -I "Subject: Notification - potential VIRUS $VIRUS found in your message" \
          -I "X-Loop: $LOOPALERT" \
          -I "From: $BOUNCER" ) | $SENDMAIL -f$BOUNCER $VREPLY

        # Finally, we take the ORIGINAL (not a copy - see, no 'c' flag)
        # THOUGH AT THIS POINT, MODIFIED BECAUSE OF THE FILTERS ABOVE THAT
        # DISCARDED THE BODY AND QUOTED THE ORIGINAL HEADERS, and transform
        # it into a notification message to the original intended recipient.
        :0f
        | cat $AUTOREPLY/virusnotice.msg - | \
                formail -I "Subject: notification of VIRUS $VIRUS" \
                -I "X-Loop: $LOOPALERT" \
                -I "From: $BOUNCER"
}

This keeps your autoreply and notification stuff in one convenient block rather than having it duplicated. See 'man procmailrc' for info on the flags.

$AUTOREPLY is a path to where you put autoreply texts
$LOOPALERT is a loop identifier text used to identify
$BOUNCER is the address you wish to have the bounce appear to be from.

Both of the notices should start and end with a blank line to separate them from the send message header and the header which it copies in the body.

Suggested texts might be like so:

virusbounce.msg:

The message identified by the headers below was processed by our server and
determined to possibly contain a virus or other potentially hazardous
attachment or embedded construct.  As such, the message has not been
delivered to its intended recipient here, although they have recieved a
similar notice as to its disposition.

---

Note that you don't need to tell them who you filtered it "on behalf of" - they'll have the headers, and they can figure it out from there (if they sent the message to a list for instance, they may not even know your user - but the list involvement should be clear from the headers).

virusnotice.msg:

We received a message, idenfitied by the headers below, which was determined to possibly contain a virus or other potentially hazardous attachment. Although we may have send an automated message to the sender, if you know the sender, you should contact them and inform them of the disposition of their message. If you were expecting an executable attachment from this individual, you should request that they send it to you in an archive file (such as a .ZIP), which would require a deliberate action on their part to send, and for you to extract, and is thus a much more appropriate method of sending executable programs and scripts.

---

What I'd like it to further do is email the intended recipient,
notifying them that an email was rejected, who sent it, and what the attachment was.

You don't indicate where you're executing the script.

If this is this some ill-conceived "forward my virtualized domain mail from my ont ISP mailbox running as my personal userid, to various friends based on recipient," you'll be gravely dissappointed since procmail isn't an MTA, and you'll have endless joy dealing with BCC's and multiple recipients.

If the above is in /etc/.procmailrc, you're in luck - the default delivery will continue along to the intended recipient(s) (provided you don't _deliver_ the original message, but only use copies to send notifications, etc). After identifying that the message is infected (and once you've set your variables or whatever to identify the name of the virus, etc.), pass a copy of the message through a "f"ilter rule and construct a new message which _becomes_ the message being delivered to DEFAULT. See the final rule in the common rule used above.

As per my disclaimer, this is untested code.

---
 Sean B. Straw / Professional Software Engineering

 Procmail disclaimer: <http://www.professional.org/procmail/disclaimer.html>
 Please DO NOT carbon me on list replies.  I'll get my copy from the list.

_______________________________________________
procmail mailing list
procmail(_at_)lists(_dot_)RWTH-Aachen(_dot_)DE
http://MailMan.RWTH-Aachen.DE/mailman/listinfo/procmail

<Prev in Thread] Current Thread [Next in Thread>