
kyle-qmail at memoryhole
Apr 20, 2009, 9:33 AM
Post #8 of 9
(1932 views)
Permalink
|
-----BEGIN PGP SIGNED MESSAGE----- Hash: SHA1 On Monday, April 20 at 03:35 PM, quoth Paul Terry: > Giving rejections during an SMTP session provides a means for a > spammer to determine legitimate addresses. This is a common complaint, but is generally pointless. Consider what you're defending against: a vast zombie army of SMTP senders. They *will* figure out who your valid recipients are, whether you help them or not. For example, they can create a dummy domain (e.g. alksdflkaslk.com), and make you send your bounces there. If you send bounces at all, spammers have the collective ability to force you to reveal your legitimate addresses. And, since they're using stolen bandwidth, they don't care how much they use to force that information out of you... but I suspect you'd be somewhat annoyed if they decided to do that and waste your bandwidth. (Remember: vast zombie army - you can't blacklist 'em *all*.) Rejecting messages during the SMTP connection saves you bandwidth (you don't have to receive the whole message, and/or you don't have to send a bounce) and saves you disk space (smaller queue). Plus, it saves your reputation, as many blacklists (unfortunately) include joe-job victims. Yes, if you use SMTP-time rejections, spammers CAN use a dictionary attack to find out what your legitimate addresses are. But they can do that even without SMTP-time rejections. The only difference is that SMTP-time rejections save the spammers time and (a little) bandwidth... which they were probably stealing from someone *anyway*. > I think a greater problem is differentiating which bounces are as a > result of spam and which ones aren't. With this patch, bounces can > be sent to a dedicated box to address this problem without having to > worry about the effects that resource intensive code will have on > the main queue. Assuming that you CAN determine which ones are the result of spam, that's reasonable. It seems like a lot of resources to devote to handling bounces, especially since there's a few simple ways of reducing your workload, but if it seems reasonable to you... <shrug> cool. It's certainly a popular thing to use a separate IP address to send out bounces, to avoid getting your primary server blacklisted by trigger-happy blacklists. A few things come to mind as alternatives. First, your patch seems similar to the BOUNCEQUEUE patch (http://marc.info/?l=qmail&m=108605073822238&w=2). If I point BOUNCEQUEUE at a script that uses qmail-remote to forward the message, I think I've essentially replicated your patch, right? I think this script should do it... #!/bin/bash PATH=/var/qmail/bin:$PATH BOUNCEHOST=bounces.mydomain.com # read sender read -u 1 -d $'\0' sender # read recipients i=0 while read -u 1 -d $'\0' recipient ; do [ -z "$recipient" ] && break recipients[$i]="$recipient" i=$(($i+1)) done # send to bouncehost /var/qmail/bin/qmail-remote \ $BOUNCEHOST "$sender" "${recipients[@]}" | \ while read -d $'\0' result ; do case "$result" in K*) # success exit 0;; Z*) # temporary failure exit 71;; D*) # permanent failure exit 31;; esac done exit 71 # could not determine result Obviously, your script has its own log messages, so that's different, but the BOUNCEQUEUE patch is a LOT simpler. Heck, come to think of it, you don't even really need a *patch* to do this with netqmail. All you need is to point QMAILQUEUE to a script like the one above, that's been modified to send it off with qmail-remote if the message sender is null, and use qmail-queue otherwise. Though at that point, the scripting gets a little more complicated because of the file-descriptor requirements. Also... I don't know what anti-spam analysis system you're using, but if you use SpamAssassin, you can set up spamd on a dedicated host (or even multiple dedicated hosts) and contact it via spamc over the local network without needing a separate qmail instance. I have no idea what the overhead of that would be, and you'd lose the ability to send bounces from a different IP (which has its own benefits), but it's a way to offload the resource-intensive code for choosing whether or not to actually send each bounce. As far as your particular patch goes... you may want to have a look at qmail-rspawn.c to compare. For example, if qmail-remote returned non-zero for some reason---you define exitcode, but don't do anything with it (why?). That's probably not critical, since qmail-remote is supposed to ALWAYS return 0, but there's no point in defining exitcode if you're not going to use it. You're also mishandling the qmail-remote output; the output CAN be longer than 128 bytes, and if it is, you may never see the final message report, in which case ret will be 0, and you'll return an "unknown error from qmail-remote", even if the message was delivered correctly. Assuming qmail-remote returns a long output because of some detail of the message and the bounce server, this will cause a large number of duplicate bounces, where you never stop re-sending the bounce until it finally expires from the original queue. Obviously, that's bad. FYI, since you established the qrs structure with a buffer of 128 chars, the maximum you can get from a single substdio_get() call is 128 chars, so there's no point in having buf be larger than 128. And since you don't *initialize* buf, that means that if the qmail-remote output is more than 128 chars, not only could you miss the final message report, but you could potentially walk off into the garbage end of buf. Once there, if you find a \0K 2-byte sequence, you could incorrectly think that the message was accepted, even if it was in fact rejected, thus causing the bounce message to be lost. That's probably bad too. Granted, in the common case, qmail-remote generates less than 128 characters of output, but... Anyway, I know I kinda spent this email picking apart your code, but don't take it badly. You asked for comments! :) ~Kyle - -- However many holy words you read, However many you speak, what good will they do you If you do not act on upon them? -- Buddha -----BEGIN PGP SIGNATURE----- Comment: Thank you for using encryption! iEYEARECAAYFAknso94ACgkQBkIOoMqOI16VVQCfSYWydXGwOpq0BcLza2jLxqS+ sAwAoL97yDTKWVfPj5xGUEQjSfw4gmgb =mFiD -----END PGP SIGNATURE-----
|