Hello! I know this is probably more appropriate in a Cyrus mailing list, but I wrote this so qmail users can deliver to their own mailbox in a secure fashion. The script is explained in the comments. Please review it and let me know of any security holes that may be present as well as ways to fix it. It *should* be tight because there is absolutely no user input anywhere. If this script is satisfactory, copy it to $CYRUS_BASE_DIR/bin/deliverwrapper.pl Then execute, as root -- # chown cyrus.mail $CYRUS_BASE_DIR/bin/deliverwrapper.pl # chmod 6751 $CYRUS_BASE_DIR/bin/deliverwrapper.pl and leave deliver mode 750 (as installed). Now, any user can call the wrapper and deliver mail to their own mailbox and no others. If you wish to add any parameters, they may be added to the $deliver_args variable. Oh, I also assume usernames only contain A-Z, a-z, 0-9, and "-.". If you have any other names, then you'll have to add them yourself and please let me know what you added so I can do the same. Again, please let me know of any shortcomings, bugs, holes, praises, wtf's, etc. :) Thanks, ~Patrick #!/usr/bin/perl # Wrapper for securely (hopefully ;) calling Cyrus IMAPd's deliver program # from any user. This program accepts no arguments and will only deliver # to the mailbox of the user using only the command line parameters supplied # by this script. # # There is no user input except stdin, which is presumably a message. If # it's not a message, then it only munges their own mailbox. (Actually, # deliver will complain about invalid headers.) # # Calls deliver with -e -a $USER -- $USER # $deliver_exe = "/usr/local/cyrus/bin/deliver"; $deliver_args = "-e -a "; # We tack on "$USER -- $USER" later. $id_exe = "/usr/bin/id"; $username_chars = "-A-Za-z0-9."; # Needed for security reasons $ENV{'PATH'} = ""; $ENV{'BASH_ENV'} = ""; # We need to get the caller's UID # There is probably a better way of doing this. $id = `$id_exe`; # Strip out the user's name and uid. if( $id =~ /uid=([0-9]+)\(([$username_chars]+)\).*/) { $uid = $1; $user = $2; # Deliver the message $deliver_args .= "$user -- $user"; open(DELIVER, "|$deliver_exe $deliver_args") || die "Can't open deliver!"; print DELIVER <STDIN>; } else { die("Cannot determine username!"); }