Has anyone developed a really good defense against email injection attacks?

I'm waging a prolonged campaign against these luser hordes on a number
of non-profit sites I help maintain. I've tried to secure all of the
feedback forms using the function below that I cobbled together from
various php security sites on the web. I also set it up so that every
time a 'successful' attempt is made, it gets logged to a database
before it is emailed.

The script worked well for 2-3 weeks and I enjoyed watching the
spammers bounce off of the firewall. Unfortunately, they finally
figured out how to get through last night and sent out hundreds of
emails on a couple dozen sites. I quickly took all of the forms down
to plug the breach but I can't keep them down indefinitely.

Few questions -

 - Does anyone have a better regex to use to detect email injection
attacks? Part of the problem seems to be that they figured out what
values I'm searching for and created a new attack that uses character
references (ex. Y etc) to get through.

 - The successful attacks that I logged in my database weren't helpful
because they had already been converted to HTML. Is there a better way
to store _exactly_ what they entered into the field in the database?

 - Another way to stop these attacks would be to reject any mail field
over a specified length. Is there a limit to how long an email address
can be? I don't want to set a limit (ex. 50 chars) that excludes

 - The most foolproof solution I can think of would be to continue
logging the successful entries to a database and _not_ send the email.
That way even if they get through, no emails get sent. The form would
log the feedback and send an email to the admin that a comment is
available for viewing. Is it time to abandon using mail() for all user
contributed data?

Looking forward to the discussion,

- schnippy


#-----------------------------------------------------------------------
 /**
 * Secures field against email header injection attacks.
 *
 * USAGE:
 *      secureFeedbackValue($_POST["to"]);
 *      mail($_POST["to"], $_POST["subject"], $_POST["message"]);
 *
 * @param $value value to be cleansed of evil
 */

function secureFeedbackValue( $value )
{
        # mail adress(ess) for reports...
        $report_to = "[EMAIL PROTECTED]";

        # array holding strings to check...
        $suspicious_str = array
        (
            "\r",
            "\n",
                "bcc",
                "cc:",
                "boundary=",
                "charset",
                "content-disposition",
                "content-type",
                "content-transfer-encoding",
                "errors-to",
                "in-reply-to",
                "message-id",
                "mime-version",
                "multipart/mixed",
                "multipart/alternative",
                "multipart/related",
                "reply-to",
                "x-mailer",
                "x-sender",
                "x-uidl"
        );

        // remove added slashes from $value...

        $value = stripslashes($value);
        
        foreach($suspicious_str as $suspect)
        {
                # checks if $value contains $suspect...
                if(eregi($suspect, strtolower($value)))
                {
                        $ip = (empty($_SERVER['REMOTE_ADDR'])) ? 'empty' : 
$_SERVER['REMOTE_ADDR'];
                        $rf = (empty($_SERVER['HTTP_REFERER'])) ? 'empty' : 
$_SERVER['HTTP_REFERER'];
                        $ua = (empty($_SERVER['HTTP_USER_AGENT'])) ? 'empty' :
$_SERVER['HTTP_USER_AGENT'];
                        $ru = (empty($_SERVER['REQUEST_URI'])) ? 'empty' : 
$_SERVER['REQUEST_URI'];
                        $rm = (empty($_SERVER['REQUEST_METHOD'])) ? 'empty' :
$_SERVER['REQUEST_METHOD'];
        
                        if(isset($report_to) && !empty($report_to))
                        {
                                @mail
                                (
                                $report_to
                                ,"[ABUSE] mailinjection @ " . 
$_SERVER['HTTP_HOST'] . " by " . $ip
                                ,"Stopped possible mail-injection @ " . 
$_SERVER['HTTP_HOST'] .
                                " by " . $ip . " (" . date('d/m/Y
H:i:s') . ")\r\n\r\n" .
                                "*** IP/HOST\r\n" . $ip . "\r\n\r\n" .
                                "*** USER AGENT\r\n" . $ua . "\r\n\r\n" .
                                "*** REFERER\r\n" . $rf . "\r\n\r\n" .
                                "*** REQUEST URI\r\n" . $ru . "\r\n\r\n" .
                                "*** REQUEST METHOD\r\n" . $rm . "\r\n\r\n" .
                                "*** SUSPECT\r\n--\r\n" . $value . "\r\n--"
                                );
                        }
        
                        die ('Snakes on the plane.');
                }
        }
}

--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php

Reply via email to