diff options
Diffstat (limited to 'src/cgi-wrapper.c')
| -rw-r--r-- | src/cgi-wrapper.c | 75 |
1 files changed, 75 insertions, 0 deletions
diff --git a/src/cgi-wrapper.c b/src/cgi-wrapper.c new file mode 100644 index 000000000..b54bc8ff0 --- /dev/null +++ b/src/cgi-wrapper.c @@ -0,0 +1,75 @@ +/* +** generic wrapper that will take info from a environment +** variable, and pass it to two commands. +** +** 10-17-96 : Hal Schechner +** 12-14-96 : John Viega -- changed to work on 1 command, +** take a list of valid commands, +** just pass on argv, and use execvp() +** Also threw in some useful feedback for when there's +** a failure, mainly for future debugging. +** +** 03-31-98 : John Viega -- Consolidated all CGI wrappers into 1, +** removed checking the command name, (it was +** not real security anyway...) and changed it to use +** syslog on error. This definitely doesn't have any of +** Hal's code left ;-) +** +*/ +#include <stdio.h> +#include <stdarg.h> +#include <syslog.h> + +#define COMMAND "/home/mailman/mailman/cgi/" ## SCRIPT +#define LOG_IDENT "Mailman-wrapper (" ## SCRIPT ## ")" + +const int LEGAL_PARENT_UID = 60001; /* nobody's UID */ +const int LEGAL_PARENT_GID = 60001; /* nobody's GID */ + +/* +** Report an error then exit. +*/ +void err(char *format, ...) +{ + char log_entry[1024]; + + va_list arg_ptr; + va_start(arg_ptr, format); + vsprintf(log_entry, format, arg_ptr); + va_end(arg_ptr); + + // Write to the console, maillog is often mostly ignored, + // and root should definitely know about any problems. + openlog(LOG_IDENT, LOG_CONS, LOG_MAIL); + syslog(LOG_ERR, "%s", log_entry); + closelog(); + exit(0); +} + +/* +** is the parent process allowed to call us? +*/ +void check_caller() { + /* compare to our parent's uid */ + if(LEGAL_PARENT_UID != getuid()) + { + err("Attempt to exec cgi %s made by uid %d", LEGAL_PARENT_UID, + getuid()); + } + if(LEGAL_PARENT_GID != getgid()) + { + err("Attempt to exec cgi %s made by gid %d", LEGAL_PARENT_GID, + getgid()); + } +} + +void main(int argc, char **argv, char **env) +{ + int i; + + check_caller(); + // If we get here, the caller is OK. + setuid(geteuid()); + execve(COMMAND, &argv[0], env); + err("execve of %s failed!", COMMAND); +} |
